Skip to content

Instantly share code, notes, and snippets.

@airekans
Created December 23, 2012 07:51
Show Gist options
  • Save airekans/4362514 to your computer and use it in GitHub Desktop.
Save airekans/4362514 to your computer and use it in GitHub Desktop.
Clang Preprocessor for Clang 3.2
#include <string>
#include <iostream>
#include "llvm/Config/config.h"
#include "llvm/ADT/IntrusiveRefCntPtr.h"
#include "clang/Basic/Diagnostic.h"
#include "clang/Basic/TargetOptions.h"
#include "clang/Basic/TargetInfo.h"
#include "clang/Basic/SourceManager.h"
#include "clang/Basic/FileManager.h"
#include "clang/Lex/HeaderSearch.h"
#include "clang/Lex/Preprocessor.h"
#include "clang/Frontend/TextDiagnosticPrinter.h"
#include "clang/Frontend/TextDiagnosticBuffer.h"
#include "clang/Frontend/CompilerInstance.h"
using namespace std;
using namespace clang;
struct PPContext {
// Takes ownership of client.
PPContext(clang::TargetOptions& targetOpts)
: diagID(new clang::DiagnosticIDs),
diagBuffer(new clang::TextDiagnosticBuffer),
diagEngine(diagID, diagBuffer),
target(clang::TargetInfo::CreateTargetInfo(diagEngine, targetOpts)),
fm(fsOpts),
sm(diagEngine, fm),
headers(fm, diagEngine, opts, target),
pp(diagEngine, opts, target, sm, headers, compilerInstance)
{
// Configure warnings to be similar to what command-line `clang` outputs
// (see tut03).
// XXX: move warning initialization to libDriver
using namespace clang;
// diags.setDiagnosticMapping(diag::warn_pp_undef_identifier,diag::MAP_IGNORE);
}
~PPContext()
{
delete target;
}
llvm::IntrusiveRefCntPtr<clang::DiagnosticIDs> diagID;
clang::TextDiagnosticBuffer *diagBuffer;
clang::DiagnosticsEngine diagEngine;
clang::CompilerInstance compilerInstance;
clang::LangOptions opts;
clang::TargetInfo* target;
clang::FileSystemOptions fsOpts;
clang::FileManager fm;
clang::SourceManager sm;
clang::HeaderSearch headers;
clang::Preprocessor pp;
};
int main(int argc, char *argv[])
{
if (argc != 2) {
cerr << "No filename given" << endl;
return EXIT_FAILURE;
}
clang::TargetOptions targetOpts;
targetOpts.Triple = LLVM_DEFAULT_TARGET_TRIPLE;
PPContext context(targetOpts);
// Add input file
const FileEntry* File = context.fm.getFile(argv[1]);
if (!File) {
cerr << "Failed to open \'" << argv[1] << "\'";
return EXIT_FAILURE;
}
context.sm.createMainFileID(File);
context.pp.EnterMainSourceFile();
// Parse it
Token Tok;
do {
context.pp.Lex(Tok);
if (context.diagEngine.hasErrorOccurred())
break;
context.pp.DumpToken(Tok);
cerr << endl;
} while (Tok.isNot(tok::eof));
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment