"-target-feature=" + TC->getTripleString() + "=" + *(FeatureIt + 1)));
}
+ // Pass in the bitcode library to be linked during LTO.
+ for (auto TI = OpenMPTCRange.first, TE = OpenMPTCRange.second; TI != TE;
+ ++TI) {
+ const ToolChain *TC = TI->second;
+ const Driver &D = TC->getDriver();
+ const ArgList &TCArgs = C.getArgsForToolChain(TC, "", Action::OFK_OpenMP);
+ StringRef Arch = TCArgs.getLastArgValue(options::OPT_march_EQ);
+
+ std::string BitcodeSuffix;
+ if (TCArgs.hasFlag(options::OPT_fopenmp_target_new_runtime,
+ options::OPT_fno_openmp_target_new_runtime, true))
+ BitcodeSuffix += "new-";
+ if (TC->getTriple().isNVPTX())
+ BitcodeSuffix += "nvptx-";
+ else if (TC->getTriple().isAMDGPU())
+ BitcodeSuffix += "amdgpu-";
+ BitcodeSuffix += Arch;
+
+ ArgStringList BitcodeLibrary;
+ addOpenMPDeviceRTL(D, TCArgs, BitcodeLibrary, BitcodeSuffix,
+ TC->getTriple());
+
+ if (!BitcodeLibrary.empty())
+ CmdArgs.push_back(
+ Args.MakeArgString("-target-library=" + TC->getTripleString() +
+ "-" + Arch + "=" + BitcodeLibrary.back()));
+ }
+
// Pass in the optimization level to use for LTO.
if (const Arg *A = Args.getLastArg(options::OPT_O_Group)) {
StringRef OOpt;
static cl::opt<std::string> OptLevel("opt-level",
cl::desc("Optimization level for LTO"),
- cl::init("O0"),
+ cl::init("O2"),
cl::cat(ClangLinkerWrapperCategory));
+static cl::opt<std::string>
+ BitcodeLibrary("target-library",
+ cl::desc("Path for the target bitcode library"),
+ cl::cat(ClangLinkerWrapperCategory));
+
// Do not parse linker options.
static cl::list<std::string>
HostLinkerArgs(cl::Sink, cl::desc("<options to be passed to linker>..."));
std::unique_ptr<FileOutputBuffer> Output = std::move(*OutputOrErr);
std::copy(Contents->begin(), Contents->end(), Output->getBufferStart());
if (Error E = Output->commit())
- return E;
+ return std::move(E);
DeviceFiles.emplace_back(DeviceTriple, Arch, TempFile);
ToBeStripped.push_back(*Name);
std::unique_ptr<FileOutputBuffer> Output = std::move(*OutputOrErr);
std::copy(Contents.begin(), Contents.end(), Output->getBufferStart());
if (Error E = Output->commit())
- return E;
+ return std::move(E);
StripFile = TempFile;
}
std::unique_ptr<FileOutputBuffer> Output = std::move(*OutputOrErr);
std::copy(Contents.begin(), Contents.end(), Output->getBufferStart());
if (Error E = Output->commit())
- return E;
+ return std::move(E);
DeviceFiles.emplace_back(DeviceTriple, Arch, TempFile);
ToBeDeleted.push_back(&GV);
// We need to materialize the lazy module before we make any changes.
if (Error Err = M->materializeAll())
- return Err;
+ return std::move(Err);
// Remove the global from the module and write it to a new file.
for (GlobalVariable *GV : ToBeDeleted) {
}
if (Err)
- return Err;
+ return std::move(Err);
if (!NewMembers)
return None;
std::unique_ptr<MemoryBuffer> Buffer =
MemoryBuffer::getMemBuffer(Library.getMemoryBufferRef(), false);
- if (Error WriteErr = writeArchive(TempFile, Members, true, Library.kind(),
+ if (Error Err = writeArchive(TempFile, Members, true, Library.kind(),
true, Library.isThin(), std::move(Buffer)))
- return WriteErr;
+ return std::move(Err);
return static_cast<std::string>(TempFile);
}
// Add the bitcode file with its resolved symbols to the LTO job.
if (Error Err = LTOBackend->add(std::move(BitcodeFile), Resolutions))
- return Err;
+ return std::move(Err);
}
// Run the LTO job to compile the bitcode.
std::make_unique<llvm::raw_fd_ostream>(FD, true));
};
if (Error Err = LTOBackend->run(AddStream))
- return Err;
+ return std::move(Err);
for (auto &File : Files) {
if (!TheTriple.isNVPTX())
}
}
+ // Add the device bitcode library to the device files if it was passed in.
+ if (!BitcodeLibrary.empty()) {
+ // FIXME: Hacky workaround to avoid a backend crash at O0.
+ if (OptLevel[1] - '0' == 0)
+ OptLevel[1] = '1';
+ auto DeviceAndPath = StringRef(BitcodeLibrary).split('=');
+ auto TripleAndArch = DeviceAndPath.first.rsplit('-');
+ DeviceFiles.emplace_back(TripleAndArch.first, TripleAndArch.second,
+ DeviceAndPath.second);
+ }
+
// Link the device images extracted from the linker input.
SmallVector<std::string, 16> LinkedImages;
if (Error Err = linkDeviceFiles(DeviceFiles, LinkerArgs, LinkedImages))