embassy-rs/embassy · error
unwrap of ` ` failed
Error message
unwrap of `{}` failed: {}: {:?} What it means
This is the annotated variant of embassy-net's `unwrap!` macro (non-defmt build): `unwrap!(expr, "message", args...)`. On `Err`/`None` it panics with the stringified expression, the caller-provided context message (via `format_args!`), and the debug-formatted error. The extra message text identifies which internal operation failed.
Solutions
- Use the context message in the panic output to pinpoint the failing `unwrap!(..., "ctx")` call in embassy-net sources.
- Fix the root cause: enlarge socket/resource pools (`StackResources`), ensure sockets are not used after close, and check task wiring.
- Enable the `defmt` feature for richer logging on target hardware.
- Patch the driver locally to propagate the error rather than unwrap if failures are expected in your deployment.
Example fix
// before let slot = unwrap!(self.sockets.get(handle), "get socket slot"); // after let slot = self.sockets.get(handle).ok_or(Error::SocketClosed)?;
Defensive patterns
Strategy: validation
Validate before calling
// Validate resource availability before operations that internally unwrap:
if self.stack_resources_exhausted() { return Err(Error::ConnectionReset); } Type guard
fn socket_is_open(s: &embassy_net::tcp::TcpSocket<'_>) -> bool { !matches!(s.state(), embassy_net::tcp::State::Closed) } Try / catch
// Panic hook that captures the context message plus expression, then triggers a controlled restart of the network stack; panics cannot be caught in no_std firmware.
Prevention
- Right-size StackResources and socket buffers for worst-case load.
- Avoid sharing sockets/channels across tasks without proper ownership.
- Enable defmt logging in development builds.
- Audit embassy-net version upgrades for changed internal invariants.
When it happens
Trigger: Any `unwrap!(expr, "ctx", ...)` call inside embassy-net whose `expr` evaluates to `Err(e)` or `None` — this macro arm (fmt.rs:210) fires only when extra context arguments are supplied at the call site.
Common situations: Embassy firmware running the embassy-net stack where an internal operation (queue send/receive, socket bookkeeping) fails while carrying a context label; typically seen during buffer starvation, closed resources, or race-y socket teardown.
Understand the failure class
Background: "This is a bug, please report it": internal invariant violations, unreachable panics, and SNH errors explained — this error's family across 47 libraries.
Related errors
- unwrap of ` ` failed
- unwrap of ` ` failed
- unwrap of ` ` failed
- ipv4 support not enabled
- unwrap of ` ` failed
AI-assisted analysis of embassy-rs/embassy@463a07b963 (2026-09-10).
Data as JSON: /api/errors/dee26cec36ed494c.
Report an issue: GitHub.
Appendix: source
Thrown at embassy-net/src/fmt.rs:210
};
}
#[cfg(not(feature = "defmt"))]
#[collapse_debuginfo(yes)]
macro_rules! unwrap {
($arg:expr) => {
match $crate::fmt::Try::into_result($arg) {
::core::result::Result::Ok(t) => t,
::core::result::Result::Err(e) => {
::core::panic!("unwrap of `{}` failed: {:?}", ::core::stringify!($arg), e);
}
}
};
($arg:expr, $($msg:expr),+ $(,)? ) => {
match $crate::fmt::Try::into_result($arg) {
::core::result::Result::Ok(t) => t,
::core::result::Result::Err(e) => {
::core::panic!("unwrap of `{}` failed: {}: {:?}", ::core::stringify!($arg), ::core::format_args!($($msg,)*), e);
}
}
}
}
#[derive(Debug, Copy, Clone, Eq, PartialEq)]
pub struct NoneError;
pub trait Try {
type Ok;
type Error;
fn into_result(self) -> Result<Self::Ok, Self::Error>;
}
impl<T> Try for Option<T> {
type Ok = T;
type Error = NoneError;
View on GitHub (pinned to 463a07b963)