-isysem path

Monalisa Rout via cfe-commits cfe-commits at lists.llvm.org
Wed Oct 9 03:08:22 PDT 2019


Hello,

I have created one visual studio application by using LibTooling library.
I am dumping the AST and all LLVM Types. I want to pass the isystem path to
the
clangTool object.

I have declared the isystem path in the Command Arguments
(Project->Properties->Debugging->Command Arguments)
input.c Output.json -isystem xxx

static llvm::cl::list<std::string> ISystemPaths(
"isystem", llvm::cl::ZeroOrMore, llvm::cl::value_desc("filename"),
llvm::cl::desc("This is isystem"));

I have read that command argument as well, but I have no idea how to use it
further.

Have a look at my source code if that would help you to understand the
problem clearly.

[ clang -Xclang -ast-dump input.c -isystem xxx ] - I dont want to use like
this.

Regards,
Mona
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-commits/attachments/20191009/ab90820e/attachment.html>
-------------- next part --------------

#include<iostream>
using namespace std;
#include <sstream>
#include <string>

#include "clang/AST/AST.h"
#include "clang/AST/ASTConsumer.h"
#include "clang/AST/RecursiveASTVisitor.h"
#include "clang/Frontend/ASTConsumers.h"
#include "clang/Frontend/CompilerInstance.h"
#include "clang/Frontend/FrontendActions.h"
#include "clang/Rewrite/Core/Rewriter.h"
#include "clang/Tooling/CommonOptionsParser.h"
#include "clang/Tooling/Tooling.h"
#include "llvm/Support/raw_ostream.h"
#include <fstream>
#include "llvm/Support/JSON.h"
#include "clang/AST/JSONNodeDumper.h"
#include "clang/Basic/DiagnosticIDs.h"
using namespace clang;
using namespace clang::driver;
using namespace clang::tooling;

static llvm::cl::OptionCategory ToolingSampleCategory("Tooling Sample");

static llvm::cl::list<std::string> ISystemPaths(
	"isystem", llvm::cl::ZeroOrMore, llvm::cl::value_desc("filename"),
	llvm::cl::desc("This is isystem"));


StringRef stringref1("D:\\Data\\Rout\\svn\\ASTJSONProject\\ASTJSONProject\\defaultOutput.json");
llvm::raw_fd_ostream Sdefault(stringref1, std::error_code());
std::string outputPath;
// By implementing RecursiveASTVisitor, we can specify which AST nodes
// we're interested in by overriding relevant methods.
class MyASTVisitor : public RecursiveASTVisitor<MyASTVisitor> {
public:
	MyASTVisitor(Rewriter &R) : TheRewriter(R) {}

	bool VisitStmt(Stmt *s) {
		
		return true;
	}

	// how to make out function def, fuction call and function declaration.
	bool VisitFunctionDecl(FunctionDecl *f) {
		// Only function definitions (with bodies), not declarations.
		if (f->hasBody()) {
			Stmt *FuncBody = f->getBody();
			// Type name as string
			QualType QT = f->getReturnType();
			std::string TypeStr = QT.getAsString();
			
			// Function name
			DeclarationName DeclName = f->getNameInfo().getName();
			std::string FuncName = DeclName.getAsString();
		}

		return true;
	}
	bool VisitDecl(Decl *D) 
	{ 
		if (isa<RecordDecl>(D))
		return true;
	}

	bool VisitExpr(const Expr *E)
	{
		
		
		return true;
	}
	bool VisitRecordDecl(RecordDecl *Declaration) {
		// For debugging, dumping the AST nodes will show which nodes are already
		// being visited.
		//Declaration->dump(llvm::errs(), false, clang::ADOF_JSON);

		// The return value indicates whether we want the visitation to proceed.
		// Return false to stop the traversal of the AST.
		return true;
	}

private:
	Rewriter & TheRewriter;
	//private Block block; // available in Gecos library
};


// Implementation of the ASTConsumer interface for reading an AST produced
// by the Clang parser.


class MyASTConsumer : public ASTConsumer {
public:
	llvm::raw_fd_ostream S = { StringRef(outputPath) , std::error_code() };
	MyASTConsumer(Rewriter &R) : Visitor(R) {
		/*StringRef stringref(outputPath);
		llvm::raw_fd_ostream S(stringref, std::error_code());*/
		S << "{";
		S<< "\n";
		std::string str("\"root\"");
		S << str;
		S << ":";
		S<< "\n";
		S << "[";
		S<< "\n";
	}

