blob: f5d02aaa3322ccee58c57de9d9d64f615cfdaaf3 (
plain) (
blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
|
#include <library/cpp/yt/backtrace/backtrace.h>
#include <library/cpp/dwarf_backtrace/backtrace.h>
#include <library/cpp/yt/string/raw_formatter.h>
namespace NYT::NBacktrace {
////////////////////////////////////////////////////////////////////////////////
void SymbolizeBacktrace(
TBacktrace backtrace,
const std::function<void(TStringBuf)>& frameCallback)
{
auto error = NDwarf::ResolveBacktrace({backtrace.begin(), backtrace.size()}, [&] (const NDwarf::TLineInfo& info) {
TRawFormatter<1024> formatter;
formatter.AppendNumber(info.Index + 1, 10, 2);
formatter.AppendString(". ");
formatter.AppendString("0x");
const int width = (sizeof(void*) == 8 ? 12 : 8);
// 12 for x86_64 because higher bits are always zeroed.
formatter.AppendNumber(info.Address, 16, width, '0');
formatter.AppendString(" in ");
formatter.AppendString(info.FunctionName);
const int bytesToAppendEstimate = 4 + info.FileName.Size() + 1 + 4 /* who cares about line numbers > 9999 */ + 1;
if (formatter.GetBytesRemaining() < bytesToAppendEstimate) {
const int offset = formatter.GetBytesRemaining() - bytesToAppendEstimate;
if (formatter.GetBytesWritten() + offset >= 0) {
formatter.Advance(offset);
}
}
formatter.AppendString(" at ");
formatter.AppendString(info.FileName);
formatter.AppendChar(':');
formatter.AppendNumber(info.Line);
if (formatter.GetBytesRemaining() == 0) {
formatter.Revert(1);
}
formatter.AppendString("\n");
frameCallback(formatter.GetBuffer());
// Call the callback exactly `frameCount` times,
// even if there are inline functions and one frame resolved to several lines.
// It needs for case when caller uses `frameCount` less than 100 for pretty formatting.
if (info.Index + 1 == std::ssize(backtrace)) {
return NDwarf::EResolving::Break;
}
return NDwarf::EResolving::Continue;
});
if (error) {
TRawFormatter<1024> formatter;
formatter.AppendString("*** Error symbolizing backtrace via Dwarf\n");
formatter.AppendString("*** Code: ");
formatter.AppendNumber(error->Code);
formatter.AppendString("\n");
formatter.AppendString("*** Message: ");
formatter.AppendString(error->Message);
formatter.AppendString("\n");
frameCallback(formatter.GetBuffer());
}
}
////////////////////////////////////////////////////////////////////////////////
} // namespace NYT::NBacktrace
|