Skip to content

Commit 1b3c08e

Browse files
authored
[Comgr][Cache] Cache unbundle of compressed bundles (llvm#526)
2 parents 89b1509 + 3a7f64c commit 1b3c08e

11 files changed

+507
-76
lines changed

amd/comgr/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,7 @@ set(SOURCES
8585
src/comgr-spirv-command.cpp
8686
src/comgr-symbol.cpp
8787
src/comgr-symbolizer.cpp
88+
src/comgr-unbundle-command.cpp
8889
src/time-stat/time-stat.cpp)
8990

9091
if(COMGR_BUILD_SHARED_LIBS)

amd/comgr/src/comgr-cache-command.cpp

Lines changed: 35 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -98,4 +98,39 @@ CachedCommandAdaptor::getIdentifier() const {
9898
toHex(H.final(), true, Id);
9999
return Id;
100100
}
101+
102+
llvm::Error
103+
CachedCommandAdaptor::writeSingleOutputFile(StringRef OutputFilename,
104+
StringRef CachedBuffer) {
105+
std::error_code EC;
106+
raw_fd_ostream Out(OutputFilename, EC);
107+
if (EC) {
108+
Error E = createStringError(EC, Twine("Failed to open ") + OutputFilename +
109+
" : " + EC.message() + "\n");
110+
return E;
111+
}
112+
113+
Out.write(CachedBuffer.data(), CachedBuffer.size());
114+
Out.close();
115+
if (Out.has_error()) {
116+
Error E = createStringError(EC, Twine("Failed to write ") + OutputFilename +
117+
" : " + EC.message() + "\n");
118+
return E;
119+
}
120+
121+
return Error::success();
122+
}
123+
124+
Expected<std::unique_ptr<MemoryBuffer>>
125+
CachedCommandAdaptor::readSingleOutputFile(StringRef OutputFilename) {
126+
ErrorOr<std::unique_ptr<MemoryBuffer>> MBOrErr =
127+
MemoryBuffer::getFile(OutputFilename);
128+
if (!MBOrErr) {
129+
std::error_code EC = MBOrErr.getError();
130+
return createStringError(EC, Twine("Failed to open ") + OutputFilename +
131+
" : " + EC.message() + "\n");
132+
}
133+
134+
return std::move(*MBOrErr);
135+
}
101136
} // namespace COMGR

