2019-08-01 02:51:27 +08:00
|
|
|
//===-- sanitizer_symbolizer_markup.cpp -----------------------------------===//
|
2017-08-02 06:54:51 +08:00
|
|
|
//
|
2019-01-19 16:50:56 +08:00
|
|
|
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
|
|
|
// See https://llvm.org/LICENSE.txt for license information.
|
|
|
|
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
2017-08-02 06:54:51 +08:00
|
|
|
//
|
|
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
//
|
|
|
|
// This file is shared between various sanitizers' runtime libraries.
|
|
|
|
//
|
2018-05-12 07:52:19 +08:00
|
|
|
// Implementation of offline markup symbolizer.
|
2017-08-02 06:54:51 +08:00
|
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
|
|
|
|
#include "sanitizer_platform.h"
|
2018-05-12 07:52:19 +08:00
|
|
|
#if SANITIZER_SYMBOLIZER_MARKUP
|
2017-08-02 06:54:51 +08:00
|
|
|
|
2018-05-12 07:52:19 +08:00
|
|
|
#if SANITIZER_FUCHSIA
|
|
|
|
#include "sanitizer_symbolizer_fuchsia.h"
|
2021-06-15 08:46:48 +08:00
|
|
|
# endif
|
2021-06-15 08:52:14 +08:00
|
|
|
|
2021-06-15 08:46:48 +08:00
|
|
|
# include <limits.h>
|
|
|
|
# include <unwind.h>
|
2017-08-02 06:54:51 +08:00
|
|
|
|
2021-06-15 08:46:48 +08:00
|
|
|
# include "sanitizer_stacktrace.h"
|
|
|
|
# include "sanitizer_symbolizer.h"
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
|
2017-08-02 06:54:51 +08:00
|
|
|
namespace __sanitizer {
|
|
|
|
|
2018-05-12 07:52:19 +08:00
|
|
|
// This generic support for offline symbolizing is based on the
|
|
|
|
// Fuchsia port. We don't do any actual symbolization per se.
|
2017-08-02 06:54:51 +08:00
|
|
|
// Instead, we emit text containing raw addresses and raw linkage
|
|
|
|
// symbol names, embedded in Fuchsia's symbolization markup format.
|
|
|
|
// Fuchsia's logging infrastructure emits enough information about
|
|
|
|
// process memory layout that a post-processing filter can do the
|
2017-09-06 08:00:46 +08:00
|
|
|
// symbolization and pretty-print the markup. See the spec at:
|
2017-09-13 09:18:15 +08:00
|
|
|
// https://fuchsia.googlesource.com/zircon/+/master/docs/symbolizer_markup.md
|
2017-08-02 06:54:51 +08:00
|
|
|
|
|
|
|
// This is used by UBSan for type names, and by ASan for global variable names.
|
|
|
|
// It's expected to return a static buffer that will be reused on each call.
|
|
|
|
const char *Symbolizer::Demangle(const char *name) {
|
|
|
|
static char buffer[kFormatDemangleMax];
|
|
|
|
internal_snprintf(buffer, sizeof(buffer), kFormatDemangle, name);
|
|
|
|
return buffer;
|
|
|
|
}
|
|
|
|
|
|
|
|
// This is used mostly for suppression matching. Making it work
|
|
|
|
// would enable "interceptor_via_lib" suppressions. It's also used
|
|
|
|
// once in UBSan to say "in module ..." in a message that also
|
|
|
|
// includes an address in the module, so post-processing can already
|
|
|
|
// pretty-print that so as to indicate the module.
|
|
|
|
bool Symbolizer::GetModuleNameAndOffsetForPC(uptr pc, const char **module_name,
|
|
|
|
uptr *module_address) {
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2021-03-26 06:24:12 +08:00
|
|
|
// This is mainly used by hwasan for online symbolization. This isn't needed
|
|
|
|
// since hwasan can always just dump stack frames for offline symbolization.
|
|
|
|
bool Symbolizer::SymbolizeFrame(uptr addr, FrameInfo *info) { return false; }
|
|
|
|
|
2017-08-02 06:54:51 +08:00
|
|
|
// This is used in some places for suppression checking, which we
|
|
|
|
// don't really support for Fuchsia. It's also used in UBSan to
|
|
|
|
// identify a PC location to a function name, so we always fill in
|
|
|
|
// the function member with a string containing markup around the PC
|
|
|
|
// value.
|
|
|
|
// TODO(mcgrathr): Under SANITIZER_GO, it's currently used by TSan
|
|
|
|
// to render stack frames, but that should be changed to use
|
|
|
|
// RenderStackFrame.
|
|
|
|
SymbolizedStack *Symbolizer::SymbolizePC(uptr addr) {
|
|
|
|
SymbolizedStack *s = SymbolizedStack::New(addr);
|
|
|
|
char buffer[kFormatFunctionMax];
|
|
|
|
internal_snprintf(buffer, sizeof(buffer), kFormatFunction, addr);
|
|
|
|
s->info.function = internal_strdup(buffer);
|
|
|
|
return s;
|
|
|
|
}
|
|
|
|
|
|
|
|
// Always claim we succeeded, so that RenderDataInfo will be called.
|
|
|
|
bool Symbolizer::SymbolizeData(uptr addr, DataInfo *info) {
|
|
|
|
info->Clear();
|
|
|
|
info->start = addr;
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
// We ignore the format argument to __sanitizer_symbolize_global.
|
|
|
|
void RenderData(InternalScopedString *buffer, const char *format,
|
|
|
|
const DataInfo *DI, const char *strip_path_prefix) {
|
|
|
|
buffer->append(kFormatData, DI->start);
|
|
|
|
}
|
|
|
|
|
2020-10-09 01:43:06 +08:00
|
|
|
bool RenderNeedsSymbolization(const char *format) { return false; }
|
|
|
|
|
2017-08-02 06:54:51 +08:00
|
|
|
// We don't support the stack_trace_format flag at all.
|
|
|
|
void RenderFrame(InternalScopedString *buffer, const char *format, int frame_no,
|
2020-10-09 01:43:06 +08:00
|
|
|
uptr address, const AddressInfo *info, bool vs_style,
|
2017-08-02 06:54:51 +08:00
|
|
|
const char *strip_path_prefix, const char *strip_func_prefix) {
|
2020-10-09 01:43:06 +08:00
|
|
|
CHECK(!RenderNeedsSymbolization(format));
|
|
|
|
buffer->append(kFormatFrame, frame_no, address);
|
2017-08-02 06:54:51 +08:00
|
|
|
}
|
|
|
|
|
|
|
|
Symbolizer *Symbolizer::PlatformInit() {
|
2017-09-13 09:18:15 +08:00
|
|
|
return new (symbolizer_allocator_) Symbolizer({});
|
2017-08-02 06:54:51 +08:00
|
|
|
}
|
|
|
|
|
2021-12-15 07:23:48 +08:00
|
|
|
void Symbolizer::LateInitialize() { Symbolizer::GetOrInit(); }
|
2017-08-02 06:54:51 +08:00
|
|
|
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
void StartReportDeadlySignal() {}
|
|
|
|
void ReportDeadlySignal(const SignalContext &sig, u32 tid,
|
|
|
|
UnwindSignalStackCallbackType unwind,
|
|
|
|
const void *unwind_context) {}
|
|
|
|
|
2018-05-12 07:52:19 +08:00
|
|
|
#if SANITIZER_CAN_SLOW_UNWIND
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
struct UnwindTraceArg {
|
|
|
|
BufferedStackTrace *stack;
|
|
|
|
u32 max_depth;
|
|
|
|
};
|
|
|
|
|
|
|
|
_Unwind_Reason_Code Unwind_Trace(struct _Unwind_Context *ctx, void *param) {
|
|
|
|
UnwindTraceArg *arg = static_cast<UnwindTraceArg *>(param);
|
|
|
|
CHECK_LT(arg->stack->size, arg->max_depth);
|
|
|
|
uptr pc = _Unwind_GetIP(ctx);
|
|
|
|
if (pc < PAGE_SIZE) return _URC_NORMAL_STOP;
|
|
|
|
arg->stack->trace_buffer[arg->stack->size++] = pc;
|
|
|
|
return (arg->stack->size == arg->max_depth ? _URC_NORMAL_STOP
|
|
|
|
: _URC_NO_REASON);
|
|
|
|
}
|
|
|
|
|
2019-02-23 06:03:09 +08:00
|
|
|
void BufferedStackTrace::UnwindSlow(uptr pc, u32 max_depth) {
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
CHECK_GE(max_depth, 2);
|
|
|
|
size = 0;
|
|
|
|
UnwindTraceArg arg = {this, Min(max_depth + 1, kStackTraceMax)};
|
|
|
|
_Unwind_Backtrace(Unwind_Trace, &arg);
|
|
|
|
CHECK_GT(size, 0);
|
|
|
|
// We need to pop a few frames so that pc is on top.
|
|
|
|
uptr to_pop = LocatePcInTrace(pc);
|
|
|
|
// trace_buffer[0] belongs to the current function so we always pop it,
|
|
|
|
// unless there is only 1 frame in the stack trace (1 frame is always better
|
|
|
|
// than 0!).
|
|
|
|
PopStackFrames(Min(to_pop, static_cast<uptr>(1)));
|
|
|
|
trace_buffer[0] = pc;
|
|
|
|
}
|
|
|
|
|
2019-02-23 10:36:23 +08:00
|
|
|
void BufferedStackTrace::UnwindSlow(uptr pc, void *context, u32 max_depth) {
|
|
|
|
CHECK(context);
|
|
|
|
CHECK_GE(max_depth, 2);
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
UNREACHABLE("signal context doesn't exist");
|
|
|
|
}
|
2018-05-12 07:52:19 +08:00
|
|
|
#endif // SANITIZER_CAN_SLOW_UNWIND
|
[sanitizer] Split Symbolizer/StackTraces from core RTSanitizerCommon
Summary:
Host symbolizer & stacktraces related code in their own RT:
`RTSanitizerCommonSymbolizer`, which is "libcdep" by nature. Symbolizer &
stacktraces specific code that used to live in common files is moved to a new
file `sanitizer_symbolizer_report.cc` as is.
The purpose of this is the enforce a separation between code that relies on
symbolization and code that doesn't. This saves the inclusion of spurious code
due to the interface functions with default visibility, and the extra data
associated.
The following sanitizers makefiles were modified & tested locally:
- dfsan: doesn't require the new symbolizer RT
- esan: requires it
- hwasan: requires it
- lsan: requires it
- msan: requires it
- safestack: doesn't require it
- xray: doesn't require it
- tsan: requires it
- ubsan: requires it
- ubsan_minimal: doesn't require it
- scudo: requires it (but not for Fuchsia that has a minimal runtime)
This was tested locally on Linux, Android, Fuchsia.
Reviewers: alekseyshl, eugenis, dberris, kubamracek, vitalybuka, dvyukov, mcgrathr
Reviewed By: alekseyshl, vitalybuka
Subscribers: srhines, kubamracek, mgorny, krytarowski, delcypher, llvm-commits, #sanitizers
Differential Revision: https://reviews.llvm.org/D45457
llvm-svn: 330131
2018-04-17 00:32:19 +08:00
|
|
|
|
2017-08-02 06:54:51 +08:00
|
|
|
} // namespace __sanitizer
|
|
|
|
|
2018-05-12 07:52:19 +08:00
|
|
|
#endif // SANITIZER_SYMBOLIZER_MARKUP
|