Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

One Frame, Fully Traced

Annotated execution traceRunner to GPU preparationRevision 78002f6

1. The runner owns the outer loop

App::run transfers the built application into a runner. A windowed build normally installs the winit runner; a headless schedule runner can call App::update itself. The runner, not App, defines when another frame begins.

2. Updating advances every sub-application

App::update delegates to SubApps::update. The main world runs first. Each configured sub-app can extract from the main world and run its own schedule.

3. Main expands into ordered schedules

Main::run_main runs startup schedules once, then First, PreUpdate, the fixed-step loop, Update, scene spawning, PostUpdate, and Last. These are coarse semantic barriers; each inner schedule may run many systems in parallel.

4. The schedule prepares an executable graph

Systems have explicit dependency edges and access sets generated from their parameters. MultiThreadedExecutor::init precomputes conflicting-system bitsets. A writer conflicts with readers or writers of the same component or resource; compatible readers do not.

5. Ready compatible systems enter the compute pool

The executor tracks remaining dependencies, ready, running, completed, skipped, and unapplied systems with bitsets. It scopes tasks on ComputeTaskPool and starts systems whose dependencies are satisfied and whose access does not conflict with currently running work. Non-Send and exclusive systems remain on constrained execution paths.

6. Systems receive checked views

A function system’s SystemParam state constructs values such as Query, Res, local state, messages, and Commands. The system sees only the access it declared. Unsafe world access stays inside the scheduler/parameter machinery whose compatibility checks uphold the public borrowing contract.

7. Deferred buffers become world mutations

Systems can enqueue spawns, despawns, component inserts, and custom commands without taking exclusive world access immediately. ApplyDeferred or the schedule’s final apply drains the relevant command queues sequentially into &mut World.

8. Rendering extracts a snapshot

The render sub-app temporarily exposes the main world during ExtractSchedule. Extraction systems copy or move render-relevant components and resources into the render world. Later render schedules prepare assets, queue work, and submit GPU commands without treating the simulation world as GPU-owned state.

The critical invariant is: parallel systems borrow stable storage; structural mutation happens only after those borrows have ended.