Skip to content

feat(mpmc): add capacity reservation to bounded senders - #334

Open
jiengup wants to merge 2 commits into
apache:mainfrom
jiengup:add-capacity-reservation-to-bounded-mpmc-senders
Open

jiengup wants to merge 2 commits into
apache:mainfrom
jiengup:add-capacity-reservation-to-bounded-mpmc-senders

Conversation

@jiengup

@jiengup jiengup commented Sep 26, 2026

Copy link
Copy Markdown
Contributor

Summary

Closes #297.

  • Add BoundedSender::reserve, try_reserve, and a borrowed mpmc::Permit so callers can wait for capacity before constructing a message, as requested in #297.
  • Add integration coverage for exact capacity, FIFO grants, cancellation, permit release, and receiver disconnection. Update the API documentation and changelog.
  • Commits since upstream/main: c42f549 (contract tests) and 28a0b14 (implementation).

Design Notes

Queued messages, held permits, and grants to waiting senders share the configured capacity. Sends and reservations receive grants in wait-queue order. Cancelling a granted operation or dropping an unused permit passes its slot to the next waiter. A permit reserves capacity, not message order, and Permit::send returns the value if receivers have disconnected.

Benchmarks

Lower is better. Results compare upstream/main (0f46831) with this branch (28a0b14). Each value is the median of 10 Divan run medians on an Apple M3 Pro with Rust 1.98.0. Microbenchmarks use capacity 1; batch benchmarks use capacity 64 and transfer 16,384 messages per iteration.

Existing bounded MPMC operation upstream/main This branch Time change
try_send → try_recv 11.47 ns 12.12 ns +5.7%
send → recv 15.56 ns 16.73 ns +7.5%
Wake blocked send 33.83 ns 38.39 ns +13.5%
Threads, producers→consumers 1→1 1,178.5 µs 1,164.5 µs −1.2%
Threads 1→8 16,050 µs 15,505 µs −3.4%
Threads 8→1 15,505 µs 14,355 µs −7.4%
Threads 8→8 5,959.5 µs 6,359 µs +6.7%
Tokio, current thread 1→1 268.7 µs 278.5 µs +3.6%
Tokio, current thread 1→8 336.2 µs 339.2 µs +0.9%
Tokio, current thread 8→1 301.3 µs 330.5 µs +9.7%
Tokio, current thread 8→8 307.2 µs 320.0 µs +4.2%
Tokio, 4 workers 1→1 385.0 µs 395.0 µs +2.6%
Tokio, 4 workers 1→8 1,099.5 µs 1,187.5 µs +8.0%
Tokio, 4 workers 8→1 1,095.5 µs 1,262.0 µs +15.2%
Tokio, 4 workers 8→8 1,318.0 µs 1,363.0 µs +3.4%
New reservation operation This branch
try_reserve → Permit::send → try_recv 16.52 ns
reserve → Permit::send → recv 21.56 ns
try_reserve → drop permit 10.17 ns
reserve → drop permit 12.35 ns
try_reserve on a full queue 4.64 ns
Wake blocked reserve, then send 31.40 ns

Existing single-thread round trips are 5.7%–13.5% slower. Batch results vary by topology and include both improvements and regressions; the largest measured regression is 15.2% for Tokio with 4 workers and 8 producers→1 consumer. Reservation-specific cases were measured in a temporary benchmark copy and are not part of this PR.

Validation

  • cargo x test passed, including the bounded MPMC reservation tests and doctests.

@jiengup
jiengup marked this pull request as ready for review September 26, 2026 15:39

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Add capacity reservation to bounded MPMC senders

1 participant