diff options
Diffstat (limited to 'contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc')
-rw-r--r-- | contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc | 41 |
1 files changed, 41 insertions, 0 deletions
diff --git a/contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc b/contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc index b2423951795f..27f0e01c7fbe 100644 --- a/contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc +++ b/contrib/compiler-rt/lib/tsan/rtl/tsan_symbolize.cc @@ -36,6 +36,7 @@ void ExitSymbolizer() { thr->ignore_interceptors--; } +// Legacy API. // May be overriden by JIT/JAVA/etc, // whatever produces PCs marked with kExternalPCBit. SANITIZER_WEAK_DEFAULT_IMPL @@ -45,9 +46,49 @@ bool __tsan_symbolize_external(uptr pc, char *func_buf, uptr func_siz, return false; } +// New API: call __tsan_symbolize_external_ex only when it exists. +// Once old clients are gone, provide dummy implementation. +SANITIZER_WEAK_DEFAULT_IMPL +void __tsan_symbolize_external_ex(uptr pc, + void (*add_frame)(void *, const char *, + const char *, int, int), + void *ctx) {} + +struct SymbolizedStackBuilder { + SymbolizedStack *head; + SymbolizedStack *tail; + uptr addr; +}; + +static void AddFrame(void *ctx, const char *function_name, const char *file, + int line, int column) { + SymbolizedStackBuilder *ssb = (struct SymbolizedStackBuilder *)ctx; + if (ssb->tail) { + ssb->tail->next = SymbolizedStack::New(ssb->addr); + ssb->tail = ssb->tail->next; + } else { + ssb->head = ssb->tail = SymbolizedStack::New(ssb->addr); + } + AddressInfo *info = &ssb->tail->info; + if (function_name) { + info->function = internal_strdup(function_name); + } + if (file) { + info->file = internal_strdup(file); + } + info->line = line; + info->column = column; +} + SymbolizedStack *SymbolizeCode(uptr addr) { // Check if PC comes from non-native land. if (addr & kExternalPCBit) { + SymbolizedStackBuilder ssb = {nullptr, nullptr, addr}; + __tsan_symbolize_external_ex(addr, AddFrame, &ssb); + if (ssb.head) + return ssb.head; + // Legacy code: remove along with the declaration above + // once all clients using this API are gone. // Declare static to not consume too much stack space. // We symbolize reports in a single thread, so this is fine. static char func_buf[1024]; |