Skip to content

Commit 6631a48

Browse files
committed
Use framehop for stack unwinding.
This produces much higher quality stacks than simple frame pointer stack walking: - On arm64, it correctly unwinds "frameless" leaf functions, which don't create a frame entry. Fixes #2. - When sampling happens while the current instruction is in a function prologue or epilogue, this is detected by disassembling the instructions in the vicinity, and a correct stack is built. - For binaries without frame pointers, DWARF-based stackwalking (using the information in the `__eh_frame` section) is used.
1 parent 723c2ef commit 6631a48

File tree

7 files changed

+772
-118
lines changed

7 files changed

+772
-118
lines changed

Readme.md

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,4 +83,8 @@ It can enumerate threads, pause them at will, and read process memory.
8383

8484
We use these primitives to walk the stack and enumerate shared libraries.
8585

86-
At the moment, only frame pointer stack walking is implemented. This is usually fine because keeping frame pointers is the default on macOS.
86+
Stack unwinding uses the [`framehop` crate](https://github.com/mstange/framehop/), which
87+
emits high quality stacks on both x86_64 and arm64. It supports Apple's compact unwind
88+
info format and DWARF CFI, and has heuristics for function prologues and epilogues. As
89+
a result, stacks should always be available, even for binaries that were compiled without
90+
frame pointers.

perfrecord/Cargo.lock

Lines changed: 57 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

perfrecord/Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ crossbeam-channel = "0.5.1"
2525
signal-hook = "0.3.9"
2626
serde_json = "1.0.53"
2727
gecko_profile = { version = "0.2.0", path = "../gecko_profile" }
28+
framehop = "0.2.0"
2829

2930
[profile.release]
3031
debug = true

0 commit comments

Comments
 (0)