- // Instantiate the pass manager to organize the passes.
- PassManager Passes;
-
- // Collect Target info
- std::string Err;
- const TargetMachineRegistry::Entry* March =
- TargetMachineRegistry::getClosestStaticTargetForModule(*M, Err);
-
- if (March == 0)
- return LTO_NO_TARGET;
-
- // Create target
- std::string Features;
- std::auto_ptr<TargetMachine> target(March->CtorFn(*M, Features));
- if (!target.get())
- return LTO_NO_TARGET;
-
- TargetMachine &Target = *target.get();
-
- // Start off with a verification pass.
- Passes.add(createVerifierPass());
-
- // Add an appropriate TargetData instance for this module...
- Passes.add(new TargetData(*Target.getTargetData()));
-
- // Often if the programmer does not specify proper prototypes for the
- // functions they are calling, they end up calling a vararg version of the
- // function that does not get a body filled in (the real function has typed
- // arguments). This pass merges the two functions.
- Passes.add(createFunctionResolvingPass());
-
- // Internalize symbols if export list is nonemty
- if (!exportList.empty())
- Passes.add(createInternalizePass(exportList));
-
- // Now that we internalized some globals, see if we can hack on them!
- Passes.add(createGlobalOptimizerPass());
-
- // Linking modules together can lead to duplicated global constants, only
- // keep one copy of each constant...
- Passes.add(createConstantMergePass());
-
- // If the -s command line option was specified, strip the symbols out of the
- // resulting program to make it smaller. -s is a GLD option that we are
- // supporting.
- Passes.add(createStripSymbolsPass());
-
- // Propagate constants at call sites into the functions they call.
- Passes.add(createIPConstantPropagationPass());
-
- // Remove unused arguments from functions...
- Passes.add(createDeadArgEliminationPass());
-
- Passes.add(createFunctionInliningPass()); // Inline small functions
-
- Passes.add(createPruneEHPass()); // Remove dead EH info
-
- Passes.add(createGlobalDCEPass()); // Remove dead functions
-
- // If we didn't decide to inline a function, check to see if we can
- // transform it to pass arguments by value instead of by reference.
- Passes.add(createArgumentPromotionPass());
-
- // The IPO passes may leave cruft around. Clean up after them.
- Passes.add(createInstructionCombiningPass());
-
- Passes.add(createScalarReplAggregatesPass()); // Break up allocas
-
- // Run a few AA driven optimizations here and now, to cleanup the code.
- Passes.add(createGlobalsModRefPass()); // IP alias analysis
-
- Passes.add(createLICMPass()); // Hoist loop invariants
- Passes.add(createLoadValueNumberingPass()); // GVN for load instrs
- Passes.add(createGCSEPass()); // Remove common subexprs
- Passes.add(createDeadStoreEliminationPass()); // Nuke dead stores
-
- // Cleanup and simplify the code after the scalar optimizations.
- Passes.add(createInstructionCombiningPass());
-
- // Delete basic blocks, which optimization passes may have killed...
- Passes.add(createCFGSimplificationPass());
-
- // Now that we have optimized the program, discard unreachable functions...
- Passes.add(createGlobalDCEPass());
-
- // Make sure everything is still good.
- Passes.add(createVerifierPass());
-
- FunctionPassManager *CodeGenPasses =
- new FunctionPassManager(new ExistingModuleProvider(M));
-
- CodeGenPasses->add(new TargetData(*Target.getTargetData()));
- Target.addPassesToEmitFile(*CodeGenPasses, Out, TargetMachine::AssemblyFile,
- true);
-
- // Run our queue of passes all at once now, efficiently.
- Passes.run(*M);
-
- // Run the code generator, if present.
- CodeGenPasses->doInitialization();
- for (Module::iterator I = M->begin(), E = M->end(); I != E; ++I) {
- if (!I->isExternal())
- CodeGenPasses->run(*I);
- }
- CodeGenPasses->doFinalization();
-
- return LTO_OPT_SUCCESS;