Files
punktfunk/crates
enricobuehlerandClaude Fable 5 dff63b2a29
windows-host / winget-source (push) Canceled after 0s
windows-host / package (push) Canceled after 2m32s
android / android (push) Canceled after 39s
apple / swift (push) Canceled after 0s
apple / screenshots (push) Canceled after 0s
arch / build-publish (push) Canceled after 34s
ci / rust (push) Canceled after 24s
ci / rust-arm64 (push) Canceled after 24s
ci / bench (push) Canceled after 5s
ci / web (push) Canceled after 24s
ci / docs-site (push) Canceled after 8s
deb / build-publish-client-arm64 (push) Canceled after 0s
deb / build-publish (push) Canceled after 2s
deb / build-publish-host (push) Canceled after 1s
decky / build-publish (push) Canceled after 4s
docker / build-push-arm64cross (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
docker / build-push (., web/Dockerfile, punktfunk-web) (push) Canceled after 5s
docker / build-push (--build-arg FEDORA_VERSION=44, ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm) (push) Canceled after 5s
docker / build-push (ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 5s
docker / build-push (ci, ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 2s
docker / build-push (ci, ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 2s
docker / build-push (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 2s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 1s
fix(encode/nvenc): a visible cursor no longer serializes submit — the blend goes stream-ordered
Report: iPad on a gamescope/NVIDIA 120 fps session capped at ~80 fps with
repeat_fps 0, zero loss, capture 0 µs, ASIC 15 µs — and submit p50 at
10.2 ms, ~81 % of the loop period. Under gamescope the host composites
the live pointer into EVERY frame, and a cursor-bearing frame forced the
CPU-synced submit path: a blocking CUDA copy plus a fence-waited Vulkan
blend, both exposed to the running game's GPU load. The "games hide the
cursor" assumption the gate relied on does not hold under gamescope.

The blend is now stream-ordered end to end. VkSlotBlend exports a
timeline semaphore (VK_KHR_timeline_semaphore + external_semaphore_fd)
into CUDA (cuImportExternalSemaphore, new dlopen entries): the enqueued
copy signals it on the encode thread's copy stream, the blend submission
waits for and advances it on the Vulkan queue, and a CUDA-side wait
orders the encode after the blend on the session's bound IO stream — no
CPU sync anywhere, so cursor frames keep the stream-ordered fast path.
Each ring slot gets its own command buffer + descriptor set (written
once) so several ordered blends can be in flight; cursor-bitmap uploads
and teardown quiesce through the timeline. Drivers without the timeline
export keep the previous CPU-synced blend, and any bring-up or per-frame
failure still degrades to "no cursor", never a dropped frame.

Also: the blocking multi-plane copies (the escalated/pipelined mode and
the non-stream-ordered fallback) now enqueue every plane and pay ONE
stream sync instead of one per plane (NV12 2→1, YUV444 3→1) — each
exposed wait costs scheduling latency under GPU contention, which is
what makes the escalation's blocking copies self-reinforcing.

Verified on the RTX 5070 Ti box (driver 610.43.03): all 12 nvenc_cuda
on-hardware smokes green, including the new
nvenc_cuda_cursor_blend_stream_ordered (6 cursor AUs, all ordered,
across a bitmap-serial flip); host suite 301/301; clippy --all-targets
-D warnings clean; struct layouts of the hand-flattened cuda.h params
asserted in tests.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-07-26 20:05:27 +02:00
..