amd/comgr/src/comgr-cache-command.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -69,6 +69,12 @@ class CachedCommandAdaptor {
6969
static void addString(HashAlgorithm &H, llvm::StringRef S);
7070
static std::optional<size_t> searchComgrTmpModel(llvm::StringRef S);
7171

72+
// helper since several command types just write to a single output file
73+
static llvm::Error writeSingleOutputFile(llvm::StringRef OutputFilename,
74+
llvm::StringRef CachedBuffer);
75+
static llvm::Expected<std::unique_ptr<llvm::MemoryBuffer>>
76+
readSingleOutputFile(llvm::StringRef OutputFilename);
77+
7278
protected:
7379
virtual ActionClass getClass() const = 0;
7480
virtual void addOptionsIdentifier(HashAlgorithm &) const = 0;

amd/comgr/src/comgr-clang-command.cpp

Lines changed: 7 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -158,35 +158,16 @@ bool ClangCommand::canCache() const {
158158

159159
Error ClangCommand::writeExecuteOutput(StringRef CachedBuffer) {
160160
StringRef OutputFilename = Command.getOutputFilenames().front();
161-
std::error_code EC;
162-
raw_fd_ostream Out(OutputFilename, EC);
163-
if (EC) {
164-
Error E = createStringError(EC, Twine("Failed to open ") + OutputFilename +
165-
" : " + EC.message() + "\n");
166-
return E;
167-
}
168-
169-
Out.write(CachedBuffer.data(), CachedBuffer.size());
170-
Out.close();
171-
if (Out.has_error()) {
172-
Error E = createStringError(EC, Twine("Failed to write ") + OutputFilename +
173-
" : " + EC.message() + "\n");
174-
return E;
175-
}
176-
177-
return Error::success();
161+
return CachedCommandAdaptor::writeSingleOutputFile(OutputFilename,
162+
CachedBuffer);
178163
}
179164

180165
Expected<StringRef> ClangCommand::readExecuteOutput() {
181-
StringRef OutputFilename = Command.getOutputFilenames().front();
182-
ErrorOr<std::unique_ptr<MemoryBuffer>> MBOrErr =
183-
MemoryBuffer::getFile(OutputFilename);
184-
if (!MBOrErr) {
185-
std::error_code EC = MBOrErr.getError();
186-
return createStringError(EC, Twine("Failed to open ") + OutputFilename +
187-
" : " + EC.message() + "\n");
188-
}
189-
Output = std::move(*MBOrErr);
166+
auto MaybeBuffer = CachedCommandAdaptor::readSingleOutputFile(
167+
Command.getOutputFilenames().front());
168+
if (!MaybeBuffer)
169+
return MaybeBuffer.takeError();
170+
Output = std::move(*MaybeBuffer);
190171
return Output->getBuffer();
191172
}
192173

amd/comgr/src/comgr-compiler.cpp

Lines changed: 27 additions & 50 deletions
Original file line numberDiff line numberDiff line change
@@ -43,6 +43,7 @@
4343
#include "comgr-diagnostic-handler.h"
4444
#include "comgr-env.h"
4545
#include "comgr-spirv-command.h"
46+
#include "comgr-unbundle-command.h"
4647
#include "lld/Common/CommonLinkerContext.h"
4748
#include "lld/Common/Driver.h"
4849
#include "clang/CodeGen/CodeGenAction.h"
@@ -1255,9 +1256,10 @@ amd_comgr_status_t AMDGPUCompiler::unbundle() {
12551256
}
12561257

12571258
// Collect bitcode memory buffers from bitcodes, bundles, and archives
1259+
auto Cache = CommandCache::get(LogS);
12581260
for (auto *Input : InSet->DataObjects) {
12591261

1260-
std::string FileExtension;
1262+
const char *FileExtension;
12611263
amd_comgr_data_kind_t UnbundledDataKind;
12621264
switch (Input->DataKind) {
12631265
case AMD_COMGR_DATA_KIND_BC_BUNDLE:
@@ -1288,22 +1290,22 @@ amd_comgr_status_t AMDGPUCompiler::unbundle() {
12881290
const size_t BufSize = sizeof(char) * 30;
12891291
char *Buf = (char *)malloc(BufSize);
12901292
snprintf(Buf, BufSize, "comgr-bundle-%d.%s", std::rand() % 10000,
1291-
FileExtension.c_str());
1293+
FileExtension);
12921294
Input->Name = Buf;
12931295
}
12941296

12951297
// Write input file system so that OffloadBundler API can process
12961298
// TODO: Switch write to VFS
1297-
std::string InputFilePath = getFilePath(Input, InputDir).str().str();
1299+
SmallString<128> InputFilePath = getFilePath(Input, InputDir);
12981300
if (auto Status = outputToFile(Input, InputFilePath)) {
12991301
return Status;
13001302
}
13011303

13021304
// Bundler input name
1303-
BundlerConfig.InputFileNames.push_back(InputFilePath);
1305+
BundlerConfig.InputFileNames.emplace_back(InputFilePath);
13041306

13051307
// Generate prefix for output files
1306-
std::string OutputPrefix = std::string(Input->Name);
1308+
StringRef OutputPrefix = Input->Name;
13071309
size_t Index = OutputPrefix.find_last_of(".");
13081310
OutputPrefix = OutputPrefix.substr(0, Index);
13091311

@@ -1314,53 +1316,35 @@ amd_comgr_status_t AMDGPUCompiler::unbundle() {
13141316
<< " Unbundled Files Extension: ." << FileExtension << "\n";
13151317
}
13161318

1317-
for (size_t I = 0; I < ActionInfo->BundleEntryIDs.size(); I++) {
1318-
auto Entry = ActionInfo->BundleEntryIDs[I];
1319-
BundlerConfig.TargetNames.push_back(Entry);
1320-
1319+
for (StringRef Entry : ActionInfo->BundleEntryIDs) {
13211320
// Add an output file for each target
1322-
std::string OutputFileName =
1323-
OutputPrefix + '-' + Entry + "." + FileExtension;
1321+
SmallString<128> OutputFilePath = OutputDir;
1322+
sys::path::append(OutputFilePath,
1323+
OutputPrefix + "-" + Entry + "." + FileExtension);
13241324

1325-
// TODO: Switch this to LLVM path APIs
1326-
std::string OutputFilePath = OutputDir.str().str() + "/" + OutputFileName;
1327-
BundlerConfig.OutputFileNames.push_back(OutputFilePath);
1325+
BundlerConfig.TargetNames.emplace_back(Entry);
1326+
BundlerConfig.OutputFileNames.emplace_back(OutputFilePath);
13281327

13291328
if (env::shouldEmitVerboseLogs()) {
1330-
LogS << "\tBundle Entry ID: " << BundlerConfig.TargetNames[I] << "\n"
1331-
<< "\tOutput Filename: " << BundlerConfig.OutputFileNames[I]
1332-
<< "\n";
1329+
LogS << "\tBundle Entry ID: " << Entry << "\n"
1330+
<< "\tOutput Filename: " << OutputFilePath << "\n";
13331331
LogS.flush();
13341332
}
13351333
}
13361334

1337-
OffloadBundler Bundler(BundlerConfig);
1338-
1339-
switch (Input->DataKind) {
1340-
case AMD_COMGR_DATA_KIND_BC_BUNDLE: {
1341-
llvm::Error Err = Bundler.UnbundleFiles();
1342-
llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(),
1343-
"Unbundle Bitcodes Error: ");
1344-
break;
1345-
}
1346-
case AMD_COMGR_DATA_KIND_AR_BUNDLE: {
1347-
llvm::Error Err = Bundler.UnbundleArchive();
1348-
llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(),
1349-
"Unbundle Archives Error: ");
1350-
break;
1351-
}
1352-
case AMD_COMGR_DATA_KIND_OBJ_BUNDLE: {
1353-
llvm::Error Err = Bundler.UnbundleFiles();
1354-
llvm::logAllUnhandledErrors(std::move(Err), llvm::errs(),
1355-
"Unbundle Objects Error: ");
1356-
break;
1357-
}
1358-
default:
1359-
llvm_unreachable("invalid bundle type");
1335+
UnbundleCommand Unbundle(Input->DataKind, BundlerConfig);
1336+
if (Cache) {
1337+
if (auto Status = Cache->execute(Unbundle, LogS)) {
1338+
return Status;
1339+
}
1340+
} else {
1341+
if (auto Status = Unbundle.execute(LogS)) {
1342+
return Status;
1343+
}
13601344
}
13611345

13621346
// Add new bitcodes to OutSetT
1363-
for (auto OutputFilePath : BundlerConfig.OutputFileNames) {
1347+
for (StringRef OutputFilePath : BundlerConfig.OutputFileNames) {
13641348

13651349
amd_comgr_data_t ResultT;
13661350

@@ -1371,22 +1355,15 @@ amd_comgr_status_t AMDGPUCompiler::unbundle() {
13711355
ScopedDataObjectReleaser SDOR(ResultT);
13721356

13731357
DataObject *Result = DataObject::convert(ResultT);
1374-
if (auto Status = inputFromFile(Result, StringRef(OutputFilePath)))
1358+
if (auto Status = inputFromFile(Result, OutputFilePath))
13751359
return Status;
13761360

1377-
StringRef OutputFileName =
1378-
llvm::sys::path::filename(StringRef(OutputFilePath));
1361+
StringRef OutputFileName = sys::path::filename(OutputFilePath);
13791362
Result->setName(OutputFileName);
13801363

13811364
if (auto Status = amd_comgr_data_set_add(OutSetT, ResultT)) {
13821365
return Status;
13831366
}
1384-
1385-
// Remove input and output file after reading back into Comgr data
1386-
if (!env::shouldEmitVerboseLogs()) {
1387-
sys::fs::remove(InputFilePath);
1388-
sys::fs::remove(OutputFilePath);
1389-
}
13901367
}
13911368
}
13921369

0 commit comments

Comments
 (0)