| 313 | } |
| 314 | |
| 315 | int32_t writeCallstack(WriterI* _writer, uintptr_t* _stack, uint32_t _num, Error* _err) |
| 316 | { |
| 317 | BX_ERROR_SCOPE(_err); |
| 318 | |
| 319 | char demangleBuf[4096]; |
| 320 | size_t demangleLen = BX_COUNTOF(demangleBuf); |
| 321 | |
| 322 | int32_t total = write(_writer, _err, "Callstack (%d):\n", _num); |
| 323 | |
| 324 | constexpr uint32_t kWidth = 40; |
| 325 | total += write(_writer, _err, "\t #: %-*s Line: PC --- Function ---\n", kWidth, "File ---"); |
| 326 | |
| 327 | CallbackData cbData; |
| 328 | |
| 329 | for (uint32_t ii = 0; ii < _num && _err->isOk(); ++ii) |
| 330 | { |
| 331 | backtrace_pcinfo(s_stCtx.state, _stack[ii], backtraceFullCb, NULL, &cbData); |
| 332 | |
| 333 | StringView demangledName; |
| 334 | |
| 335 | if (1 == backtrace_syminfo(s_stCtx.state, _stack[ii], backtraceSymInfoCb, NULL, &cbData) ) |
| 336 | { |
| 337 | demangleLen = BX_COUNTOF(demangleBuf); |
| 338 | int32_t demangleStatus; |
| 339 | abi::__cxa_demangle(cbData.resolvedName.getPtr(), demangleBuf, &demangleLen, &demangleStatus); |
| 340 | |
| 341 | if (0 == demangleStatus) |
| 342 | { |
| 343 | demangledName.set(demangleBuf, demangleLen); |
| 344 | } |
| 345 | else |
| 346 | { |
| 347 | demangledName = cbData.resolvedName; |
| 348 | } |
| 349 | } |
| 350 | else |
| 351 | { |
| 352 | demangledName = "???"; |
| 353 | } |
| 354 | |
| 355 | const StringView fn = strTail(cbData.fileName, kWidth); |
| 356 | |
| 357 | total += write(_writer, _err |
| 358 | , "\t%2d: %-*S % 5d: %p %S\n" |
| 359 | , ii |
| 360 | , kWidth |
| 361 | , &fn |
| 362 | , cbData.line |
| 363 | , _stack[ii] |
| 364 | , &demangledName |
| 365 | ); |
| 366 | |
| 367 | if (0 == strCmp(demangledName, "main", 4) ) |
| 368 | { |
| 369 | if (0 != _num-1-ii) |
| 370 | { |
| 371 | total += write(_writer, _err |
| 372 | , "\t... %d more stack frames below 'main'.\n" |
no test coverage detected