Description
One of the best ways to profile Rust code is with dtrace, as described at https://www.brendangregg.com/FlameGraphs/cpuflamegraphs.html#DTrace . As recently as Rust 1.55.0 that worked fine. But with Rust 1.56.0 the stack just isn't there. Dtrace can only see a single Rust-level stack frame. For example:
Code
With Rust 1.55.0
$ sudo dtrace -x ustackframes=100 -n 'profile-199 /pid == $target && arg1/ {@[ustack()] = count();}' -c "target/debug/deps/test-bc98e078c2bbb61b"
....
libc.so.7`__je_malloc_mutex_prefork+0x124
libc.so.7`__je_arena_prefork7+0x73
libc.so.7`_malloc_prefork+0x15b
libthr.so.3`0x392e4a8c4686
libthr.so.3`_fork+0x18
test-dad15ed382b075cf`nix::unistd::fork::h358225d652a86eab+0xe
test-dad15ed382b075cf`test::test_unistd::test_fork_and_waitpid::hb93c7cdf2b79d680+0x36
test-dad15ed382b075cf`test::test_unistd::test_fork_and_waitpid::_$u7b$$u7b$closure$u7d$$u7d$::h329a121974ff9291+0x11
test-dad15ed382b075cf`core::ops::function::FnOnce::call_once::h2261827bcba63036+0x11
test-dad15ed382b075cf`test::__rust_begin_short_backtrace::hefb7644d11da2ff9+0xa
test-dad15ed382b075cf`test::run_test::run_test_inner::_$u7b$$u7b$closure$u7d$$u7d$::hdaa0fb71aac8d97e+0x2f3
test-dad15ed382b075cf`std::sys_common::backtrace::__rust_begin_short_backtrace::h8bcc057a546c1087+0xce
test-dad15ed382b075cf`core::ops::function::FnOnce::call_once$u7b$$u7b$vtable.shim$u7d$$u7d$::hf7d978d08be459d0+0x6a
test-dad15ed382b075cf`std::sys::unix::thread::Thread::new::thread_start::h6b52ca0eca213387+0x2b
libthr.so.3`0x392e4a8c3a7a
...
With Rust 1.56.0
$ sudo dtrace -x ustackframes=100 -n 'profile-199 /pid == $target && arg1/ {@[ustack()] = count();}' -c "target/debug/deps/test-bc98e078c2bbb61b"
...
libc.so.7`__je_malloc_mutex_prefork+0x124
libc.so.7`__je_arena_prefork7+0x73
libc.so.7`_malloc_prefork+0x15b
libthr.so.3`0x1106cebc6686
libthr.so.3`_fork+0x18
test-b377ad62cc9e0624`nix::unistd::fork::hbf1ed55b658aa870+0xa
0x8
0xcccccccccccccccc
...
Version it worked on
It most recently worked on: Rust 1.55.0
Version with regression
rustc 1.56.0 (09c42c458 2021-10-18)
Workaround
The old behavior can be restored by compiling with RUSTFLAGS="-C force-frame-pointers"
. This flag was added by #48785 , but that was a long time ago. There is nothing in the 1.56.0 release notes, nor any recent commit messages, that mention anything about frame pointers. Was this change therefore accidental? Or could it have been a by product of switching to LLVM 13?