Skip to main content

Crate indicatrix_dispatch

Crate indicatrix_dispatch 

Source
Expand description

Sample-range and work-item scheduling for indicatrix render lanes.

This crate is the scheduler a render coordinator runs: several backends (“lanes”: a joined remote worker, the coordinator’s own CPU/GPU, anything implementing WorkerLane) contribute disjoint absolute sample ranges to ONE image, and their per-chunk radiance sums are merged into one buffer with an exact sample count.

It holds no networking, no GUI and no GPU code. It depends only on the protocol crate (for indicatrix_net::SceneState) and glam, so it can be linked into the worker binary as well as the desktop app.

§Why merging by plain addition is sound

A path sample is identified by (global_pixel_index, absolute_sample_index) and nothing else, on every backend. Any set of backends tracing disjoint sample ranges of the same scene at the same resolution therefore merges by per-pixel addition, divided by the total count. Disjointness is the whole correctness guarantee, and SampleCursor provides it by construction.

§Contents

  • SampleCursor: the atomic claim point handing out disjoint sample ranges.
  • WorkerLane, ChunkResult, SampleRange: what a lane is and returns.
  • RateModel, ChunkPolicy: per-lane throughput calibration and chunk sizing.
  • LanePool: N lanes against one cursor for one image epoch, with failure reclaim, backoff, retirement, cancellation and events.
  • Merger: the deterministic, chunk-start-ordered merge of chunk sums.
  • ItemQueue: whole-item distribution (batches) over N lanes.
  • CancelToken: a cloneable cancellation flag.

Structs§

CancelToken
A cloneable cancellation flag. Every clone observes the same flag, so the owner of a job keeps one clone and hands others to the lanes working on it.
ChunkPolicy
How chunks are sized for a crate::LanePool run.
ChunkResult
What one WorkerLane::render_chunk call produced.
ItemQueue
See the module doc. Shared by reference between the lane threads.
ItemTicket
One claimed item. Hand it back through ItemQueue::complete or ItemQueue::fail; the queue counts it as in flight until then, so dropping a ticket instead would keep idle lanes waiting for it forever.
LanePool
See the module doc. Lanes and their rate models persist across runs, so a caller rendering many images of one scene (a tilt video, successive coordinator jobs) calibrates each lane once.
Merger
See the module doc. Shared by reference between the pool’s lane threads (which add) and any observer thread (which reads snapshot_into / total).
MergerMismatch
LanePool::run_into was handed a Merger built for a different image or range.
PoolConfig
Failure handling and chunk sizing for a LanePool.
PoolOutcome
The result of LanePool::run.
QueueCounts
A snapshot of the queue’s bookkeeping.
RateModel
One lane’s throughput estimate in samples per second. See the module doc.
SampleCursor
See this module’s doc comment. Every method takes &self, so one instance can be shared (by reference inside a thread::scope, or behind an Arc) across every lane’s own thread.
SampleRange
A contiguous absolute sample range [first_sample, first_sample + samples), named like the protocol’s RenderRequest fields.

Enums§

FailOutcome
What ItemQueue::fail did with the item.
MergeError
Why Merger::add refused a chunk. A refused chunk contributes nothing, so the count always matches the buffer.
PoolEvent
Something that happened during a LanePool run. lane is the index LanePool::add_lane returned; LanePool::lane_name names it.
PoolStatus
How a run ended.

Constants§

DEFAULT_MAX_CHUNK_SAMPLES
The worker’s hidden per-request cap (MAX_SAMPLES_PER_REQUEST in indicatrix-worker’s request validation): a chunk sent to a worker must never be larger, or the worker rejects the whole request.

Traits§

WorkerLane
One backend contributing samples to an image: a joined remote worker, a TLS connection to a plain worker, or the local CPU/GPU. The crate::LanePool does not care which.

Functions§

marginal_rate
Throughput in samples per second: delta_samples traced over elapsed. None when nothing was traced or the span is zero, so a degenerate measurement never reaches a RateModel.