207 lines · cpp
1//===-- FormatEntityTest.cpp ---------------------------------------------===//2//3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.4// See https://llvm.org/LICENSE.txt for license information.5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception6//7//===----------------------------------------------------------------------===//8 9#include "lldb/Core/FormatEntity.h"10#include "lldb/Utility/Status.h"11#include "lldb/Utility/StreamString.h"12#include "llvm/ADT/StringRef.h"13#include "llvm/Support/Error.h"14#include "llvm/Testing/Support/Error.h"15#include "gtest/gtest.h"16 17using namespace lldb_private;18using namespace llvm;19 20using Definition = FormatEntity::Entry::Definition;21using Entry = FormatEntity::Entry;22 23static Expected<std::string> Format(StringRef format_str) {24 StreamString stream;25 FormatEntity::Entry format;26 Status status = FormatEntity::Parse(format_str, format);27 if (status.Fail())28 return status.ToError();29 30 FormatEntity::Format(format, stream, nullptr, nullptr, nullptr, nullptr,31 false, false);32 return stream.GetString().str();33}34 35TEST(FormatEntityTest, DefinitionConstructionNameAndType) {36 Definition d("foo", FormatEntity::Entry::Type::Invalid);37 38 EXPECT_STREQ(d.name, "foo");39 EXPECT_EQ(d.string, nullptr);40 EXPECT_EQ(d.type, FormatEntity::Entry::Type::Invalid);41 EXPECT_EQ(d.data, 0UL);42 EXPECT_EQ(d.num_children, 0UL);43 EXPECT_EQ(d.children, nullptr);44 EXPECT_FALSE(d.keep_separator);45}46 47TEST(FormatEntityTest, DefinitionConstructionNameAndString) {48 Definition d("foo", "string");49 50 EXPECT_STREQ(d.name, "foo");51 EXPECT_STREQ(d.string, "string");52 EXPECT_EQ(d.type, FormatEntity::Entry::Type::EscapeCode);53 EXPECT_EQ(d.data, 0UL);54 EXPECT_EQ(d.num_children, 0UL);55 EXPECT_EQ(d.children, nullptr);56 EXPECT_FALSE(d.keep_separator);57}58 59TEST(FormatEntityTest, DefinitionConstructionNameTypeData) {60 Definition d("foo", FormatEntity::Entry::Type::Invalid, 33);61 62 EXPECT_STREQ(d.name, "foo");63 EXPECT_EQ(d.string, nullptr);64 EXPECT_EQ(d.type, FormatEntity::Entry::Type::Invalid);65 EXPECT_EQ(d.data, 33UL);66 EXPECT_EQ(d.num_children, 0UL);67 EXPECT_EQ(d.children, nullptr);68 EXPECT_FALSE(d.keep_separator);69}70 71TEST(FormatEntityTest, DefinitionConstructionNameTypeChildren) {72 Definition d("foo", FormatEntity::Entry::Type::Invalid, 33);73 Definition parent("parent", FormatEntity::Entry::Type::Invalid, 1, &d);74 EXPECT_STREQ(parent.name, "parent");75 EXPECT_STREQ(parent.string, nullptr);76 EXPECT_EQ(parent.type, FormatEntity::Entry::Type::Invalid);77 EXPECT_EQ(parent.num_children, 1UL);78 EXPECT_EQ(parent.children, &d);79 EXPECT_FALSE(parent.keep_separator);80 81 EXPECT_STREQ(parent.children[0].name, "foo");82 EXPECT_EQ(parent.children[0].string, nullptr);83 EXPECT_EQ(parent.children[0].type, FormatEntity::Entry::Type::Invalid);84 EXPECT_EQ(parent.children[0].data, 33UL);85 EXPECT_EQ(parent.children[0].num_children, 0UL);86 EXPECT_EQ(parent.children[0].children, nullptr);87 EXPECT_FALSE(d.keep_separator);88}89 90constexpr llvm::StringRef lookupStrings[] = {91 "${addr.load}",92 "${addr.file}",93 "${ansi.fg.black}",94 "${ansi.fg.red}",95 "${ansi.fg.green}",96 "${ansi.fg.yellow}",97 "${ansi.fg.blue}",98 "${ansi.fg.purple}",99 "${ansi.fg.cyan}",100 "${ansi.fg.white}",101 "${ansi.bg.black}",102 "${ansi.bg.red}",103 "${ansi.bg.green}",104 "${ansi.bg.yellow}",105 "${ansi.bg.blue}",106 "${ansi.bg.purple}",107 "${ansi.bg.cyan}",108 "${ansi.bg.white}",109 "${file.basename}",110 "${file.dirname}",111 "${file.fullpath}",112 "${frame.index}",113 "${frame.pc}",114 "${frame.fp}",115 "${frame.sp}",116 "${frame.flags}",117 "${frame.no-debug}",118 "${frame.reg.*}",119 "${frame.is-artificial}",120 "${frame.kind}",121 "${function.id}",122 "${function.name}",123 "${function.name-without-args}",124 "${function.name-with-args}",125 "${function.mangled-name}",126 "${function.addr-offset}",127 "${function.concrete-only-addr-offset-no-padding}",128 "${function.line-offset}",129 "${function.pc-offset}",130 "${function.initial-function}",131 "${function.changed}",132 "${function.is-optimized}",133 "${function.is-inlined}",134 "${line.file.basename}",135 "${line.file.dirname}",136 "${line.file.fullpath}",137 "${line.number}",138 "${line.column}",139 "${line.start-addr}",140 "${line.end-addr}",141 "${module.file.basename}",142 "${module.file.dirname}",143 "${module.file.fullpath}",144 "${process.id}",145 "${process.name}",146 "${process.file.basename}",147 "${process.file.dirname}",148 "${process.file.fullpath}",149 "${script.frame}",150 "${script.process}",151 "${script.target}",152 "${script.thread}",153 "${script.var}",154 "${script.svar}",155 "${script.thread}",156 "${svar.dummy-svar-to-test-wildcard}",157 "${thread.id}",158 "${thread.protocol_id}",159 "${thread.index}",160 "${thread.info.*}",161 "${thread.queue}",162 "${thread.name}",163 "${thread.stop-reason}",164 "${thread.stop-reason-raw}",165 "${thread.return-value}",166 "${thread.completed-expression}",167 "${target.arch}",168 "${target.file.basename}",169 "${target.file.dirname}",170 "${target.file.fullpath}",171 "${var.dummy-var-to-test-wildcard}"};172 173TEST(FormatEntityTest, LookupAllEntriesInTree) {174 for (const llvm::StringRef testString : lookupStrings) {175 Entry e;176 EXPECT_TRUE(FormatEntity::Parse(testString, e).Success())177 << "Formatting " << testString << " did not succeed";178 }179}180 181TEST(FormatEntityTest, Scope) {182 // Scope with one alternative.183 EXPECT_THAT_EXPECTED(Format("{${frame.pc}|foo}"), HasValue("foo"));184 185 // Scope with multiple alternatives.186 EXPECT_THAT_EXPECTED(Format("{${frame.pc}|${function.name}|foo}"),187 HasValue("foo"));188 189 // Escaped pipe inside a scope.190 EXPECT_THAT_EXPECTED(Format("{foo\\|bar}"), HasValue("foo|bar"));191 192 // Unescaped pipe outside a scope.193 EXPECT_THAT_EXPECTED(Format("foo|bar"), HasValue("foo|bar"));194 195 // Nested scopes. Note that scopes always resolve.196 EXPECT_THAT_EXPECTED(Format("{{${frame.pc}|foo}|{bar}}"), HasValue("foo"));197 EXPECT_THAT_EXPECTED(Format("{{${frame.pc}}|{bar}}"), HasValue(""));198 199 // Pipe between scopes.200 EXPECT_THAT_EXPECTED(Format("{foo}|{bar}"), HasValue("foo|bar"));201 EXPECT_THAT_EXPECTED(Format("{foo}||{bar}"), HasValue("foo||bar"));202 203 // Empty space between pipes.204 EXPECT_THAT_EXPECTED(Format("{{foo}||{bar}}"), HasValue("foo"));205 EXPECT_THAT_EXPECTED(Format("{${frame.pc}||{bar}}"), HasValue(""));206}207