feat(host): intra-refresh loss recovery + delivery-anchored latency instrumentation

Intra-refresh (opt-in PUNKTFUNK_INTRA_REFRESH=1 until on-glass
validated): NVENC runs a moving intra band + recovery-point SEI
(gop_size becomes the wave period, ffmpeg forces the real GOP infinite;
default fps/2, PUNKTFUNK_IR_PERIOD_FRAMES overrides; ENOSYS latches a
fallback to IDR-only). Clients request a keyframe on every
FEC-unrecoverable frame, so under intra-refresh the session glue serves
the first request instantly and suppresses the rest for a 2s window —
the wave heals loss without the 20-40x IDR spike cascade. VAAPI/software
keep IDR recovery.

Instrumentation: the wire pts now anchors at the PipeWire delivery stamp
(client-measured latency covers delivery + queue age, not just
submit->glass; repeats/synthetic stamps fall back to now), encode_us
keeps its submit->AU meaning via a separate inflight stamp, and a new
'queue' stage (delivery->submit age of fresh frames) rides
PUNKTFUNK_PERF and the web-console stats samples.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-02 12:06:29 +00:00
parent 315eb6ef7c
commit 21eded8d88
3 changed files with 177 additions and 24 deletions
+6
View File
@@ -154,6 +154,12 @@ pub struct EncoderCaps {
/// the encoder's real chroma disagrees with what was negotiated (the in-band SPS is authoritative
/// for the decoder either way).
pub chroma_444: bool,
/// The encoder runs a periodic **intra-refresh wave** (a moving band of intra blocks +
/// recovery-point SEI, no periodic IDR): FEC-unrecoverable loss self-heals within one wave, so
/// the session glue rate-limits client keyframe requests instead of answering each with a full
/// IDR (the 20-40× frame-size spike that cascades under loss). Linux NVENC sets it when
/// `PUNKTFUNK_INTRA_REFRESH` opened the encoder in that mode; VAAPI/software never do.
pub intra_refresh: bool,
}
/// A hardware encoder. One per session; runs on the encode thread.