[clang] 1bfa88d - [LinkerWrapper] Remove stripping features from the linker wrapper
Joseph Huber via cfe-commits
cfe-commits at lists.llvm.org
Thu May 12 17:52:38 PDT 2022
Author: Joseph Huber
Date: 2022-05-12T20:45:49-04:00
New Revision: 1bfa88d0c5ad9e5ef06b770e8ca4d6d3a3aaca2d
URL: https://github.com/llvm/llvm-project/commit/1bfa88d0c5ad9e5ef06b770e8ca4d6d3a3aaca2d
DIFF: https://github.com/llvm/llvm-project/commit/1bfa88d0c5ad9e5ef06b770e8ca4d6d3a3aaca2d.diff
LOG: [LinkerWrapper] Remove stripping features from the linker wrapper
Summary:
The linker wrapper previously had functionality to strip the sections
manually. We don't use this at all because this is much better done by
the linker via the `SHF_EXCLUDE` flag. This patch simply removes the
support for thi sfeature to simplify the code.
Added:
Modified:
clang/tools/clang-linker-wrapper/ClangLinkerWrapper.cpp
Removed:
################################################################################
diff --git a/clang/tools/clang-linker-wrapper/ClangLinkerWrapper.cpp b/clang/tools/clang-linker-wrapper/ClangLinkerWrapper.cpp
index ad9f6c9b55770..9358227e3151f 100644
--- a/clang/tools/clang-linker-wrapper/ClangLinkerWrapper.cpp
+++ b/clang/tools/clang-linker-wrapper/ClangLinkerWrapper.cpp
@@ -63,11 +63,6 @@ enum DebugKind {
static cl::OptionCategory
ClangLinkerWrapperCategory("clang-linker-wrapper options");
-static cl::opt<bool> StripSections(
- "strip-sections", cl::ZeroOrMore,
- cl::desc("Strip offloading sections from the host object file."),
- cl::init(false), cl::cat(ClangLinkerWrapperCategory));
-
static cl::opt<std::string> LinkerUserPath("linker-path", cl::Required,
cl::desc("Path of linker binary"),
cl::cat(ClangLinkerWrapperCategory));
@@ -221,10 +216,9 @@ template <> struct DenseMapInfo<DeviceFile> {
namespace {
-Expected<Optional<std::string>>
-extractFromBuffer(std::unique_ptr<MemoryBuffer> Buffer,
- SmallVectorImpl<DeviceFile> &DeviceFiles,
- bool IsLibrary = false);
+Error extractFromBuffer(std::unique_ptr<MemoryBuffer> Buffer,
+ SmallVectorImpl<DeviceFile> &DeviceFiles,
+ bool IsLibrary = false);
void printCommands(ArrayRef<StringRef> CmdArgs) {
if (CmdArgs.empty())
@@ -307,35 +301,6 @@ void PrintVersion(raw_ostream &OS) {
OS << clang::getClangToolFullVersion("clang-linker-wrapper") << '\n';
}
-void removeFromCompilerUsed(Module &M, GlobalValue &Value) {
- GlobalVariable *GV = M.getGlobalVariable("llvm.compiler.used");
- Type *Int8PtrTy = Type::getInt8PtrTy(M.getContext());
- Constant *ValueToRemove =
- ConstantExpr::getPointerBitCastOrAddrSpaceCast(&Value, Int8PtrTy);
- SmallPtrSet<Constant *, 16> InitAsSet;
- SmallVector<Constant *, 16> Init;
- if (GV) {
- if (GV->hasInitializer()) {
- auto *CA = cast<ConstantArray>(GV->getInitializer());
- for (auto &Op : CA->operands()) {
- Constant *C = cast_or_null<Constant>(Op);
- if (C != ValueToRemove && InitAsSet.insert(C).second)
- Init.push_back(C);
- }
- }
- GV->eraseFromParent();
- }
-
- if (Init.empty())
- return;
-
- ArrayType *ATy = ArrayType::get(Int8PtrTy, Init.size());
- GV = new llvm::GlobalVariable(M, ATy, false, GlobalValue::AppendingLinkage,
- ConstantArray::get(ATy, Init),
- "llvm.compiler.used");
- GV->setSection("llvm.metadata");
-}
-
/// Attempts to extract all the embedded device images contained inside the
/// buffer \p Contents. The buffer is expected to contain a valid offloading
/// binary format.
@@ -386,13 +351,10 @@ Error extractOffloadFiles(StringRef Contents, StringRef Prefix,
return Error::success();
}
-Expected<Optional<std::string>>
-extractFromBinary(const ObjectFile &Obj,
- SmallVectorImpl<DeviceFile> &DeviceFiles,
- bool IsLibrary = false) {
- StringRef Extension = sys::path::extension(Obj.getFileName()).drop_front();
+Error extractFromBinary(const ObjectFile &Obj,
+ SmallVectorImpl<DeviceFile> &DeviceFiles,
+ bool IsLibrary = false) {
StringRef Prefix = sys::path::stem(Obj.getFileName());
- SmallVector<StringRef, 4> ToBeStripped;
// Extract offloading binaries from sections with the name `.llvm.offloading`.
for (const SectionRef &Sec : Obj.sections()) {
@@ -406,68 +368,15 @@ extractFromBinary(const ObjectFile &Obj,
if (Error Err =
extractOffloadFiles(*Contents, Prefix, DeviceFiles, IsLibrary))
- return std::move(Err);
-
- ToBeStripped.push_back(*Name);
- }
-
- if (ToBeStripped.empty() || !StripSections)
- return None;
-
- // If the object file to strip doesn't exist we need to write it so we can
- // pass it to llvm-strip.
- SmallString<128> StripFile = Obj.getFileName();
- if (!sys::fs::exists(StripFile)) {
- SmallString<128> TempFile;
- if (Error Err = createOutputFile(
- sys::path::stem(StripFile),
- sys::path::extension(StripFile).drop_front(), TempFile))
- return std::move(Err);
-
- auto Contents = Obj.getMemoryBufferRef().getBuffer();
- Expected<std::unique_ptr<FileOutputBuffer>> OutputOrErr =
- FileOutputBuffer::create(TempFile, Contents.size());
- if (!OutputOrErr)
- return OutputOrErr.takeError();
- std::unique_ptr<FileOutputBuffer> Output = std::move(*OutputOrErr);
- std::copy(Contents.begin(), Contents.end(), Output->getBufferStart());
- if (Error E = Output->commit())
- return std::move(E);
- StripFile = TempFile;
- }
-
- // We will use llvm-strip to remove the now unneeded section containing the
- // offloading code.
- Expected<std::string> StripPath =
- findProgram("llvm-strip", {getMainExecutable("llvm-strip")});
- if (!StripPath)
- return StripPath.takeError();
-
- SmallString<128> TempFile;
- if (Error Err = createOutputFile(Prefix + "-host", Extension, TempFile))
- return std::move(Err);
-
- SmallVector<StringRef, 8> StripArgs;
- StripArgs.push_back(*StripPath);
- StripArgs.push_back("--no-strip-all");
- StripArgs.push_back(StripFile);
- for (auto &Section : ToBeStripped) {
- StripArgs.push_back("--remove-section");
- StripArgs.push_back(Section);
+ return Err;
}
- StripArgs.push_back("-o");
- StripArgs.push_back(TempFile);
- if (Error Err = executeCommands(*StripPath, StripArgs))
- return std::move(Err);
-
- return static_cast<std::string>(TempFile);
+ return Error::success();
}
-Expected<Optional<std::string>>
-extractFromBitcode(std::unique_ptr<MemoryBuffer> Buffer,
- SmallVectorImpl<DeviceFile> &DeviceFiles,
- bool IsLibrary = false) {
+Error extractFromBitcode(std::unique_ptr<MemoryBuffer> Buffer,
+ SmallVectorImpl<DeviceFile> &DeviceFiles,
+ bool IsLibrary = false) {
LLVMContext Context;
SMDiagnostic Err;
std::unique_ptr<Module> M = getLazyIRModule(std::move(Buffer), Err, Context);
@@ -475,12 +384,9 @@ extractFromBitcode(std::unique_ptr<MemoryBuffer> Buffer,
return createStringError(inconvertibleErrorCode(),
"Failed to create module");
- StringRef Extension = sys::path::extension(M->getName()).drop_front();
StringRef Prefix =
sys::path::stem(M->getName()).take_until([](char C) { return C == '-'; });
- SmallVector<GlobalVariable *, 4> ToBeDeleted;
-
// Extract offloading data from globals with the `.llvm.offloading` section
// name.
for (GlobalVariable &GV : M->globals()) {
@@ -495,45 +401,15 @@ extractFromBitcode(std::unique_ptr<MemoryBuffer> Buffer,
if (Error Err =
extractOffloadFiles(Contents, Prefix, DeviceFiles, IsLibrary))
- return std::move(Err);
-
- ToBeDeleted.push_back(&GV);
- }
-
- if (ToBeDeleted.empty() || !StripSections)
- return None;
-
- // We need to materialize the lazy module before we make any changes.
- if (Error Err = M->materializeAll())
- return std::move(Err);
-
- // Remove the global from the module and write it to a new file.
- for (GlobalVariable *GV : ToBeDeleted) {
- removeFromCompilerUsed(*M, *GV);
- GV->eraseFromParent();
+ return Err;
}
- SmallString<128> TempFile;
- if (Error Err = createOutputFile(Prefix + "-host", Extension, TempFile))
- return std::move(Err);
-
- std::error_code EC;
- raw_fd_ostream HostOutput(TempFile, EC, sys::fs::OF_None);
- if (EC)
- return createFileError(TempFile, EC);
- WriteBitcodeToFile(*M, HostOutput);
- return static_cast<std::string>(TempFile);
+ return Error::success();
}
-Expected<Optional<std::string>>
-extractFromArchive(const Archive &Library,
- SmallVectorImpl<DeviceFile> &DeviceFiles) {
- bool NewMembers = false;
- SmallVector<NewArchiveMember, 8> Members;
-
+Error extractFromArchive(const Archive &Library,
+ SmallVectorImpl<DeviceFile> &DeviceFiles) {
// Try to extract device code from each file stored in the static archive.
- // Save the stripped archive members to create a new host archive with the
- // offloading code removed.
Error Err = Error::success();
for (auto Child : Library.children(Err)) {
auto ChildBufferOrErr = Child.getMemoryBufferRef();
@@ -549,60 +425,21 @@ extractFromArchive(const Archive &Library,
ChildBufferOrErr->getBuffer(),
ChildBufferOrErr->getBufferIdentifier());
- auto FileOrErr = extractFromBuffer(std::move(ChildBuffer), DeviceFiles,
- /*IsLibrary*/ true);
- if (!FileOrErr)
- return FileOrErr.takeError();
-
- // If we created a new stripped host file, use it to create a new archive
- // member, otherwise use the old member.
- if (!FileOrErr->hasValue()) {
- Expected<NewArchiveMember> NewMember =
- NewArchiveMember::getOldMember(Child, true);
- if (!NewMember)
- return NewMember.takeError();
- Members.push_back(std::move(*NewMember));
- } else {
- Expected<NewArchiveMember> NewMember =
- NewArchiveMember::getFile(**FileOrErr, true);
- if (!NewMember)
- return NewMember.takeError();
- Members.push_back(std::move(*NewMember));
- NewMembers = true;
-
- // We no longer need the stripped file, remove it.
- if (std::error_code EC = sys::fs::remove(**FileOrErr))
- return createFileError(**FileOrErr, EC);
- }
+ if (Error Err = extractFromBuffer(std::move(ChildBuffer), DeviceFiles,
+ /*IsLibrary*/ true))
+ return Err;
}
if (Err)
- return std::move(Err);
-
- if (!NewMembers || !StripSections)
- return None;
-
- // Create a new static library using the stripped host files.
- SmallString<128> TempFile;
- StringRef Prefix = sys::path::stem(Library.getFileName());
- if (Error Err = createOutputFile(Prefix + "-host", "a", TempFile))
- return std::move(Err);
-
- std::unique_ptr<MemoryBuffer> Buffer =
- MemoryBuffer::getMemBuffer(Library.getMemoryBufferRef(), false);
- if (Error Err = writeArchive(TempFile, Members, true, Library.kind(), true,
- Library.isThin(), std::move(Buffer)))
- return std::move(Err);
-
- return static_cast<std::string>(TempFile);
+ return Err;
+ return Error::success();
}
/// Extracts embedded device offloading code from a memory \p Buffer to a list
-/// of \p DeviceFiles. If device code was extracted a new file with the embedded
-/// device code stripped from the buffer will be returned.
-Expected<Optional<std::string>>
-extractFromBuffer(std::unique_ptr<MemoryBuffer> Buffer,
- SmallVectorImpl<DeviceFile> &DeviceFiles, bool IsLibrary) {
+/// of \p DeviceFiles.
+Error extractFromBuffer(std::unique_ptr<MemoryBuffer> Buffer,
+ SmallVectorImpl<DeviceFile> &DeviceFiles,
+ bool IsLibrary) {
file_magic Type = identify_magic(Buffer->getBuffer());
switch (Type) {
case file_magic::bitcode:
@@ -624,7 +461,7 @@ extractFromBuffer(std::unique_ptr<MemoryBuffer> Buffer,
return extractFromArchive(*LibFile->get(), DeviceFiles);
}
default:
- return None;
+ return Error::success();
}
}
@@ -1229,7 +1066,8 @@ Error linkDeviceFiles(ArrayRef<DeviceFile> DeviceFiles,
LinkedImages.emplace_back(OFK_OpenMP, TheTriple.getTriple(), File.Arch,
LinkerInputFiles.front());
continue;
- } else if (WholeProgram && TheTriple.isNVPTX()) {
+ }
+ if (WholeProgram && TheTriple.isNVPTX()) {
// If we performed LTO on NVPTX and had whole program visibility, we can
// use CUDA in non-RDC mode.
if (LinkerInputFiles.size() != 1)
@@ -1477,8 +1315,7 @@ int main(int argc, const char **argv) {
LibraryPaths.push_back(Arg.drop_front(2));
}
- // Try to extract device code from the linker input and replace the linker
- // input with a new file that has the device section stripped.
+ // Try to extract device code from the linker input.
SmallVector<DeviceFile, 4> DeviceFiles;
for (std::string &Arg : LinkerArgs) {
if (Arg == ExecutableName)
@@ -1495,14 +1332,8 @@ int main(int argc, const char **argv) {
if (std::error_code EC = BufferOrErr.getError())
return reportError(createFileError(Filename, EC));
- auto NewFileOrErr =
- extractFromBuffer(std::move(*BufferOrErr), DeviceFiles);
-
- if (!NewFileOrErr)
- return reportError(NewFileOrErr.takeError());
-
- if (NewFileOrErr->hasValue())
- Arg = **NewFileOrErr;
+ if (Error Err = extractFromBuffer(std::move(*BufferOrErr), DeviceFiles))
+ return reportError(std::move(Err));
}
}
@@ -1524,7 +1355,7 @@ int main(int argc, const char **argv) {
// We need to insert the new files next to the old ones to make sure they're
// linked with the same libraries / arguments.
if (!FileOrErr->empty()) {
- auto FirstInput = std::next(llvm::find_if(LinkerArgs, [](StringRef Str) {
+ auto *FirstInput = std::next(llvm::find_if(LinkerArgs, [](StringRef Str) {
return sys::fs::exists(Str) && !sys::fs::is_directory(Str) &&
Str != ExecutableName;
}));
More information about the cfe-commits
mailing list