summaryrefslogtreecommitdiffstats
path: root/llvm/lib
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib')
-rw-r--r--llvm/lib/LTO/LTO.cpp5
-rw-r--r--llvm/lib/LTO/ThinLTOCodeGenerator.cpp132
2 files changed, 85 insertions, 52 deletions
diff --git a/llvm/lib/LTO/LTO.cpp b/llvm/lib/LTO/LTO.cpp
index 99318c19a89..1accbf40b96 100644
--- a/llvm/lib/LTO/LTO.cpp
+++ b/llvm/lib/LTO/LTO.cpp
@@ -420,6 +420,11 @@ StringRef InputFile::getName() const {
return Mods[0].getModuleIdentifier();
}
+BitcodeModule &InputFile::getSingleBitcodeModule() {
+ assert(Mods.size() == 1 && "Expect only one bitcode module");
+ return Mods[0];
+}
+
LTO::RegularLTOState::RegularLTOState(unsigned ParallelCodeGenParallelismLevel,
Config &Conf)
: ParallelCodeGenParallelismLevel(ParallelCodeGenParallelismLevel),
diff --git a/llvm/lib/LTO/ThinLTOCodeGenerator.cpp b/llvm/lib/LTO/ThinLTOCodeGenerator.cpp
index d4ee66a53e0..0423db85b81 100644
--- a/llvm/lib/LTO/ThinLTOCodeGenerator.cpp
+++ b/llvm/lib/LTO/ThinLTOCodeGenerator.cpp
@@ -135,14 +135,13 @@ static void computePrevailingCopies(
}
}
-static StringMap<MemoryBufferRef>
-generateModuleMap(const std::vector<ThinLTOBuffer> &Modules) {
- StringMap<MemoryBufferRef> ModuleMap;
- for (auto &ModuleBuffer : Modules) {
- assert(ModuleMap.find(ModuleBuffer.getBufferIdentifier()) ==
- ModuleMap.end() &&
+static StringMap<lto::InputFile *>
+generateModuleMap(std::vector<std::unique_ptr<lto::InputFile>> &Modules) {
+ StringMap<lto::InputFile *> ModuleMap;
+ for (auto &M : Modules) {
+ assert(ModuleMap.find(M->getName()) == ModuleMap.end() &&
"Expect unique Buffer Identifier");
- ModuleMap[ModuleBuffer.getBufferIdentifier()] = ModuleBuffer.getMemBuffer();
+ ModuleMap[M->getName()] = M.get();
}
return ModuleMap;
}
@@ -175,18 +174,19 @@ static void verifyLoadedModule(Module &TheModule) {
}
}
-static std::unique_ptr<Module>
-loadModuleFromBuffer(const MemoryBufferRef &Buffer, LLVMContext &Context,
- bool Lazy, bool IsImporting) {
+static std::unique_ptr<Module> loadModuleFromInput(lto::InputFile *Input,
+ LLVMContext &Context,
+ bool Lazy,
+ bool IsImporting) {
+ auto &Mod = Input->getSingleBitcodeModule();
SMDiagnostic Err;
Expected<std::unique_ptr<Module>> ModuleOrErr =
- Lazy
- ? getLazyBitcodeModule(Buffer, Context,
- /* ShouldLazyLoadMetadata */ true, IsImporting)
- : parseBitcodeFile(Buffer, Context);
+ Lazy ? Mod.getLazyModule(Context,
+ /* ShouldLazyLoadMetadata */ true, IsImporting)
+ : Mod.parseModule(Context);
if (!ModuleOrErr) {
handleAllErrors(ModuleOrErr.takeError(), [&](ErrorInfoBase &EIB) {
- SMDiagnostic Err = SMDiagnostic(Buffer.getBufferIdentifier(),
+ SMDiagnostic Err = SMDiagnostic(Mod.getModuleIdentifier(),
SourceMgr::DK_Error, EIB.message());
Err.print("ThinLTO", errs());
});
@@ -194,16 +194,17 @@ loadModuleFromBuffer(const MemoryBufferRef &Buffer, LLVMContext &Context,
}
if (!Lazy)
verifyLoadedModule(*ModuleOrErr.get());
- return std::move(ModuleOrErr.get());
+ return std::move(*ModuleOrErr);
}
static void
crossImportIntoModule(Module &TheModule, const ModuleSummaryIndex &Index,
- StringMap<MemoryBufferRef> &ModuleMap,
+ StringMap<lto::InputFile*> &ModuleMap,
const FunctionImporter::ImportMapTy &ImportList) {
auto Loader = [&](StringRef Identifier) {
- return loadModuleFromBuffer(ModuleMap[Identifier], TheModule.getContext(),
- /*Lazy=*/true, /*IsImporting*/ true);
+ auto &Input = ModuleMap[Identifier];
+ return loadModuleFromInput(Input, TheModule.getContext(),
+ /*Lazy=*/true, /*IsImporting*/ true);
};
FunctionImporter Importer(Index, Loader);
@@ -248,6 +249,15 @@ static void optimizeModule(Module &TheModule, TargetMachine &TM,
PM.run(TheModule);
}
+static void
+addUsedSymbolToPreservedGUID(const lto::InputFile &File,
+ DenseSet<GlobalValue::GUID> &PreservedGUID) {
+ for (const auto &Sym : File.symbols()) {
+ if (Sym.isUsed())
+ PreservedGUID.insert(GlobalValue::getGUID(Sym.getIRName()));
+ }
+}
+
// Convert the PreservedSymbols map from "Name" based to "GUID" based.
static DenseSet<GlobalValue::GUID>
computeGUIDPreservedSymbols(const StringSet<> &PreservedSymbols,
@@ -381,7 +391,7 @@ public:
static std::unique_ptr<MemoryBuffer>
ProcessThinLTOModule(Module &TheModule, ModuleSummaryIndex &Index,
- StringMap<MemoryBufferRef> &ModuleMap, TargetMachine &TM,
+ StringMap<lto::InputFile *> &ModuleMap, TargetMachine &TM,
const FunctionImporter::ImportMapTy &ImportList,
const FunctionImporter::ExportSetTy &ExportList,
const DenseSet<GlobalValue::GUID> &GUIDPreservedSymbols,
@@ -488,15 +498,13 @@ static void initTMBuilder(TargetMachineBuilder &TMBuilder,
} // end anonymous namespace
void ThinLTOCodeGenerator::addModule(StringRef Identifier, StringRef Data) {
- ThinLTOBuffer Buffer(Data, Identifier);
- LLVMContext Context;
- StringRef TripleStr;
- ErrorOr<std::string> TripleOrErr = expectedToErrorOrAndEmitErrors(
- Context, getBitcodeTargetTriple(Buffer.getMemBuffer()));
+ MemoryBufferRef Buffer(Data, Identifier);
- if (TripleOrErr)
- TripleStr = *TripleOrErr;
+ auto InputOrError = lto::InputFile::create(Buffer);
+ if (!InputOrError)
+ report_fatal_error("ThinLTO cannot create input file");
+ auto TripleStr = (*InputOrError)->getTargetTriple();
Triple TheTriple(TripleStr);
if (Modules.empty())
@@ -508,7 +516,7 @@ void ThinLTOCodeGenerator::addModule(StringRef Identifier, StringRef Data) {
initTMBuilder(TMBuilder, Triple(TMBuilder.TheTriple.merge(TheTriple)));
}
- Modules.push_back(Buffer);
+ Modules.emplace_back(std::move(*InputOrError));
}
void ThinLTOCodeGenerator::preserveSymbol(StringRef Name) {
@@ -549,9 +557,10 @@ std::unique_ptr<ModuleSummaryIndex> ThinLTOCodeGenerator::linkCombinedIndex() {
std::unique_ptr<ModuleSummaryIndex> CombinedIndex =
llvm::make_unique<ModuleSummaryIndex>(/*HaveGVs=*/false);
uint64_t NextModuleId = 0;
- for (auto &ModuleBuffer : Modules) {
- if (Error Err = readModuleSummaryIndex(ModuleBuffer.getMemBuffer(),
- *CombinedIndex, NextModuleId++)) {
+ for (auto &Mod : Modules) {
+ auto &M = Mod->getSingleBitcodeModule();
+ if (Error Err =
+ M.readSummary(*CombinedIndex, Mod->getName(), NextModuleId++)) {
// FIXME diagnose
logAllUnhandledErrors(
std::move(Err), errs(),
@@ -593,8 +602,8 @@ static void computeDeadSymbolsInIndex(
* Perform promotion and renaming of exported internal functions.
* Index is updated to reflect linkage changes from weak resolution.
*/
-void ThinLTOCodeGenerator::promote(Module &TheModule,
- ModuleSummaryIndex &Index) {
+void ThinLTOCodeGenerator::promote(Module &TheModule, ModuleSummaryIndex &Index,
+ const lto::InputFile &File) {
auto ModuleCount = Index.modulePaths().size();
auto ModuleIdentifier = TheModule.getModuleIdentifier();
@@ -606,6 +615,9 @@ void ThinLTOCodeGenerator::promote(Module &TheModule,
auto GUIDPreservedSymbols = computeGUIDPreservedSymbols(
PreservedSymbols, Triple(TheModule.getTargetTriple()));
+ // Add used symbol to the preserved symbols.
+ addUsedSymbolToPreservedGUID(File, GUIDPreservedSymbols);
+
// Compute "dead" symbols, we don't want to import/export these!
computeDeadSymbolsInIndex(Index, GUIDPreservedSymbols);
@@ -619,21 +631,22 @@ void ThinLTOCodeGenerator::promote(Module &TheModule,
StringMap<std::map<GlobalValue::GUID, GlobalValue::LinkageTypes>> ResolvedODR;
resolvePrevailingInIndex(Index, ResolvedODR);
- thinLTOResolvePrevailingInModule(
- TheModule, ModuleToDefinedGVSummaries[ModuleIdentifier]);
-
// Promote the exported values in the index, so that they are promoted
// in the module.
internalizeAndPromoteInIndex(ExportLists, GUIDPreservedSymbols, Index);
promoteModule(TheModule, Index);
+
+ thinLTOResolvePrevailingInModule(
+ TheModule, ModuleToDefinedGVSummaries[ModuleIdentifier]);
}
/**
* Perform cross-module importing for the module identified by ModuleIdentifier.
*/
void ThinLTOCodeGenerator::crossModuleImport(Module &TheModule,
- ModuleSummaryIndex &Index) {
+ ModuleSummaryIndex &Index,
+ const lto::InputFile &File) {
auto ModuleMap = generateModuleMap(Modules);
auto ModuleCount = Index.modulePaths().size();
@@ -645,6 +658,8 @@ void ThinLTOCodeGenerator::crossModuleImport(Module &TheModule,
auto GUIDPreservedSymbols = computeGUIDPreservedSymbols(
PreservedSymbols, Triple(TheModule.getTargetTriple()));
+ addUsedSymbolToPreservedGUID(File, GUIDPreservedSymbols);
+
// Compute "dead" symbols, we don't want to import/export these!
computeDeadSymbolsInIndex(Index, GUIDPreservedSymbols);
@@ -663,7 +678,8 @@ void ThinLTOCodeGenerator::crossModuleImport(Module &TheModule,
*/
void ThinLTOCodeGenerator::gatherImportedSummariesForModule(
Module &TheModule, ModuleSummaryIndex &Index,
- std::map<std::string, GVSummaryMapTy> &ModuleToSummariesForIndex) {
+ std::map<std::string, GVSummaryMapTy> &ModuleToSummariesForIndex,
+ const lto::InputFile &File) {
auto ModuleCount = Index.modulePaths().size();
auto ModuleIdentifier = TheModule.getModuleIdentifier();
@@ -675,6 +691,8 @@ void ThinLTOCodeGenerator::gatherImportedSummariesForModule(
auto GUIDPreservedSymbols = computeGUIDPreservedSymbols(
PreservedSymbols, Triple(TheModule.getTargetTriple()));
+ addUsedSymbolToPreservedGUID(File, GUIDPreservedSymbols);
+
// Compute "dead" symbols, we don't want to import/export these!
computeDeadSymbolsInIndex(Index, GUIDPreservedSymbols);
@@ -693,7 +711,8 @@ void ThinLTOCodeGenerator::gatherImportedSummariesForModule(
* Emit the list of files needed for importing into module.
*/
void ThinLTOCodeGenerator::emitImports(Module &TheModule, StringRef OutputName,
- ModuleSummaryIndex &Index) {
+ ModuleSummaryIndex &Index,
+ const lto::InputFile &File) {
auto ModuleCount = Index.modulePaths().size();
auto ModuleIdentifier = TheModule.getModuleIdentifier();
@@ -705,6 +724,8 @@ void ThinLTOCodeGenerator::emitImports(Module &TheModule, StringRef OutputName,
auto GUIDPreservedSymbols = computeGUIDPreservedSymbols(
PreservedSymbols, Triple(TheModule.getTargetTriple()));
+ addUsedSymbolToPreservedGUID(File, GUIDPreservedSymbols);
+
// Compute "dead" symbols, we don't want to import/export these!
computeDeadSymbolsInIndex(Index, GUIDPreservedSymbols);
@@ -730,7 +751,8 @@ void ThinLTOCodeGenerator::emitImports(Module &TheModule, StringRef OutputName,
* Perform internalization. Index is updated to reflect linkage changes.
*/
void ThinLTOCodeGenerator::internalize(Module &TheModule,
- ModuleSummaryIndex &Index) {
+ ModuleSummaryIndex &Index,
+ const lto::InputFile &File) {
initTMBuilder(TMBuilder, Triple(TheModule.getTargetTriple()));
auto ModuleCount = Index.modulePaths().size();
auto ModuleIdentifier = TheModule.getModuleIdentifier();
@@ -739,6 +761,8 @@ void ThinLTOCodeGenerator::internalize(Module &TheModule,
auto GUIDPreservedSymbols =
computeGUIDPreservedSymbols(PreservedSymbols, TMBuilder.TheTriple);
+ addUsedSymbolToPreservedGUID(File, GUIDPreservedSymbols);
+
// Collect for each module the list of function it defines (GUID -> Summary).
StringMap<GVSummaryMapTy> ModuleToDefinedGVSummaries(ModuleCount);
Index.collectDefinedGVSummariesPerModule(ModuleToDefinedGVSummaries);
@@ -830,15 +854,14 @@ void ThinLTOCodeGenerator::run() {
// Perform only parallel codegen and return.
ThreadPool Pool;
int count = 0;
- for (auto &ModuleBuffer : Modules) {
+ for (auto &Mod : Modules) {
Pool.async([&](int count) {
LLVMContext Context;
Context.setDiscardValueNames(LTODiscardValueNames);
// Parse module now
- auto TheModule =
- loadModuleFromBuffer(ModuleBuffer.getMemBuffer(), Context, false,
- /*IsImporting*/ false);
+ auto TheModule = loadModuleFromInput(Mod.get(), Context, false,
+ /*IsImporting*/ false);
// CodeGen
auto OutputBuffer = codegenModule(*TheModule, *TMBuilder.create());
@@ -881,6 +904,10 @@ void ThinLTOCodeGenerator::run() {
auto GUIDPreservedSymbols =
computeGUIDPreservedSymbols(PreservedSymbols, TMBuilder.TheTriple);
+ // Add used symbol from inputs to the preserved symbols.
+ for (const auto &M : Modules)
+ addUsedSymbolToPreservedGUID(*M, GUIDPreservedSymbols);
+
// Compute "dead" symbols, we don't want to import/export these!
computeDeadSymbolsInIndex(*Index, GUIDPreservedSymbols);
@@ -913,7 +940,7 @@ void ThinLTOCodeGenerator::run() {
// GVSummary and ResolvedODR maps to enable threaded access to these maps
// below.
for (auto &Module : Modules) {
- auto ModuleIdentifier = Module.getBufferIdentifier();
+ auto ModuleIdentifier = Module->getName();
ExportLists[ModuleIdentifier];
ImportLists[ModuleIdentifier];
ResolvedODR[ModuleIdentifier];
@@ -927,8 +954,10 @@ void ThinLTOCodeGenerator::run() {
ModulesOrdering.resize(Modules.size());
std::iota(ModulesOrdering.begin(), ModulesOrdering.end(), 0);
llvm::sort(ModulesOrdering, [&](int LeftIndex, int RightIndex) {
- auto LSize = Modules[LeftIndex].getBuffer().size();
- auto RSize = Modules[RightIndex].getBuffer().size();
+ auto LSize =
+ Modules[LeftIndex]->getSingleBitcodeModule().getBuffer().size();
+ auto RSize =
+ Modules[RightIndex]->getSingleBitcodeModule().getBuffer().size();
return LSize > RSize;
});
@@ -936,9 +965,9 @@ void ThinLTOCodeGenerator::run() {
{
ThreadPool Pool(ThreadCount);
for (auto IndexCount : ModulesOrdering) {
- auto &ModuleBuffer = Modules[IndexCount];
+ auto &Mod = Modules[IndexCount];
Pool.async([&](int count) {
- auto ModuleIdentifier = ModuleBuffer.getBufferIdentifier();
+ auto ModuleIdentifier = Mod->getName();
auto &ExportList = ExportLists[ModuleIdentifier];
auto &DefinedGVSummaries = ModuleToDefinedGVSummaries[ModuleIdentifier];
@@ -982,9 +1011,8 @@ void ThinLTOCodeGenerator::run() {
}
// Parse module now
- auto TheModule =
- loadModuleFromBuffer(ModuleBuffer.getMemBuffer(), Context, false,
- /*IsImporting*/ false);
+ auto TheModule = loadModuleFromInput(Mod.get(), Context, false,
+ /*IsImporting*/ false);
// Save temps: original file.
saveTempBitcode(*TheModule, SaveTempsDir, count, ".0.original.bc");
OpenPOWER on IntegriCloud