Skip to content

Instantly share code, notes, and snippets.

@KodrAus
Last active November 14, 2023 17:19
Show Gist options
  • Save KodrAus/97c92c07a90b1fdd6853654357fd557a to your computer and use it in GitHub Desktop.
Save KodrAus/97c92c07a90b1fdd6853654357fd557a to your computer and use it in GitHub Desktop.
Profiling Rust Applications

Profiling performance

Using perf:

$ perf record -g binary
$ perf script | stackcollapse-perf.pl | rust-unmangle | flamegraph.pl > flame.svg

NOTE: See @GabrielMajeri's comments below about the -g option.

This requires you have flamegraph available in your path. The rust-unmangle script is optional but nice.

Also check out @dlaehnemann's more detailed walkthrough about generating flamegraphs here.

Profiling heap memory

Using valgrind (massif) and massif-visualiser:

$ valgrind --tool=massif binary

Also check out heaptrack, it's similar to massif but more useful out-of-the-box. It also has a nice gui experience:

$ heaptrack binary

Debugging

$ rust-gdb binary

Namespaces are prefixed by the crate name, which is probably also the name of the binary. You can do stuff like:

  • break to set breakpoints
  • print to print a variable
  • step,next,finish to step through calls

Links

@dlaehnemann
Copy link

Jep, thanks to @KodrAus and @GabrielMajeri for your infos on using perf for rust binaries. In the spirit of this gist, I just posted my own more detailed walk-through as a gist after getting flamegraphing to work for my rust project:
https://gist.github.com/dlaehnemann/df31787c41bd50c0fe223df07cf6eb89

Two additions in that walk-through are:

  • using c++filt for demangling (apparently Rust uses some C++ name mangling) further stuff, that rust-unmangle doesn't seem to catch
  • specifying a larger dwarf stack size to accommodate deeper stacks and avoid mis-collapsing of stacks

@hcpl
Copy link

hcpl commented Nov 27, 2018

Please update the example code to:

use std::alloc::System;

#[global_allocator]
static A: System = System;

The current code doesn't compile anymore: https://play.rust-lang.org/?version=nightly&mode=debug&edition=2015&gist=1922d218714af5ccf676452859906b0a.

@HenningTimm
Copy link

@KodrAus Thank you for this post. @hcpl Since Rust 1.32 (January 2019) you no longer need to change the system allocator for heap memory profiling with heaptrack and can use an unmodified binary with heaptrack. I wrote a little tutorial about this: https://gist.github.com/HenningTimm/ab1e5c05867e9c528b38599693d70b35

@hcpl
Copy link

hcpl commented May 14, 2019

Thanks for the notice; you're right, now not even that is needed anymore. And thanks for your tutorial as well, the heaptrack_gui part was new to me!

@anurbol
Copy link

anurbol commented Nov 26, 2019

Is there a similar thing for Windows?

@dlaehnemann
Copy link

Now, there is a cargo subcommand that can be used for flamegraphing Rust code. This should work cross-platform and a little less hacky than the solutions in these gists. Check it out here:
https://github.com/flamegraph-rs/flamegraph

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment