I am playing around with LibTooling: What I want to do is output all the locations of all variables in a source file.
To find all occurences of variables, I overloaded the RecursiveASTVisitor and the method "bool VisitStmt(Stmt)" (see below), but now I don't know how to output the name of the variable. At the moment, my code only outputs "DeclRefExpr", but I want something like "myNewVariable" or whatever I defined in my input file.
class MyASTVisitor : public RecursiveASTVisitor<MyASTVisitor>
{
public:
explicit MyASTVisitor(ASTContext *Context_passed) : Context(Context_passed) {}
bool VisitStmt(Stmt *sta)
{
FullSourceLoc FullLocation = Context->getFullLoc(sta->getLocStart());
SourceManager &srcMgr = Context->getSourceManager();
if
(
FullLocation.isValid() &&
strcmp(sta->getStmtClassName(), "DeclRefExpr") == 0
)
{
// Print function name
printf("stm: %-23s at %3u:%-3u in %-15s\n",
sta->getStmtClassName(),
FullLocation.getSpellingLineNumber(),
FullLocation.getSpellingColumnNumber(),
srcMgr.getFilename(FullLocation).data());
}
return true;
}
private:
ASTContext *Context;
};
How can I get the name, i.e. the statement itself? By using the Source Manager and extracting it from the original source code?
Using the method getFoundDecl(), an instance of the class "NamedDecl" can be acquired and then, using the method getNameAsString(), the name can be acquired as a string, so the code now looks like this:
class MyASTVisitor : public RecursiveASTVisitor<MyASTVisitor>
{
public:
explicit MyASTVisitor(ASTContext *Context_passed) : Context(Context_passed) {}
bool VisitDeclRefExpr(DeclRefExpr *sta)
{
FullSourceLoc FullLocation = Context->getFullLoc(sta->getLocStart());
SourceManager &srcMgr = Context->getSourceManager();
if ( FullLocation.isValid() )
{
// Print function or variable name
printf("stm: %-23s at %3u:%-3u in %-15s\n",
(sta->getFoundDecl())->getNameAsString().c_str(),
FullLocation.getSpellingLineNumber(),
FullLocation.getSpellingColumnNumber(),
srcMgr.getFilename(FullLocation).data());
}
return true;
}
private:
ASTContext *Context;
};