1f785676fSDimitry Andric //===-LTOCodeGenerator.cpp - LLVM Link Time Optimizer ---------------------===//
2f785676fSDimitry Andric //
3f785676fSDimitry Andric //                     The LLVM Compiler Infrastructure
4f785676fSDimitry Andric //
5f785676fSDimitry Andric // This file is distributed under the University of Illinois Open Source
6f785676fSDimitry Andric // License. See LICENSE.TXT for details.
7f785676fSDimitry Andric //
8f785676fSDimitry Andric //===----------------------------------------------------------------------===//
9f785676fSDimitry Andric //
10f785676fSDimitry Andric // This file implements the Link Time Optimization library. This library is
11f785676fSDimitry Andric // intended to be used by linker to optimize code at link time.
12f785676fSDimitry Andric //
13f785676fSDimitry Andric //===----------------------------------------------------------------------===//
14f785676fSDimitry Andric 
15f785676fSDimitry Andric #include "llvm/LTO/LTOCodeGenerator.h"
16f785676fSDimitry Andric #include "llvm/LTO/LTOModule.h"
17f785676fSDimitry Andric #include "llvm/ADT/StringExtras.h"
18f785676fSDimitry Andric #include "llvm/Analysis/Passes.h"
19f785676fSDimitry Andric #include "llvm/Analysis/Verifier.h"
20f785676fSDimitry Andric #include "llvm/Bitcode/ReaderWriter.h"
21f785676fSDimitry Andric #include "llvm/CodeGen/RuntimeLibcalls.h"
22f785676fSDimitry Andric #include "llvm/Config/config.h"
23f785676fSDimitry Andric #include "llvm/IR/Constants.h"
24f785676fSDimitry Andric #include "llvm/IR/DataLayout.h"
25f785676fSDimitry Andric #include "llvm/IR/DerivedTypes.h"
26f785676fSDimitry Andric #include "llvm/IR/LLVMContext.h"
27f785676fSDimitry Andric #include "llvm/IR/Module.h"
28f785676fSDimitry Andric #include "llvm/InitializePasses.h"
29f785676fSDimitry Andric #include "llvm/Linker.h"
30f785676fSDimitry Andric #include "llvm/MC/MCAsmInfo.h"
31f785676fSDimitry Andric #include "llvm/MC/MCContext.h"
32f785676fSDimitry Andric #include "llvm/MC/SubtargetFeature.h"
33f785676fSDimitry Andric #include "llvm/PassManager.h"
34f785676fSDimitry Andric #include "llvm/Support/CommandLine.h"
35f785676fSDimitry Andric #include "llvm/Support/FileSystem.h"
36f785676fSDimitry Andric #include "llvm/Support/FormattedStream.h"
37f785676fSDimitry Andric #include "llvm/Support/Host.h"
38f785676fSDimitry Andric #include "llvm/Support/MemoryBuffer.h"
39f785676fSDimitry Andric #include "llvm/Support/Signals.h"
40f785676fSDimitry Andric #include "llvm/Support/TargetRegistry.h"
41f785676fSDimitry Andric #include "llvm/Support/TargetSelect.h"
42f785676fSDimitry Andric #include "llvm/Support/ToolOutputFile.h"
43f785676fSDimitry Andric #include "llvm/Support/system_error.h"
44f785676fSDimitry Andric #include "llvm/Target/TargetLibraryInfo.h"
45f785676fSDimitry Andric #include "llvm/Target/TargetLowering.h"
46f785676fSDimitry Andric #include "llvm/Target/TargetOptions.h"
47f785676fSDimitry Andric #include "llvm/Target/TargetRegisterInfo.h"
48f785676fSDimitry Andric #include "llvm/Target/Mangler.h"
49f785676fSDimitry Andric #include "llvm/Transforms/IPO.h"
50f785676fSDimitry Andric #include "llvm/Transforms/IPO/PassManagerBuilder.h"
51f785676fSDimitry Andric #include "llvm/Transforms/ObjCARC.h"
52f785676fSDimitry Andric using namespace llvm;
53f785676fSDimitry Andric 
54f785676fSDimitry Andric const char* LTOCodeGenerator::getVersionString() {
55f785676fSDimitry Andric #ifdef LLVM_VERSION_INFO
56f785676fSDimitry Andric   return PACKAGE_NAME " version " PACKAGE_VERSION ", " LLVM_VERSION_INFO;
57f785676fSDimitry Andric #else
58f785676fSDimitry Andric   return PACKAGE_NAME " version " PACKAGE_VERSION;
59f785676fSDimitry Andric #endif
60f785676fSDimitry Andric }
61f785676fSDimitry Andric 
62f785676fSDimitry Andric LTOCodeGenerator::LTOCodeGenerator()
63f785676fSDimitry Andric     : Context(getGlobalContext()), Linker(new Module("ld-temp.o", Context)),
64f785676fSDimitry Andric       TargetMach(NULL), EmitDwarfDebugInfo(false), ScopeRestrictionsDone(false),
65f785676fSDimitry Andric       CodeModel(LTO_CODEGEN_PIC_MODEL_DYNAMIC), NativeObjectFile(NULL) {
66f785676fSDimitry Andric   initializeLTOPasses();
67f785676fSDimitry Andric }
68f785676fSDimitry Andric 
69f785676fSDimitry Andric LTOCodeGenerator::~LTOCodeGenerator() {
70f785676fSDimitry Andric   delete TargetMach;
71f785676fSDimitry Andric   delete NativeObjectFile;
72f785676fSDimitry Andric   TargetMach = NULL;
73f785676fSDimitry Andric   NativeObjectFile = NULL;
74f785676fSDimitry Andric 
75f785676fSDimitry Andric   Linker.deleteModule();
76f785676fSDimitry Andric 
77f785676fSDimitry Andric   for (std::vector<char *>::iterator I = CodegenOptions.begin(),
78f785676fSDimitry Andric                                      E = CodegenOptions.end();
79f785676fSDimitry Andric        I != E; ++I)
80f785676fSDimitry Andric     free(*I);
81f785676fSDimitry Andric }
82f785676fSDimitry Andric 
83f785676fSDimitry Andric // Initialize LTO passes. Please keep this funciton in sync with
84f785676fSDimitry Andric // PassManagerBuilder::populateLTOPassManager(), and make sure all LTO
85f785676fSDimitry Andric // passes are initialized.
86f785676fSDimitry Andric //
87f785676fSDimitry Andric void LTOCodeGenerator::initializeLTOPasses() {
88f785676fSDimitry Andric   PassRegistry &R = *PassRegistry::getPassRegistry();
89f785676fSDimitry Andric 
90f785676fSDimitry Andric   initializeInternalizePassPass(R);
91f785676fSDimitry Andric   initializeIPSCCPPass(R);
92f785676fSDimitry Andric   initializeGlobalOptPass(R);
93f785676fSDimitry Andric   initializeConstantMergePass(R);
94f785676fSDimitry Andric   initializeDAHPass(R);
95f785676fSDimitry Andric   initializeInstCombinerPass(R);
96f785676fSDimitry Andric   initializeSimpleInlinerPass(R);
97f785676fSDimitry Andric   initializePruneEHPass(R);
98f785676fSDimitry Andric   initializeGlobalDCEPass(R);
99f785676fSDimitry Andric   initializeArgPromotionPass(R);
100f785676fSDimitry Andric   initializeJumpThreadingPass(R);
101f785676fSDimitry Andric   initializeSROAPass(R);
102f785676fSDimitry Andric   initializeSROA_DTPass(R);
103f785676fSDimitry Andric   initializeSROA_SSAUpPass(R);
104f785676fSDimitry Andric   initializeFunctionAttrsPass(R);
105f785676fSDimitry Andric   initializeGlobalsModRefPass(R);
106f785676fSDimitry Andric   initializeLICMPass(R);
107f785676fSDimitry Andric   initializeGVNPass(R);
108f785676fSDimitry Andric   initializeMemCpyOptPass(R);
109f785676fSDimitry Andric   initializeDCEPass(R);
110f785676fSDimitry Andric   initializeCFGSimplifyPassPass(R);
111f785676fSDimitry Andric }
112f785676fSDimitry Andric 
113f785676fSDimitry Andric bool LTOCodeGenerator::addModule(LTOModule* mod, std::string& errMsg) {
114f785676fSDimitry Andric   bool ret = Linker.linkInModule(mod->getLLVVMModule(), &errMsg);
115f785676fSDimitry Andric 
116f785676fSDimitry Andric   const std::vector<const char*> &undefs = mod->getAsmUndefinedRefs();
117f785676fSDimitry Andric   for (int i = 0, e = undefs.size(); i != e; ++i)
118f785676fSDimitry Andric     AsmUndefinedRefs[undefs[i]] = 1;
119f785676fSDimitry Andric 
120f785676fSDimitry Andric   return !ret;
121f785676fSDimitry Andric }
122f785676fSDimitry Andric 
123f785676fSDimitry Andric void LTOCodeGenerator::setTargetOptions(TargetOptions options) {
124f785676fSDimitry Andric   Options.LessPreciseFPMADOption = options.LessPreciseFPMADOption;
125f785676fSDimitry Andric   Options.NoFramePointerElim = options.NoFramePointerElim;
126f785676fSDimitry Andric   Options.AllowFPOpFusion = options.AllowFPOpFusion;
127f785676fSDimitry Andric   Options.UnsafeFPMath = options.UnsafeFPMath;
128f785676fSDimitry Andric   Options.NoInfsFPMath = options.NoInfsFPMath;
129f785676fSDimitry Andric   Options.NoNaNsFPMath = options.NoNaNsFPMath;
130f785676fSDimitry Andric   Options.HonorSignDependentRoundingFPMathOption =
131f785676fSDimitry Andric     options.HonorSignDependentRoundingFPMathOption;
132f785676fSDimitry Andric   Options.UseSoftFloat = options.UseSoftFloat;
133f785676fSDimitry Andric   Options.FloatABIType = options.FloatABIType;
134f785676fSDimitry Andric   Options.NoZerosInBSS = options.NoZerosInBSS;
135f785676fSDimitry Andric   Options.GuaranteedTailCallOpt = options.GuaranteedTailCallOpt;
136f785676fSDimitry Andric   Options.DisableTailCalls = options.DisableTailCalls;
137f785676fSDimitry Andric   Options.StackAlignmentOverride = options.StackAlignmentOverride;
138f785676fSDimitry Andric   Options.TrapFuncName = options.TrapFuncName;
139f785676fSDimitry Andric   Options.PositionIndependentExecutable = options.PositionIndependentExecutable;
140f785676fSDimitry Andric   Options.EnableSegmentedStacks = options.EnableSegmentedStacks;
141f785676fSDimitry Andric   Options.UseInitArray = options.UseInitArray;
142f785676fSDimitry Andric }
143f785676fSDimitry Andric 
144f785676fSDimitry Andric void LTOCodeGenerator::setDebugInfo(lto_debug_model debug) {
145f785676fSDimitry Andric   switch (debug) {
146f785676fSDimitry Andric   case LTO_DEBUG_MODEL_NONE:
147f785676fSDimitry Andric     EmitDwarfDebugInfo = false;
148f785676fSDimitry Andric     return;
149f785676fSDimitry Andric 
150f785676fSDimitry Andric   case LTO_DEBUG_MODEL_DWARF:
151f785676fSDimitry Andric     EmitDwarfDebugInfo = true;
152f785676fSDimitry Andric     return;
153f785676fSDimitry Andric   }
154f785676fSDimitry Andric   llvm_unreachable("Unknown debug format!");
155f785676fSDimitry Andric }
156f785676fSDimitry Andric 
157f785676fSDimitry Andric void LTOCodeGenerator::setCodePICModel(lto_codegen_model model) {
158f785676fSDimitry Andric   switch (model) {
159f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_STATIC:
160f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_DYNAMIC:
161f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_DYNAMIC_NO_PIC:
162f785676fSDimitry Andric     CodeModel = model;
163f785676fSDimitry Andric     return;
164f785676fSDimitry Andric   }
165f785676fSDimitry Andric   llvm_unreachable("Unknown PIC model!");
166f785676fSDimitry Andric }
167f785676fSDimitry Andric 
168f785676fSDimitry Andric bool LTOCodeGenerator::writeMergedModules(const char *path,
169f785676fSDimitry Andric                                           std::string &errMsg) {
170f785676fSDimitry Andric   if (!determineTarget(errMsg))
171f785676fSDimitry Andric     return false;
172f785676fSDimitry Andric 
173f785676fSDimitry Andric   // mark which symbols can not be internalized
174f785676fSDimitry Andric   applyScopeRestrictions();
175f785676fSDimitry Andric 
176f785676fSDimitry Andric   // create output file
177f785676fSDimitry Andric   std::string ErrInfo;
178f785676fSDimitry Andric   tool_output_file Out(path, ErrInfo, sys::fs::F_Binary);
179f785676fSDimitry Andric   if (!ErrInfo.empty()) {
180f785676fSDimitry Andric     errMsg = "could not open bitcode file for writing: ";
181f785676fSDimitry Andric     errMsg += path;
182f785676fSDimitry Andric     return false;
183f785676fSDimitry Andric   }
184f785676fSDimitry Andric 
185f785676fSDimitry Andric   // write bitcode to it
186f785676fSDimitry Andric   WriteBitcodeToFile(Linker.getModule(), Out.os());
187f785676fSDimitry Andric   Out.os().close();
188f785676fSDimitry Andric 
189f785676fSDimitry Andric   if (Out.os().has_error()) {
190f785676fSDimitry Andric     errMsg = "could not write bitcode file: ";
191f785676fSDimitry Andric     errMsg += path;
192f785676fSDimitry Andric     Out.os().clear_error();
193f785676fSDimitry Andric     return false;
194f785676fSDimitry Andric   }
195f785676fSDimitry Andric 
196f785676fSDimitry Andric   Out.keep();
197f785676fSDimitry Andric   return true;
198f785676fSDimitry Andric }
199f785676fSDimitry Andric 
200f785676fSDimitry Andric bool LTOCodeGenerator::compile_to_file(const char** name,
201f785676fSDimitry Andric                                        bool disableOpt,
202f785676fSDimitry Andric                                        bool disableInline,
203f785676fSDimitry Andric                                        bool disableGVNLoadPRE,
204f785676fSDimitry Andric                                        std::string& errMsg) {
205f785676fSDimitry Andric   // make unique temp .o file to put generated object file
206f785676fSDimitry Andric   SmallString<128> Filename;
207f785676fSDimitry Andric   int FD;
208f785676fSDimitry Andric   error_code EC = sys::fs::createTemporaryFile("lto-llvm", "o", FD, Filename);
209f785676fSDimitry Andric   if (EC) {
210f785676fSDimitry Andric     errMsg = EC.message();
211f785676fSDimitry Andric     return false;
212f785676fSDimitry Andric   }
213f785676fSDimitry Andric 
214f785676fSDimitry Andric   // generate object file
215f785676fSDimitry Andric   tool_output_file objFile(Filename.c_str(), FD);
216f785676fSDimitry Andric 
217f785676fSDimitry Andric   bool genResult = generateObjectFile(objFile.os(), disableOpt, disableInline,
218f785676fSDimitry Andric                                       disableGVNLoadPRE, errMsg);
219f785676fSDimitry Andric   objFile.os().close();
220f785676fSDimitry Andric   if (objFile.os().has_error()) {
221f785676fSDimitry Andric     objFile.os().clear_error();
222f785676fSDimitry Andric     sys::fs::remove(Twine(Filename));
223f785676fSDimitry Andric     return false;
224f785676fSDimitry Andric   }
225f785676fSDimitry Andric 
226f785676fSDimitry Andric   objFile.keep();
227f785676fSDimitry Andric   if (!genResult) {
228f785676fSDimitry Andric     sys::fs::remove(Twine(Filename));
229f785676fSDimitry Andric     return false;
230f785676fSDimitry Andric   }
231f785676fSDimitry Andric 
232f785676fSDimitry Andric   NativeObjectPath = Filename.c_str();
233f785676fSDimitry Andric   *name = NativeObjectPath.c_str();
234f785676fSDimitry Andric   return true;
235f785676fSDimitry Andric }
236f785676fSDimitry Andric 
237f785676fSDimitry Andric const void* LTOCodeGenerator::compile(size_t* length,
238f785676fSDimitry Andric                                       bool disableOpt,
239f785676fSDimitry Andric                                       bool disableInline,
240f785676fSDimitry Andric                                       bool disableGVNLoadPRE,
241f785676fSDimitry Andric                                       std::string& errMsg) {
242f785676fSDimitry Andric   const char *name;
243f785676fSDimitry Andric   if (!compile_to_file(&name, disableOpt, disableInline, disableGVNLoadPRE,
244f785676fSDimitry Andric                        errMsg))
245f785676fSDimitry Andric     return NULL;
246f785676fSDimitry Andric 
247f785676fSDimitry Andric   // remove old buffer if compile() called twice
248f785676fSDimitry Andric   delete NativeObjectFile;
249f785676fSDimitry Andric 
250f785676fSDimitry Andric   // read .o file into memory buffer
251f785676fSDimitry Andric   OwningPtr<MemoryBuffer> BuffPtr;
252f785676fSDimitry Andric   if (error_code ec = MemoryBuffer::getFile(name, BuffPtr, -1, false)) {
253f785676fSDimitry Andric     errMsg = ec.message();
254f785676fSDimitry Andric     sys::fs::remove(NativeObjectPath);
255f785676fSDimitry Andric     return NULL;
256f785676fSDimitry Andric   }
257f785676fSDimitry Andric   NativeObjectFile = BuffPtr.take();
258f785676fSDimitry Andric 
259f785676fSDimitry Andric   // remove temp files
260f785676fSDimitry Andric   sys::fs::remove(NativeObjectPath);
261f785676fSDimitry Andric 
262f785676fSDimitry Andric   // return buffer, unless error
263f785676fSDimitry Andric   if (NativeObjectFile == NULL)
264f785676fSDimitry Andric     return NULL;
265f785676fSDimitry Andric   *length = NativeObjectFile->getBufferSize();
266f785676fSDimitry Andric   return NativeObjectFile->getBufferStart();
267f785676fSDimitry Andric }
268f785676fSDimitry Andric 
269f785676fSDimitry Andric bool LTOCodeGenerator::determineTarget(std::string &errMsg) {
270f785676fSDimitry Andric   if (TargetMach != NULL)
271f785676fSDimitry Andric     return true;
272f785676fSDimitry Andric 
273f785676fSDimitry Andric   std::string TripleStr = Linker.getModule()->getTargetTriple();
274f785676fSDimitry Andric   if (TripleStr.empty())
275f785676fSDimitry Andric     TripleStr = sys::getDefaultTargetTriple();
276f785676fSDimitry Andric   llvm::Triple Triple(TripleStr);
277f785676fSDimitry Andric 
278f785676fSDimitry Andric   // create target machine from info for merged modules
279f785676fSDimitry Andric   const Target *march = TargetRegistry::lookupTarget(TripleStr, errMsg);
280f785676fSDimitry Andric   if (march == NULL)
281f785676fSDimitry Andric     return false;
282f785676fSDimitry Andric 
283f785676fSDimitry Andric   // The relocation model is actually a static member of TargetMachine and
284f785676fSDimitry Andric   // needs to be set before the TargetMachine is instantiated.
285f785676fSDimitry Andric   Reloc::Model RelocModel = Reloc::Default;
286f785676fSDimitry Andric   switch (CodeModel) {
287f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_STATIC:
288f785676fSDimitry Andric     RelocModel = Reloc::Static;
289f785676fSDimitry Andric     break;
290f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_DYNAMIC:
291f785676fSDimitry Andric     RelocModel = Reloc::PIC_;
292f785676fSDimitry Andric     break;
293f785676fSDimitry Andric   case LTO_CODEGEN_PIC_MODEL_DYNAMIC_NO_PIC:
294f785676fSDimitry Andric     RelocModel = Reloc::DynamicNoPIC;
295f785676fSDimitry Andric     break;
296f785676fSDimitry Andric   }
297f785676fSDimitry Andric 
298f785676fSDimitry Andric   // construct LTOModule, hand over ownership of module and target
299f785676fSDimitry Andric   SubtargetFeatures Features;
300f785676fSDimitry Andric   Features.getDefaultSubtargetFeatures(Triple);
301f785676fSDimitry Andric   std::string FeatureStr = Features.getString();
302f785676fSDimitry Andric   // Set a default CPU for Darwin triples.
303f785676fSDimitry Andric   if (MCpu.empty() && Triple.isOSDarwin()) {
304f785676fSDimitry Andric     if (Triple.getArch() == llvm::Triple::x86_64)
305f785676fSDimitry Andric       MCpu = "core2";
306f785676fSDimitry Andric     else if (Triple.getArch() == llvm::Triple::x86)
307f785676fSDimitry Andric       MCpu = "yonah";
308f785676fSDimitry Andric   }
309f785676fSDimitry Andric 
310f785676fSDimitry Andric   TargetMach = march->createTargetMachine(TripleStr, MCpu, FeatureStr, Options,
311f785676fSDimitry Andric                                           RelocModel, CodeModel::Default,
312f785676fSDimitry Andric                                           CodeGenOpt::Aggressive);
313f785676fSDimitry Andric   return true;
314f785676fSDimitry Andric }
315f785676fSDimitry Andric 
316f785676fSDimitry Andric void LTOCodeGenerator::
317f785676fSDimitry Andric applyRestriction(GlobalValue &GV,
318f785676fSDimitry Andric                  const ArrayRef<StringRef> &Libcalls,
319f785676fSDimitry Andric                  std::vector<const char*> &MustPreserveList,
320f785676fSDimitry Andric                  SmallPtrSet<GlobalValue*, 8> &AsmUsed,
321f785676fSDimitry Andric                  Mangler &Mangler) {
322f785676fSDimitry Andric   SmallString<64> Buffer;
323f785676fSDimitry Andric   Mangler.getNameWithPrefix(Buffer, &GV, false);
324f785676fSDimitry Andric 
325f785676fSDimitry Andric   if (GV.isDeclaration())
326f785676fSDimitry Andric     return;
327f785676fSDimitry Andric   if (MustPreserveSymbols.count(Buffer))
328f785676fSDimitry Andric     MustPreserveList.push_back(GV.getName().data());
329f785676fSDimitry Andric   if (AsmUndefinedRefs.count(Buffer))
330f785676fSDimitry Andric     AsmUsed.insert(&GV);
331f785676fSDimitry Andric 
332f785676fSDimitry Andric   // Conservatively append user-supplied runtime library functions to
333f785676fSDimitry Andric   // llvm.compiler.used.  These could be internalized and deleted by
334f785676fSDimitry Andric   // optimizations like -globalopt, causing problems when later optimizations
335f785676fSDimitry Andric   // add new library calls (e.g., llvm.memset => memset and printf => puts).
336f785676fSDimitry Andric   // Leave it to the linker to remove any dead code (e.g. with -dead_strip).
337f785676fSDimitry Andric   if (isa<Function>(GV) &&
338f785676fSDimitry Andric       std::binary_search(Libcalls.begin(), Libcalls.end(), GV.getName()))
339f785676fSDimitry Andric     AsmUsed.insert(&GV);
340f785676fSDimitry Andric }
341f785676fSDimitry Andric 
342f785676fSDimitry Andric static void findUsedValues(GlobalVariable *LLVMUsed,
343f785676fSDimitry Andric                            SmallPtrSet<GlobalValue*, 8> &UsedValues) {
344f785676fSDimitry Andric   if (LLVMUsed == 0) return;
345f785676fSDimitry Andric 
346f785676fSDimitry Andric   ConstantArray *Inits = cast<ConstantArray>(LLVMUsed->getInitializer());
347f785676fSDimitry Andric   for (unsigned i = 0, e = Inits->getNumOperands(); i != e; ++i)
348f785676fSDimitry Andric     if (GlobalValue *GV =
349f785676fSDimitry Andric         dyn_cast<GlobalValue>(Inits->getOperand(i)->stripPointerCasts()))
350f785676fSDimitry Andric       UsedValues.insert(GV);
351f785676fSDimitry Andric }
352f785676fSDimitry Andric 
353f785676fSDimitry Andric static void accumulateAndSortLibcalls(std::vector<StringRef> &Libcalls,
354f785676fSDimitry Andric                                       const TargetLibraryInfo& TLI,
355f785676fSDimitry Andric                                       const TargetLowering *Lowering)
356f785676fSDimitry Andric {
357f785676fSDimitry Andric   // TargetLibraryInfo has info on C runtime library calls on the current
358f785676fSDimitry Andric   // target.
359f785676fSDimitry Andric   for (unsigned I = 0, E = static_cast<unsigned>(LibFunc::NumLibFuncs);
360f785676fSDimitry Andric        I != E; ++I) {
361f785676fSDimitry Andric     LibFunc::Func F = static_cast<LibFunc::Func>(I);
362f785676fSDimitry Andric     if (TLI.has(F))
363f785676fSDimitry Andric       Libcalls.push_back(TLI.getName(F));
364f785676fSDimitry Andric   }
365f785676fSDimitry Andric 
366f785676fSDimitry Andric   // TargetLowering has info on library calls that CodeGen expects to be
367f785676fSDimitry Andric   // available, both from the C runtime and compiler-rt.
368f785676fSDimitry Andric   if (Lowering)
369f785676fSDimitry Andric     for (unsigned I = 0, E = static_cast<unsigned>(RTLIB::UNKNOWN_LIBCALL);
370f785676fSDimitry Andric          I != E; ++I)
371f785676fSDimitry Andric       if (const char *Name
372f785676fSDimitry Andric           = Lowering->getLibcallName(static_cast<RTLIB::Libcall>(I)))
373f785676fSDimitry Andric         Libcalls.push_back(Name);
374f785676fSDimitry Andric 
375f785676fSDimitry Andric   array_pod_sort(Libcalls.begin(), Libcalls.end());
376f785676fSDimitry Andric   Libcalls.erase(std::unique(Libcalls.begin(), Libcalls.end()),
377f785676fSDimitry Andric                  Libcalls.end());
378f785676fSDimitry Andric }
379f785676fSDimitry Andric 
380f785676fSDimitry Andric void LTOCodeGenerator::applyScopeRestrictions() {
381f785676fSDimitry Andric   if (ScopeRestrictionsDone)
382f785676fSDimitry Andric     return;
383f785676fSDimitry Andric   Module *mergedModule = Linker.getModule();
384f785676fSDimitry Andric 
385f785676fSDimitry Andric   // Start off with a verification pass.
386f785676fSDimitry Andric   PassManager passes;
387f785676fSDimitry Andric   passes.add(createVerifierPass());
388f785676fSDimitry Andric 
389f785676fSDimitry Andric   // mark which symbols can not be internalized
390f785676fSDimitry Andric   Mangler Mangler(TargetMach);
391f785676fSDimitry Andric   std::vector<const char*> MustPreserveList;
392f785676fSDimitry Andric   SmallPtrSet<GlobalValue*, 8> AsmUsed;
393f785676fSDimitry Andric   std::vector<StringRef> Libcalls;
394f785676fSDimitry Andric   TargetLibraryInfo TLI(Triple(TargetMach->getTargetTriple()));
395f785676fSDimitry Andric   accumulateAndSortLibcalls(Libcalls, TLI, TargetMach->getTargetLowering());
396f785676fSDimitry Andric 
397f785676fSDimitry Andric   for (Module::iterator f = mergedModule->begin(),
398f785676fSDimitry Andric          e = mergedModule->end(); f != e; ++f)
399f785676fSDimitry Andric     applyRestriction(*f, Libcalls, MustPreserveList, AsmUsed, Mangler);
400f785676fSDimitry Andric   for (Module::global_iterator v = mergedModule->global_begin(),
401f785676fSDimitry Andric          e = mergedModule->global_end(); v !=  e; ++v)
402f785676fSDimitry Andric     applyRestriction(*v, Libcalls, MustPreserveList, AsmUsed, Mangler);
403f785676fSDimitry Andric   for (Module::alias_iterator a = mergedModule->alias_begin(),
404f785676fSDimitry Andric          e = mergedModule->alias_end(); a != e; ++a)
405f785676fSDimitry Andric     applyRestriction(*a, Libcalls, MustPreserveList, AsmUsed, Mangler);
406f785676fSDimitry Andric 
407f785676fSDimitry Andric   GlobalVariable *LLVMCompilerUsed =
408f785676fSDimitry Andric     mergedModule->getGlobalVariable("llvm.compiler.used");
409f785676fSDimitry Andric   findUsedValues(LLVMCompilerUsed, AsmUsed);
410f785676fSDimitry Andric   if (LLVMCompilerUsed)
411f785676fSDimitry Andric     LLVMCompilerUsed->eraseFromParent();
412f785676fSDimitry Andric 
413f785676fSDimitry Andric   if (!AsmUsed.empty()) {
414f785676fSDimitry Andric     llvm::Type *i8PTy = llvm::Type::getInt8PtrTy(Context);
415f785676fSDimitry Andric     std::vector<Constant*> asmUsed2;
416f785676fSDimitry Andric     for (SmallPtrSet<GlobalValue*, 16>::const_iterator i = AsmUsed.begin(),
417f785676fSDimitry Andric            e = AsmUsed.end(); i !=e; ++i) {
418f785676fSDimitry Andric       GlobalValue *GV = *i;
419f785676fSDimitry Andric       Constant *c = ConstantExpr::getBitCast(GV, i8PTy);
420f785676fSDimitry Andric       asmUsed2.push_back(c);
421f785676fSDimitry Andric     }
422f785676fSDimitry Andric 
423f785676fSDimitry Andric     llvm::ArrayType *ATy = llvm::ArrayType::get(i8PTy, asmUsed2.size());
424f785676fSDimitry Andric     LLVMCompilerUsed =
425f785676fSDimitry Andric       new llvm::GlobalVariable(*mergedModule, ATy, false,
426f785676fSDimitry Andric                                llvm::GlobalValue::AppendingLinkage,
427f785676fSDimitry Andric                                llvm::ConstantArray::get(ATy, asmUsed2),
428f785676fSDimitry Andric                                "llvm.compiler.used");
429f785676fSDimitry Andric 
430f785676fSDimitry Andric     LLVMCompilerUsed->setSection("llvm.metadata");
431f785676fSDimitry Andric   }
432f785676fSDimitry Andric 
433f785676fSDimitry Andric   passes.add(createInternalizePass(MustPreserveList));
434f785676fSDimitry Andric 
435f785676fSDimitry Andric   // apply scope restrictions
436f785676fSDimitry Andric   passes.run(*mergedModule);
437f785676fSDimitry Andric 
438f785676fSDimitry Andric   ScopeRestrictionsDone = true;
439f785676fSDimitry Andric }
440f785676fSDimitry Andric 
441f785676fSDimitry Andric /// Optimize merged modules using various IPO passes
442f785676fSDimitry Andric bool LTOCodeGenerator::generateObjectFile(raw_ostream &out,
443f785676fSDimitry Andric                                           bool DisableOpt,
444f785676fSDimitry Andric                                           bool DisableInline,
445f785676fSDimitry Andric                                           bool DisableGVNLoadPRE,
446f785676fSDimitry Andric                                           std::string &errMsg) {
447f785676fSDimitry Andric   if (!this->determineTarget(errMsg))
448f785676fSDimitry Andric     return false;
449f785676fSDimitry Andric 
450f785676fSDimitry Andric   Module *mergedModule = Linker.getModule();
451f785676fSDimitry Andric 
452f785676fSDimitry Andric   // Mark which symbols can not be internalized
453f785676fSDimitry Andric   this->applyScopeRestrictions();
454f785676fSDimitry Andric 
455f785676fSDimitry Andric   // Instantiate the pass manager to organize the passes.
456f785676fSDimitry Andric   PassManager passes;
457f785676fSDimitry Andric 
458f785676fSDimitry Andric   // Start off with a verification pass.
459f785676fSDimitry Andric   passes.add(createVerifierPass());
460f785676fSDimitry Andric 
461f785676fSDimitry Andric   // Add an appropriate DataLayout instance for this module...
462f785676fSDimitry Andric   passes.add(new DataLayout(*TargetMach->getDataLayout()));
463f785676fSDimitry Andric   TargetMach->addAnalysisPasses(passes);
464f785676fSDimitry Andric 
465f785676fSDimitry Andric   // Enabling internalize here would use its AllButMain variant. It
466f785676fSDimitry Andric   // keeps only main if it exists and does nothing for libraries. Instead
467f785676fSDimitry Andric   // we create the pass ourselves with the symbol list provided by the linker.
468f785676fSDimitry Andric   if (!DisableOpt)
469f785676fSDimitry Andric     PassManagerBuilder().populateLTOPassManager(passes,
470f785676fSDimitry Andric                                               /*Internalize=*/false,
471f785676fSDimitry Andric                                               !DisableInline,
472f785676fSDimitry Andric                                               DisableGVNLoadPRE);
473f785676fSDimitry Andric 
474f785676fSDimitry Andric   // Make sure everything is still good.
475f785676fSDimitry Andric   passes.add(createVerifierPass());
476f785676fSDimitry Andric 
477f785676fSDimitry Andric   PassManager codeGenPasses;
478f785676fSDimitry Andric 
479f785676fSDimitry Andric   codeGenPasses.add(new DataLayout(*TargetMach->getDataLayout()));
480f785676fSDimitry Andric   TargetMach->addAnalysisPasses(codeGenPasses);
481f785676fSDimitry Andric 
482f785676fSDimitry Andric   formatted_raw_ostream Out(out);
483f785676fSDimitry Andric 
484f785676fSDimitry Andric   // If the bitcode files contain ARC code and were compiled with optimization,
485f785676fSDimitry Andric   // the ObjCARCContractPass must be run, so do it unconditionally here.
486f785676fSDimitry Andric   codeGenPasses.add(createObjCARCContractPass());
487f785676fSDimitry Andric 
488f785676fSDimitry Andric   if (TargetMach->addPassesToEmitFile(codeGenPasses, Out,
489f785676fSDimitry Andric                                       TargetMachine::CGFT_ObjectFile)) {
490f785676fSDimitry Andric     errMsg = "target file type not supported";
491f785676fSDimitry Andric     return false;
492f785676fSDimitry Andric   }
493f785676fSDimitry Andric 
494f785676fSDimitry Andric   // Run our queue of passes all at once now, efficiently.
495f785676fSDimitry Andric   passes.run(*mergedModule);
496f785676fSDimitry Andric 
497f785676fSDimitry Andric   // Run the code generator, and write assembly file
498f785676fSDimitry Andric   codeGenPasses.run(*mergedModule);
499f785676fSDimitry Andric 
500f785676fSDimitry Andric   return true;
501f785676fSDimitry Andric }
502f785676fSDimitry Andric 
503f785676fSDimitry Andric /// setCodeGenDebugOptions - Set codegen debugging options to aid in debugging
504f785676fSDimitry Andric /// LTO problems.
505f785676fSDimitry Andric void LTOCodeGenerator::setCodeGenDebugOptions(const char *options) {
506f785676fSDimitry Andric   for (std::pair<StringRef, StringRef> o = getToken(options);
507f785676fSDimitry Andric        !o.first.empty(); o = getToken(o.second)) {
508f785676fSDimitry Andric     // ParseCommandLineOptions() expects argv[0] to be program name. Lazily add
509f785676fSDimitry Andric     // that.
510f785676fSDimitry Andric     if (CodegenOptions.empty())
511f785676fSDimitry Andric       CodegenOptions.push_back(strdup("libLLVMLTO"));
512f785676fSDimitry Andric     CodegenOptions.push_back(strdup(o.first.str().c_str()));
513f785676fSDimitry Andric   }
514f785676fSDimitry Andric }
515f785676fSDimitry Andric 
516f785676fSDimitry Andric void LTOCodeGenerator::parseCodeGenDebugOptions() {
517f785676fSDimitry Andric   // if options were requested, set them
518f785676fSDimitry Andric   if (!CodegenOptions.empty())
519f785676fSDimitry Andric     cl::ParseCommandLineOptions(CodegenOptions.size(),
520f785676fSDimitry Andric                                 const_cast<char **>(&CodegenOptions[0]));
521f785676fSDimitry Andric }
522