	// Override the method that gets called for each parsed top-level
	// declaration.
	bool HandleTopLevelDecl(DeclGroupRef DR) override {	
		
		for (DeclGroupRef::iterator b = DR.begin(), e = DR.end(); b != e; ++b) {
			// Traverse the declaration using our AST visitor.
			RecordDecl *recordDecl = dyn_cast<RecordDecl>(*b);
			TypedefDecl* typedefdecl = dyn_cast<TypedefDecl>(*b);
			if (recordDecl)
			{
				std::vector<QualType> recordVec;
				//const struct
				QualType recordType = (*b)->getASTContext().getRecordType(recordDecl);
				recordType.addConst();
				recordVec.push_back(recordType);

				// const volatile struct
				recordType.addVolatile();
				recordVec.push_back(recordType);

				//volatile struct
				recordType = (*b)->getASTContext().getRecordType(recordDecl);
				recordType.addVolatile();
				recordVec.push_back(recordType);

				

				ASTContext &Ctx = (*b)->getASTContext();
				const SourceManager &SM = Ctx.getSourceManager();
				for (QualType item : recordVec)
				{
					item.dump(Sdefault);
					JSONDumper P(S, SM, Ctx, Ctx.getPrintingPolicy(),
						&Ctx.getCommentCommandTraits());
					P.Visit(item);
					S << "," << "\n";
				}
			}
			if (typedefdecl)
			{
				std::vector<QualType> typeDefVec;
				//If you afre creating it is already added to the type vector
				//const typedef
				QualType recordType = (*b)->getASTContext().getTypedefType(typedefdecl);
				recordType.addConst();
				typeDefVec.push_back(recordType);
				ASTContext &Ctx = (*b)->getASTContext();
				const SourceManager &SM = Ctx.getSourceManager();
				for (QualType item : typeDefVec)
				{
					item.dump(Sdefault);
					JSONDumper P(S, SM, Ctx, Ctx.getPrintingPolicy(),
						&Ctx.getCommentCommandTraits());
					P.Visit(item);
					S << "," << "\n";
				}
				
			}
			PresumedLoc Presumed = (*b)->getASTContext().getSourceManager()
				.getPresumedLoc((*b)->getLocation());
			string Filename = Presumed.getFilename();
			std::size_t found = Filename.find("Program Files (x86)");
			if (Filename.find("Program Files (x86)") == std::string::npos)
			{
				(*b)->dump(llvm::errs(), false, clang::ADOF_JSON);
				Visitor.TraverseDecl(*b);
				(*b)->dump(Sdefault, false, clang::ADOF_Default);
				(*b)->dump(S, false, clang::ADOF_JSON);
				S << "," << "\n";
			}
				
			
		}

		
		return true;
	}
	void HandleTranslationUnit(ASTContext & 	Ctx)
	{
		const SourceManager &SM = Ctx.getSourceManager();

		const SmallVectorImpl<Type *>& vecTypes = Ctx.getTypes();

		for (auto *Ty : vecTypes)
		{
			Ty->dump(Sdefault);

			JSONDumper P(S, SM, Ctx, Ctx.getPrintingPolicy(),
				&Ctx.getCommentCommandTraits());
			P.Visit(Ty);
			S << "," << "\n";
		}


		 // Dumping Specifiers
		std::vector<QualType> qualTypeVec;

		// const int  
		QualType intqualtype = Ctx.IntTy;
		intqualtype.addConst();
		qualTypeVec.push_back(intqualtype);
		// const volatile int
		intqualtype.addVolatile();
		qualTypeVec.push_back(intqualtype);

		//volatile int
		intqualtype = Ctx.IntTy;
		intqualtype.addVolatile();
		qualTypeVec.push_back(intqualtype);

		//const char
		QualType charqualtype = Ctx.CharTy;
		charqualtype.addConst();
		qualTypeVec.push_back(charqualtype);

		//volatile char
		charqualtype = Ctx.CharTy;
		charqualtype.addVolatile();
		qualTypeVec.push_back(charqualtype);
		// int*
		intqualtype = Ctx.getPointerType(Ctx.IntTy);
		qualTypeVec.push_back(intqualtype);
		// int **
		intqualtype = Ctx.getPointerType(Ctx.IntTy);
		intqualtype = Ctx.getPointerType(intqualtype);
		qualTypeVec.push_back(intqualtype);

		// int ** restrict

		intqualtype.addRestrict();
		qualTypeVec.push_back(intqualtype);

		// const int **

		intqualtype = Ctx.getPointerType(Ctx.IntTy.withConst());
		intqualtype = Ctx.getPointerType(intqualtype);
		qualTypeVec.push_back(intqualtype);
		// const char **
		charqualtype = Ctx.getPointerType(Ctx.CharTy.withConst());
		charqualtype = Ctx.getPointerType(charqualtype);
		qualTypeVec.push_back(charqualtype);

		// const void*
		QualType voidqualType = Ctx.getPointerType(Ctx.VoidTy.withConst());
		qualTypeVec.push_back(voidqualType);
		// void
		voidqualType = Ctx.VoidTy;
		qualTypeVec.push_back(voidqualType);
		// const void
		voidqualType.addConst();
		qualTypeVec.push_back(voidqualType);
		// int* const, 
		intqualtype = Ctx.getPointerType(Ctx.IntTy);
		intqualtype.addConst(); // it adds after the pointer
		qualTypeVec.push_back(intqualtype);

		// int* volatile,
		intqualtype = Ctx.getPointerType(Ctx.IntTy);
		intqualtype.addVolatile(); // it adds after the pointer
		qualTypeVec.push_back(intqualtype);

		// volatile int*
		QualType volInt = Ctx.IntTy;
		volInt.addVolatile();
		intqualtype = Ctx.getPointerType(volInt);
		qualTypeVec.push_back(intqualtype);

		// int* restrict
		intqualtype = Ctx.getPointerType(Ctx.IntTy);
		intqualtype.addRestrict(); // it adds after the pointer
		qualTypeVec.push_back(intqualtype);

		// const double
		QualType doublequaltype = Ctx.DoubleTy;
		doublequaltype.addConst();
		qualTypeVec.push_back(doublequaltype);
		

		// double* restrict
		doublequaltype = Ctx.getPointerType(Ctx.DoubleTy);
		doublequaltype.addRestrict(); // it adds after the pointer
		qualTypeVec.push_back(doublequaltype);

		//char* const
		charqualtype = Ctx.getPointerType(Ctx.CharTy);
		charqualtype.addConst();
		qualTypeVec.push_back(charqualtype);

		//char* volatile
		charqualtype = Ctx.getPointerType(Ctx.CharTy);
		charqualtype.addVolatile();
		qualTypeVec.push_back(charqualtype);

		// const int* const
		intqualtype = Ctx.getPointerType(Ctx.IntTy.withConst());
		intqualtype.addConst();
		qualTypeVec.push_back(intqualtype);

		// const char* const
		charqualtype = Ctx.getPointerType(Ctx.CharTy.withConst());
		charqualtype.addConst();
		qualTypeVec.push_back(charqualtype);

		// const Unigned int
		QualType uint = Ctx.UnsignedIntTy;
		uint.addConst();
		qualTypeVec.push_back(uint);

		// const unsignedchar *restrict 
		QualType uchar = Ctx.getPointerType(Ctx.UnsignedCharTy.withConst());
		uchar.addRestrict();
		qualTypeVec.push_back(uchar);

		//  volatile Complex double
		QualType complexDouble = Ctx.DoubleComplexTy;
		complexDouble.addVolatile();
		qualTypeVec.push_back(complexDouble);

		for (QualType item : qualTypeVec)
		{

		item.dump(Sdefault);
		JSONDumper P(S, SM, Ctx, Ctx.getPrintingPolicy(),
		&Ctx.getCommentCommandTraits());
		P.Visit(item);
		S << "," << "\n";
		}	
		// to the end
		S << "]";
		S << "\n";
		S << "}";
	}

private:
	MyASTVisitor Visitor;
};

