For embedded/OS development one often writes code for a specific no_std
target, so it makes sense to override the default target by setting the build.target
configuration key. This allows running cargo build
and cargo check
without passing an explicit --target
argument on every invocation. It is even possible to override the runner and then use cargo run
, for example for running the executable in QEMU or flashing it to a connected development board.
The problem is cargo test
. Rust’s test library requires the standard library so we can’t use it in no_std
environments. But what we can do is to run platform independent unit tests on the host system (example). The problem is that cargo uses the specified default target for all subcommands and tries to compile the std-dependent tests for our bare metal system, which of course fails.
To work around this, we need to pass the host target triple as an explicit --target
argument on each invocation of cargo test
. This is problematic since it makes the command platform specific. Users on Linux need to invoke cargo test --target x86_64-unknown-linux-gnu
and users on Windows need to invoke cargo test --target 86_64-pc-windows-msvc
.
I’m not sure what the best solution to this could be. One solution could be to add a new .cargo/config
key that sets the default target only for the build
/check
/run
subcommands, but not for test
/bench
. Alternatively, we could add a --target HOST
alias that at least provides a platform independent way to clear the build.target
default and compile for the host target.
What do you think about this? Maybe there are other/better solutions?
Edit: I experimented a bit with adding a new .cargo/config
key. The implementation was much simpler than I thought, so I opened a PR at https://github.com/rust-lang/cargo/pull/6825.