diff --git a/clang/Driver/ASTStreamers.cpp b/clang/Driver/ASTStreamers.cpp index 3c67d9524a84..7ef3001e3ba4 100644 --- a/clang/Driver/ASTStreamers.cpp +++ b/clang/Driver/ASTStreamers.cpp @@ -232,3 +232,57 @@ namespace { ASTConsumer *clang::CreateDeadStoreChecker(Diagnostic &Diags) { return new DeadStoreVisitor(Diags); } + +//===----------------------------------------------------------------------===// +// LLVM Emitter + +#include "clang/Basic/Diagnostic.h" +#include "clang/CodeGen/ModuleBuilder.h" +#include "llvm/Module.h" +#include + +namespace { + class LLVMEmitter : public ASTConsumer { + Diagnostic &Diags; + llvm::Module *M; + ASTContext *Ctx; + CodeGen::BuilderTy *Builder; + public: + LLVMEmitter(Diagnostic &diags) : Diags(diags) {} + virtual void Initialize(ASTContext &Context, unsigned MainFileID) { + Ctx = &Context; + M = new llvm::Module("foo"); + Builder = CodeGen::Init(Context, *M); + } + + virtual void HandleTopLevelDecl(Decl *D) { + // If an error occurred, stop code generation, but continue parsing and + // semantic analysis (to ensure all warnings and errors are emitted). + if (Diags.hasErrorOccurred()) + return; + + if (FunctionDecl *FD = dyn_cast(D)) { + CodeGen::CodeGenFunction(Builder, FD); + } else if (FileVarDecl *FVD = dyn_cast(D)) { + CodeGen::CodeGenGlobalVar(Builder, FVD); + } else { + assert(isa(D) && "Only expected typedefs here"); + // don't codegen for now, eventually pass down for debug info. + //std::cerr << "Read top-level typedef decl: '" << D->getName() << "'\n"; + } + } + + ~LLVMEmitter() { + CodeGen::Terminate(Builder); + + // Print the generated code. + M->print(std::cout); + delete M; + } + }; +} // end anonymous namespace + +ASTConsumer *clang::CreateLLVMEmitter(Diagnostic &Diags) { + return new LLVMEmitter(Diags); +} + diff --git a/clang/Driver/ASTStreamers.h b/clang/Driver/ASTStreamers.h index 60b23ef70d33..d9ea3bdcf3ca 100644 --- a/clang/Driver/ASTStreamers.h +++ b/clang/Driver/ASTStreamers.h @@ -24,6 +24,7 @@ ASTConsumer *CreateASTDumper(); ASTConsumer *CreateCFGDumper(bool ViewGraphs = false); ASTConsumer *CreateLiveVarAnalyzer(); ASTConsumer *CreateDeadStoreChecker(Diagnostic &Diags); +ASTConsumer *CreateLLVMEmitter(Diagnostic &Diags); } // end clang namespace diff --git a/clang/Driver/LLVMCodegen.cpp b/clang/Driver/LLVMCodegen.cpp deleted file mode 100644 index 95d23f584e25..000000000000 --- a/clang/Driver/LLVMCodegen.cpp +++ /dev/null @@ -1,71 +0,0 @@ -//===--- LLVMCodegen.cpp - Emit LLVM Code from ASTs -----------------------===// -// -// The LLVM Compiler Infrastructure -// -// This file was developed by Chris Lattner and is distributed under -// the University of Illinois Open Source License. See LICENSE.TXT for details. -// -//===----------------------------------------------------------------------===// -// -// This builds an AST and converts it to LLVM Code. -// -//===----------------------------------------------------------------------===// - -#include "clang.h" -#include "clang/CodeGen/ModuleBuilder.h" -#include "clang/Sema/ASTStreamer.h" -#include "clang/AST/AST.h" -#include "clang/Lex/Preprocessor.h" -#include "clang/Basic/Diagnostic.h" -#include "llvm/Module.h" -#include -using namespace clang; - -//===----------------------------------------------------------------------===// -// LLVM Emission -//===----------------------------------------------------------------------===// - -void clang::EmitLLVMFromASTs(Preprocessor &PP, unsigned MainFileID, - bool PrintStats) { - Diagnostic &Diags = PP.getDiagnostics(); - // Create the streamer to read the file. - ASTContext Context(PP.getSourceManager(), PP.getTargetInfo(), - PP.getIdentifierTable()); - ASTStreamerTy *Streamer = ASTStreamer_Init(PP, Context, MainFileID); - - // Create the module to codegen into. - llvm::Module M("foo"); - - CodeGen::BuilderTy *Builder = CodeGen::Init(Context, M); - - while (Decl *D = ASTStreamer_ReadTopLevelDecl(Streamer)) { - // If an error occurred, stop code generation, but continue parsing and - // semantic analysis (to ensure all warnings and errors are emitted). - if (Diags.hasErrorOccurred()) - continue; - - if (FunctionDecl *FD = dyn_cast(D)) { - CodeGen::CodeGenFunction(Builder, FD); - } else if (FileVarDecl *FVD = dyn_cast(D)) { - CodeGen::CodeGenGlobalVar(Builder, FVD); - } else { - assert(isa(D) && "Only expected typedefs here"); - // don't codegen for now, eventually pass down for debug info. - //std::cerr << "Read top-level typedef decl: '" << D->getName() << "'\n"; - } - } - - if (PrintStats) { - std::cerr << "\nSTATISTICS:\n"; - CodeGen::PrintStats(Builder); - ASTStreamer_PrintStats(Streamer); - Context.PrintStats(); - } - - CodeGen::Terminate(Builder); - ASTStreamer_Terminate(Streamer); - - // Print the generated code. - M.print(std::cout); -} - diff --git a/clang/Driver/clang.cpp b/clang/Driver/clang.cpp index 7301354c176d..405180671823 100644 --- a/clang/Driver/clang.cpp +++ b/clang/Driver/clang.cpp @@ -870,9 +870,11 @@ static void ProcessInputFile(Preprocessor &PP, unsigned MainFileID, ParseAST(PP, MainFileID, *C.get(), Stats); break; } - case EmitLLVM: - EmitLLVMFromASTs(PP, MainFileID, Stats); + case EmitLLVM: { + std::auto_ptr C(CreateLLVMEmitter(PP.getDiagnostics())); + ParseAST(PP, MainFileID, *C.get(), Stats); break; + } case ParseASTCheck: exit(CheckDiagnostics(PP, MainFileID)); break; diff --git a/clang/clang.xcodeproj/project.pbxproj b/clang/clang.xcodeproj/project.pbxproj index 578a156700ed..985c974dbac0 100644 --- a/clang/clang.xcodeproj/project.pbxproj +++ b/clang/clang.xcodeproj/project.pbxproj @@ -70,7 +70,6 @@ DE6954640C5121BD00A5826B /* Token.h in CopyFiles */ = {isa = PBXBuildFile; fileRef = DE6954630C5121BD00A5826B /* Token.h */; }; DE75ED290B044DC90020CF81 /* ASTContext.h in CopyFiles */ = {isa = PBXBuildFile; fileRef = DE75ED280B044DC90020CF81 /* ASTContext.h */; }; DE75EDF10B06880E0020CF81 /* Type.cpp in Sources */ = {isa = PBXBuildFile; fileRef = DE75EDF00B06880E0020CF81 /* Type.cpp */; }; - DE927FFD0C055DE900231DA4 /* LLVMCodegen.cpp in Sources */ = {isa = PBXBuildFile; fileRef = DE927FFC0C055DE900231DA4 /* LLVMCodegen.cpp */; }; DE928B130C05659200231DA4 /* ModuleBuilder.cpp in Sources */ = {isa = PBXBuildFile; fileRef = DE928B120C05659200231DA4 /* ModuleBuilder.cpp */; }; DE928B200C0565B000231DA4 /* ModuleBuilder.h in CopyFiles */ = {isa = PBXBuildFile; fileRef = DE928B1F0C0565B000231DA4 /* ModuleBuilder.h */; }; DE928B7D0C0A615100231DA4 /* CodeGenModule.h in CopyFiles */ = {isa = PBXBuildFile; fileRef = DE928B7C0C0A615100231DA4 /* CodeGenModule.h */; }; @@ -228,7 +227,7 @@ 35AE0F680C9B4CC200CC1279 /* UnintializedValues.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = UnintializedValues.cpp; path = Analysis/UnintializedValues.cpp; sourceTree = ""; }; 84D9A8870C1A57E100AC7ABC /* AttributeList.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; name = AttributeList.cpp; path = Parse/AttributeList.cpp; sourceTree = ""; }; 84D9A88B0C1A581300AC7ABC /* AttributeList.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; name = AttributeList.h; path = clang/Parse/AttributeList.h; sourceTree = ""; }; - 8DD76F6C0486A84900D96B5E /* clang */ = {isa = PBXFileReference; explicitFileType = "compiled.mach-o.executable"; includeInIndex = 0; path = clang; sourceTree = BUILT_PRODUCTS_DIR; }; + 8DD76F6C0486A84900D96B5E /* clang */ = {isa = PBXFileReference; includeInIndex = 0; lastKnownFileType = "compiled.mach-o.executable"; path = clang; sourceTree = BUILT_PRODUCTS_DIR; }; DE01DA480B12ADA300AC22CE /* PPCallbacks.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = PPCallbacks.h; sourceTree = ""; }; DE06756B0C051CFE00EBBFD8 /* ParseExprCXX.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; name = ParseExprCXX.cpp; path = Parse/ParseExprCXX.cpp; sourceTree = ""; }; DE06B73D0A8307640050E87E /* LangOptions.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = LangOptions.h; sourceTree = ""; }; @@ -281,7 +280,6 @@ DE6954630C5121BD00A5826B /* Token.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; path = Token.h; sourceTree = ""; }; DE75ED280B044DC90020CF81 /* ASTContext.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; name = ASTContext.h; path = clang/AST/ASTContext.h; sourceTree = ""; }; DE75EDF00B06880E0020CF81 /* Type.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; name = Type.cpp; path = AST/Type.cpp; sourceTree = ""; }; - DE927FFC0C055DE900231DA4 /* LLVMCodegen.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; name = LLVMCodegen.cpp; path = Driver/LLVMCodegen.cpp; sourceTree = ""; }; DE928B120C05659200231DA4 /* ModuleBuilder.cpp */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.cpp.cpp; name = ModuleBuilder.cpp; path = CodeGen/ModuleBuilder.cpp; sourceTree = ""; }; DE928B1F0C0565B000231DA4 /* ModuleBuilder.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; name = ModuleBuilder.h; path = clang/CodeGen/ModuleBuilder.h; sourceTree = ""; }; DE928B7C0C0A615100231DA4 /* CodeGenModule.h */ = {isa = PBXFileReference; fileEncoding = 30; lastKnownFileType = sourcecode.c.h; name = CodeGenModule.h; path = CodeGen/CodeGenModule.h; sourceTree = ""; }; @@ -532,7 +530,6 @@ DED67AEF0B6DB92F00AAD4A3 /* PPCBuiltins.def */, DED67AED0B6DB92A00AAD4A3 /* X86Builtins.def */, DEC82DC30C32D50A00BAC245 /* DiagChecker.cpp */, - DE927FFC0C055DE900231DA4 /* LLVMCodegen.cpp */, DE5932CF0AD60FF400BC794C /* PrintParserCallbacks.cpp */, DE5932D00AD60FF400BC794C /* PrintPreprocessedOutput.cpp */, DED627020AE0C51D001E80A4 /* Targets.cpp */, @@ -766,7 +763,6 @@ DE67E7170C020EE400F66BC5 /* Sema.cpp in Sources */, DE67E71A0C020F4F00F66BC5 /* ASTStreamer.cpp in Sources */, DE06756C0C051CFE00EBBFD8 /* ParseExprCXX.cpp in Sources */, - DE927FFD0C055DE900231DA4 /* LLVMCodegen.cpp in Sources */, DE928B130C05659200231DA4 /* ModuleBuilder.cpp in Sources */, DE928B7F0C0A615600231DA4 /* CodeGenModule.cpp in Sources */, DE928B830C0A616000231DA4 /* CodeGenFunction.cpp in Sources */,