forked from OSchip/llvm-project
Improve error message for -thinlto-object-suffix-replace and simplify code.
llvm-svn: 332643
This commit is contained in:
parent
d6c6678766
commit
f06d494f46
|
|
@ -1024,22 +1024,21 @@ BitcodeFile::BitcodeFile(MemoryBufferRef MB, StringRef ArchiveName,
|
|||
: InputFile(BitcodeKind, MB) {
|
||||
this->ArchiveName = ArchiveName;
|
||||
|
||||
// Here we pass a new MemoryBufferRef which is identified by ArchiveName
|
||||
// (the fully resolved path of the archive) + member name + offset of the
|
||||
// member in the archive.
|
||||
// ThinLTO uses the MemoryBufferRef identifier to access its internal
|
||||
// data structures and if two archives define two members with the same name,
|
||||
// this causes a collision which result in only one of the objects being
|
||||
// taken into consideration at LTO time (which very likely causes undefined
|
||||
// symbols later in the link stage).
|
||||
std::string Path = MB.getBufferIdentifier().str();
|
||||
if (Config->ThinLTOIndexOnly)
|
||||
Path = updateSuffixInPath(MB.getBufferIdentifier());
|
||||
Path = replaceThinLTOSuffix(MB.getBufferIdentifier());
|
||||
|
||||
// ThinLTO assumes that all MemoryBufferRefs given to it have a unique
|
||||
// name. If two archives define two members with the same name, this
|
||||
// causes a collision which result in only one of the objects being taken
|
||||
// into consideration at LTO time (which very likely causes undefined
|
||||
// symbols later in the link stage). So we append file offset to make
|
||||
// filename unique.
|
||||
MemoryBufferRef MBRef(
|
||||
MB.getBuffer(),
|
||||
Saver.save(ArchiveName + Path +
|
||||
(ArchiveName.empty() ? "" : utostr(OffsetInArchive))));
|
||||
|
||||
Obj = CHECK(lto::InputFile::create(MBRef), this);
|
||||
|
||||
Triple T(Obj->getTargetTriple());
|
||||
|
|
@ -1242,6 +1241,18 @@ template <class ELFT> void LazyObjFile::addElfSymbols() {
|
|||
}
|
||||
}
|
||||
|
||||
std::string elf::replaceThinLTOSuffix(StringRef Path) {
|
||||
StringRef Suffix = Config->ThinLTOObjectSuffixReplace.first;
|
||||
StringRef Repl = Config->ThinLTOObjectSuffixReplace.second;
|
||||
|
||||
if (!Path.endswith(Suffix)) {
|
||||
error("-thinlto-object-suffix-replace=" + Suffix + ";" + Repl +
|
||||
" was given, but " + Path + " does not ends with the suffix");
|
||||
return "";
|
||||
}
|
||||
return (Path.drop_back(Suffix.size()) + Repl).str();
|
||||
}
|
||||
|
||||
template void ArchiveFile::parse<ELF32LE>();
|
||||
template void ArchiveFile::parse<ELF32BE>();
|
||||
template void ArchiveFile::parse<ELF64LE>();
|
||||
|
|
|
|||
|
|
@ -355,19 +355,7 @@ inline bool isBitcode(MemoryBufferRef MB) {
|
|||
return identify_magic(MB.getBuffer()) == llvm::file_magic::bitcode;
|
||||
}
|
||||
|
||||
inline std::string updateSuffixInPath(llvm::StringRef Path) {
|
||||
if (Path.endswith(Config->ThinLTOObjectSuffixReplace.first)) {
|
||||
size_t pos = Path.rfind(Config->ThinLTOObjectSuffixReplace.first);
|
||||
std::string SuffixedPath =
|
||||
(Path.str().substr(0, pos) +
|
||||
Config->ThinLTOObjectSuffixReplace.second.str());
|
||||
return SuffixedPath;
|
||||
} else {
|
||||
error("cannot find suffix " +
|
||||
Config->ThinLTOObjectSuffixReplace.first.str());
|
||||
return "";
|
||||
}
|
||||
}
|
||||
std::string replaceThinLTOSuffix(StringRef Path);
|
||||
|
||||
extern std::vector<BinaryFile *> BinaryFiles;
|
||||
extern std::vector<BitcodeFile *> BitcodeFiles;
|
||||
|
|
|
|||
|
|
@ -221,11 +221,28 @@ void BitcodeCompiler::add(BitcodeFile &F) {
|
|||
checkError(LTOObj->add(std::move(F.Obj), Resols));
|
||||
}
|
||||
|
||||
static void createEmptyIndex(StringRef ModulePath) {
|
||||
std::string Path = replaceThinLTOSuffix(getThinLTOOutputFile(ModulePath));
|
||||
if (Path.empty())
|
||||
return;
|
||||
|
||||
std::unique_ptr<raw_fd_ostream> OS = openFile(Path + ".thinlto.bc");
|
||||
if (!OS)
|
||||
return;
|
||||
|
||||
ModuleSummaryIndex M(false);
|
||||
M.setSkipModuleByDistributedBackend();
|
||||
WriteIndexToFile(M, *OS);
|
||||
|
||||
if (Config->ThinLTOEmitImportsFiles)
|
||||
openFile(Path + ".imports");
|
||||
}
|
||||
|
||||
// Merge all the bitcode files we have seen, codegen the result
|
||||
// and return the resulting ObjectFile(s).
|
||||
std::vector<InputFile *> BitcodeCompiler::compile() {
|
||||
unsigned MaxTasks = LTOObj->getMaxTasks();
|
||||
Buff.resize(MaxTasks);
|
||||
Buf.resize(MaxTasks);
|
||||
Files.resize(MaxTasks);
|
||||
|
||||
// The --thinlto-cache-dir option specifies the path to a directory in which
|
||||
|
|
@ -242,7 +259,7 @@ std::vector<InputFile *> BitcodeCompiler::compile() {
|
|||
checkError(LTOObj->run(
|
||||
[&](size_t Task) {
|
||||
return llvm::make_unique<lto::NativeObjectStream>(
|
||||
llvm::make_unique<raw_svector_ostream>(Buff[Task]));
|
||||
llvm::make_unique<raw_svector_ostream>(Buf[Task]));
|
||||
},
|
||||
Cache));
|
||||
|
||||
|
|
@ -262,26 +279,12 @@ std::vector<InputFile *> BitcodeCompiler::compile() {
|
|||
// This is needed because this is what GNU gold plugin does and we have a
|
||||
// distributed build system that depends on that behavior.
|
||||
if (Config->ThinLTOIndexOnly) {
|
||||
for (LazyObjFile *F : LazyObjFiles) {
|
||||
if (F->AddedToLink || !isBitcode(F->MB))
|
||||
continue;
|
||||
|
||||
std::string Path = updateSuffixInPath(getThinLTOOutputFile(F->getName()));
|
||||
|
||||
std::unique_ptr<raw_fd_ostream> OS = openFile(Path + ".thinlto.bc");
|
||||
if (!OS)
|
||||
continue;
|
||||
|
||||
ModuleSummaryIndex M(false);
|
||||
M.setSkipModuleByDistributedBackend();
|
||||
WriteIndexToFile(M, *OS);
|
||||
|
||||
if (Config->ThinLTOEmitImportsFiles)
|
||||
openFile(Path + ".imports");
|
||||
}
|
||||
for (LazyObjFile *F : LazyObjFiles)
|
||||
if (!F->AddedToLink && isBitcode(F->MB))
|
||||
createEmptyIndex(F->getName());
|
||||
|
||||
if (!Config->LTOObjPath.empty())
|
||||
saveBuffer(Buff[0], Config->LTOObjPath);
|
||||
saveBuffer(Buf[0], Config->LTOObjPath);
|
||||
|
||||
// ThinLTO with index only option is required to generate only the index
|
||||
// files. After that, we exit from linker and ThinLTO backend runs in a
|
||||
|
|
@ -290,20 +293,21 @@ std::vector<InputFile *> BitcodeCompiler::compile() {
|
|||
IndexFile->close();
|
||||
return {};
|
||||
}
|
||||
|
||||
if (!Config->ThinLTOCacheDir.empty())
|
||||
pruneCache(Config->ThinLTOCacheDir, Config->ThinLTOCachePolicy);
|
||||
|
||||
std::vector<InputFile *> Ret;
|
||||
for (unsigned I = 0; I != MaxTasks; ++I) {
|
||||
if (Buff[I].empty())
|
||||
if (Buf[I].empty())
|
||||
continue;
|
||||
if (Config->SaveTemps) {
|
||||
if (I == 0)
|
||||
saveBuffer(Buff[I], Config->OutputFile + ".lto.o");
|
||||
saveBuffer(Buf[I], Config->OutputFile + ".lto.o");
|
||||
else
|
||||
saveBuffer(Buff[I], Config->OutputFile + Twine(I) + ".lto.o");
|
||||
saveBuffer(Buf[I], Config->OutputFile + Twine(I) + ".lto.o");
|
||||
}
|
||||
InputFile *Obj = createObjectFile(MemoryBufferRef(Buff[I], "lto.tmp"));
|
||||
InputFile *Obj = createObjectFile(MemoryBufferRef(Buf[I], "lto.tmp"));
|
||||
Ret.push_back(Obj);
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -51,7 +51,7 @@ public:
|
|||
|
||||
private:
|
||||
std::unique_ptr<llvm::lto::LTO> LTOObj;
|
||||
std::vector<SmallString<0>> Buff;
|
||||
std::vector<SmallString<0>> Buf;
|
||||
std::vector<std::unique_ptr<MemoryBuffer>> Files;
|
||||
llvm::DenseSet<StringRef> UsedStartStop;
|
||||
std::unique_ptr<llvm::raw_fd_ostream> IndexFile;
|
||||
|
|
|
|||
|
|
@ -34,8 +34,7 @@
|
|||
; RUN: not ld.lld -m elf_x86_64 --plugin-opt=thinlto-index-only \
|
||||
; RUN: --plugin-opt=thinlto-object-suffix-replace=".abc;.o" -shared %t1.thinlink.bc \
|
||||
; RUN: -o %t3 2>&1 | FileCheck %s --check-prefix=ERR2
|
||||
; ERR2: cannot find suffix .abc
|
||||
|
||||
; ERR2: error: -thinlto-object-suffix-replace=.abc;.o was given, but {{.*}} does not ends with the suffix
|
||||
|
||||
target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
|
||||
target triple = "x86_64-unknown-linux-gnu"
|
||||
|
|
|
|||
Loading…
Reference in New Issue