embassy-rs/embassy · error
No stm32xx Cargo feature enabled
Error message
No stm32xx Cargo feature enabled
What it means
embassy-stm32's build script generates chip-specific code and must know which STM32 chip to target. It reads env vars starting with CARGO_FEATURE_STM32 (excluding the HRTIM feature); if none exists it panics because no chip feature was enabled.
Solutions
- Enable exactly one chip feature in Cargo.toml, e.g. `embassy-stm32 = { version = "0.1", features = ["stm32wb15cc"] }`
- Run `cargo tree -f '{p} {f}'` to verify the feature list actually reaches embassy-stm32
- If building a support crate on top, re-export or require the user to enable a chip feature
Example fix
# before
embassy-stm32 = "0.1"
# after
embassy-stm32 = { version = "0.1", features = ["stm32h743zi"] } Defensive patterns
Strategy: validation
Validate before calling
# CI check
cargo tree -f '{p} {f}' | grep -E 'embassy-stm32 .*stm32' || echo 'MISSING chip feature' Prevention
- Never add embassy-stm32 without a chip feature
- Keep a template with the chip feature filled in
- Verify builds early in CI rather than locally
When it happens
Trigger: Adding embassy-stm32 as a dependency without any stm32xx chip feature (e.g. `embassy-stm32 = "0.1"` with empty features array) and building.
Common situations: Forgetting the features list when adding the dependency; deleting features while debugging; a template or snippet with a placeholder chip name left unfilled.
Related errors
- Multiple stm32xx Cargo features enabled
- Multiple stm32xx Cargo features enabled
- No mspm0xx/mspsxx Cargo feature enabled
- Multiple mspm0xx/mspsxx Cargo features enabled
- Both 'single-bank' and 'dual-bank' features enabled
AI-assisted analysis of embassy-rs/embassy@463a07b963 (2026-09-10).
Data as JSON: /api/errors/cbf194e67ebb7230.
Report an issue: GitHub.
Appendix: source
Thrown at embassy-stm32/build.rs:58
fn main() {
let mut cfgs = common::CfgSet::new();
common::set_target_cfgs(&mut cfgs);
if std::env::var("CARGO_FEATURE_RT").is_err()
&& std::env::var("CARGO_CFG_TARGET_OS") == Ok("none".to_string())
&& std::env::var("CARGO_CFG_TARGET_ARCH") == Ok("arm".to_string())
{
println!("cargo::warning=Building for bare-metal ARM without `rt` feature: interrupts will loop forever.");
}
let chip_name = match env::vars()
.map(|(a, _)| a)
.filter(|x| x.starts_with("CARGO_FEATURE_STM32") && x != "CARGO_FEATURE_STM32_HRTIM")
.get_one()
{
Ok(x) => x,
Err(GetOneError::None) => panic!("No stm32xx Cargo feature enabled"),
Err(GetOneError::Multiple) => panic!("Multiple stm32xx Cargo features enabled"),
}
.strip_prefix("CARGO_FEATURE_")
.unwrap()
.to_ascii_lowercase();
eprintln!("chip: {chip_name}");
for p in METADATA.peripherals {
if let Some(r) = &p.registers {
// The AES driver enables the peripheral's clock, which the metadata does not
// know for the AES of some chips (STM32L0, L1, F423): no driver there.
if r.kind == "aes" && p.rcc.is_none() {
continue;
}
cfgs.enable(r.kind);
foreach_version_cfg(&mut cfgs, r.kind, r.version, |cfgs, cfg_name| {
cfgs.enable(cfg_name);View on GitHub (pinned to 463a07b963)