///|
/// QUIC flow control (RFC 9000 ยง4): a `SendFlow` window shrinks with sends and
/// grows only via MAX_DATA; a `RecvFlow` enforces the advertised limit and
/// auto-extends once half a window is consumed; and a connection-wide
/// `QuicSendFlow` bounds each stream by the smaller of its own and the
/// connection window.
///
/// moon run src/examples/23-quic-flow --target native
#coverage.skip
fn main {
run() catch {
e => println("flow error: \{e}")
}
}
///|
fn run() -> Unit raise {
let f = @stream.Credit::new(100UL)
f.spend(30UL)
println(
"send: available=\{f.available().to_string()} sent=\{f.sent().to_string()} blocked=\{f.blocked()}",
)
f.spend(70UL)
println("send: available=\{f.available().to_string()} blocked=\{f.blocked()}")
f.grant(200UL)
println("after MAX_DATA 200: available=\{f.available().to_string()}")
let r = @stream.Window::new(100UL)
r.arrived(60UL)
r.consume(60UL)
println(
"recv: should_extend=\{r.should_grant()} new_limit=\{r.grant().to_string()}",
)
let q = @stream.Budget::new(1000UL, 600UL)
println(
"stream 0 window = \{q.available(0UL).to_string()} (min of conn 1000, stream 600)",
)
q.spend(0UL, 400UL)
q.spend(4UL, 500UL)
println(
"conn available = \{q.connection().to_string()}, stream 0 now bounded to \{q.available(0UL).to_string()}",
)
}