Skip to content

[DeviceSanitizer] Fix libstdc++ and libc++ mismatch problem #2006

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 3 commits into from
Aug 26, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 20 additions & 0 deletions source/loader/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,26 @@ if(UR_ENABLE_SANITIZER)
)
target_include_directories(ur_loader PRIVATE ${LLVM_INCLUDE_DIRS})
target_link_libraries(ur_loader PRIVATE LLVMSupport LLVMSymbolize)
# In in-tree build, if LLVM is built with libc++, we also need to build
# symbolizer.cpp with libc++ abi and link libc++ in.
if(NOT UR_STANDALONE_BUILD AND LLVM_LIBCXX_USED)
execute_process(
COMMAND ${CMAKE_CXX_COMPILER} --print-file-name=libc++.a
OUTPUT_VARIABLE LIBCXX_PATH
OUTPUT_STRIP_TRAILING_WHITESPACE)
execute_process(
COMMAND ${CMAKE_CXX_COMPILER} --print-file-name=libc++abi.a
OUTPUT_VARIABLE LIBCXX_ABI_PATH
OUTPUT_STRIP_TRAILING_WHITESPACE)
set_property(SOURCE
${CMAKE_CURRENT_SOURCE_DIR}/layers/sanitizer/linux/symbolizer.cpp
APPEND_STRING PROPERTY COMPILE_FLAGS
" -stdlib=libc++ ")
if(NOT EXISTS ${LIBCXX_PATH} OR NOT EXISTS ${LIBCXX_ABI_PATH})
message(FATAL_ERROR "libc++ is required but can't find the libraries")
endif()
target_link_libraries(ur_loader PRIVATE ${LIBCXX_PATH} ${LIBCXX_ABI_PATH})
endif()
endif()

target_include_directories(ur_loader PRIVATE
Expand Down
15 changes: 11 additions & 4 deletions source/loader/layers/sanitizer/linux/symbolizer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,9 @@ llvm::symbolize::PrinterConfig GetPrinterConfig() {

extern "C" {

bool SymbolizeCode(const std::string ModuleName, uint64_t ModuleOffset,
std::string &Result) {
void SymbolizeCode(const char *ModuleName, uint64_t ModuleOffset,
char *ResultString, size_t ResultSize, size_t *RetSize) {
std::string Result;
llvm::raw_string_ostream OS(Result);
llvm::symbolize::Request Request{ModuleName, ModuleOffset};
llvm::symbolize::PrinterConfig Config =
Expand All @@ -51,10 +52,16 @@ bool SymbolizeCode(const std::string ModuleName, uint64_t ModuleOffset,
{ModuleOffset, llvm::object::SectionedAddress::UndefSection});

if (!ResOrErr) {
return false;
return;
}
Printer->print(Request, *ResOrErr);
ur_sanitizer_layer::GetSymbolizer()->pruneCache();
return true;
if (RetSize) {
*RetSize = Result.size() + 1;
}
if (ResultString) {
std::strncpy(ResultString, Result.c_str(), ResultSize);
ResultString[ResultSize - 1] = '\0';
}
}
}
21 changes: 14 additions & 7 deletions source/loader/layers/sanitizer/stacktrace.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,9 +15,10 @@

extern "C" {

__attribute__((weak)) bool SymbolizeCode(const std::string ModuleName,
__attribute__((weak)) void SymbolizeCode(const char *ModuleName,
uint64_t ModuleOffset,
std::string &Result);
char *ResultString, size_t ResultSize,
size_t *RetSize);
}

namespace ur_sanitizer_layer {
Expand Down Expand Up @@ -49,7 +50,7 @@ void ParseBacktraceInfo(BacktraceInfo BI, std::string &ModuleName,
// Parse symbolizer output in the following formats:
// <function_name>
// <file_name>:<line_number>[:<column_number>]
SourceInfo ParseSymbolizerOutput(std::string Output) {
SourceInfo ParseSymbolizerOutput(const std::string &Output) {
SourceInfo Info;
// Parse function name
size_t End = Output.find_first_of('\n');
Expand Down Expand Up @@ -98,8 +99,14 @@ void StackTrace::print() const {
std::string ModuleName;
uptr Offset;
ParseBacktraceInfo(BI, ModuleName, Offset);
if (SymbolizeCode(ModuleName, Offset, Result)) {
SourceInfo SrcInfo = ParseSymbolizerOutput(std::move(Result));
size_t ResultSize = 0;
SymbolizeCode(ModuleName.c_str(), Offset, nullptr, 0, &ResultSize);
if (ResultSize) {
std::vector<char> ResultVector(ResultSize);
SymbolizeCode(ModuleName.c_str(), Offset, ResultVector.data(),
ResultSize, nullptr);
std::string Result((char *)ResultVector.data());
SourceInfo SrcInfo = ParseSymbolizerOutput(Result);
if (SrcInfo.file != "??") {
getContext()->logger.always(" #{} in {} {}:{}:{}", index,
SrcInfo.function, SrcInfo.file,
Expand All @@ -109,10 +116,10 @@ void StackTrace::print() const {
SrcInfo.function, ModuleName,
(void *)Offset);
}
continue;
}
} else {
getContext()->logger.always(" #{} {}", index, BI);
}
getContext()->logger.always(" #{} {}", index, BI);
++index;
}
getContext()->logger.always("");
Expand Down
Loading