Repository navigation
refactor: create timer resources with the first timer - #404
Conversation
Each scheduler created the timer service in its own constructor, so the timer service was older than the scheduler. It was therefore shut down after the scheduler's drain, and every scheduler shut it down early by hand so its waiters were drained too. The timer service is now created with a context's first timer, like every other service, and attaches itself to the scheduler. Being newer than the scheduler, it shuts down before the drain without help, and the early shutdown is gone. A context that never uses timers creates no timer service, and on IOCP starts no timer thread. The scheduler holds the attached service in an atomic pointer, since the first timer can be made on another thread than the one running the loop, and treats a null one as having no timers. Only the service the context keeps is attached: a concurrent first use can construct a second one that the context discards.
The epoll scheduler created and registered its timerfd in its constructor, so every context paid for a descriptor and two syscalls whether or not it used timers. It is now created when the timer service attaches, with the context's first timer. If creating or registering it fails, the epoll_wait timeout drives the timers instead: the first timer is often made inside a delay or timeout, where a throw could only terminate.
The IOCP scheduler created its waitable timer in its constructor but started the thread that waits on it with the first timer. It now creates both with the first timer, so a context that uses no timers holds neither. A waitable timer that could not be created was never reported: the thread was not started and timers never fired. If the waitable timer or its thread cannot be created now, the completion-port wait timeout drives the timers instead, as on epoll. A thread started by a timer made after shutdown is joined before the completion port closes.
A timer's completion runs on the scheduler, then posted the waiter's continuation, so every expiry and cancellation went through the queue twice. It now dispatches the continuation, as I/O completions do: the waiter resumes at once when its executor's context is running on this thread, and is queued as before otherwise.
|
An automated preview of the documentation is available at https://404.corosio.prtest3.cppalliance.org/index.html If more commits are pushed to the pull request, the docs will rebuild at the same URL. 2026-10-22 14:24:29 UTC |
|
GCOVR code coverage report https://404.corosio.prtest3.cppalliance.org/gcovr/index.html Build time: 2026-10-22 14:39:21 UTC |
Benchmark report
|
| Platform | Backend | Benchmark | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|---|
| macos | kqueue | local_socket_throughput/unidirectional/1048576 | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.26% | 0.39% |
| macos | kqueue | local_socket_throughput/unidirectional/16384 | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.00% | 0.42% |
| macos | kqueue | local_socket_throughput/unidirectional/262144 | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.33% | 0.41% |
| macos | kqueue | local_socket_throughput/unidirectional/65536 | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.24% | 0.41% |
| macos | kqueue | local_socket_throughput/unidirectional_lockless/1048576 | bytes_per_sec | 3.52 GB/s | 3.60 GB/s | 🟢▲ +2.59% | 0.82% |
| macos | kqueue | local_socket_throughput/unidirectional_lockless/16384 | bytes_per_sec | 3.51 GB/s | 3.61 GB/s | 🟢▲ +2.66% | 0.26% |
| macos | kqueue | local_socket_throughput/unidirectional_lockless/262144 | bytes_per_sec | 3.51 GB/s | 3.60 GB/s | 🟢▲ +2.68% | 0.68% |
| macos | kqueue | local_socket_throughput/unidirectional_lockless/65536 | bytes_per_sec | 3.51 GB/s | 3.60 GB/s | 🟢▲ +2.93% | 0.53% |
linux — full results (226 benchmarks, 5 iterations, 1.5s each)
accept_churn
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| burst/10 | epoll | ops_per_sec | 1.91K ops/s | 1.92K ops/s | 🟢▲ +0.45% | 0.36% |
| burst/10 | uring | ops_per_sec | 1.82K ops/s | 1.81K ops/s | 🟢▲ +0.08% | 1.03% |
| burst/100 | epoll | ops_per_sec | 192.8 ops/s | 194.3 ops/s | 🟢▲ +0.38% | 0.97% |
| burst/100 | uring | ops_per_sec | 187.1 ops/s | 186.2 ops/s | 🔴▼ -0.02% | 0.62% |
| burst_lockless/10 | epoll | ops_per_sec | 1.93K ops/s | 1.94K ops/s | 🟢▲ +0.34% | 0.90% |
| burst_lockless/10 | uring | ops_per_sec | 1.94K ops/s | 1.94K ops/s | 🟢▲ +0.07% | 0.23% |
| burst_lockless/100 | epoll | ops_per_sec | 195.2 ops/s | 196.3 ops/s | 🟢▲ +0.12% | 0.89% |
| burst_lockless/100 | uring | ops_per_sec | 200.2 ops/s | 199.8 ops/s | 🔴▼ -0.24% | 0.62% |
| concurrent/1 | epoll | ops_per_sec | 15.23K ops/s | 15.24K ops/s | 🟢▲ +0.31% | 1.22% |
| concurrent/1 | uring | ops_per_sec | 13.64K ops/s | 13.58K ops/s | 🔴▼ -0.16% | 0.78% |
| concurrent/16 | epoll | ops_per_sec | 15.27K ops/s | 15.33K ops/s | 🟢▲ +0.29% | 0.69% |
| concurrent/16 | uring | ops_per_sec | 13.64K ops/s | 13.55K ops/s | 🔴▼ -0.20% | 1.26% |
| concurrent/4 | epoll | ops_per_sec | 15.27K ops/s | 15.30K ops/s | 🟢▲ +0.23% | 0.80% |
| concurrent/4 | uring | ops_per_sec | 13.64K ops/s | 13.55K ops/s | 🔴▼ -0.19% | 1.35% |
| sequential | epoll | ops_per_sec | 15.33K ops/s | 15.24K ops/s | 🟢▲ +0.19% | 1.61% |
| sequential | uring | ops_per_sec | 13.63K ops/s | 13.64K ops/s | 🟢▲ +0.12% | 0.50% |
| sequential_lockless | epoll | ops_per_sec | 15.42K ops/s | 15.39K ops/s | 🟢▲ +0.30% | 1.40% |
| sequential_lockless | uring | ops_per_sec | 14.52K ops/s | 14.55K ops/s | 🟢▲ +0.33% | 0.33% |
fan_out
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent_parents/1 | epoll | ops_per_sec | 3.67K ops/s | 3.68K ops/s | 🟢▲ +0.25% | 0.30% |
| concurrent_parents/1 | uring | ops_per_sec | 3.45K ops/s | 3.44K ops/s | 🟢▲ +0.06% | 1.14% |
| concurrent_parents/16 | epoll | ops_per_sec | 3.58K ops/s | 3.57K ops/s | 🔴▼ -0.32% | 0.20% |
| concurrent_parents/16 | uring | ops_per_sec | 3.32K ops/s | 3.31K ops/s | 🔴▼ -0.13% | 0.32% |
| concurrent_parents/4 | epoll | ops_per_sec | 3.59K ops/s | 3.59K ops/s | 🔴▼ -0.10% | 0.24% |
| concurrent_parents/4 | uring | ops_per_sec | 3.35K ops/s | 3.34K ops/s | 🟢▲ +0.15% | 0.91% |
| concurrent_parents_lockless/1 | epoll | ops_per_sec | 3.73K ops/s | 3.72K ops/s | 🔴▼ -0.06% | 1.06% |
| concurrent_parents_lockless/1 | uring | ops_per_sec | 3.47K ops/s | 3.46K ops/s | 🔴▼ -0.40% | 0.29% |
| concurrent_parents_lockless/16 | epoll | ops_per_sec | 3.62K ops/s | 3.61K ops/s | 🔴▼ -0.05% | 1.01% |
| concurrent_parents_lockless/16 | uring | ops_per_sec | 3.35K ops/s | 3.35K ops/s | 🟢▲ +0.12% | 0.28% |
| concurrent_parents_lockless/4 | epoll | ops_per_sec | 3.64K ops/s | 3.63K ops/s | 🟢▲ +0.07% | 1.04% |
| concurrent_parents_lockless/4 | uring | ops_per_sec | 3.37K ops/s | 3.37K ops/s | ⚪ 0.00% | 0.15% |
| fork_join/1 | epoll | ops_per_sec | 54.38K ops/s | 54.71K ops/s | 🟢▲ +0.25% | 1.05% |
| fork_join/1 | uring | ops_per_sec | 53.24K ops/s | 53.11K ops/s | 🟢▲ +0.05% | 0.42% |
| fork_join/16 | epoll | ops_per_sec | 3.69K ops/s | 3.70K ops/s | 🟢▲ +0.31% | 1.05% |
| fork_join/16 | uring | ops_per_sec | 3.44K ops/s | 3.43K ops/s | 🟢▲ +0.06% | 0.26% |
| fork_join/4 | epoll | ops_per_sec | 14.61K ops/s | 14.66K ops/s | 🟢▲ +0.08% | 1.00% |
| fork_join/4 | uring | ops_per_sec | 13.69K ops/s | 13.71K ops/s | 🟢▲ +0.12% | 0.41% |
| fork_join/64 | epoll | ops_per_sec | 901.3 ops/s | 899.7 ops/s | 🟢▲ +0.16% | 0.92% |
| fork_join/64 | uring | ops_per_sec | 816.6 ops/s | 814.4 ops/s | 🔴▼ -0.07% | 0.60% |
| fork_join_lockless/1 | epoll | ops_per_sec | 55.45K ops/s | 55.53K ops/s | 🟢▲ +0.26% | 1.14% |
| fork_join_lockless/1 | uring | ops_per_sec | 53.88K ops/s | 53.73K ops/s | 🔴▼ -0.33% | 0.27% |
| fork_join_lockless/16 | epoll | ops_per_sec | 3.72K ops/s | 3.74K ops/s | 🟢▲ +0.57% | 1.27% |
| fork_join_lockless/16 | uring | ops_per_sec | 3.47K ops/s | 3.46K ops/s | 🔴▼ -0.25% | 0.20% |
| fork_join_lockless/4 | epoll | ops_per_sec | 14.74K ops/s | 14.87K ops/s | 🟢▲ +0.81% | 1.16% |
| fork_join_lockless/4 | uring | ops_per_sec | 13.85K ops/s | 13.85K ops/s | 🔴▼ -0.12% | 0.30% |
| fork_join_lockless/64 | epoll | ops_per_sec | 908.0 ops/s | 912.6 ops/s | 🟢▲ +0.65% | 1.17% |
| fork_join_lockless/64 | uring | ops_per_sec | 829.7 ops/s | 822.8 ops/s | 🔴▼ -0.47% | 1.17% |
| nested/16 | epoll | ops_per_sec | 889.7 ops/s | 895.7 ops/s | 🟢▲ +0.17% | 1.24% |
| nested/16 | uring | ops_per_sec | 807.4 ops/s | 803.6 ops/s | 🔴▼ -0.05% | 1.13% |
| nested/4 | epoll | ops_per_sec | 3.64K ops/s | 3.68K ops/s | 🟢▲ +0.32% | 1.19% |
| nested/4 | uring | ops_per_sec | 3.41K ops/s | 3.40K ops/s | 🔴▼ -0.04% | 1.19% |
| nested_lockless/16 | epoll | ops_per_sec | 898.8 ops/s | 901.5 ops/s | 🟢▲ +0.11% | 0.37% |
| nested_lockless/16 | uring | ops_per_sec | 820.9 ops/s | 813.9 ops/s | 🔴▼ -0.42% | 1.20% |
| nested_lockless/4 | epoll | ops_per_sec | 3.68K ops/s | 3.72K ops/s | 🟢▲ +0.75% | 1.12% |
| nested_lockless/4 | uring | ops_per_sec | 3.45K ops/s | 3.43K ops/s | 🔴▼ -0.12% | 1.18% |
http_server
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | epoll | ops_per_sec | 54.78K ops/s | 54.94K ops/s | 🟢▲ +0.33% | 0.25% |
| concurrent/1 | uring | ops_per_sec | 53.89K ops/s | 54.04K ops/s | 🟢▲ +0.29% | 1.31% |
| concurrent/16 | epoll | ops_per_sec | 57.53K ops/s | 57.74K ops/s | 🟢▲ +0.34% | 0.17% |
| concurrent/16 | uring | ops_per_sec | 52.95K ops/s | 53.29K ops/s | 🟢▲ +0.06% | 1.31% |
| concurrent/32 | epoll | ops_per_sec | 57.16K ops/s | 57.33K ops/s | 🟢▲ +0.26% | 0.14% |
| concurrent/32 | uring | ops_per_sec | 52.49K ops/s | 52.88K ops/s | 🟢▲ +0.49% | 1.09% |
| concurrent/4 | epoll | ops_per_sec | 56.93K ops/s | 57.10K ops/s | 🟢▲ +0.21% | 0.14% |
| concurrent/4 | uring | ops_per_sec | 53.26K ops/s | 53.53K ops/s | 🟢▲ +0.34% | 1.17% |
| multithread/1 | epoll | ops_per_sec | 57.13K ops/s | 57.20K ops/s | 🟢▲ +0.12% | 0.18% |
| multithread/1 | uring | ops_per_sec | 52.46K ops/s | 52.62K ops/s | 🟢▲ +0.25% | 0.20% |
| multithread/16 | epoll | ops_per_sec | 161.5K ops/s | 160.9K ops/s | 🔴▼ -0.55% | 0.54% |
| multithread/16 | uring | ops_per_sec | 83.10K ops/s | 76.30K ops/s | 🔴▼ -0.16% | 19.55% |
| multithread/2 | epoll | ops_per_sec | 86.88K ops/s | 86.23K ops/s | 🔴▼ -0.71% | 1.33% |
| multithread/2 | uring | ops_per_sec | 91.26K ops/s | 91.51K ops/s | 🟢▲ +0.50% | 0.88% |
| multithread/4 | epoll | ops_per_sec | 159.5K ops/s | 158.8K ops/s | 🔴▼ -0.42% | 0.37% |
| multithread/4 | uring | ops_per_sec | 80.64K ops/s | 80.88K ops/s | 🟢▲ +0.71% | 0.62% |
| multithread/8 | epoll | ops_per_sec | 161.1K ops/s | 160.2K ops/s | 🔴▼ -0.69% | 0.37% |
| multithread/8 | uring | ops_per_sec | 78.39K ops/s | 72.05K ops/s | 🔴▼ -0.11% | 19.45% |
| single_conn | epoll | ops_per_sec | 55.02K ops/s | 55.17K ops/s | 🟢▲ +0.38% | 1.00% |
| single_conn | uring | ops_per_sec | 53.87K ops/s | 54.03K ops/s | 🟢▲ +0.18% | 1.28% |
| single_conn_lockless | epoll | ops_per_sec | 55.57K ops/s | 55.49K ops/s | 🔴▼ -0.02% | 0.45% |
| single_conn_lockless | uring | ops_per_sec | 54.47K ops/s | 54.55K ops/s | 🟢▲ +0.15% | 1.27% |
local_socket_latency
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | epoll | latency_mean_ns | 7.28 µs | 7.24 µs | 🔴▼ -0.02% | 4.69% |
| concurrent/1 | uring | latency_mean_ns | 6.89 µs | 6.61 µs | 🟢▲ +0.30% | 5.37% |
| concurrent/16 | epoll | latency_mean_ns | 110.18 µs | 109.87 µs | 🔴▼ -0.32% | 1.02% |
| concurrent/16 | uring | latency_mean_ns | 108.87 µs | 109.10 µs | 🔴▼ -0.14% | 0.28% |
| concurrent/4 | epoll | latency_mean_ns | 27.82 µs | 27.96 µs | 🔴▼ -0.53% | 1.27% |
| concurrent/4 | uring | latency_mean_ns | 27.37 µs | 26.95 µs | 🟢▲ +2.10% | 1.34% |
| concurrent_lockless/1 | epoll | latency_mean_ns | 7.14 µs | 6.99 µs | 🟢▲ +0.78% | 4.25% |
| concurrent_lockless/1 | uring | latency_mean_ns | 6.69 µs | 6.86 µs | 🔴▼ -0.58% | 5.16% |
| concurrent_lockless/16 | epoll | latency_mean_ns | 108.60 µs | 109.05 µs | 🔴▼ -0.61% | 0.75% |
| concurrent_lockless/16 | uring | latency_mean_ns | 108.36 µs | 108.38 µs | 🔴▼ -0.12% | 0.31% |
| concurrent_lockless/4 | epoll | latency_mean_ns | 27.27 µs | 27.56 µs | 🔴▼ -0.96% | 1.98% |
| concurrent_lockless/4 | uring | latency_mean_ns | 27.10 µs | 27.09 µs | 🔴▼ -0.03% | 1.15% |
| pingpong/1 | epoll | latency_mean_ns | 7.20 µs | 7.31 µs | 🔴▼ -0.43% | 4.29% |
| pingpong/1 | uring | latency_mean_ns | 6.64 µs | 6.54 µs | 🟢▲ +0.34% | 2.69% |
| pingpong/1024 | epoll | latency_mean_ns | 7.57 µs | 7.66 µs | 🔴▼ -0.53% | 4.92% |
| pingpong/1024 | uring | latency_mean_ns | 7.25 µs | 6.98 µs | 🟢▲ +0.11% | 5.10% |
| pingpong/64 | epoll | latency_mean_ns | 7.21 µs | 7.27 µs | 🔴▼ -0.31% | 4.23% |
| pingpong/64 | uring | latency_mean_ns | 6.84 µs | 6.87 µs | 🟢▲ +0.21% | 5.49% |
| pingpong_lockless/1 | epoll | latency_mean_ns | 7.06 µs | 7.39 µs | 🔴▼ -2.21% | 5.41% |
| pingpong_lockless/1 | uring | latency_mean_ns | 6.69 µs | 6.69 µs | 🟢▲ +0.04% | 4.60% |
| pingpong_lockless/1024 | epoll | latency_mean_ns | 7.71 µs | 7.69 µs | 🟢▲ +0.10% | 4.71% |
| pingpong_lockless/1024 | uring | latency_mean_ns | 6.93 µs | 7.23 µs | 🔴▼ -2.17% | 4.93% |
| pingpong_lockless/64 | epoll | latency_mean_ns | 7.10 µs | 7.01 µs | 🟢▲ +0.03% | 3.59% |
| pingpong_lockless/64 | uring | latency_mean_ns | 6.78 µs | 6.69 µs | 🟢▲ +0.39% | 4.36% |
local_socket_throughput
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| bidirectional/1024 | epoll | bytes_per_sec | 305.4 MB/s | 305.0 MB/s | 🟢▲ +0.03% | 1.38% |
| bidirectional/1024 | uring | bytes_per_sec | 300.9 MB/s | 301.0 MB/s | 🔴▼ -0.24% | 0.85% |
| bidirectional/1048576 | epoll | bytes_per_sec | 3.16 GB/s | 3.19 GB/s | 🟢▲ +1.17% | 3.63% |
| bidirectional/1048576 | uring | bytes_per_sec | 3.31 GB/s | 3.25 GB/s | 🔴▼ -2.21% | 2.04% |
| bidirectional/16384 | epoll | bytes_per_sec | 3.05 GB/s | 3.05 GB/s | 🟢▲ +2.19% | 2.42% |
| bidirectional/16384 | uring | bytes_per_sec | 2.41 GB/s | 2.39 GB/s | 🟢▲ +0.39% | 2.79% |
| bidirectional/262144 | epoll | bytes_per_sec | 3.20 GB/s | 3.17 GB/s | 🔴▼ -0.07% | 3.11% |
| bidirectional/262144 | uring | bytes_per_sec | 3.33 GB/s | 3.30 GB/s | 🔴▼ -0.88% | 1.54% |
| bidirectional/4096 | epoll | bytes_per_sec | 999.7 MB/s | 1.00 GB/s | 🔴▼ -0.09% | 1.35% |
| bidirectional/4096 | uring | bytes_per_sec | 989.1 MB/s | 988.3 MB/s | ⚪ 0.00% | 0.66% |
| bidirectional/65536 | epoll | bytes_per_sec | 2.94 GB/s | 2.96 GB/s | 🟢▲ +1.49% | 2.08% |
| bidirectional/65536 | uring | bytes_per_sec | 3.02 GB/s | 3.02 GB/s | 🔴▼ -0.06% | 2.14% |
| bidirectional_lockless/1024 | epoll | bytes_per_sec | 307.7 MB/s | 311.5 MB/s | 🟢▲ +1.69% | 1.29% |
| bidirectional_lockless/1024 | uring | bytes_per_sec | 301.7 MB/s | 301.8 MB/s | ⚪ 0.00% | 0.56% |
| bidirectional_lockless/1048576 | epoll | bytes_per_sec | 3.17 GB/s | 3.20 GB/s | 🟢▲ +2.67% | 3.18% |
| bidirectional_lockless/1048576 | uring | bytes_per_sec | 3.30 GB/s | 3.25 GB/s | 🔴▼ -1.55% | 2.77% |
| bidirectional_lockless/16384 | epoll | bytes_per_sec | 3.06 GB/s | 3.10 GB/s | 🟢▲ +1.65% | 2.05% |
| bidirectional_lockless/16384 | uring | bytes_per_sec | 2.42 GB/s | 2.40 GB/s | 🟢▲ +0.37% | 3.00% |
| bidirectional_lockless/262144 | epoll | bytes_per_sec | 3.21 GB/s | 3.17 GB/s | 🟢▲ +0.31% | 2.81% |
| bidirectional_lockless/262144 | uring | bytes_per_sec | 3.33 GB/s | 3.29 GB/s | 🔴▼ -0.94% | 1.65% |
| bidirectional_lockless/4096 | epoll | bytes_per_sec | 1.00 GB/s | 1.01 GB/s | 🟢▲ +0.62% | 0.98% |
| bidirectional_lockless/4096 | uring | bytes_per_sec | 989.4 MB/s | 990.1 MB/s | 🔴▼ -0.44% | 0.81% |
| bidirectional_lockless/65536 | epoll | bytes_per_sec | 2.95 GB/s | 2.97 GB/s | 🟢▲ +1.60% | 2.21% |
| bidirectional_lockless/65536 | uring | bytes_per_sec | 3.01 GB/s | 3.01 GB/s | 🟢▲ +0.35% | 1.97% |
| unidirectional/1024 | epoll | bytes_per_sec | 298.1 MB/s | 298.9 MB/s | 🟢▲ +0.02% | 2.06% |
| unidirectional/1024 | uring | bytes_per_sec | 302.0 MB/s | 300.9 MB/s | 🔴▼ -0.28% | 0.77% |
| unidirectional/1048576 | epoll | bytes_per_sec | 3.29 GB/s | 3.27 GB/s | 🔴▼ -1.53% | 4.08% |
| unidirectional/1048576 | uring | bytes_per_sec | 3.43 GB/s | 3.39 GB/s | 🔴▼ -1.12% | 3.04% |
| unidirectional/16384 | epoll | bytes_per_sec | 3.07 GB/s | 3.03 GB/s | 🔴▼ -0.59% | 2.84% |
| unidirectional/16384 | uring | bytes_per_sec | 2.65 GB/s | 2.66 GB/s | ⚪ 0.00% | 1.42% |
| unidirectional/262144 | epoll | bytes_per_sec | 3.36 GB/s | 3.21 GB/s | 🔴▼ -1.95% | 5.55% |
| unidirectional/262144 | uring | bytes_per_sec | 3.50 GB/s | 3.43 GB/s | 🔴▼ -0.80% | 1.43% |
| unidirectional/4096 | epoll | bytes_per_sec | 980.1 MB/s | 985.2 MB/s | 🟢▲ +0.14% | 1.27% |
| unidirectional/4096 | uring | bytes_per_sec | 990.1 MB/s | 987.9 MB/s | 🔴▼ -0.31% | 0.64% |
| unidirectional/65536 | epoll | bytes_per_sec | 3.16 GB/s | 3.27 GB/s | 🟢▲ +3.29% | 3.98% |
| unidirectional/65536 | uring | bytes_per_sec | 3.27 GB/s | 3.29 GB/s | 🟢▲ +0.41% | 2.35% |
| unidirectional_lockless/1024 | epoll | bytes_per_sec | 302.0 MB/s | 302.6 MB/s | 🔴▼ -0.15% | 1.18% |
| unidirectional_lockless/1024 | uring | bytes_per_sec | 301.6 MB/s | 302.8 MB/s | 🟢▲ +0.40% | 0.35% |
| unidirectional_lockless/1048576 | epoll | bytes_per_sec | 3.30 GB/s | 3.30 GB/s | 🔴▼ -0.26% | 4.34% |
| unidirectional_lockless/1048576 | uring | bytes_per_sec | 3.42 GB/s | 3.40 GB/s | 🔴▼ -0.73% | 2.70% |
| unidirectional_lockless/16384 | epoll | bytes_per_sec | 3.08 GB/s | 3.07 GB/s | 🔴▼ -0.22% | 2.38% |
| unidirectional_lockless/16384 | uring | bytes_per_sec | 2.66 GB/s | 2.66 GB/s | 🔴▼ -1.00% | 1.42% |
| unidirectional_lockless/262144 | epoll | bytes_per_sec | 3.33 GB/s | 3.32 GB/s | 🟢▲ +0.55% | 1.17% |
| unidirectional_lockless/262144 | uring | bytes_per_sec | 3.47 GB/s | 3.46 GB/s | 🔴▼ -0.14% | 2.12% |
| unidirectional_lockless/4096 | epoll | bytes_per_sec | 984.8 MB/s | 996.2 MB/s | 🟢▲ +0.82% | 0.74% |
| unidirectional_lockless/4096 | uring | bytes_per_sec | 993.9 MB/s | 990.7 MB/s | 🔴▼ -0.27% | 0.64% |
| unidirectional_lockless/65536 | epoll | bytes_per_sec | 3.25 GB/s | 3.29 GB/s | 🟢▲ +0.88% | 1.69% |
| unidirectional_lockless/65536 | uring | bytes_per_sec | 3.26 GB/s | 3.30 GB/s | 🟢▲ +0.80% | 1.24% |
socket_latency
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | epoll | latency_mean_ns | 14.81 µs | 14.83 µs | 🔴▼ -0.10% | 0.32% |
| concurrent/1 | uring | latency_mean_ns | 14.57 µs | 14.59 µs | 🔴▼ -0.29% | 0.21% |
| concurrent/16 | epoll | latency_mean_ns | 232.34 µs | 233.35 µs | 🟢▲ +0.12% | 1.30% |
| concurrent/16 | uring | latency_mean_ns | 235.83 µs | 236.20 µs | 🔴▼ -0.15% | 0.20% |
| concurrent/4 | epoll | latency_mean_ns | 58.04 µs | 58.24 µs | 🔴▼ -0.11% | 1.18% |
| concurrent/4 | uring | latency_mean_ns | 58.55 µs | 58.55 µs | 🟢▲ +0.02% | 0.22% |
| concurrent_lockless/1 | epoll | latency_mean_ns | 14.61 µs | 14.62 µs | 🔴▼ -0.12% | 1.23% |
| concurrent_lockless/1 | uring | latency_mean_ns | 14.50 µs | 14.54 µs | 🟢▲ +0.26% | 1.15% |
| concurrent_lockless/16 | epoll | latency_mean_ns | 230.61 µs | 230.69 µs | 🔴▼ -0.07% | 1.10% |
| concurrent_lockless/16 | uring | latency_mean_ns | 233.84 µs | 234.86 µs | 🔴▼ -0.35% | 1.34% |
| concurrent_lockless/4 | epoll | latency_mean_ns | 57.53 µs | 57.59 µs | 🔴▼ -0.09% | 1.22% |
| concurrent_lockless/4 | uring | latency_mean_ns | 58.10 µs | 58.53 µs | 🔴▼ -0.29% | 1.37% |
| pingpong/1 | epoll | latency_mean_ns | 14.75 µs | 14.75 µs | 🟢▲ +0.01% | 0.23% |
| pingpong/1 | uring | latency_mean_ns | 14.49 µs | 14.51 µs | 🔴▼ -0.15% | 0.30% |
| pingpong/1024 | epoll | latency_mean_ns | 15.09 µs | 15.09 µs | 🔴▼ -0.08% | 0.32% |
| pingpong/1024 | uring | latency_mean_ns | 14.83 µs | 14.80 µs | 🟢▲ +0.15% | 0.33% |
| pingpong/64 | epoll | latency_mean_ns | 14.82 µs | 14.82 µs | 🔴▼ -0.01% | 0.27% |
| pingpong/64 | uring | latency_mean_ns | 14.56 µs | 14.58 µs | 🔴▼ -0.10% | 0.30% |
| pingpong_lockless/1 | epoll | latency_mean_ns | 14.64 µs | 14.62 µs | 🔴▼ -0.01% | 0.30% |
| pingpong_lockless/1 | uring | latency_mean_ns | 14.46 µs | 14.48 µs | 🔴▼ -0.16% | 0.27% |
| pingpong_lockless/1024 | epoll | latency_mean_ns | 14.99 µs | 14.97 µs | 🟢▲ +0.12% | 0.29% |
| pingpong_lockless/1024 | uring | latency_mean_ns | 14.83 µs | 14.81 µs | 🟢▲ +0.04% | 0.32% |
| pingpong_lockless/64 | epoll | latency_mean_ns | 14.71 µs | 14.70 µs | 🟢▲ +0.07% | 0.32% |
| pingpong_lockless/64 | uring | latency_mean_ns | 14.56 µs | 14.55 µs | 🟢▲ +0.12% | 0.32% |
socket_throughput
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| bidirectional/1024 | epoll | bytes_per_sec | 133.5 MB/s | 133.8 MB/s | 🟢▲ +0.31% | 0.26% |
| bidirectional/1024 | uring | bytes_per_sec | 140.0 MB/s | 140.1 MB/s | 🟢▲ +0.11% | 0.23% |
| bidirectional/1048576 | epoll | bytes_per_sec | 3.24 GB/s | 3.25 GB/s | 🟢▲ +0.38% | 2.71% |
| bidirectional/1048576 | uring | bytes_per_sec | 3.23 GB/s | 3.22 GB/s | 🔴▼ -0.46% | 1.18% |
| bidirectional/16384 | epoll | bytes_per_sec | 1.62 GB/s | 1.63 GB/s | 🟢▲ +0.18% | 1.38% |
| bidirectional/16384 | uring | bytes_per_sec | 1.53 GB/s | 1.52 GB/s | 🟢▲ +0.10% | 1.99% |
| bidirectional/262144 | epoll | bytes_per_sec | 3.22 GB/s | 3.19 GB/s | 🔴▼ -0.95% | 0.91% |
| bidirectional/262144 | uring | bytes_per_sec | 3.17 GB/s | 3.18 GB/s | 🔴▼ -0.28% | 1.49% |
| bidirectional/4096 | epoll | bytes_per_sec | 503.8 MB/s | 504.9 MB/s | 🟢▲ +0.06% | 0.54% |
| bidirectional/4096 | uring | bytes_per_sec | 491.4 MB/s | 492.2 MB/s | 🟢▲ +0.30% | 0.52% |
| bidirectional/65536 | epoll | bytes_per_sec | 2.61 GB/s | 2.53 GB/s | 🔴▼ -4.64% | 4.86% |
| bidirectional/65536 | uring | bytes_per_sec | 2.76 GB/s | 2.76 GB/s | 🔴▼ -0.89% | 1.73% |
| bidirectional_lockless/1024 | epoll | bytes_per_sec | 133.8 MB/s | 134.3 MB/s | 🟢▲ +0.35% | 0.39% |
| bidirectional_lockless/1024 | uring | bytes_per_sec | 141.7 MB/s | 140.6 MB/s | 🔴▼ -0.46% | 0.98% |
| bidirectional_lockless/1048576 | epoll | bytes_per_sec | 3.28 GB/s | 3.27 GB/s | 🔴▼ -0.03% | 2.72% |
| bidirectional_lockless/1048576 | uring | bytes_per_sec | 3.21 GB/s | 3.22 GB/s | 🟢▲ +0.34% | 0.64% |
| bidirectional_lockless/16384 | epoll | bytes_per_sec | 1.63 GB/s | 1.63 GB/s | 🔴▼ -0.07% | 1.02% |
| bidirectional_lockless/16384 | uring | bytes_per_sec | 1.55 GB/s | 1.53 GB/s | 🔴▼ -1.03% | 0.81% |
| bidirectional_lockless/262144 | epoll | bytes_per_sec | 3.22 GB/s | 3.19 GB/s | 🔴▼ -0.75% | 1.03% |
| bidirectional_lockless/262144 | uring | bytes_per_sec | 3.13 GB/s | 3.16 GB/s | 🟢▲ +1.44% | 0.89% |
| bidirectional_lockless/4096 | epoll | bytes_per_sec | 507.3 MB/s | 508.4 MB/s | 🟢▲ +0.37% | 0.53% |
| bidirectional_lockless/4096 | uring | bytes_per_sec | 495.4 MB/s | 494.6 MB/s | 🔴▼ -0.32% | 0.75% |
| bidirectional_lockless/65536 | epoll | bytes_per_sec | 2.56 GB/s | 2.57 GB/s | 🔴▼ -0.08% | 2.92% |
| bidirectional_lockless/65536 | uring | bytes_per_sec | 2.74 GB/s | 2.76 GB/s | 🟢▲ +0.49% | 1.76% |
| multithread/2 | epoll | bytes_per_sec | 3.43 GB/s | 3.42 GB/s | 🔴▼ -0.49% | 1.10% |
| multithread/2 | uring | bytes_per_sec | 3.64 GB/s | 3.67 GB/s | 🟢▲ +1.33% | 0.78% |
| multithread/4 | epoll | bytes_per_sec | 4.87 GB/s | 4.86 GB/s | 🔴▼ -0.55% | 0.60% |
| multithread/4 | uring | bytes_per_sec | 5.07 GB/s | 5.07 GB/s | 🔴▼ -0.04% | 0.28% |
| multithread/8 | epoll | bytes_per_sec | 4.96 GB/s | 4.97 GB/s | 🟢▲ +0.23% | 0.13% |
| multithread/8 | uring | bytes_per_sec | 5.13 GB/s | 5.13 GB/s | 🟢▲ +0.23% | 0.28% |
| unidirectional/1024 | epoll | bytes_per_sec | 125.0 MB/s | 125.3 MB/s | 🟢▲ +0.17% | 0.25% |
| unidirectional/1024 | uring | bytes_per_sec | 139.6 MB/s | 138.9 MB/s | 🔴▼ -0.31% | 0.93% |
| unidirectional/1048576 | epoll | bytes_per_sec | 3.38 GB/s | 3.36 GB/s | 🔴▼ -1.18% | 1.07% |
| unidirectional/1048576 | uring | bytes_per_sec | 3.41 GB/s | 3.40 GB/s | 🔴▼ -0.09% | 0.99% |
| unidirectional/16384 | epoll | bytes_per_sec | 1.55 GB/s | 1.55 GB/s | 🟢▲ +0.17% | 1.19% |
| unidirectional/16384 | uring | bytes_per_sec | 1.55 GB/s | 1.54 GB/s | 🔴▼ -0.71% | 1.04% |
| unidirectional/262144 | epoll | bytes_per_sec | 3.32 GB/s | 3.31 GB/s | 🔴▼ -0.03% | 1.30% |
| unidirectional/262144 | uring | bytes_per_sec | 3.18 GB/s | 3.18 GB/s | 🔴▼ -0.03% | 1.58% |
| unidirectional/4096 | epoll | bytes_per_sec | 470.8 MB/s | 472.3 MB/s | 🟢▲ +0.18% | 0.34% |
| unidirectional/4096 | uring | bytes_per_sec | 491.2 MB/s | 488.6 MB/s | 🔴▼ -0.36% | 1.02% |
| unidirectional/65536 | epoll | bytes_per_sec | 2.69 GB/s | 2.69 GB/s | 🔴▼ -0.85% | 4.45% |
| unidirectional/65536 | uring | bytes_per_sec | 2.71 GB/s | 2.70 GB/s | 🟢▲ +0.02% | 1.21% |
| unidirectional_lockless/1024 | epoll | bytes_per_sec | 126.1 MB/s | 125.6 MB/s | 🟢▲ +0.18% | 1.12% |
| unidirectional_lockless/1024 | uring | bytes_per_sec | 139.8 MB/s | 139.1 MB/s | 🔴▼ -0.19% | 1.01% |
| unidirectional_lockless/1048576 | epoll | bytes_per_sec | 3.33 GB/s | 3.35 GB/s | 🟢▲ +1.24% | 1.45% |
| unidirectional_lockless/1048576 | uring | bytes_per_sec | 3.34 GB/s | 3.38 GB/s | 🟢▲ +1.18% | 0.42% |
| unidirectional_lockless/16384 | epoll | bytes_per_sec | 1.56 GB/s | 1.56 GB/s | 🟢▲ +1.42% | 1.92% |
| unidirectional_lockless/16384 | uring | bytes_per_sec | 1.59 GB/s | 1.58 GB/s | 🔴▼ -0.66% | 3.13% |
| unidirectional_lockless/262144 | epoll | bytes_per_sec | 3.33 GB/s | 3.32 GB/s | 🔴▼ -0.16% | 1.25% |
| unidirectional_lockless/262144 | uring | bytes_per_sec | 3.20 GB/s | 3.22 GB/s | 🟢▲ +1.23% | 1.62% |
| unidirectional_lockless/4096 | epoll | bytes_per_sec | 473.2 MB/s | 472.5 MB/s | 🔴▼ -0.01% | 0.65% |
| unidirectional_lockless/4096 | uring | bytes_per_sec | 487.7 MB/s | 492.7 MB/s | 🟢▲ +1.27% | 0.81% |
| unidirectional_lockless/65536 | epoll | bytes_per_sec | 2.70 GB/s | 2.75 GB/s | 🟢▲ +0.40% | 3.35% |
| unidirectional_lockless/65536 | uring | bytes_per_sec | 2.71 GB/s | 2.70 GB/s | 🔴▼ -0.24% | 0.75% |
windows — full results (77 benchmarks, 5 iterations, 1.5s each)
accept_churn
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| burst/10 | iocp | ops_per_sec | 1.57K ops/s | 1.57K ops/s | 🟢▲ +0.13% | 0.34% |
| burst/100 | iocp | ops_per_sec | 157.2 ops/s | 157.2 ops/s | 🔴▼ -0.03% | 0.63% |
| burst_lockless/10 | iocp | ops_per_sec | 1.57K ops/s | 1.58K ops/s | 🟢▲ +0.38% | 0.36% |
| burst_lockless/100 | iocp | ops_per_sec | 159.8 ops/s | 160.6 ops/s | 🟢▲ +0.54% | 0.39% |
| concurrent/1 | iocp | ops_per_sec | 12.50K ops/s | 12.50K ops/s | 🟢▲ +0.02% | 0.22% |
| concurrent/16 | iocp | ops_per_sec | 13.48K ops/s | 13.54K ops/s | 🟢▲ +0.43% | 0.29% |
| concurrent/4 | iocp | ops_per_sec | 13.16K ops/s | 13.18K ops/s | 🟢▲ +0.16% | 0.34% |
| sequential | iocp | ops_per_sec | 12.47K ops/s | 12.51K ops/s | 🟢▲ +0.39% | 0.22% |
| sequential_lockless | iocp | ops_per_sec | 12.51K ops/s | 12.52K ops/s | 🟢▲ +0.10% | 0.25% |
fan_out
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent_parents/1 | iocp | ops_per_sec | 7.37K ops/s | 7.34K ops/s | 🔴▼ -0.35% | 0.32% |
| concurrent_parents/16 | iocp | ops_per_sec | 6.24K ops/s | 6.29K ops/s | 🟢▲ +0.63% | 1.79% |
| concurrent_parents/4 | iocp | ops_per_sec | 6.91K ops/s | 6.90K ops/s | 🔴▼ -0.79% | 1.42% |
| concurrent_parents_lockless/1 | iocp | ops_per_sec | 7.35K ops/s | 7.36K ops/s | 🟢▲ +0.08% | 0.49% |
| concurrent_parents_lockless/16 | iocp | ops_per_sec | 6.42K ops/s | 6.44K ops/s | 🟢▲ +0.56% | 1.34% |
| concurrent_parents_lockless/4 | iocp | ops_per_sec | 6.95K ops/s | 6.96K ops/s | 🔴▼ -0.07% | 0.83% |
| fork_join/1 | iocp | ops_per_sec | 113.0K ops/s | 112.5K ops/s | 🔴▼ -0.67% | 0.47% |
| fork_join/16 | iocp | ops_per_sec | 7.35K ops/s | 7.33K ops/s | 🔴▼ -0.32% | 0.34% |
| fork_join/4 | iocp | ops_per_sec | 29.19K ops/s | 29.13K ops/s | 🔴▼ -0.19% | 0.44% |
| fork_join/64 | iocp | ops_per_sec | 1.73K ops/s | 1.74K ops/s | 🔴▼ -0.19% | 1.55% |
| fork_join_lockless/1 | iocp | ops_per_sec | 112.7K ops/s | 112.7K ops/s | 🟢▲ +0.18% | 0.69% |
| fork_join_lockless/16 | iocp | ops_per_sec | 7.37K ops/s | 7.34K ops/s | 🔴▼ -0.43% | 0.33% |
| fork_join_lockless/4 | iocp | ops_per_sec | 29.18K ops/s | 29.08K ops/s | 🔴▼ -0.58% | 0.55% |
| fork_join_lockless/64 | iocp | ops_per_sec | 1.74K ops/s | 1.74K ops/s | 🔴▼ -0.13% | 1.25% |
| nested/16 | iocp | ops_per_sec | 1.69K ops/s | 1.69K ops/s | 🔴▼ -0.48% | 1.40% |
| nested/4 | iocp | ops_per_sec | 7.16K ops/s | 7.15K ops/s | 🔴▼ -0.21% | 0.36% |
| nested_lockless/16 | iocp | ops_per_sec | 1.69K ops/s | 1.69K ops/s | 🔴▼ -0.24% | 1.38% |
| nested_lockless/4 | iocp | ops_per_sec | 7.16K ops/s | 7.16K ops/s | 🔴▼ -0.02% | 0.30% |
http_server
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | iocp | ops_per_sec | 110.8K ops/s | 111.7K ops/s | 🟢▲ +0.68% | 0.48% |
| concurrent/16 | iocp | ops_per_sec | 108.2K ops/s | 108.4K ops/s | 🔴▼ -0.08% | 0.41% |
| concurrent/32 | iocp | ops_per_sec | 107.6K ops/s | 107.8K ops/s | 🟢▲ +0.10% | 0.44% |
| concurrent/4 | iocp | ops_per_sec | 108.8K ops/s | 108.9K ops/s | 🟢▲ +0.09% | 0.38% |
| multithread/1 | iocp | ops_per_sec | 107.7K ops/s | 107.6K ops/s | 🔴▼ -0.02% | 0.36% |
| multithread/16 | iocp | ops_per_sec | 266.8K ops/s | 269.1K ops/s | 🟢▲ +0.94% | 0.61% |
| multithread/2 | iocp | ops_per_sec | 181.8K ops/s | 182.2K ops/s | 🟢▲ +0.41% | 0.54% |
| multithread/4 | iocp | ops_per_sec | 225.6K ops/s | 226.9K ops/s | 🟢▲ +0.69% | 0.78% |
| multithread/8 | iocp | ops_per_sec | 266.9K ops/s | 268.4K ops/s | 🟢▲ +0.67% | 0.25% |
| single_conn | iocp | ops_per_sec | 110.5K ops/s | 111.5K ops/s | 🟢▲ +0.86% | 0.42% |
| single_conn_lockless | iocp | ops_per_sec | 110.9K ops/s | 111.6K ops/s | 🟢▲ +0.67% | 0.45% |
socket_latency
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | iocp | latency_mean_ns | 7.58 µs | 7.59 µs | 🔴▼ -0.11% | 0.38% |
| concurrent/16 | iocp | latency_mean_ns | 129.40 µs | 128.33 µs | 🟢▲ +0.35% | 3.79% |
| concurrent/4 | iocp | latency_mean_ns | 30.43 µs | 30.42 µs | 🔴▼ -0.15% | 0.57% |
| concurrent_lockless/1 | iocp | latency_mean_ns | 7.57 µs | 7.59 µs | 🔴▼ -0.01% | 0.44% |
| concurrent_lockless/16 | iocp | latency_mean_ns | 121.19 µs | 121.68 µs | 🔴▼ -0.25% | 0.32% |
| concurrent_lockless/4 | iocp | latency_mean_ns | 30.37 µs | 30.43 µs | 🔴▼ -0.25% | 0.24% |
| pingpong/1 | iocp | latency_mean_ns | 7.56 µs | 7.58 µs | 🔴▼ -0.36% | 0.43% |
| pingpong/1024 | iocp | latency_mean_ns | 7.69 µs | 7.71 µs | 🔴▼ -0.34% | 0.32% |
| pingpong/64 | iocp | latency_mean_ns | 7.56 µs | 7.61 µs | 🔴▼ -0.82% | 0.41% |
| pingpong_lockless/1 | iocp | latency_mean_ns | 7.54 µs | 7.57 µs | 🔴▼ -0.41% | 0.42% |
| pingpong_lockless/1024 | iocp | latency_mean_ns | 7.69 µs | 7.70 µs | 🔴▼ -0.14% | 0.37% |
| pingpong_lockless/64 | iocp | latency_mean_ns | 7.58 µs | 7.61 µs | 🔴▼ -0.30% | 0.34% |
socket_throughput
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| bidirectional/1024 | iocp | bytes_per_sec | 280.8 MB/s | 281.6 MB/s | 🟢▲ +0.26% | 0.47% |
| bidirectional/1048576 | iocp | bytes_per_sec | 5.15 GB/s | 5.67 GB/s | 🟢▲ +9.44% | 8.42% |
| bidirectional/16384 | iocp | bytes_per_sec | 3.71 GB/s | 3.77 GB/s | 🟢▲ +0.46% | 3.04% |
| bidirectional/262144 | iocp | bytes_per_sec | 9.34 GB/s | 9.68 GB/s | 🟢▲ +0.82% | 7.37% |
| bidirectional/4096 | iocp | bytes_per_sec | 1.08 GB/s | 1.08 GB/s | 🔴▼ -0.18% | 0.67% |
| bidirectional/65536 | iocp | bytes_per_sec | 8.85 GB/s | 9.16 GB/s | 🟢▲ +0.10% | 6.96% |
| bidirectional_lockless/1024 | iocp | bytes_per_sec | 280.7 MB/s | 282.0 MB/s | 🟢▲ +0.51% | 0.61% |
| bidirectional_lockless/1048576 | iocp | bytes_per_sec | 5.40 GB/s | 5.93 GB/s | 🟢▲ +7.52% | 7.66% |
| bidirectional_lockless/16384 | iocp | bytes_per_sec | 3.76 GB/s | 3.73 GB/s | 🔴▼ -1.20% | 1.12% |
| bidirectional_lockless/262144 | iocp | bytes_per_sec | 9.84 GB/s | 9.79 GB/s | 🔴▼ -0.10% | 1.72% |
| bidirectional_lockless/4096 | iocp | bytes_per_sec | 1.08 GB/s | 1.08 GB/s | 🟢▲ +0.10% | 0.49% |
| bidirectional_lockless/65536 | iocp | bytes_per_sec | 9.11 GB/s | 9.00 GB/s | 🔴▼ -1.61% | 1.39% |
| multithread/2 | iocp | bytes_per_sec | 12.88 GB/s | 12.91 GB/s | 🔴▼ -0.11% | 0.58% |
| multithread/4 | iocp | bytes_per_sec | 17.15 GB/s | 17.15 GB/s | 🔴▼ -0.10% | 0.44% |
| multithread/8 | iocp | bytes_per_sec | 18.32 GB/s | 18.42 GB/s | 🟢▲ +0.46% | 1.15% |
| unidirectional/1024 | iocp | bytes_per_sec | 287.1 MB/s | 285.6 MB/s | 🔴▼ -0.56% | 0.59% |
| unidirectional/1048576 | iocp | bytes_per_sec | 4.47 GB/s | 4.62 GB/s | 🟢▲ +3.60% | 4.60% |
| unidirectional/16384 | iocp | bytes_per_sec | 3.80 GB/s | 3.80 GB/s | 🔴▼ -0.02% | 1.00% |
| unidirectional/262144 | iocp | bytes_per_sec | 9.04 GB/s | 8.96 GB/s | 🔴▼ -2.24% | 5.25% |
| unidirectional/4096 | iocp | bytes_per_sec | 1.10 GB/s | 1.10 GB/s | 🟢▲ +0.03% | 0.47% |
| unidirectional/65536 | iocp | bytes_per_sec | 9.20 GB/s | 9.38 GB/s | 🟢▲ +0.41% | 2.39% |
| unidirectional_lockless/1024 | iocp | bytes_per_sec | 286.8 MB/s | 285.8 MB/s | 🔴▼ -0.33% | 0.52% |
| unidirectional_lockless/1048576 | iocp | bytes_per_sec | 4.86 GB/s | 5.27 GB/s | 🟢▲ +9.41% | 4.66% |
| unidirectional_lockless/16384 | iocp | bytes_per_sec | 3.84 GB/s | 3.79 GB/s | 🔴▼ -1.37% | 0.78% |
| unidirectional_lockless/262144 | iocp | bytes_per_sec | 9.80 GB/s | 9.80 GB/s | 🔴▼ -0.03% | 1.50% |
| unidirectional_lockless/4096 | iocp | bytes_per_sec | 1.10 GB/s | 1.09 GB/s | 🔴▼ -0.60% | 0.50% |
| unidirectional_lockless/65536 | iocp | bytes_per_sec | 9.47 GB/s | 9.35 GB/s | 🟢▲ +0.10% | 2.22% |
macos — full results (113 benchmarks, 5 iterations, 1.5s each)
accept_churn
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| burst/10 | kqueue | ops_per_sec | 4.33K ops/s | 4.35K ops/s | 🟢▲ +0.26% | 0.62% |
| burst/100 | kqueue | ops_per_sec | 442.2 ops/s | 444.9 ops/s | 🟢▲ +0.74% | 0.98% |
| burst_lockless/10 | kqueue | ops_per_sec | 4.37K ops/s | 4.36K ops/s | 🟢▲ +0.14% | 0.90% |
| burst_lockless/100 | kqueue | ops_per_sec | 444.5 ops/s | 447.4 ops/s | 🟢▲ +0.57% | 0.56% |
| concurrent/1 | kqueue | ops_per_sec | 20.05K ops/s | 20.20K ops/s | 🟢▲ +0.36% | 1.11% |
| concurrent/16 | kqueue | ops_per_sec | 35.95K ops/s | 36.21K ops/s | 🟢▲ +0.45% | 1.31% |
| concurrent/4 | kqueue | ops_per_sec | 29.28K ops/s | 29.37K ops/s | 🟢▲ +0.38% | 0.36% |
| sequential | kqueue | ops_per_sec | 20.25K ops/s | 20.42K ops/s | 🟢▲ +0.61% | 0.62% |
| sequential_lockless | kqueue | ops_per_sec | 20.23K ops/s | 20.25K ops/s | 🟢▲ +0.32% | 1.10% |
fan_out
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent_parents/1 | kqueue | ops_per_sec | 8.00K ops/s | 8.10K ops/s | 🟢▲ +1.05% | 0.71% |
| concurrent_parents/16 | kqueue | ops_per_sec | 8.40K ops/s | 6.58K ops/s | 🔴▼ -27.21% | 16.71% |
| concurrent_parents/4 | kqueue | ops_per_sec | 8.10K ops/s | 8.32K ops/s | 🟢▲ +3.22% | 1.29% |
| concurrent_parents_lockless/1 | kqueue | ops_per_sec | 8.11K ops/s | 8.20K ops/s | 🟢▲ +1.79% | 1.22% |
| concurrent_parents_lockless/16 | kqueue | ops_per_sec | 6.98K ops/s | 6.54K ops/s | 🔴▼ -2.95% | 20.92% |
| concurrent_parents_lockless/4 | kqueue | ops_per_sec | 8.32K ops/s | 8.38K ops/s | 🟢▲ +0.13% | 1.63% |
| fork_join/1 | kqueue | ops_per_sec | 48.12K ops/s | 49.02K ops/s | 🟢▲ +1.58% | 0.75% |
| fork_join/16 | kqueue | ops_per_sec | 8.00K ops/s | 8.09K ops/s | 🟢▲ +1.09% | 0.69% |
| fork_join/4 | kqueue | ops_per_sec | 23.63K ops/s | 23.65K ops/s | 🟢▲ +0.10% | 0.64% |
| fork_join/64 | kqueue | ops_per_sec | 2.02K ops/s | 2.05K ops/s | 🟢▲ +1.09% | 2.18% |
| fork_join_lockless/1 | kqueue | ops_per_sec | 49.49K ops/s | 50.13K ops/s | 🟢▲ +1.26% | 0.75% |
| fork_join_lockless/16 | kqueue | ops_per_sec | 8.06K ops/s | 8.15K ops/s | 🟢▲ +1.38% | 0.96% |
| fork_join_lockless/4 | kqueue | ops_per_sec | 23.71K ops/s | 23.74K ops/s | 🟢▲ +0.11% | 0.56% |
| fork_join_lockless/64 | kqueue | ops_per_sec | 2.03K ops/s | 2.07K ops/s | 🟢▲ +1.01% | 2.19% |
| nested/16 | kqueue | ops_per_sec | 1.99K ops/s | 2.05K ops/s | 🟢▲ +3.85% | 1.48% |
| nested/4 | kqueue | ops_per_sec | 7.92K ops/s | 8.00K ops/s | 🟢▲ +0.63% | 0.64% |
| nested_lockless/16 | kqueue | ops_per_sec | 2.01K ops/s | 2.08K ops/s | 🟢▲ +4.09% | 1.48% |
| nested_lockless/4 | kqueue | ops_per_sec | 8.00K ops/s | 8.10K ops/s | 🟢▲ +1.32% | 0.63% |
http_server
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | kqueue | ops_per_sec | 49.12K ops/s | 49.53K ops/s | 🟢▲ +0.80% | 0.22% |
| concurrent/16 | kqueue | ops_per_sec | 129.9K ops/s | 130.4K ops/s | 🟢▲ +0.41% | 0.46% |
| concurrent/32 | kqueue | ops_per_sec | 129.7K ops/s | 129.4K ops/s | 🔴▼ -0.26% | 1.21% |
| concurrent/4 | kqueue | ops_per_sec | 89.15K ops/s | 89.99K ops/s | 🟢▲ +0.81% | 0.96% |
| multithread/1 | kqueue | ops_per_sec | 129.7K ops/s | 129.6K ops/s | 🟢▲ +0.50% | 1.15% |
| multithread/16 | kqueue | ops_per_sec | 132.7K ops/s | 133.1K ops/s | 🟢▲ +0.27% | 0.30% |
| multithread/2 | kqueue | ops_per_sec | 183.9K ops/s | 185.4K ops/s | 🟢▲ +0.58% | 0.99% |
| multithread/4 | kqueue | ops_per_sec | 162.3K ops/s | 161.8K ops/s | 🔴▼ -0.31% | 0.57% |
| multithread/8 | kqueue | ops_per_sec | 139.1K ops/s | 137.4K ops/s | 🔴▼ -1.78% | 1.21% |
| single_conn | kqueue | ops_per_sec | 49.10K ops/s | 49.52K ops/s | 🟢▲ +0.99% | 0.37% |
| single_conn_lockless | kqueue | ops_per_sec | 49.29K ops/s | 49.92K ops/s | 🟢▲ +1.51% | 0.51% |
local_socket_latency
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | kqueue | latency_mean_ns | 1.85 µs | 1.83 µs | 🟢▲ +0.76% | 0.27% |
| concurrent/16 | kqueue | latency_mean_ns | 27.32 µs | 27.16 µs | 🟢▲ +0.73% | 0.32% |
| concurrent/4 | kqueue | latency_mean_ns | 6.86 µs | 6.85 µs | 🟢▲ +0.11% | 0.33% |
| concurrent_lockless/1 | kqueue | latency_mean_ns | 1.84 µs | 1.81 µs | 🟢▲ +1.25% | 0.39% |
| concurrent_lockless/16 | kqueue | latency_mean_ns | 27.12 µs | 27.04 µs | 🟢▲ +0.32% | 0.24% |
| concurrent_lockless/4 | kqueue | latency_mean_ns | 6.82 µs | 6.78 µs | 🟢▲ +0.55% | 0.39% |
| pingpong/1 | kqueue | latency_mean_ns | 1.84 µs | 1.83 µs | 🟢▲ +0.99% | 0.60% |
| pingpong/1024 | kqueue | latency_mean_ns | 1.95 µs | 1.92 µs | 🟢▲ +1.46% | 0.31% |
| pingpong/64 | kqueue | latency_mean_ns | 1.85 µs | 1.83 µs | 🟢▲ +0.87% | 0.34% |
| pingpong_lockless/1 | kqueue | latency_mean_ns | 1.83 µs | 1.82 µs | 🟢▲ +0.81% | 0.29% |
| pingpong_lockless/1024 | kqueue | latency_mean_ns | 1.93 µs | 1.91 µs | 🟢▲ +1.02% | 0.52% |
| pingpong_lockless/64 | kqueue | latency_mean_ns | 1.83 µs | 1.81 µs | 🟢▲ +1.16% | 0.35% |
local_socket_throughput
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| bidirectional/1024 | kqueue | bytes_per_sec | 1.29 GB/s | 1.30 GB/s | 🟢▲ +0.49% | 0.35% |
| bidirectional/1048576 | kqueue | bytes_per_sec | 3.84 GB/s | 3.88 GB/s | 🟢▲ +1.27% | 0.74% |
| bidirectional/16384 | kqueue | bytes_per_sec | 3.84 GB/s | 3.87 GB/s | 🟢▲ +1.13% | 0.48% |
| bidirectional/262144 | kqueue | bytes_per_sec | 3.84 GB/s | 3.88 GB/s | 🟢▲ +1.39% | 0.70% |
| bidirectional/4096 | kqueue | bytes_per_sec | 2.89 GB/s | 2.91 GB/s | 🟢▲ +0.63% | 0.33% |
| bidirectional/65536 | kqueue | bytes_per_sec | 3.87 GB/s | 3.90 GB/s | 🟢▲ +0.61% | 0.47% |
| bidirectional_lockless/1024 | kqueue | bytes_per_sec | 1.30 GB/s | 1.31 GB/s | 🟢▲ +0.52% | 0.43% |
| bidirectional_lockless/1048576 | kqueue | bytes_per_sec | 3.92 GB/s | 3.96 GB/s | 🟢▲ +0.89% | 0.53% |
| bidirectional_lockless/16384 | kqueue | bytes_per_sec | 3.91 GB/s | 3.95 GB/s | 🟢▲ +0.73% | 0.64% |
| bidirectional_lockless/262144 | kqueue | bytes_per_sec | 3.92 GB/s | 3.94 GB/s | 🟢▲ +0.76% | 0.62% |
| bidirectional_lockless/4096 | kqueue | bytes_per_sec | 2.93 GB/s | 2.97 GB/s | 🟢▲ +1.16% | 0.55% |
| bidirectional_lockless/65536 | kqueue | bytes_per_sec | 3.91 GB/s | 3.96 GB/s | 🟢▲ +0.74% | 0.66% |
| unidirectional/1024 | kqueue | bytes_per_sec | 1.27 GB/s | 1.28 GB/s | 🟢▲ +0.64% | 0.43% |
| unidirectional/1048576 | kqueue | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.26% | 0.39% |
| unidirectional/16384 | kqueue | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.00% | 0.42% |
| unidirectional/262144 | kqueue | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.33% | 0.41% |
| unidirectional/4096 | kqueue | bytes_per_sec | 2.67 GB/s | 2.72 GB/s | 🟢▲ +1.70% | 0.42% |
| unidirectional/65536 | kqueue | bytes_per_sec | 3.46 GB/s | 3.53 GB/s | 🟢▲ +2.24% | 0.41% |
| unidirectional_lockless/1024 | kqueue | bytes_per_sec | 1.28 GB/s | 1.29 GB/s | 🟢▲ +0.82% | 0.34% |
| unidirectional_lockless/1048576 | kqueue | bytes_per_sec | 3.52 GB/s | 3.60 GB/s | 🟢▲ +2.59% | 0.82% |
| unidirectional_lockless/16384 | kqueue | bytes_per_sec | 3.51 GB/s | 3.61 GB/s | 🟢▲ +2.66% | 0.26% |
| unidirectional_lockless/262144 | kqueue | bytes_per_sec | 3.51 GB/s | 3.60 GB/s | 🟢▲ +2.68% | 0.68% |
| unidirectional_lockless/4096 | kqueue | bytes_per_sec | 2.71 GB/s | 2.77 GB/s | 🟢▲ +1.91% | 0.69% |
| unidirectional_lockless/65536 | kqueue | bytes_per_sec | 3.51 GB/s | 3.60 GB/s | 🟢▲ +2.93% | 0.53% |
socket_latency
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| concurrent/1 | kqueue | latency_mean_ns | 18.87 µs | 18.82 µs | 🟢▲ +0.42% | 0.36% |
| concurrent/16 | kqueue | latency_mean_ns | 120.65 µs | 120.16 µs | 🟢▲ +0.26% | 0.69% |
| concurrent/4 | kqueue | latency_mean_ns | 43.70 µs | 43.27 µs | 🟢▲ +0.76% | 0.97% |
| concurrent_lockless/1 | kqueue | latency_mean_ns | 18.84 µs | 18.75 µs | 🟢▲ +0.29% | 0.46% |
| concurrent_lockless/16 | kqueue | latency_mean_ns | 120.74 µs | 120.22 µs | 🔴▼ -0.09% | 1.04% |
| concurrent_lockless/4 | kqueue | latency_mean_ns | 43.01 µs | 42.81 µs | 🟢▲ +0.74% | 0.65% |
| pingpong/1 | kqueue | latency_mean_ns | 15.48 µs | 15.39 µs | 🟢▲ +0.20% | 0.79% |
| pingpong/1024 | kqueue | latency_mean_ns | 19.14 µs | 19.06 µs | 🟢▲ +0.41% | 0.41% |
| pingpong/64 | kqueue | latency_mean_ns | 18.91 µs | 18.80 µs | 🟢▲ +0.40% | 0.70% |
| pingpong_lockless/1 | kqueue | latency_mean_ns | 15.39 µs | 15.37 µs | 🟢▲ +0.06% | 0.13% |
| pingpong_lockless/1024 | kqueue | latency_mean_ns | 19.08 µs | 19.03 µs | 🟢▲ +0.38% | 0.41% |
| pingpong_lockless/64 | kqueue | latency_mean_ns | 18.83 µs | 18.71 µs | 🟢▲ +0.54% | 0.24% |
socket_throughput
| Benchmark | Backend | Metric | Base | Head | Δ | Noise |
|---|---|---|---|---|---|---|
| bidirectional/1024 | kqueue | bytes_per_sec | 473.4 MB/s | 473.6 MB/s | 🟢▲ +0.27% | 0.83% |
| bidirectional/1048576 | kqueue | bytes_per_sec | 7.83 GB/s | 7.57 GB/s | 🔴▼ -0.25% | 4.72% |
| bidirectional/16384 | kqueue | bytes_per_sec | 4.53 GB/s | 4.52 GB/s | 🟢▲ +0.45% | 1.63% |
| bidirectional/262144 | kqueue | bytes_per_sec | 8.86 GB/s | 8.71 GB/s | 🔴▼ -0.56% | 2.06% |
| bidirectional/4096 | kqueue | bytes_per_sec | 1.81 GB/s | 1.82 GB/s | 🟢▲ +0.54% | 1.21% |
| bidirectional/65536 | kqueue | bytes_per_sec | 7.70 GB/s | 7.55 GB/s | 🔴▼ -2.23% | 2.09% |
| bidirectional_lockless/1024 | kqueue | bytes_per_sec | 474.5 MB/s | 477.4 MB/s | 🟢▲ +0.65% | 0.40% |
| bidirectional_lockless/1048576 | kqueue | bytes_per_sec | 7.87 GB/s | 7.65 GB/s | 🔴▼ -0.34% | 5.34% |
| bidirectional_lockless/16384 | kqueue | bytes_per_sec | 4.60 GB/s | 4.58 GB/s | 🔴▼ -0.67% | 1.18% |
| bidirectional_lockless/262144 | kqueue | bytes_per_sec | 8.99 GB/s | 8.85 GB/s | 🔴▼ -0.28% | 4.56% |
| bidirectional_lockless/4096 | kqueue | bytes_per_sec | 1.82 GB/s | 1.82 GB/s | 🟢▲ +0.34% | 0.71% |
| bidirectional_lockless/65536 | kqueue | bytes_per_sec | 7.60 GB/s | 7.57 GB/s | 🔴▼ -0.57% | 2.38% |
| multithread/2 | kqueue | bytes_per_sec | 7.64 GB/s | 7.65 GB/s | 🟢▲ +0.76% | 3.88% |
| multithread/4 | kqueue | bytes_per_sec | 3.58 GB/s | 3.70 GB/s | 🟢▲ +3.15% | 6.84% |
| multithread/8 | kqueue | bytes_per_sec | 3.23 GB/s | 3.42 GB/s | 🟢▲ +8.59% | 7.43% |
| unidirectional/1024 | kqueue | bytes_per_sec | 460.3 MB/s | 456.3 MB/s | 🔴▼ -0.85% | 2.39% |
| unidirectional/1048576 | kqueue | bytes_per_sec | 9.11 GB/s | 8.77 GB/s | 🔴▼ -1.20% | 5.78% |
| unidirectional/16384 | kqueue | bytes_per_sec | 4.46 GB/s | 4.45 GB/s | 🔴▼ -1.16% | 1.33% |
| unidirectional/262144 | kqueue | bytes_per_sec | 8.82 GB/s | 8.86 GB/s | 🟢▲ +0.79% | 1.52% |
| unidirectional/4096 | kqueue | bytes_per_sec | 1.80 GB/s | 1.79 GB/s | 🟢▲ +0.80% | 1.53% |
| unidirectional/65536 | kqueue | bytes_per_sec | 7.32 GB/s | 7.41 GB/s | 🔴▼ -0.11% | 2.96% |
| unidirectional_lockless/1024 | kqueue | bytes_per_sec | 476.8 MB/s | 473.7 MB/s | 🔴▼ -0.82% | 2.31% |
| unidirectional_lockless/1048576 | kqueue | bytes_per_sec | 9.13 GB/s | 8.84 GB/s | 🔴▼ -1.76% | 5.47% |
| unidirectional_lockless/16384 | kqueue | bytes_per_sec | 4.44 GB/s | 4.53 GB/s | 🟢▲ +2.57% | 1.86% |
| unidirectional_lockless/262144 | kqueue | bytes_per_sec | 8.92 GB/s | 8.98 GB/s | 🟢▲ +0.28% | 2.10% |
| unidirectional_lockless/4096 | kqueue | bytes_per_sec | 1.81 GB/s | 1.81 GB/s | 🟢▲ +0.13% | 1.75% |
| unidirectional_lockless/65536 | kqueue | bytes_per_sec | 7.40 GB/s | 7.32 GB/s | 🔴▼ -0.96% | 2.42% |
Run & raw JSON artifacts · flag rule: |median Δ| > max(2%, 3×CV of the noisier side) · advisory only
Creates the timer service, epoll's timerfd and IOCP's waitable timer and thread with the context's first timer. A context that never uses timers creates none of them.
delay()ortimeout(), where a throw can only terminate. On IOCP this also fixes timers that silently never fire when the waitable timer cannot be created.Testing
lazy_services: no timer resources before the first timer; concurrent first timers attach exactly one service.delay:testCompletionResumesWaiterInlinefails if completions post.timerfd_createfails on epoll, or whenCreateWaitableTimerWor the thread fails on IOCP.Resolves #402