// For each source file provided to the tool, a new FrontendAction is created.
class MyFrontendAction : public ASTFrontendAction {
public:
	MyFrontendAction() {}
	void EndSourceFileAction() override {
		SourceManager &SM = TheRewriter.getSourceMgr();
		llvm::errs() << "** EndSourceFileAction for: "
			<< SM.getFileEntryForID(SM.getMainFileID())->getName() << "\n";

		// Now emit the rewritten buffer.
		TheRewriter.getEditBuffer(SM.getMainFileID()).write(llvm::outs());
	}

	std::unique_ptr<ASTConsumer> CreateASTConsumer(CompilerInstance &CI,
		StringRef file) override {
		llvm::errs() << "** Creating AST consumer for: " << file << "\n";
		TheRewriter.setSourceMgr(CI.getSourceManager(), CI.getLangOpts());
		return llvm::make_unique<MyASTConsumer>(TheRewriter);
	}

private:
	Rewriter TheRewriter;
};

int main(int argc, const char **argv) {

	outputPath = argv[2];
	
	CommonOptionsParser op(argc, argv, ToolingSampleCategory);
	std::vector<std::string> sourcepath = op.getSourcePathList();
	std::vector<std::string> isystemPath = ISystemPaths;
	//sourcepath = ISystemPaths;
	for(std::string path: isystemPath)
	sourcepath.push_back(path);
	ClangTool Tool(op.getCompilations(), sourcepath);
	
	// ClangTool::run accepts a FrontendActionFactory, which is then used to
	// create new objects implementing the FrontendAction interface. Here we use
	// the helper newFrontendActionFactory to create a default factory that will
	// return a new MyFrontendAction object every time.
	// To further customize this, we could create our own factory class.
	Tool.run(newFrontendActionFactory<MyFrontendAction>().get());
	
	/*
	Adding closing braces to the stream
	*/
	//S.seek(S.tell());


	return 0;
}


More information about the cfe-commits mailing list