-
-
Notifications
You must be signed in to change notification settings - Fork 0
Tasks And Scopes
An async function call creates a task. In the current interpreter, a task is a cold description of work with separate success and failure channels; creating it does not start a background thread.
async fn loadCount() -> Result[Int, Str] {
Ok(3)
}
Calling loadCount() produces Task[Int, Str]. Awaiting it produces its success value or routes
its failure through the enclosing async computation.
export async fn main() -> Result[Int, Str] {
let count = loadCount().await
Ok(count + 1)
}
.await is legal only where async evaluation is permitted. It is not a method looked up on an
ordinary value; it is a control boundary understood by the checker and evaluator.
Calls and arguments retain their ordinary left-to-right evaluation order around that boundary. The present evaluator runs the awaited task deterministically rather than scheduling it in parallel.
export async fn main() -> Result[Int, Str] {
async with scope {
let left = loadCount()
let right = loadCount()
let first = left.await
let second = right.await
Ok(first + second)
}
}
A task created inside async with scope is registered as a child of that scope. Awaiting a child
evaluates it. When control leaves the scope, the interpreter joins registered children that were
not explicitly awaited, in creation order. No child is detached from the lifetime of its scope.
This is a task-tree lifetime rule. It should not be confused with a claim of simultaneous execution: the current implementation has no scheduler, worker pool, native thread runtime, or parallel evaluator.
Task[T, E] records both channels at the type boundary. A child failure is carried by the task and
propagated through the enclosing async evaluation according to the interpreter's task-result
rules. Pudu does not erase it into an untyped exception.
The postfix ? operator applies to Result and Option, not to a task itself. Await first, then
work with the resulting value or the enclosing failure channel dictated by the async signature.
The following are outside the current contract:
-
spawnand detached tasks; - cancellation state, cancellation tokens, or sibling cancellation;
- parallel execution and scheduling fairness;
- native
Send/Syncenforcement; - thread-local storage and synchronization primitives.
The parser reserves parts of the intended surface, but a reserved word is not an execution guarantee. Programs written for the current interpreter should rely only on deterministic task-tree evaluation.
- Modules And Imports
- Values, Bindings, And Blocks
- Types And Inference
- Records, Sums, And Tuples
- Functions Generics And Traits
- Pattern Language
- Control Flow And Patterns
- Iteration And Loops
- Failure And Propagation
- Numbers And Collections
- Sets Maps And Sequences
- Keyed Structures
- Trees And Hierarchies
- Standard Library
- Output Formatting And Testing
- Tasks And Scopes
- Compile-Time Evaluation
- Typed Macros
- References And Unsafe
- Worked Programs