185dd0bd1SPeter Collingbourne //===--- ExecuteCompilerInvocation.cpp ------------------------------------===// 285dd0bd1SPeter Collingbourne // 385dd0bd1SPeter Collingbourne // The LLVM Compiler Infrastructure 485dd0bd1SPeter Collingbourne // 585dd0bd1SPeter Collingbourne // This file is distributed under the University of Illinois Open Source 685dd0bd1SPeter Collingbourne // License. See LICENSE.TXT for details. 785dd0bd1SPeter Collingbourne // 885dd0bd1SPeter Collingbourne //===----------------------------------------------------------------------===// 985dd0bd1SPeter Collingbourne // 1085dd0bd1SPeter Collingbourne // This file holds ExecuteCompilerInvocation(). It is split into its own file to 1185dd0bd1SPeter Collingbourne // minimize the impact of pulling in essentially everything else in Clang. 1285dd0bd1SPeter Collingbourne // 1385dd0bd1SPeter Collingbourne //===----------------------------------------------------------------------===// 1485dd0bd1SPeter Collingbourne 1585dd0bd1SPeter Collingbourne #include "clang/FrontendTool/Utils.h" 16556c45e9SArgyrios Kyrtzidis #include "clang/StaticAnalyzer/Frontend/FrontendActions.h" 17b5703510SChandler Carruth #include "clang/ARCMigrate/ARCMTActions.h" 1885dd0bd1SPeter Collingbourne #include "clang/CodeGen/CodeGenAction.h" 19a3c85b86SJames Molloy #include "clang/Driver/Options.h" 2085dd0bd1SPeter Collingbourne #include "clang/Driver/OptTable.h" 2185dd0bd1SPeter Collingbourne #include "clang/Frontend/CompilerInvocation.h" 2285dd0bd1SPeter Collingbourne #include "clang/Frontend/CompilerInstance.h" 2385dd0bd1SPeter Collingbourne #include "clang/Frontend/FrontendActions.h" 2485dd0bd1SPeter Collingbourne #include "clang/Frontend/FrontendDiagnostic.h" 2585dd0bd1SPeter Collingbourne #include "clang/Frontend/FrontendPluginRegistry.h" 2685dd0bd1SPeter Collingbourne #include "clang/Rewrite/FrontendActions.h" 2785dd0bd1SPeter Collingbourne #include "llvm/Support/ErrorHandling.h" 288aaf4995SMichael J. Spencer #include "llvm/Support/DynamicLibrary.h" 2985dd0bd1SPeter Collingbourne using namespace clang; 3085dd0bd1SPeter Collingbourne 3185dd0bd1SPeter Collingbourne static FrontendAction *CreateFrontendBaseAction(CompilerInstance &CI) { 3285dd0bd1SPeter Collingbourne using namespace clang::frontend; 3385dd0bd1SPeter Collingbourne 3485dd0bd1SPeter Collingbourne switch (CI.getFrontendOpts().ProgramAction) { 354de03594SAlexander Kornienko case ASTDeclList: return new ASTDeclListAction(); 3685dd0bd1SPeter Collingbourne case ASTDump: return new ASTDumpAction(); 379b66c4bbSJohn McCall case ASTDumpXML: return new ASTDumpXMLAction(); 3885dd0bd1SPeter Collingbourne case ASTPrint: return new ASTPrintAction(); 3985dd0bd1SPeter Collingbourne case ASTView: return new ASTViewAction(); 4085dd0bd1SPeter Collingbourne case DumpRawTokens: return new DumpRawTokensAction(); 4185dd0bd1SPeter Collingbourne case DumpTokens: return new DumpTokensAction(); 4285dd0bd1SPeter Collingbourne case EmitAssembly: return new EmitAssemblyAction(); 4385dd0bd1SPeter Collingbourne case EmitBC: return new EmitBCAction(); 4485dd0bd1SPeter Collingbourne case EmitHTML: return new HTMLPrintAction(); 4585dd0bd1SPeter Collingbourne case EmitLLVM: return new EmitLLVMAction(); 4685dd0bd1SPeter Collingbourne case EmitLLVMOnly: return new EmitLLVMOnlyAction(); 4785dd0bd1SPeter Collingbourne case EmitCodeGenOnly: return new EmitCodeGenOnlyAction(); 4885dd0bd1SPeter Collingbourne case EmitObj: return new EmitObjAction(); 4985dd0bd1SPeter Collingbourne case FixIt: return new FixItAction(); 5070db54f1SDouglas Gregor case GenerateModule: return new GenerateModuleAction; 5170db54f1SDouglas Gregor case GeneratePCH: return new GeneratePCHAction; 5285dd0bd1SPeter Collingbourne case GeneratePTH: return new GeneratePTHAction(); 5385dd0bd1SPeter Collingbourne case InitOnly: return new InitOnlyAction(); 5485dd0bd1SPeter Collingbourne case ParseSyntaxOnly: return new SyntaxOnlyAction(); 5585dd0bd1SPeter Collingbourne 5685dd0bd1SPeter Collingbourne case PluginAction: { 5785dd0bd1SPeter Collingbourne for (FrontendPluginRegistry::iterator it = 5885dd0bd1SPeter Collingbourne FrontendPluginRegistry::begin(), ie = FrontendPluginRegistry::end(); 5985dd0bd1SPeter Collingbourne it != ie; ++it) { 6085dd0bd1SPeter Collingbourne if (it->getName() == CI.getFrontendOpts().ActionName) { 61e2778999SDylan Noblesmith OwningPtr<PluginASTAction> P(it->instantiate()); 6285dd0bd1SPeter Collingbourne if (!P->ParseArgs(CI, CI.getFrontendOpts().PluginArgs)) 6385dd0bd1SPeter Collingbourne return 0; 6485dd0bd1SPeter Collingbourne return P.take(); 6585dd0bd1SPeter Collingbourne } 6685dd0bd1SPeter Collingbourne } 6785dd0bd1SPeter Collingbourne 6885dd0bd1SPeter Collingbourne CI.getDiagnostics().Report(diag::err_fe_invalid_plugin_name) 6985dd0bd1SPeter Collingbourne << CI.getFrontendOpts().ActionName; 7085dd0bd1SPeter Collingbourne return 0; 7185dd0bd1SPeter Collingbourne } 7285dd0bd1SPeter Collingbourne 7385dd0bd1SPeter Collingbourne case PrintDeclContext: return new DeclContextPrintAction(); 7485dd0bd1SPeter Collingbourne case PrintPreamble: return new PrintPreambleAction(); 75e993e4cdSDavid Blaikie case PrintPreprocessedInput: { 76e993e4cdSDavid Blaikie if (CI.getPreprocessorOutputOpts().RewriteIncludes) 77e993e4cdSDavid Blaikie return new RewriteIncludesAction(); 78e993e4cdSDavid Blaikie return new PrintPreprocessedAction(); 79e993e4cdSDavid Blaikie } 80e993e4cdSDavid Blaikie 8185dd0bd1SPeter Collingbourne case RewriteMacros: return new RewriteMacrosAction(); 8285dd0bd1SPeter Collingbourne case RewriteObjC: return new RewriteObjCAction(); 8385dd0bd1SPeter Collingbourne case RewriteTest: return new RewriteTestAction(); 8498857c98STed Kremenek case RunAnalysis: return new ento::AnalysisAction(); 85f7639e1bSTed Kremenek case MigrateSource: return new arcmt::MigrateSourceAction(); 8685dd0bd1SPeter Collingbourne case RunPreprocessorOnly: return new PreprocessOnlyAction(); 8785dd0bd1SPeter Collingbourne } 88f47fa304SDavid Blaikie llvm_unreachable("Invalid program action!"); 8985dd0bd1SPeter Collingbourne } 9085dd0bd1SPeter Collingbourne 9185dd0bd1SPeter Collingbourne static FrontendAction *CreateFrontendAction(CompilerInstance &CI) { 9285dd0bd1SPeter Collingbourne // Create the underlying action. 9385dd0bd1SPeter Collingbourne FrontendAction *Act = CreateFrontendBaseAction(CI); 9485dd0bd1SPeter Collingbourne if (!Act) 9585dd0bd1SPeter Collingbourne return 0; 9685dd0bd1SPeter Collingbourne 973d97a9beSArgyrios Kyrtzidis const FrontendOptions &FEOpts = CI.getFrontendOpts(); 983d97a9beSArgyrios Kyrtzidis 993d97a9beSArgyrios Kyrtzidis if (FEOpts.FixAndRecompile) { 10024e9afffSArgyrios Kyrtzidis Act = new FixItRecompile(Act); 10124e9afffSArgyrios Kyrtzidis } 10224e9afffSArgyrios Kyrtzidis 103b5703510SChandler Carruth // Potentially wrap the base FE action in an ARC Migrate Tool action. 1043d97a9beSArgyrios Kyrtzidis switch (FEOpts.ARCMTAction) { 105b5703510SChandler Carruth case FrontendOptions::ARCMT_None: 106b5703510SChandler Carruth break; 107b5703510SChandler Carruth case FrontendOptions::ARCMT_Check: 108b5703510SChandler Carruth Act = new arcmt::CheckAction(Act); 109b5703510SChandler Carruth break; 110b5703510SChandler Carruth case FrontendOptions::ARCMT_Modify: 1117fbd97f6SArgyrios Kyrtzidis Act = new arcmt::ModifyAction(Act); 1127fbd97f6SArgyrios Kyrtzidis break; 1137fbd97f6SArgyrios Kyrtzidis case FrontendOptions::ARCMT_Migrate: 114d571363eSArgyrios Kyrtzidis Act = new arcmt::MigrateAction(Act, 115f7639e1bSTed Kremenek FEOpts.MTMigrateDir, 1163d97a9beSArgyrios Kyrtzidis FEOpts.ARCMTMigrateReportOut, 1173d97a9beSArgyrios Kyrtzidis FEOpts.ARCMTMigrateEmitARCErrors); 118b5703510SChandler Carruth break; 119b5703510SChandler Carruth } 120b5703510SChandler Carruth 121f7639e1bSTed Kremenek if (FEOpts.ObjCMTAction != FrontendOptions::ObjCMT_None) { 122f7639e1bSTed Kremenek Act = new arcmt::ObjCMigrateAction(Act, FEOpts.MTMigrateDir, 123f7639e1bSTed Kremenek FEOpts.ObjCMTAction & ~FrontendOptions::ObjCMT_Literals, 124f7639e1bSTed Kremenek FEOpts.ObjCMTAction & ~FrontendOptions::ObjCMT_Subscripting); 125f7639e1bSTed Kremenek } 126f7639e1bSTed Kremenek 12785dd0bd1SPeter Collingbourne // If there are any AST files to merge, create a frontend action 12885dd0bd1SPeter Collingbourne // adaptor to perform the merge. 1293d97a9beSArgyrios Kyrtzidis if (!FEOpts.ASTMergeFiles.empty()) 130bd6a7d4cSArgyrios Kyrtzidis Act = new ASTMergeAction(Act, FEOpts.ASTMergeFiles); 13185dd0bd1SPeter Collingbourne 13285dd0bd1SPeter Collingbourne return Act; 13385dd0bd1SPeter Collingbourne } 13485dd0bd1SPeter Collingbourne 13585dd0bd1SPeter Collingbourne bool clang::ExecuteCompilerInvocation(CompilerInstance *Clang) { 13685dd0bd1SPeter Collingbourne // Honor -help. 13785dd0bd1SPeter Collingbourne if (Clang->getFrontendOpts().ShowHelp) { 138a3c85b86SJames Molloy OwningPtr<driver::OptTable> Opts(driver::createDriverOptTable()); 13985dd0bd1SPeter Collingbourne Opts->PrintHelp(llvm::outs(), "clang -cc1", 14085dd0bd1SPeter Collingbourne "LLVM 'Clang' Compiler: http://clang.llvm.org"); 14185dd0bd1SPeter Collingbourne return 0; 14285dd0bd1SPeter Collingbourne } 14385dd0bd1SPeter Collingbourne 14485dd0bd1SPeter Collingbourne // Honor -version. 14585dd0bd1SPeter Collingbourne // 14685dd0bd1SPeter Collingbourne // FIXME: Use a better -version message? 14785dd0bd1SPeter Collingbourne if (Clang->getFrontendOpts().ShowVersion) { 14885dd0bd1SPeter Collingbourne llvm::cl::PrintVersionMessage(); 14985dd0bd1SPeter Collingbourne return 0; 15085dd0bd1SPeter Collingbourne } 15185dd0bd1SPeter Collingbourne 15285dd0bd1SPeter Collingbourne // Load any requested plugins. 15385dd0bd1SPeter Collingbourne for (unsigned i = 0, 15485dd0bd1SPeter Collingbourne e = Clang->getFrontendOpts().Plugins.size(); i != e; ++i) { 15585dd0bd1SPeter Collingbourne const std::string &Path = Clang->getFrontendOpts().Plugins[i]; 15685dd0bd1SPeter Collingbourne std::string Error; 15785dd0bd1SPeter Collingbourne if (llvm::sys::DynamicLibrary::LoadLibraryPermanently(Path.c_str(), &Error)) 15885dd0bd1SPeter Collingbourne Clang->getDiagnostics().Report(diag::err_fe_unable_to_load_plugin) 15985dd0bd1SPeter Collingbourne << Path << Error; 16085dd0bd1SPeter Collingbourne } 16185dd0bd1SPeter Collingbourne 16211ce9224STobias Grosser // Honor -mllvm. 16311ce9224STobias Grosser // 16411ce9224STobias Grosser // FIXME: Remove this, one day. 16511ce9224STobias Grosser // This should happen AFTER plugins have been loaded! 16611ce9224STobias Grosser if (!Clang->getFrontendOpts().LLVMArgs.empty()) { 16711ce9224STobias Grosser unsigned NumArgs = Clang->getFrontendOpts().LLVMArgs.size(); 16811ce9224STobias Grosser const char **Args = new const char*[NumArgs + 2]; 16911ce9224STobias Grosser Args[0] = "clang (LLVM option parsing)"; 17011ce9224STobias Grosser for (unsigned i = 0; i != NumArgs; ++i) 17111ce9224STobias Grosser Args[i + 1] = Clang->getFrontendOpts().LLVMArgs[i].c_str(); 17211ce9224STobias Grosser Args[NumArgs + 1] = 0; 17309d20eefSDavid Blaikie llvm::cl::ParseCommandLineOptions(NumArgs + 1, Args); 17411ce9224STobias Grosser } 17511ce9224STobias Grosser 17659cce71aSJordy Rose // Honor -analyzer-checker-help. 17759cce71aSJordy Rose // This should happen AFTER plugins have been loaded! 178*40ea0eaaSTed Kremenek if (Clang->getAnalyzerOpts()->ShowCheckerHelp) { 17959cce71aSJordy Rose ento::printCheckerHelp(llvm::outs(), Clang->getFrontendOpts().Plugins); 18059cce71aSJordy Rose return 0; 18159cce71aSJordy Rose } 18259cce71aSJordy Rose 18385dd0bd1SPeter Collingbourne // If there were errors in processing arguments, don't do anything else. 18485dd0bd1SPeter Collingbourne bool Success = false; 1855c26cda2SArgyrios Kyrtzidis if (!Clang->getDiagnostics().hasErrorOccurred()) { 18685dd0bd1SPeter Collingbourne // Create and execute the frontend action. 187e2778999SDylan Noblesmith OwningPtr<FrontendAction> Act(CreateFrontendAction(*Clang)); 1884f76f4aeSTed Kremenek if (Act) { 18985dd0bd1SPeter Collingbourne Success = Clang->ExecuteAction(*Act); 1904f76f4aeSTed Kremenek if (Clang->getFrontendOpts().DisableFree) 1914f76f4aeSTed Kremenek Act.take(); 1924f76f4aeSTed Kremenek } 19385dd0bd1SPeter Collingbourne } 19485dd0bd1SPeter Collingbourne 19585dd0bd1SPeter Collingbourne return Success; 19685dd0bd1SPeter Collingbourne } 197