|
tess 1.0.0
Performance-first tile and path simulation substrate
|
#include <tess/ops/async_work.h>
Public Types | |
| using | WorkFn = AsyncWorkStep (*)(void*, AsyncWorkBudget, T&) |
Public Member Functions | |
| ResumableWorkQueue (const ResumableWorkQueue &)=delete | |
| auto | operator= (const ResumableWorkQueue &) -> ResumableWorkQueue &=delete |
| ResumableWorkQueue (ResumableWorkQueue &&)=delete | |
| auto | operator= (ResumableWorkQueue &&) -> ResumableWorkQueue &=delete |
| void | set_flow_accounting (diagnostics::FlowAccounting *accounting) noexcept |
| void | observe_flow_tick (std::uint64_t tick) noexcept |
| void | reserve_tickets (std::size_t count) |
| template<typename Work> | |
| auto | submit (Work &work, AsyncVersion required_version={}, std::source_location source=std::source_location::current()) -> AsyncTicket |
| auto | submit (void *context, WorkFn work, AsyncVersion required_version={}, std::source_location source=std::source_location::current()) -> AsyncTicket |
| auto | submit_immediate (T value, AsyncVersion result_version={}, std::source_location source=std::source_location::current()) -> AsyncTicket |
| auto | advance (AsyncWorkBudget budget) -> AsyncAdvanceStats |
| auto | state (AsyncTicket ticket) const noexcept -> AsyncResultState |
| auto | result (AsyncTicket ticket) const noexcept -> const T * |
| auto | required_version (AsyncTicket ticket) const noexcept -> AsyncVersion |
| auto | result_version (AsyncTicket ticket) const noexcept -> AsyncVersion |
| auto | source (AsyncTicket ticket) const noexcept -> std::source_location |
| bool | cancel (AsyncTicket ticket) noexcept |
| bool | supersede (AsyncTicket ticket) noexcept |
| Moves a Pending ticket to Superseded; see cancel for false. | |
| bool | fail (AsyncTicket ticket) noexcept |
| Moves a Pending ticket to Failed; see cancel for false. | |
| bool | mark_stale (AsyncTicket ticket) noexcept |
| Moves a Pending ticket to Stale; see cancel for false. | |
| bool | mark_stale_if_version (AsyncTicket ticket, AsyncVersion current) noexcept |
| auto | size () const noexcept -> std::size_t |
| auto | generation () const noexcept -> std::uint64_t |
| void | clear () noexcept |
Owns versioned result slots and advances caller-owned continuations.
This queue is cooperative rather than internally threaded: advance invokes pending work in submission order and bounds both reported items and callback invocations by the supplied deterministic item budget. Queue-state summaries still scan all retained tickets, so callers should clear old batches instead of treating the queue as an unbounded history. A callback and its context are non-owning and must outlive the ticket. Tickets remain observable across calls until clear, which invalidates them by generation. Submission order is strict: with a one-invocation budget, a front continuation that repeatedly reports zero progress can starve later work. Choose a larger invocation budget or terminalize the stalled ticket when fairness is required. Callbacks may inspect the queue but must not mutate it or call advance; those reentrant operations are rejected. Instances are externally synchronized. If a callback throws, the exception propagates and its slot remains Pending; any mutations it already made to the result value remain, and a later advance retries that callback. Earlier completed slots retain their terminal states.
|
inlinenodiscardnoexcept |
Moves a Pending ticket to Cancelled.
The four terminal setters below all answer one question: did this call change the state? false therefore covers three unrelated situations, and the queue already exposes which one applies — state(ticket) returns Unbound for a ticket this queue never issued or has since retired, and the slot's own state for one that was already terminal. A caller that needs to tell them apart asks state(ticket) rather than reading it out of the bool:
|
inlinenodiscardnoexcept |
Reclassifies a settled result as Stale when its version does not match current.
The comparison is equality, not ordering: a result stamped ahead of current is marked stale too.
The state rule is the opposite of the setters above: this one acts on Immediate or Ready slots and refuses Pending ones. false adds a fourth case to their three, and it is the ordinary one — the result's version already equals current, so there is nothing to reclassify. That is a no-change outcome rather than a failure, and a caller that retries on it will retry forever; compare result_version(ticket) if the distinction matters.
|
inlinenoexcept |
Observes one monotonic simulation tick for time accounting.
Call once per tick before that tick's transitions: weights the outstanding inventory by elapsed ticks and refreshes the oldest outstanding age from per-slot submission stamps.
|
inlinenodiscardnoexcept |
Borrows a completed value until queue storage may move.
A later submit or submit_immediate can grow the slot vector and invalidate the pointer. clear also invalidates it. Copy or consume the value before mutating the queue.
|
inlinenoexcept |
Attaches caller-owned flow accounting; null detaches.
Attach or detach only while the queue is empty so the retention identity starts true; the accountant must outlive the attachment.