Hi all! I decided I would try my hand at implementing C++23’s <stacktrace>
:
https://eel.is/c++draft/stacktrace
To actually implement stacktrace we need a few things: (1) walking the stack and grabbing caller addresses; (2) resolving those to symbols; and (3) resolving them to source file and line number.
For the first one we have libunwind
, so that’s straightfoward enough. (At least I think libcxx can use it, since it’s embedded in libcxxabi
? In my build tree, under build/libcxx/test-suite-install/include
, I see unwind.h
and libunwind.h
.)
But for the others, I’m not sure how to proceed. I can’t seem to find a library that’s #include
-able by libcxx code. Of course there are many places where executable and debug formats are parsed – lldb, lld, ob2yaml, dwarfdump, compiler-rt for -SAN error reporting – but they’re not feasible to include directly, or even copy-pasta under libcxx.
(For fun / educational purposes, I tried creating one supporting only 64-bit OS X, but even that one implementation got nontrivial enough to give me pause. And that’s not including ELF, PE, (both the 32 and 64-bit variants of all these), DWARF, PDB, and the intricacies of those platforms’ dynamic loaders.)
So to that end I’d like to ask the community what the most preferable way forward is. Taking a step back: ideally there would be a library for parsing object files and interpreting debug information. It would preferably be lean and fast, since this may be done at runtime for various reasons, e.g. error reporting and tracing hotspots for performance. Finally, since stacktrace
accepts a caller-provided allocator, there’s probably concern about how (and how much) memory can be allocated during the operation.
I’m very interested to hear what y’all think. Thanks!