perf(runtime): bound scheduler service latency - #1029
Conversation
There was a problem hiding this comment.
Pull request overview
Adds cooperative scheduler service points to prevent persistent local work from starving remote submissions and pending I/O.
Changes:
- Services external work every 256 scheduler dispatches and I/O every 16,384.
- Adds epoll/io_uring regression coverage.
- Documents service guarantees and performance trade-offs.
Reviewed changes
Copilot reviewed 8 out of 8 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
include/elio/runtime/worker_thread.hpp |
Defines service quanta and state. |
include/elio/runtime/scheduler.hpp |
Implements periodic service points. |
tests/unit/test_scheduler.cpp |
Tests service under local backlog. |
README.md |
Advertises bounded cooperative service. |
CHANGELOG.md |
Records the behavioral change. |
wiki/API-Contracts.md |
Updates the scheduler contract. |
wiki/API-Reference.md |
Documents service semantics. |
wiki/Performance-Tuning.md |
Explains bounds and performance trade-offs. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
|
@copilot Please review the current head only. Please do not modify code or push commits. |
Reviewed the current head. The documentation fix is consistent and accurate across all four surfaces — the inline scheduler comments, The implementation at |
Description
Bound scheduler service delay while a worker remains continuously runnable.
Workers now periodically transfer cross-thread submissions and non-blockingly
poll pending I/O instead of waiting for the runnable workload to become idle.
The contract is deliberately cooperative and expressed in completed task
dispatches from the main worker loop, not elapsed time: user code must return to
the scheduler before a service bound can advance. Inline resumptions delivered
as part of one backend completion batch are not separate worker-loop dispatches.
Type of Change
Related Issues
Closes #1028
Changes Made
Core Changes
point every 256 completed worker-loop task dispatches without another hot-path
counter mutation.
worker-loop dispatches while the worker remains runnable; CPU-only workloads
do not make an added I/O syscall.
stealing, shutdown, and resize/drain behavior.
task and ready eventfd I/O, and proves both complete while the local yield
backlog is still running on epoll and io_uring.
API Changes (if applicable)
No signature changes. Scheduler behavior now guarantees cooperative service
points under persistent runnable work, including continuously stolen work:
These are not wall-clock deadlines. A non-suspending coroutine can still occupy
its worker indefinitely, and one backend poll may deliver a completion batch
inline before control returns to the worker loop.
Testing
Unit Tests
Integration Tests
Sanitizer Testing
Test Results
Three interleaved, CPU-pinned Release runs of
scheduler_service_benchmark --trials 40 --backlog-ms 20measured:mainmeanTwo additional interleaved, CPU-pinned
quick_benchmarkruns measured meanyield at 21.35 -> 20.31 ns, scheduler reschedule at 21.18 -> 21.64 ns (+2.2%),
and external submission at 50.15 -> 50.81 ns (+1.3%). These local timings are
evidence for selecting the 256 / 16,384 quanta, not CI thresholds.
Checklist
Code Quality
Documentation
Testing
Compatibility
Performance (if applicable)
Screenshots / Diagrams
Not applicable.
Additional Notes
The separate quanta are intentional. External queue inspection is cheap enough
for a tight bound; a backend poll has measurable cost, so its wider bound keeps
pending-I/O throughput close to the no-service baseline while still eliminating
unbounded starvation.
Reviewer Guidance
Areas requiring special attention:
clearly enough and does not imply a wall-clock guarantee.
poll(0)followed by external-inbox transferinto the owner-LIFO deque.
Questions for reviewers:
run_task()and thereforebypasses these service points?
concrete use case that justifies public configuration now?
Thank you for contributing to Elio! 🎉