How to get assembly output from building with Cargo?
Solution 1
You can use Cargo's cargo rustc
command to send arguments to rustc
directly:
cargo rustc -- --emit asm
ls target/debug/deps/<crate_name>-<hash>.s
For optimized assembly:
cargo rustc --release -- --emit asm
ls target/release/deps/<crate_name>-<hash>.s
If you see multiple <crate_name>-<hash>-<hash>.rcgu.s
files instead of a <crate_name>-<hash>.s
file, disable incremental compilation by setting the environment variable CARGO_INCREMENTAL=0
.
Solution 2
Both existing answers (using cargo rustc
and RUSTFLAGS
) are the best ways to obtain assembly with standard tools. If you find yourself trying to look at assembly fairly often, you might want to consider using the cargo asm
subcommand. After installing it with cargo install cargo-asm
, you can print assembly like:
cargo build --release
cargo asm my_crate::my_function
There are a few things to pay attention to, though:
- Unsure about the path of your function? Just run
cargo asm
and it will list all symbols you can inspect. - You have to
cargo build --release
before trying to look at the assembly, becausecargo asm
(apparently) only looks at the already existing build-artifacts - The code for the function you want to inspect has to be actually generated. For generic functions this means that the function has to be instantiated/monomorphized with a concrete type. If that doesn't happen in your crate, you can always add a dummy function at the top level that does everything you want to inspect the assembly of.
Solution 3
In addition to kennytm's answer, you can also use the RUSTFLAGS
environment variable and use the standard cargo commands:
RUSTFLAGS="--emit asm" cargo build
cat target/debug/deps/project_name-hash.s
Or in release mode (with optimizations):
RUSTFLAGS="--emit asm" cargo build --release
cat target/release/deps/project_name-hash.s
You can pass different values to the --emit
parameter, including (but not limited to):
-
mir
(Rust intermediate representation) -
llvm-ir
(LLVM intermediate representation) -
llvm-bc
(LLVM byte code) -
asm
(assembly)
ideasman42
Updated on July 08, 2022Comments
-
ideasman42 almost 2 years
While I've seen docs on using
rustc
directly to output assembly, having to manually extract commands used by Cargo and edit them to write assembly is tedious.Is there a way to run Cargo that writes out assembly files?
-
davidanderle about 5 yearsIs there a way to change the assembly type? Say I want ARM instead of x86
-
kennytm about 5 years@davidanderle Supply an ARM target to
cargo rustc
, e.g.cargo rustc --target aarch64-apple-ios --release -- --emit asm
. The assembly will be intarget/aarch64-apple-ios/release/deps/*.s
. -
Andru about 5 yearsHow to get intel asm?
-
Amir Pdl almost 5 yearsYou can get intel syntax with
cargo rustc -- --emit asm -C "llvm-args=-x86-asm-syntax=intel"
-
Sebi2020 almost 3 yearsOutput of cargo: error: no such subcommand:
asm
-
Lukas Kalbertodt almost 3 years@Sebi2020 "After installing it with
cargo install cargo-asm
" <- did you do that? -
yume_chan over 2 yearsfor my particular project, adding
--emit asm
argument quadruples the compile time, and the result executable binary is 40% larger. Why does emitting assembly need so much time and why does the output binary file also change?