Release Recap — June 21 to July 22, 2026 — the 1.0 line settles in
by okdistributeWelcome to the latest release recap for iroh, a modular networking stack in Rust for building direct connections between devices. This one covers June 21 through July 22, 2026: three iroh patch releases, two noq releases, and the first iroh-ffi release since 1.0. It was mostly a month of sanding down edges that shipping 1.0 exposed — connection reliability on real networks, discovery paths that quietly weren't wired up, and a few new capabilities we'd been sitting on.
The top changes
-
Windows connections survive stray ICMP errors.
noq-udpnow sets the Windows ioctls that suppress ICMP errors on receive, so an unrelated ICMP response no longer surfaces as a transient recv failure that can tear down a working socket. This landed in noq 1.0.1 and reached iroh users through the dependency bump in iroh v1.0.1; iroh v1.0.2 added a regression test so it stays fixed. -
Hole punching gets more reliable address discovery. A cluster of fixes in noq 1.0.1 reworked how
OBSERVED_ADDRframes are queued, sent and retransmitted, including a path-specific retransmittable data queue so an observed address for one path can't be lost behind another. Observed addresses are what your peers use to find you, so dropping them meant slower direct connections — or none at all. Shipped to iroh in v1.0.1. -
Switching networks behaves better. Path migration picked up several correctness fixes across noq 1.0.1 and noq 1.1.0: probing packets no longer update
local_ip, pending path responses moved to the packet number space they belong to,PATH_CIDS_BLOCKEDis ignored when it refers to an abandoned path, the loss detection timer is now set when path validation fails, and opening a new path uses the path idle timeout for validation. If you've watched a connection get stuck moving from wifi to cellular, this is the release to be on — it's in iroh as of v1.0.3. -
Two discovery gaps closed. iroh v1.0.3 adds the pkarr resolver to the n0 preset, so the default discovery setup actually resolves through pkarr instead of relying on the rest of the preset to cover for it. And iroh v1.0.1 makes iroh-dns fall back to default nameservers when no JNI context has been initialized, which fixes DNS discovery on Android in embeddings where iroh never gets handed a JNI context.
-
Relay operators can retune rate limits without a restart. iroh v1.0.2 lets you update the per-client rate limit on a running iroh-relay. If you're self-hosting a relay, responding to a traffic spike no longer means a config change plus a bounce that drops every connected client.
-
Throughput fixes in congestion control and receive fairness. noq 1.1.0 fixes CUBIC double-reducing on fast convergence and now preserves the excess congestion window increment, so connections recover their send rate after loss the way CUBIC intends rather than under-shooting. Alongside it, iroh v1.0.2 fixes a counter bug in the fairness logic for receive transport lanes, which is what shares receive capacity across the transports a connection is using. The noq half is in iroh as of v1.0.3.
-
The bindings grow a Mac Catalyst slice and a real endpoint builder. iroh-ffi v1.1.0 shipped without a written changelog, so here's what's in it: the Swift xcframework now includes a Mac Catalyst slice, the endpoint API gained an
EndpointBuilderconstructor plus abind()method so you can configure an endpoint before binding it, error handling across the bindings got more useful, and the release artifacts are now verified as part of publishing. The docs also dropped stale x86_64 macOS claims and now point Go users at iroh-go. -
You can tell when a connection's peer is authenticated. noq 1.1.0 adds
noq::Connection::authenticated, which gives you a clear point to wait for before treating incoming data as trusted — the thing you want when you're accepting 0-RTT data that arrives before the handshake finishes. The same release expands theRecvStream::is_0rttdocs and documents usingSendStream::stoppedto detect 0-RTT rejection, which together make 0-RTT considerably less of a guessing game. -
Kernel receive timestamps on Linux and Android. Also in noq 1.1.0: noq-udp now reads timestamps from the kernel rather than stamping packets when your process gets around to them. RTT estimates — and everything downstream of them, like loss detection and pacing — stop being distorted by time spent waiting in a busy event loop.
-
Relays handle garbage traffic more gracefully. iroh v1.0.2 properly handles invalid relay protocol messages and widened the proptests that check the protocol, and noq 1.1.0 now drops Initial packets silently when saturated instead of making noise about them. Malformed or excessive traffic is a fact of life on a public relay; it should be boring.
-
Quieter, more honest logs. iroh v1.0.1 stopped using span levels above info, iroh v1.0.3 cut a batch of warn-level logs that fired during normal operation, and noq demoted an
error!todebug!and movedsendmsgerrors to debug in 1.1.0. If iroh's logs have been drowning your own at default levels, they should be much calmer now.
Breaking changes
Nothing in this window breaks the 1.0 API — both iroh and noq tightened their semver checks for the stable series this month — but three things behave differently after you upgrade:
-
Connecting with an empty ALPN now returns an error. In iroh v1.0.3, an empty ALPN fails at connect time instead of proceeding into a confusing failure later. If you were passing an empty ALPN anywhere — often by accident, through a config default — give it a real protocol identifier.
-
Oversized DATAGRAMs are rejected instead of accepted. noq 1.1.0 rejects DATAGRAMs larger than the send buffer rather than taking them and failing downstream. Check your datagram sizes against the maximum and handle the error path.
-
UdpStats::iosis deprecated. Also in noq 1.1.0: the count of IO operations can't be measured accurately from that crate, so it's on its way out. Stop reading it if you're graphing it.
Also in this window
- iroh-docs (unreleased): the receive loop no longer aborts when it gets an invalid message. Previously one bad message could take down sync for a whole session; now it's handled and the loop keeps running. Not yet in a release.
- iroh-services (unreleased): net diagnostics now builds for wasm, so the same diagnostics can run in browser targets, and the README picked up usage and setup instructions.
- iroh-ffi (unreleased, after v1.1.0): the Python example now handles ALPNs as bytes directly, and the release workflow gained a dry-run mode plus more artifact verification.
- Server-side connection counters are correct again. Both noq releases fixed
active_connectionsunderflows — one direct, and one caused by aDrainingevent being emitted twice (1.0.1, 1.1.0). Stats reported inDiscardedevents are now updated properly too. - Small CPU wins in noq 1.1.0: overdue timers are handled without polling the async timer, and
ArrayRangeSetuses binary search. There are also patches for Redox targets if you're building there. - Docs that were wrong are now right: keep-alive documentation, the description of QUIC streams, more context around portmapping configuration (iroh v1.0.1) and iroh-relay's system dependencies and build command (iroh v1.0.3).
- A missing item came back. iroh v1.0.1 restored an item that had been dropped, for backwards compatibility with pre-1.0 code — worth knowing if a 1.0 upgrade left you with an unexpected unresolved import.
- iroh v1.0.3 bumped crossbeam-epoch to pick up a fix for an invalid pointer dereference, and dropped
vergenfrom the build scripts, which is one less thing between you and a clean build. - irpc was quiet: semver checks in CI and a docs.rs cfg simplification, nothing user-facing.
- Our hosted service (private repo) moved to iroh 1.0.2 and got dashboard and backend reliability work.
What's next
The shape of this window is the shape we want the 1.0 line to have: steady patch releases, real fixes for things people hit on real networks, no surprises in the API. Multipath and path migration in noq are still where most of the deep work is happening, and it keeps flowing into iroh through the regular dependency bumps.
If something's broken, or a fix here didn't fix it for you, tell us: https://github.com/n0-computer/iroh/issues. See you at the next release.
To get started, take a look at our docs, dive directly into the code, or chat with us in our discord channel.