1f4a2713aSLionel Sambuc //===-- cc1_main.cpp - Clang CC1 Compiler Frontend ------------------------===//
2f4a2713aSLionel Sambuc //
3f4a2713aSLionel Sambuc // The LLVM Compiler Infrastructure
4f4a2713aSLionel Sambuc //
5f4a2713aSLionel Sambuc // This file is distributed under the University of Illinois Open Source
6f4a2713aSLionel Sambuc // License. See LICENSE.TXT for details.
7f4a2713aSLionel Sambuc //
8f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
9f4a2713aSLionel Sambuc //
10f4a2713aSLionel Sambuc // This is the entry point to the clang -cc1 functionality, which implements the
11f4a2713aSLionel Sambuc // core compiler functionality along with a number of additional tools for
12f4a2713aSLionel Sambuc // demonstration and testing purposes.
13f4a2713aSLionel Sambuc //
14f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
15f4a2713aSLionel Sambuc
16f4a2713aSLionel Sambuc #include "llvm/Option/Arg.h"
17f4a2713aSLionel Sambuc #include "clang/Driver/DriverDiagnostic.h"
18f4a2713aSLionel Sambuc #include "clang/Driver/Options.h"
19f4a2713aSLionel Sambuc #include "clang/Frontend/CompilerInstance.h"
20f4a2713aSLionel Sambuc #include "clang/Frontend/CompilerInvocation.h"
21f4a2713aSLionel Sambuc #include "clang/Frontend/FrontendDiagnostic.h"
22f4a2713aSLionel Sambuc #include "clang/Frontend/TextDiagnosticBuffer.h"
23f4a2713aSLionel Sambuc #include "clang/Frontend/TextDiagnosticPrinter.h"
24*0a6a1f1dSLionel Sambuc #include "clang/Frontend/Utils.h"
25f4a2713aSLionel Sambuc #include "clang/FrontendTool/Utils.h"
26f4a2713aSLionel Sambuc #include "llvm/ADT/Statistic.h"
27f4a2713aSLionel Sambuc #include "llvm/LinkAllPasses.h"
28f4a2713aSLionel Sambuc #include "llvm/Option/ArgList.h"
29f4a2713aSLionel Sambuc #include "llvm/Option/OptTable.h"
30f4a2713aSLionel Sambuc #include "llvm/Support/ErrorHandling.h"
31f4a2713aSLionel Sambuc #include "llvm/Support/ManagedStatic.h"
32f4a2713aSLionel Sambuc #include "llvm/Support/Signals.h"
33f4a2713aSLionel Sambuc #include "llvm/Support/TargetSelect.h"
34f4a2713aSLionel Sambuc #include "llvm/Support/Timer.h"
35f4a2713aSLionel Sambuc #include "llvm/Support/raw_ostream.h"
36f4a2713aSLionel Sambuc #include <cstdio>
37f4a2713aSLionel Sambuc using namespace clang;
38f4a2713aSLionel Sambuc using namespace llvm::opt;
39f4a2713aSLionel Sambuc
40f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
41f4a2713aSLionel Sambuc // Main driver
42f4a2713aSLionel Sambuc //===----------------------------------------------------------------------===//
43f4a2713aSLionel Sambuc
LLVMErrorHandler(void * UserData,const std::string & Message,bool GenCrashDiag)44f4a2713aSLionel Sambuc static void LLVMErrorHandler(void *UserData, const std::string &Message,
45f4a2713aSLionel Sambuc bool GenCrashDiag) {
46f4a2713aSLionel Sambuc DiagnosticsEngine &Diags = *static_cast<DiagnosticsEngine*>(UserData);
47f4a2713aSLionel Sambuc
48f4a2713aSLionel Sambuc Diags.Report(diag::err_fe_error_backend) << Message;
49f4a2713aSLionel Sambuc
50f4a2713aSLionel Sambuc // Run the interrupt handlers to make sure any special cleanups get done, in
51f4a2713aSLionel Sambuc // particular that we remove files registered with RemoveFileOnSignal.
52f4a2713aSLionel Sambuc llvm::sys::RunInterruptHandlers();
53f4a2713aSLionel Sambuc
54f4a2713aSLionel Sambuc // We cannot recover from llvm errors. When reporting a fatal error, exit
55f4a2713aSLionel Sambuc // with status 70 to generate crash diagnostics. For BSD systems this is
56f4a2713aSLionel Sambuc // defined as an internal software error. Otherwise, exit with status 1.
57f4a2713aSLionel Sambuc exit(GenCrashDiag ? 70 : 1);
58f4a2713aSLionel Sambuc }
59f4a2713aSLionel Sambuc
60*0a6a1f1dSLionel Sambuc #ifdef LINK_POLLY_INTO_TOOLS
61*0a6a1f1dSLionel Sambuc namespace polly {
62*0a6a1f1dSLionel Sambuc void initializePollyPasses(llvm::PassRegistry &Registry);
63*0a6a1f1dSLionel Sambuc }
64*0a6a1f1dSLionel Sambuc #endif
65*0a6a1f1dSLionel Sambuc
cc1_main(ArrayRef<const char * > Argv,const char * Argv0,void * MainAddr)66*0a6a1f1dSLionel Sambuc int cc1_main(ArrayRef<const char *> Argv, const char *Argv0, void *MainAddr) {
67*0a6a1f1dSLionel Sambuc std::unique_ptr<CompilerInstance> Clang(new CompilerInstance());
68f4a2713aSLionel Sambuc IntrusiveRefCntPtr<DiagnosticIDs> DiagID(new DiagnosticIDs());
69f4a2713aSLionel Sambuc
70f4a2713aSLionel Sambuc // Initialize targets first, so that --version shows registered targets.
71f4a2713aSLionel Sambuc llvm::InitializeAllTargets();
72f4a2713aSLionel Sambuc llvm::InitializeAllTargetMCs();
73f4a2713aSLionel Sambuc llvm::InitializeAllAsmPrinters();
74f4a2713aSLionel Sambuc llvm::InitializeAllAsmParsers();
75f4a2713aSLionel Sambuc
76*0a6a1f1dSLionel Sambuc #ifdef LINK_POLLY_INTO_TOOLS
77*0a6a1f1dSLionel Sambuc llvm::PassRegistry &Registry = *llvm::PassRegistry::getPassRegistry();
78*0a6a1f1dSLionel Sambuc polly::initializePollyPasses(Registry);
79*0a6a1f1dSLionel Sambuc #endif
80*0a6a1f1dSLionel Sambuc
81f4a2713aSLionel Sambuc // Buffer diagnostics from argument parsing so that we can output them using a
82f4a2713aSLionel Sambuc // well formed diagnostic object.
83f4a2713aSLionel Sambuc IntrusiveRefCntPtr<DiagnosticOptions> DiagOpts = new DiagnosticOptions();
84f4a2713aSLionel Sambuc TextDiagnosticBuffer *DiagsBuffer = new TextDiagnosticBuffer;
85f4a2713aSLionel Sambuc DiagnosticsEngine Diags(DiagID, &*DiagOpts, DiagsBuffer);
86*0a6a1f1dSLionel Sambuc bool Success = CompilerInvocation::CreateFromArgs(
87*0a6a1f1dSLionel Sambuc Clang->getInvocation(), Argv.begin(), Argv.end(), Diags);
88f4a2713aSLionel Sambuc
89f4a2713aSLionel Sambuc // Infer the builtin include path if unspecified.
90f4a2713aSLionel Sambuc if (Clang->getHeaderSearchOpts().UseBuiltinIncludes &&
91f4a2713aSLionel Sambuc Clang->getHeaderSearchOpts().ResourceDir.empty())
92f4a2713aSLionel Sambuc Clang->getHeaderSearchOpts().ResourceDir =
93f4a2713aSLionel Sambuc CompilerInvocation::GetResourcesPath(Argv0, MainAddr);
94f4a2713aSLionel Sambuc
95f4a2713aSLionel Sambuc // Create the actual diagnostics engine.
96f4a2713aSLionel Sambuc Clang->createDiagnostics();
97f4a2713aSLionel Sambuc if (!Clang->hasDiagnostics())
98f4a2713aSLionel Sambuc return 1;
99f4a2713aSLionel Sambuc
100f4a2713aSLionel Sambuc // Set an error handler, so that any LLVM backend diagnostics go through our
101f4a2713aSLionel Sambuc // error handler.
102f4a2713aSLionel Sambuc llvm::install_fatal_error_handler(LLVMErrorHandler,
103f4a2713aSLionel Sambuc static_cast<void*>(&Clang->getDiagnostics()));
104f4a2713aSLionel Sambuc
105f4a2713aSLionel Sambuc DiagsBuffer->FlushDiagnostics(Clang->getDiagnostics());
106f4a2713aSLionel Sambuc if (!Success)
107f4a2713aSLionel Sambuc return 1;
108f4a2713aSLionel Sambuc
109f4a2713aSLionel Sambuc // Execute the frontend actions.
110f4a2713aSLionel Sambuc Success = ExecuteCompilerInvocation(Clang.get());
111f4a2713aSLionel Sambuc
112f4a2713aSLionel Sambuc // If any timers were active but haven't been destroyed yet, print their
113f4a2713aSLionel Sambuc // results now. This happens in -disable-free mode.
114f4a2713aSLionel Sambuc llvm::TimerGroup::printAll(llvm::errs());
115f4a2713aSLionel Sambuc
116f4a2713aSLionel Sambuc // Our error handler depends on the Diagnostics object, which we're
117f4a2713aSLionel Sambuc // potentially about to delete. Uninstall the handler now so that any
118f4a2713aSLionel Sambuc // later errors use the default handling behavior instead.
119f4a2713aSLionel Sambuc llvm::remove_fatal_error_handler();
120f4a2713aSLionel Sambuc
121f4a2713aSLionel Sambuc // When running with -disable-free, don't do any destruction or shutdown.
122f4a2713aSLionel Sambuc if (Clang->getFrontendOpts().DisableFree) {
123f4a2713aSLionel Sambuc if (llvm::AreStatisticsEnabled() || Clang->getFrontendOpts().ShowStats)
124f4a2713aSLionel Sambuc llvm::PrintStatistics();
125*0a6a1f1dSLionel Sambuc BuryPointer(std::move(Clang));
126f4a2713aSLionel Sambuc return !Success;
127f4a2713aSLionel Sambuc }
128f4a2713aSLionel Sambuc
129f4a2713aSLionel Sambuc // Managed static deconstruction. Useful for making things like
130f4a2713aSLionel Sambuc // -time-passes usable.
131f4a2713aSLionel Sambuc llvm::llvm_shutdown();
132f4a2713aSLionel Sambuc
133f4a2713aSLionel Sambuc return !Success;
134f4a2713aSLionel Sambuc }
135