eduucaldas created this revision.
Herald added a project: clang.
Herald added a subscriber: cfe-commits.
eduucaldas requested review of this revision.
Functional changes in the dump:
- Surround Leaf tokens with `'`
- Append `Node` dumps with `NodeRole` information, except for unknown roles
Non-functional changes:
- `::dumpTokens(llvm::raw_ostream, ArrayRef<syntax::Token>, const SourceManager
&SM)` always received as parameter a `syntax::Token *` pointing to
`Leaf::token()`. Changed the function to `strOfLeaf(syntax::Leaf *, const
SourceManager&)`
- `dumpTree` acted on a Node, rename to `dumpNode`
TODO:
Adapt all the tree dumps in `TreeTest.cpp` to this new format.
Repository:
rG LLVM Github Monorepo
https://reviews.llvm.org/D85330
Files:
clang/include/clang/Tooling/Syntax/Tree.h
clang/lib/Tooling/Syntax/BuildTree.cpp
clang/lib/Tooling/Syntax/Tree.cpp
clang/unittests/Tooling/Syntax/TreeTest.cpp
Index: clang/unittests/Tooling/Syntax/TreeTest.cpp
===================================================================
--- clang/unittests/Tooling/Syntax/TreeTest.cpp
+++ clang/unittests/Tooling/Syntax/TreeTest.cpp
@@ -159,7 +159,8 @@
<< "Source file has syntax errors, they were printed to the test "
"log";
}
- std::string Actual = std::string(StringRef(Root->dump(*Arena)).trim());
+ std::string Actual =
+ std::string(StringRef(Root->dump(Arena->sourceManager())).trim());
// EXPECT_EQ shows the diff between the two strings if they are different.
EXPECT_EQ(Tree.trim().str(), Actual);
if (Actual != Tree.trim().str()) {
Index: clang/lib/Tooling/Syntax/Tree.cpp
===================================================================
--- clang/lib/Tooling/Syntax/Tree.cpp
+++ clang/lib/Tooling/Syntax/Tree.cpp
@@ -135,46 +135,43 @@
}
namespace {
-static void dumpTokens(llvm::raw_ostream &OS, ArrayRef<syntax::Token> Tokens,
- const SourceManager &SM) {
- assert(!Tokens.empty());
- bool First = true;
- for (const auto &T : Tokens) {
- if (!First)
- OS << " ";
- else
- First = false;
- // Handle 'eof' separately, calling text() on it produces an empty string.
- if (T.kind() == tok::eof) {
- OS << "<eof>";
- continue;
- }
- OS << T.text(SM);
- }
+static llvm::StringRef strOfLeaf(const syntax::Leaf *L,
+ const SourceManager &SM) {
+ assert(L);
+ const auto *Token = L->token();
+ assert(Token);
+ // Handle 'eof' separately, calling text() on it produces an empty string.
+ if (Token->kind() == tok::eof)
+ return "<eof>";
+ return Token->text(SM);
}
-static void dumpTree(llvm::raw_ostream &OS, const syntax::Node *N,
- const syntax::Arena &A, std::vector<bool> IndentMask) {
+static void dumpNode(llvm::raw_ostream &OS, const syntax::Node *N,
+ const SourceManager &SM, std::vector<bool> IndentMask) {
std::string Marks;
if (!N->isOriginal())
Marks += "M";
- if (N->role() == syntax::NodeRole::Detached)
- Marks += "*"; // FIXME: find a nice way to print other roles.
if (!N->canModify())
Marks += "I";
if (!Marks.empty())
OS << Marks << ": ";
if (auto *L = llvm::dyn_cast<syntax::Leaf>(N)) {
- dumpTokens(OS, *L->token(), A.sourceManager());
+ OS << "'" << strOfLeaf(L, SM) << "'";
+ if (L->role() != syntax::NodeRole::Unknown)
+ OS << " " << L->role();
OS << "\n";
return;
}
auto *T = llvm::cast<syntax::Tree>(N);
- OS << T->kind() << "\n";
+ OS << T->kind();
+ if (T->role() != syntax::NodeRole::Unknown)
+ OS << " " << T->role();
+ OS << "\n";
- for (auto It = T->firstChild(); It != nullptr; It = It->nextSibling()) {
+ for (const auto *It = T->firstChild(); It != nullptr;
+ It = It->nextSibling()) {
for (bool Filled : IndentMask) {
if (Filled)
OS << "| ";
@@ -188,28 +185,26 @@
OS << "|-";
IndentMask.push_back(true);
}
- dumpTree(OS, It, A, IndentMask);
+ dumpNode(OS, It, SM, IndentMask);
IndentMask.pop_back();
}
}
} // namespace
-std::string syntax::Node::dump(const Arena &A) const {
+std::string syntax::Node::dump(const SourceManager &SM) const {
std::string Str;
llvm::raw_string_ostream OS(Str);
- dumpTree(OS, this, A, /*IndentMask=*/{});
+ dumpNode(OS, this, SM, /*IndentMask=*/{});
return std::move(OS.str());
}
-std::string syntax::Node::dumpTokens(const Arena &A) const {
+std::string syntax::Node::dumpTokens(const SourceManager &SM) const {
std::string Storage;
llvm::raw_string_ostream OS(Storage);
traverse(this, [&](const syntax::Node *N) {
- auto *L = llvm::dyn_cast<syntax::Leaf>(N);
- if (!L)
- return;
- ::dumpTokens(OS, *L->token(), A.sourceManager());
- OS << " ";
+ if (auto *L = llvm::dyn_cast<syntax::Leaf>(N)) {
+ OS << strOfLeaf(L, SM) << " ";
+ }
});
return OS.str();
}
Index: clang/lib/Tooling/Syntax/BuildTree.cpp
===================================================================
--- clang/lib/Tooling/Syntax/BuildTree.cpp
+++ clang/lib/Tooling/Syntax/BuildTree.cpp
@@ -526,7 +526,7 @@
R += std::string(llvm::formatv(
"- '{0}' covers '{1}'+{2} tokens\n", It->second->kind(),
It->first->text(A.sourceManager()), CoveredTokens));
- R += It->second->dump(A);
+ R += It->second->dump(A.sourceManager());
}
return R;
}
Index: clang/include/clang/Tooling/Syntax/Tree.h
===================================================================
--- clang/include/clang/Tooling/Syntax/Tree.h
+++ clang/include/clang/Tooling/Syntax/Tree.h
@@ -106,9 +106,9 @@
Node *nextSibling() { return NextSibling; }
/// Dumps the structure of a subtree. For debugging and testing purposes.
- std::string dump(const Arena &A) const;
+ std::string dump(const SourceManager &SM) const;
/// Dumps the tokens forming this subtree.
- std::string dumpTokens(const Arena &A) const;
+ std::string dumpTokens(const SourceManager &SM) const;
/// Asserts invariants on this node of the tree and its immediate children.
/// Will not recurse into the subtree. No-op if NDEBUG is set.
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits