CodeQL / Analyze (actions) (push) Canceled after 0s
CodeQL / Analyze (python) (push) Canceled after 0s
pre-commit / pre-commit (push) Canceled after 0s
Multi-Arch CI / setup (push) Canceled after 0s
Publish build_manylinux_x86_64 images / publish_build_manylinux_x86_64 (push) Canceled after 0s
Setup (Multi-Arch) / setup (push) Canceled after 0s
Multi-Arch CI / Linux::${{ fromJSON(needs.setup.outputs.linux_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubi10 image / publish_no_rocm_image_ubi10 (push) Canceled after 0s
Multi-Arch CI / Windows::${{ fromJSON(needs.setup.outputs.windows_build_config || '{}').build_variant_label || 'skip' }} (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Multi-Arch CI / Manifest Diff (push) Canceled after 0s
TheRock Manifest Diff Report / Generate Manifest Diff Report (push) Canceled after 0s
Multi-Arch CI / CI Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_ocl_rt images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04_rocgdb images / publish_no_rocm_image_ubuntu24_04_rocgdb (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_ocl_rt (push) Canceled after 0s
Publish TheRock Docker image / build-and-push-image (push) Canceled after 0s
Unit Tests / Unit Tests :: ubuntu-24.04 (push) Canceled after 0s
Unit Tests / Unit Tests :: windows-2022 (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_media (push) Canceled after 0s
Unit Tests / Unit Tests Summary (push) Canceled after 0s
Publish no_rocm_image_ubuntu24_04 images / publish_no_rocm_image_ubuntu24_04_openmpi (push) Canceled after 0s
176 lines
5.3 KiB
C++
176 lines
5.3 KiB
C++
//===- comgr-cache-command.cpp - CacheCommand implementation --------------===//
|
|
//
|
|
// Part of Comgr, under the Apache License v2.0 with LLVM Exceptions. See
|
|
// amd/comgr/LICENSE.TXT in this repository for license information.
|
|
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
|
//
|
|
//===----------------------------------------------------------------------===//
|
|
///
|
|
/// \file
|
|
/// This file implements the CachedCommandAdaptor: the interface and common
|
|
/// operations for commands that save their execution results in the cache.
|
|
///
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
#include "comgr-cache-command.h"
|
|
#include "comgr-cache.h"
|
|
#include "comgr-device-libs.h"
|
|
#include "comgr-env.h"
|
|
#include "comgr.h"
|
|
|
|
#include <clang/Basic/Version.h>
|
|
#include <llvm/ADT/StringExtras.h>
|
|
|
|
#include <optional>
|
|
|
|
namespace COMGR {
|
|
using namespace llvm;
|
|
using namespace clang;
|
|
|
|
std::optional<CachedCommandAdaptor::ComgrTmpSearchResult>
|
|
CachedCommandAdaptor::searchComgrTmpModel(StringRef S) {
|
|
// Ideally, we would use std::regex_search with the regex
|
|
// "comgr-[[:num:]]+-[[:num:]]+-[[:alnum:]]{6}". However, due to a bug in
|
|
// stdlibc++ (https://gcc.gnu.org/bugzilla/show_bug.cgi?id=85824) we have to
|
|
// roll our own search of this regular expression. This bug resulted in a
|
|
// crash in luxmarkv3, during the std::regex constructor.
|
|
|
|
const StringRef Prefix = "comgr";
|
|
const size_t AlnumCount = 6;
|
|
|
|
StringRef Remaining = S;
|
|
while (!Remaining.empty()) {
|
|
size_t PosInRemaining = Remaining.find(Prefix);
|
|
if (PosInRemaining == StringRef::npos)
|
|
return std::nullopt;
|
|
|
|
size_t PosInS = Remaining.data() + PosInRemaining - S.data();
|
|
|
|
Remaining = Remaining.substr(PosInRemaining + Prefix.size());
|
|
|
|
unsigned Pid;
|
|
if (!Remaining.consume_front("-") ||
|
|
Remaining.consumeInteger<unsigned>(10, Pid)) {
|
|
continue;
|
|
}
|
|
|
|
unsigned Id;
|
|
if (!Remaining.consume_front("-") ||
|
|
Remaining.consumeInteger<unsigned>(10, Id)) {
|
|
continue;
|
|
}
|
|
|
|
if (!Remaining.consume_front("-")) {
|
|
continue;
|
|
}
|
|
|
|
if (Remaining.size() < AlnumCount) {
|
|
continue;
|
|
}
|
|
|
|
// Use llvm::isAlnum and not std::isalnum. The later is locale dependent and
|
|
// can have issues depending on the stdlib version and application.
|
|
if (!all_of(Remaining.substr(0, AlnumCount), llvm::isAlnum)) {
|
|
continue;
|
|
}
|
|
|
|
// `Remaining` begin is one after the end of the pattern
|
|
Remaining = Remaining.drop_front(AlnumCount);
|
|
|
|
size_t MatchSize = Remaining.data() - S.data() - PosInS;
|
|
|
|
return {{PosInS, MatchSize}};
|
|
}
|
|
|
|
return std::nullopt;
|
|
}
|
|
|
|
void CachedCommandAdaptor::addUInt(CachedCommandAdaptor::HashAlgorithm &H,
|
|
uint64_t I) {
|
|
uint8_t Bytes[sizeof(I)];
|
|
memcpy(&Bytes, &I, sizeof(I));
|
|
H.update(Bytes);
|
|
}
|
|
|
|
void CachedCommandAdaptor::addString(CachedCommandAdaptor::HashAlgorithm &H,
|
|
StringRef S) {
|
|
// hash size + contents to avoid collisions
|
|
// for example, we have to ensure that the result of hashing "AA" "BB" is
|
|
// different from "A" "ABB"
|
|
addUInt(H, S.size());
|
|
H.update(S);
|
|
}
|
|
|
|
void CachedCommandAdaptor::addFileContents(
|
|
CachedCommandAdaptor::HashAlgorithm &H, StringRef Buf) {
|
|
// this is a workaround temporary paths getting in the output files of the
|
|
// different commands in #line directives in preprocessed files, and the
|
|
// ModuleID or source_filename in the bitcode.
|
|
while (!Buf.empty()) {
|
|
auto ComgrTmpPos = searchComgrTmpModel(Buf);
|
|
if (!ComgrTmpPos) {
|
|
addString(H, Buf);
|
|
break;
|
|
}
|
|
|
|
StringRef ToHash = Buf.substr(0, ComgrTmpPos->StartPosition);
|
|
addString(H, ToHash);
|
|
Buf = Buf.substr(ToHash.size() + ComgrTmpPos->MatchSize);
|
|
}
|
|
}
|
|
|
|
Expected<CachedCommandAdaptor::Identifier>
|
|
CachedCommandAdaptor::getIdentifier() const {
|
|
CachedCommandAdaptor::HashAlgorithm H;
|
|
H.update(getClass());
|
|
H.update(env::shouldEmitVerboseLogs());
|
|
addString(H, getClangFullVersion());
|
|
addString(H, getComgrHashIdentifier());
|
|
H.update(getDeviceLibrariesIdentifier());
|
|
|
|
if (Error E = addInputIdentifier(H))
|
|
return E;
|
|
|
|
addOptionsIdentifier(H);
|
|
|
|
CachedCommandAdaptor::Identifier Id;
|
|
toHex(H.final(), true, Id);
|
|
return Id;
|
|
}
|
|
|
|
llvm::Error
|
|
CachedCommandAdaptor::writeSingleOutputFile(StringRef OutputFilename,
|
|
StringRef CachedBuffer) {
|
|
std::error_code EC;
|
|
raw_fd_ostream Out(OutputFilename, EC);
|
|
if (EC) {
|
|
Error E = createStringError(EC, Twine("Failed to open ") + OutputFilename +
|
|
" : " + EC.message() + "\n");
|
|
return E;
|
|
}
|
|
|
|
Out.write(CachedBuffer.data(), CachedBuffer.size());
|
|
Out.close();
|
|
if (Out.has_error()) {
|
|
Error E = createStringError(EC, Twine("Failed to write ") + OutputFilename +
|
|
" : " + EC.message() + "\n");
|
|
return E;
|
|
}
|
|
|
|
return Error::success();
|
|
}
|
|
|
|
Expected<std::unique_ptr<MemoryBuffer>>
|
|
CachedCommandAdaptor::readSingleOutputFile(StringRef OutputFilename) {
|
|
ErrorOr<std::unique_ptr<MemoryBuffer>> MBOrErr =
|
|
MemoryBuffer::getFile(OutputFilename);
|
|
if (!MBOrErr) {
|
|
std::error_code EC = MBOrErr.getError();
|
|
return createStringError(EC, Twine("Failed to open ") + OutputFilename +
|
|
" : " + EC.message() + "\n");
|
|
}
|
|
|
|
return std::move(*MBOrErr);
|
|
}
|
|
} // namespace COMGR
|