017867f211d602fd991397fdadf3451d323f7ee3
3016
Commits
| Author | SHA1 | Message | Date | |
|---|---|---|---|---|
|
|
017867f211 |
fix(ci): the gates the PR run reaches and the boxes could not
ci / rust-arm64 (pull_request) Failing after 1m43s
ci / web (pull_request) Successful in 1m52s
ci / bun-nix (pull_request) Successful in 28s
ci / docs-site (pull_request) Successful in 3m36s
apple / swift (pull_request) Successful in 1m44s
apple / screenshots (pull_request) Skipped
ci / rust (pull_request) Failing after 2m52s
android / android (pull_request) Successful in 6m23s
- adl_emul.rs adl_malloc: panic-free (a reachable expect in an extern fn is an abort — gate B; the Err arm is unreachable, ADL treats null as failure) - punktfunk-host main.rs: reword the carve-out comments so gate C's textual count stays at its baseline (comments count) - clients/linux: forbid(unsafe_code) -> deny with two named allows — the SDL device-filter clear and the spawn test's HOME scoping are unsafe calls in edition 2024 (caught by the aarch64 leg, the only one with glib) |
||
|
|
c68e0be688 |
Merge remote-tracking branch 'origin/main' into worktree-edition-2024
ci / bun-nix (pull_request) Successful in 24s
windows-drivers / probe-and-proto (pull_request) Successful in 34s
ci / docs-site (pull_request) Successful in 1m23s
apple / swift (pull_request) Successful in 1m45s
apple / screenshots (pull_request) Skipped
ci / web (pull_request) Successful in 3m4s
windows-drivers / driver-build (pull_request) Successful in 2m23s
ci / rust (pull_request) Failing after 4m6s
ci / rust-arm64 (pull_request) Failing after 5m5s
windows / build (x86_64-pc-windows-msvc) (pull_request) Failing after 1m54s
nix / flake (pull_request) Successful in 13m36s
windows / build (aarch64-pc-windows-msvc) (pull_request) Failing after 54s
android / android (pull_request) Successful in 15m6s
|
||
|
|
f373dffb5e |
chore: migrate the main workspace and pf-vkhdr-layer to edition 2024 (WP20)
The safety half of the rust-safety programme's §8.4: `std::env::set_var`/`remove_var` are
`unsafe fn` in edition 2024, converting the class of bug the programme found the hard way
(the
|
||
|
|
28b6633058 |
Merge pull request 'feat(display): edid_lock policy axis — pin AMD connector EDID emulation while streaming' (#176) from worktree-edid-lock-toggle into main
audit / bun-audit (sdk) (push) Successful in 25s
audit / bun-audit (plugin-kit) (push) Successful in 26s
audit / bun-audit (web) (push) Successful in 23s
audit / docs-site-audit (push) Successful in 22s
audit / pnpm-audit (push) Successful in 13s
apple / swift (push) Successful in 1m36s
audit / license-gate (push) Successful in 4m52s
ci / bun-nix (push) Successful in 23s
audit / miri (push) Successful in 5m50s
apple / screenshots (push) Successful in 5m56s
ci / web (push) Successful in 3m49s
ci / rust-arm64 (push) Successful in 4m6s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 16s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 23s
ci / docs-site (push) Successful in 3m50s
audit / c-abi-asan (push) Successful in 5m55s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 16s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 15s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 15s
deb / build-publish-client-arm64 (push) Successful in 2m56s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 2m38s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 2m54s
audit / cargo-audit (push) Successful in 36s
deb / build-publish-host (push) Successful in 8m38s
release / apple (push) Successful in 9m55s
deb / build-publish (push) Successful in 6m27s
docker / deploy-docs (push) Successful in 37s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Failing after 14m53s
docker / builders-arm64cross (push) Skipped
android / android (push) Successful in 15m34s
ci / rust (push) Failing after 14m34s
flatpak / build-publish (push) Successful in 20m11s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 20m1s
nix / flake (push) Failing after 20m46s
arch / build-publish (push) Successful in 21m46s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 19m45s
windows-host / package (push) Successful in 38m25s
windows-host / winget-source (push) Skipped
windows-host / canary-manifest (push) Successful in 29s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 5m20s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 3m17s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 1m45s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 4m20s
|
||
|
|
c58217e403 |
Merge pull request 'fix(client): stop the double-arm race re-freezing RFI-healed streams' (#174) from worktree-gate-double-arm-fix into main
android / android (push) Canceled after 0s
apple / swift (push) Canceled after 0s
apple / screenshots (push) Canceled after 0s
arch / build-publish (push) Canceled after 0s
audit / cargo-audit (push) Canceled after 0s
audit / bun-audit (plugin-kit) (push) Canceled after 0s
audit / bun-audit (sdk) (push) Canceled after 0s
audit / bun-audit (web) (push) Canceled after 0s
audit / docs-site-audit (push) Canceled after 0s
audit / pnpm-audit (push) Canceled after 0s
audit / license-gate (push) Canceled after 0s
audit / miri (push) Canceled after 0s
audit / c-abi-asan (push) Canceled after 0s
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 0s
ci / web (push) Canceled after 0s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
deb / build-publish (push) Canceled after 0s
deb / build-publish-host (push) Canceled after 0s
deb / build-publish-client-arm64 (push) Canceled after 0s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 0s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
flatpak / build-publish (push) Canceled after 0s
nix / flake (push) Canceled after 0s
release / apple (push) Canceled after 0s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 0s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 0s
windows-host / package (push) Canceled after 0s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Canceled after 0s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Canceled after 0s
windows / build (aarch64-pc-windows-msvc) (push) Canceled after 0s
windows / build (x86_64-pc-windows-msvc) (push) Canceled after 0s
|
||
|
|
23f9b1130e |
Merge pull request 'Black-stream fixes: CCD restore snapshot pruning, iOS silent-black recovery, devnode journal retention' (#175) from worktree-black-stream-fixes into main
android / android (push) Canceled after 0s
apple / swift (push) Canceled after 0s
apple / screenshots (push) Canceled after 0s
arch / build-publish (push) Canceled after 0s
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 0s
ci / web (push) Canceled after 0s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
deb / build-publish (push) Canceled after 0s
deb / build-publish-host (push) Canceled after 0s
deb / build-publish-client-arm64 (push) Canceled after 0s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 0s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
release / apple (push) Canceled after 24s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 0s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 0s
windows-host / package (push) Canceled after 0s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
|
||
|
|
c2c71f0ac5 |
Merge pull request 'fix(vdisplay/driver,pf-frame): no punktfunk process holds REALTIME GPU priority by default' (#173) from worktree-rt-gpu-priority-defaults into main
android / android (push) Canceled after 0s
apple / swift (push) Canceled after 0s
apple / screenshots (push) Canceled after 0s
arch / build-publish (push) Canceled after 0s
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 0s
ci / web (push) Canceled after 0s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
deb / build-publish (push) Canceled after 0s
deb / build-publish-host (push) Canceled after 0s
deb / build-publish-client-arm64 (push) Canceled after 0s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 0s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 0s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 0s
windows-host / package (push) Canceled after 0s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
windows-drivers / probe-and-proto (push) Successful in 24s
windows-drivers / driver-build (push) Successful in 1m54s
|
||
|
|
6a506a8fa9 |
fix(vdisplay/driver,pf-frame): no punktfunk process holds REALTIME GPU priority by default
windows-drivers / probe-and-proto (pull_request) Successful in 30s
ci / bun-nix (pull_request) Successful in 56s
ci / docs-site (pull_request) Successful in 1m16s
ci / web (pull_request) Successful in 1m17s
ci / rust-arm64 (pull_request) Successful in 1m31s
windows-drivers / driver-build (pull_request) Successful in 1m47s
android / android (pull_request) Successful in 4m40s
ci / rust (pull_request) Successful in 9m54s
apple / swift (pull_request) Failing after 13m27s
apple / screenshots (pull_request) Skipped
The RX 9070 XT field A/B (2026-08-11/12 logs) convicted BOTH of our REALTIME GPU-scheduling levers of generating the metronomic capture-stall class the stall program has chased for weeks — compose-silence holes of 150-800 ms in which ETW shows NO process presenting while the GPU stays responsive: - the vdisplay driver's IddCxSetRealtimeGPUPriority raise beat at ~1.75-1.78 s (PFVD_NO_RT_GPU=1 alone removed that metronome: ~0.35 stalls/s metronomic -> 10 sparse aperiodic over 3.9 min); - the host auto-gate's HIGH->REALTIME upgrade (pf-frame dxgi.rs, T2.3) beat at ~3.58 s in the AV1 sessions where it promoted (vram_pct=1, 12:59:26); pinning PUNKTFUNK_GPU_PRIORITY_CLASS=high removed that residual too (13:45 session: zero metronomic, stall rate at the clean-run baseline). Neither period matches any punktfunk clock: the full periodic-actor census (driver: event-paced drain + 16 ms E_PENDING wait, 33 ms cursor poll, 3 s watchdog reap; host: 250 ms descriptor poll, 5/50/100 ms probes + ~2 s scanline retarget, 2 s VRAM gate, 2 s exclusive re-assert, 3.33 s pinger, 1 s stats, ~1 Hz phase-lock, fps/2 LTR marks) has nothing in the 1.69-2.29 s band, and every host-side actor ran unchanged in the A/B that killed the fast metronome. The periodicity is emergent from holding an unreachable-priority queue against the WDDM scheduler on this AMD family (the period even differs by which of our processes holds REALTIME); it is not a punktfunk cadence being amplified, so there is nothing punktfunk-periodic to fix - the fix is to stop holding REALTIME by default, which is also canonical parity (no shipping IDD raises it, and HIGH was the class that delivered the original Sunshine-parity encode win). - Driver: PFVD_NO_RT_GPU (default-ON, opt-OUT) becomes the PFVD_RT_GPU ladder, default OFF on every vendor: unset = no raise (canonical IDD behavior); =thread = SetGPUThreadPriority(+7), a graduated in-band middle rung for field A/B (not default: unmeasured here, and the host measured the same call as "no help" for its own starvation case); anything else = the old REALTIME DDI. PFVD_NO_RT_GPU stays recognized and WINS over the opt-in, so the field boxes that carry it through the default-ON era keep meaning OFF. Both directions remain A/B-able without a rebuild (machine env + device restart). The CPU half of the original branch-2 hardening (MMCSS / TIME_CRITICAL) is untouched - it addressed the delivery holes that were actually observed. - Host: PUNKTFUNK_GPU_PRIORITY_CLASS default auto -> high. `auto` (the gated REALTIME upgrade) stays available as an explicit opt-in, `realtime` still pins; unrecognized values now land on the HIGH default instead of silently opting into the gate - a typo must not buy the hazard. The VRAM/HAGS gate machinery is unchanged for `auto`; it guards the NVENC-hang hazard but cannot see this one. - stall.rs: the no-OS-event METRONOMIC warning now carries rt_gpu_driver / rt_gpu_host fields (the machine-env state of both levers) and names clearing them as the FIRST cure, ahead of the display-hardware suspects - a field log self-answers the triage question this program just spent a week on. No console policy axis for the driver knob: the lever is default-safe now, the driver reads config at WUDFHost scope where machine env already matches the device-restart lifecycle, and a policy axis would need pf-driver-proto churn (or a device-key registry write) for an experimental lever that only exists to be A/B-ed. If the `thread` rung ever proves out as a default-worthy raise, that is the moment to revisit. |
||
|
|
712ee935d6 |
fix(win-display): a failed devnode re-enable must keep its crash-journal entry
ci / rust-arm64 (pull_request) Successful in 1m36s
ci / docs-site (pull_request) Successful in 1m22s
apple / swift (pull_request) Successful in 1m43s
apple / screenshots (pull_request) Skipped
ci / bun-nix (pull_request) Successful in 3m34s
ci / web (pull_request) Successful in 4m2s
android / android (pull_request) Successful in 4m13s
ci / rust (pull_request) Successful in 5m56s
enable_instances cleared every requested id from the pnp-disabled-monitors journal unconditionally — a mid-life re-enable failure erased its own crash-recovery entry, so neither the running host nor the next start would ever retry, leaving the operator's monitor disabled (invisible to Windows and every display listing) until a manual Device Manager fix. Field 2026-08-12 (Android-client host running the pnp_disable_monitors axis): displays gone from the client after 2-3 sessions, only a full host restart bringing them back — the restart path only works while the journal still has the entry. Only successfully re-enabled ids clear now; failures stay journaled (and are logged with the consequence) so startup_recover retries them. |
||
|
|
a2aa0a5f97 |
fix(apple): never sit black AND silent while the video format is unseeded
Both pumps (Stage2Pipeline + the stage-1 StreamPump) dropped every AU in a silent guard while 'format' was nil — the opening IDR's parameter sets never arrived or never parsed, and under the host's infinite GOP nothing re-delivers them unless the client asks. Field 2026-08-12 (iOS, H265): sessions decoding nothing, requesting nothing, host streaming perfectly — a black stream with zero recovery requests, randomly self-healing only when some later event produced a fresh IDR. While format is nil after the first received AU, the pumps now set awaitingIDR (routing through the existing 100 ms-throttled recovery.request()) and log the state once, so a lost/unparsed opening IDR converts to a normal recovery round-trip instead of a permanent silent black. |
||
|
|
d6b9862f1e |
fix(win-display): prune unplugged targets from the CCD restore snapshot
A monitor unplugged mid-session left the teardown replaying a snapshot whose paths reference an absent target — SetDisplayConfig rejects the WHOLE array with 0x57 ERROR_INVALID_PARAMETER, nothing restores, the desk stays dark, and the next session snapshots the wreckage (the poisoned-snapshot chain; field 2026-08-12: rc=0x57 across a mid-session unplug, then sessions flipping between black and working at random, incl. one that genuinely encoded black). The restore now prunes the snapshot against a live QDC_ALL_PATHS availability sweep before replaying: stale paths drop, the mode table is rebuilt with only the entries the survivors reference (an orphaned mode entry is itself an 0x57), and an empty survivor set skips the apply so the dark-desk backstop decides. Verbatim behavior is unchanged when everything is still attached or when the availability query itself fails. |
||
|
|
f4e39a442b |
feat(display): edid_lock policy axis — pin AMD connector EDID emulation while streaming
windows / build (x86_64-pc-windows-msvc) (pull_request) Successful in 2m45s
apple / swift (pull_request) Successful in 1m45s
apple / screenshots (pull_request) Skipped
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m14s
ci / web (pull_request) Successful in 1m27s
ci / bun-nix (pull_request) Successful in 34s
android / android (pull_request) Successful in 5m52s
ci / rust (pull_request) Failing after 7m55s
ci / docs-site (pull_request) Successful in 7m54s
ci / rust-arm64 (pull_request) Successful in 9m13s
nix / flake (pull_request) Successful in 14m26s
Productizes the adl-emul probe (the prior commit) as the display-policy axis its PR promised: the ADL FFI moves to pf_win_display::adl_emul (one surface shared by the probe tool and the host, so a reporter's probe and the console's toggle exercise byte-identical driver calls), and an EXPERIMENTAL edid_lock axis joins ddc_power_off/pnp_disable_monitors — orthogonal to presets, off by default. At the first Exclusive isolate the host pins each occupied AMD connector's live EDID + ADL_EMUL_MODE_ALWAYS (the software HPD dummy) BEFORE the physicals deactivate; last-member teardown unlocks. Pinned emulation outlives the process, so a crash journal (edid-lock-active.json) unlocks on the next host start, mirroring the pnp_disable_monitors recovery. Inert without an AMD driver. The console shows the toggle ONLY when the GPU inventory lists an AMD adapter — the lever exists nowhere else, and a toggle that can never act is the 'saved and then did nothing' trap the enforced-axes list exists to prevent. |
||
|
|
a0577cb86e |
feat(tools/display-disturb): adl-emul — AMD connector-emulation probe (software HPD dummy)
The standby-sink stall program's §3 dead-end list marked ADL EmulationMode 'likely Pro-gated' on field hearsay, with 'probe once, log rc' as the owed falsification — never run. Three RX 9070 XT field cases later (ASUS VG32VQ1B/DP, Odyssey G60SD/DP, LG UltraGear 32GS95UE/HDMI), this is that probe, shippable to reporters: read-only caps/board-layout/connection-state walk by default, --lock pins the live EDID + ADL_EMUL_MODE_ALWAYS on occupied connectors (the software HPD-holding dummy), --unlock restores. Every call prints the bench's epoch_ms correlation line with the decoded ADL rc — ADL_ERR_NOT_SUPPORTED(-8) vs ADL_OK on consumer Adrenalin is the Pro-gating answer, and a --lock run during a stream with the sink asleep is the direct A/B for the metronomic stall class. atiadlxx.dll is bound dynamically (absent = clean exit 2), structs mirror adl_structures.h verbatim, and the probe touches only connectors the board-layout walk enumerated. Gates: check/clippy -D warnings (msvc cross-target) + fmt clean; native stub unaffected. |
||
|
|
2a62fe7857 |
fix(client): stop the double-arm race re-freezing RFI-healed streams
ci / bun-nix (pull_request) Successful in 30s
ci / docs-site (pull_request) Successful in 1m22s
ci / rust-arm64 (pull_request) Successful in 1m42s
ci / web (pull_request) Successful in 1m51s
apple / swift (pull_request) Successful in 1m50s
apple / screenshots (pull_request) Skipped
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m28s
android / android (pull_request) Successful in 6m39s
windows / build (x86_64-pc-windows-msvc) (pull_request) Failing after 13m7s
ci / rust (pull_request) Successful in 14m4s
Every unrecoverable loss armed the client's freeze gate twice: instantly at frame-index-gap detection (which fires the RFI), and ~120 ms later when the reassembler ages the lost frame into frames_dropped and poll() re-armed unconditionally. An LTR-RFI recovery anchor lands in ~60 ms — between the two signals — so the stale climb re-froze a bit-exact-healed stream, the host swallowed the re-ask as an RFI echo, and the picture stayed frozen until the overdue backstop extracted a full IDR: the field 'H265 freezes on every loss, AV1 fine' signature on AMD hosts (AMF is the only LTR-RFI backend; the slower IDR path usually lands after the climb and dodged the race). The gap-arm now pre-credits the expected climb (ReanchorGate::arm_expecting_drops; credit expires after DROP_CREDIT_WINDOW so a straggler-filled gap can't mask a later real loss), and poll() consumes credited climbs instead of re-arming. Plumbed through every embedder: pf-client-core's session pump, Android's sync/async loops (note_frame_index now returns the gap width), and the Swift client via new ABI exports punktfunk_connection_note_frame_index_ex + punktfunk_reanchor_gate_arm_expecting_drops (additive; the bool ABI stays). |
||
|
|
66ba61b12c |
Merge pull request 'Safety round 2: ASAN+LSAN over the C ABI boundary, two soundness fixes, and WP4's AvFrame RAII' (#172) from worktree-safety-round-2 into main
audit / bun-audit (plugin-kit) (push) Successful in 24s
audit / bun-audit (sdk) (push) Successful in 24s
audit / bun-audit (web) (push) Successful in 27s
audit / cargo-audit (push) Successful in 34s
audit / docs-site-audit (push) Successful in 26s
apple / swift (push) Successful in 1m46s
audit / pnpm-audit (push) Successful in 1m16s
ci / rust-arm64 (push) Successful in 1m35s
ci / web (push) Successful in 1m25s
ci / docs-site (push) Successful in 1m22s
ci / bun-nix (push) Successful in 23s
audit / miri (push) Successful in 5m10s
audit / license-gate (push) Successful in 7m0s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 15s
android / android (push) Successful in 8m2s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 9s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 8s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 9s
deb / build-publish-client-arm64 (push) Successful in 2m34s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 9s
audit / c-abi-asan (push) Successful in 7m51s
arch / build-publish (push) Successful in 8m42s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 16s
deb / build-publish (push) Successful in 5m49s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 1m25s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 1m39s
docker / builders-arm64cross (push) Successful in 10s
docker / deploy-docs (push) Failing after 1m4s
deb / build-publish-host (push) Successful in 8m54s
release / apple (push) Successful in 12m10s
windows-host / package (push) Successful in 13m41s
windows-host / winget-source (push) Skipped
windows-host / canary-manifest (push) Successful in 20s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 3m19s
apple / screenshots (push) Successful in 5m52s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 4m0s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 1m14s
ci / rust (push) Successful in 13m52s
flatpak / build-publish (push) Successful in 15m17s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 2m54s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 18m39s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 19m41s
Reviewed-on: #172 |
||
|
|
5002849737 |
feat(pf-encode): WP4 — AvFrame/AvSwsContext RAII across all three libav backends
ci / bun-nix (pull_request) Successful in 31s
ci / docs-site (pull_request) Successful in 1m17s
ci / rust-arm64 (pull_request) Successful in 1m45s
apple / swift (pull_request) Successful in 1m49s
apple / screenshots (pull_request) Skipped
ci / web (pull_request) Successful in 2m7s
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m56s
android / android (pull_request) Successful in 6m21s
ci / rust (pull_request) Successful in 7m42s
windows / build (x86_64-pc-windows-msvc) (pull_request) Failing after 12m28s
Two newtypes beside AvBuffer/AvFilterGraph (same house shape: alloc/from_raw rejects the allocator's null once, as_ptr lends, Drop frees, no Clone; NonNull inside so the Options get a niche). 8 av_frame_alloc + 3 sws_getContext sites converted; all 22 hand-placed av_frame_free and 5 sws_freeContext calls are gone, and the three hand-written Drop impls (CpuInner, SystemInner, NvencEncoder) with them. The live defect this closes: ZeroCopyInner::submit (ffmpeg_win) leaked the frame AND one pooled hwframe surface on each of three ? exits between the pool pull and the send — under a SAFETY comment asserting no leak — and with POOL=8, eight such failures starved the pool and wedged the encoder with no error naming the cause. Every exit now returns the surface. Drop-order care (the hidden cost the survey flagged): NvencEncoder's sws_csc moved to field #1 (its hand-Drop freed it before all fields; this path runs on every stall-watchdog recovery via *self = fresh); CpuInner's nv12/sws declaration order flipped to match its hand-Drop; SystemInner's already agreed. Pinned by FIELD ORDER comments, not offset_of asserts — the survey's assert suggestion is the wrong tool: offset_of measures repr(Rust) memory layout, which the compiler may reorder independently of the declaration order that drop order actually follows. The dmabuf path keeps its early descriptor release via an explicit drop() at the exact point the hand-written free sat. Gates: .25 clippy -D warnings + tests green (nvenc,vulkan-encode,pyrowave); .133 check --all-targets + clippy --release -D warnings + 80 tests green (nvenc,amf-qsv,qsv; test step needs ffmpeg\bin on Path — 0xC0000135 otherwise). Owed on hardware: the #[ignore]d alloc/drop cycles on .136/.116/.173/.47 and the pool-exhaustion assertion (9th submit succeeds after 8 forced failures). |
||
|
|
9a59504ba4 |
fix(punktfunk-core): validate InputKind before forming &InputEvent in the C ABI
abi.rs's two send-input entry points built &InputEvent straight out of caller memory with ev.as_ref(); InputKind is repr(u8) with 16 valid discriminants, so a C embedder writing ev->kind = 42 was immediate UB the moment the reference formed — in a file whose stated principle is that failures become status codes. New read_input_event() checks null, reads the tag as a raw byte, validates through the same InputKind::from_u8 the wire path uses, and only then forms the reference; bad tags return InvalidArg. Every other field is a plain integer, valid for any pattern. Test stages the event in MaybeUninit storage so the test itself never holds a reference to the invalid value. 380 lib tests + the C harness round-trip + clippy -D warnings green on .25; header regenerated. |
||
|
|
e8c306b9c0 |
fix(punktfunk-host): WP3c/3d — align the TOKEN_USER buffer, make EqualSid fail closed
3c: forming &TOKEN_USER (align 8) out of a bare [u8; 256] (align 1) was UB by the validity rule whenever the stack slot landed misaligned — shipped codegen happened to 8-align it, which is luck, not a contract. Fixed with a repr(align(8)) wrapper that keeps the buffer at 256 BYTES; the comment records why [u64; 32] is the wrong shape (len() would silently become 32 and misclassify every hand-run host as SYSTEM via ERROR_INSUFFICIENT_BUFFER, invisibly to a SYSTEM-side test). Length arg now size_of_val. 3d: EqualSid().is_ok() read BOTH 'SIDs differ' and 'EqualSid failed' as Err, so a genuine failure yielded 'not SYSTEM' — the fail-OPEN direction, contradicting the documented fail-closed contract. Now split three ways on the last-error code, with SetLastError(0) cleared first so a stale value cannot misclassify. Gate: cargo check -p punktfunk-host + cargo clippy --release -D warnings both green on .133 (real MSVC, fresh extraction, sentinel-verified). |
||
|
|
c3b57438e1 |
chore(ci): c-abi-asan job in audit.yml — the harness under ASAN+LSAN, weekly + on demand
Same shape as the miri job (dated nightly, own san- cache prefixes, non-blocking day one via a step-level ::warning::, a proved-it-ran grep). run.sh gains PF_SAN_TOOLCHAIN so CI can pin its dated nightly — bare +nightly would ask for the rolling channel the job never installs. Both the pinned and vanilla paths re-verified green on .25. |
||
|
|
e20b614059 |
chore(safety): PF_SAN sanitizer gate for the C ABI harness
PF_SAN=address builds the punktfunk-core staticlib on nightly with -Zsanitizer/-Zbuild-std and the C harness with clang -fsanitize, so ASAN instruments both sides of the boundary at once and LSAN (detect_leaks=1) becomes the first automated check on abi.rs's Box::into_raw/from_raw leak contract. Verified on the .25 box: green run passes byte-exact; deleting one punktfunk_session_free() in the harness makes LSAN report the 308 Rust-side allocations behind the handle and the script exit 1. The harness binary moves from mktemp to target/ — a debug+ASAN static binary can exceed a tmpfs /tmp (it did, on .25's 3.6G tmpfs). |
||
|
|
6eb89b3f34 |
Merge pull request 'The lint ratchets (WP2b + WP2c): crate-level gaps closed, the three-workspace hoist, three blocking grep gates' (#171) from worktree-lint-ratchets into main
apple / swift (push) Successful in 1m39s
windows-drivers / probe-and-proto (push) Successful in 26s
ci / rust-arm64 (push) Successful in 2m18s
windows-drivers / driver-build (push) Successful in 2m15s
ci / web (push) Successful in 1m27s
android / android (push) Successful in 6m53s
ci / bun-nix (push) Successful in 1m3s
ci / docs-site (push) Successful in 1m52s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 3m14s
release / apple (push) Successful in 10m10s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 3m9s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 1m20s
deb / build-publish-client-arm64 (push) Successful in 6m37s
apple / screenshots (push) Successful in 6m16s
ci / rust (push) Successful in 14m7s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 2m33s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 51s
decky / build-publish (push) Successful in 33s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 8s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 1m23s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 10s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 9s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 10s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 10s
deb / build-publish (push) Successful in 11m15s
deb / build-publish-host (push) Successful in 11m36s
arch / build-publish (push) Successful in 19m0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 1m3s
docker / builders-arm64cross (push) Successful in 19s
docker / deploy-docs (push) Successful in 6m39s
flatpak / build-publish (push) Successful in 8m5s
windows-host / package (push) Successful in 15m24s
windows-host / winget-source (push) Skipped
windows-host / canary-manifest (push) Successful in 21s
nix / flake (push) Successful in 14m13s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 20m18s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 19m5s
|
||
|
|
bbd26ea82c |
Merge pull request 'Miri interprets the FFI-free leaf crates, one of them at MSVC layout' (#169) from worktree-miri-ci into main
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 0s
ci / web (push) Canceled after 0s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 0s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
audit / cargo-audit (push) Successful in 42s
audit / bun-audit (sdk) (push) Successful in 31s
audit / bun-audit (plugin-kit) (push) Successful in 43s
audit / bun-audit (web) (push) Successful in 29s
audit / pnpm-audit (push) Successful in 10s
audit / docs-site-audit (push) Successful in 28s
audit / license-gate (push) Successful in 6m9s
audit / miri (push) Successful in 7m20s
|
||
|
|
549fdf238b |
Merge branch 'main' into worktree-lint-ratchets
apple / swift (pull_request) Successful in 1m45s
apple / screenshots (pull_request) Skipped
windows-drivers / driver-build (pull_request) Successful in 2m1s
ci / rust-arm64 (pull_request) Successful in 1m54s
ci / web (pull_request) Successful in 1m13s
ci / docs-site (pull_request) Successful in 1m17s
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m58s
ci / bun-nix (pull_request) Successful in 1m15s
ci / rust (pull_request) Successful in 6m1s
windows / build (x86_64-pc-windows-msvc) (pull_request) Successful in 2m44s
windows-drivers / probe-and-proto (pull_request) Successful in 26s
android / android (pull_request) Successful in 7m1s
nix / flake (pull_request) Successful in 16m48s
|
||
|
|
3ea411fa39 | Merge branch 'main' into worktree-miri-ci | ||
|
|
3b2fcd076d |
Merge pull request 'chore(api): regenerate openapi.json — #164's unpair change rewrote the unpairClient description without regenerating' (#170) from worktree-openapi-regen into main
ci / rust (push) Canceled after 31s
ci / rust-arm64 (push) Canceled after 29s
ci / web (push) Canceled after 26s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 17s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 17s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 15s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 13s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
|
||
|
|
d67ab9ede4 |
chore(safety): two .133 gate findings — cfg the abi lock helper, re-anchor a layer proof
ci / bun-nix (pull_request) Successful in 40s
ci / web (pull_request) Successful in 1m24s
ci / docs-site (pull_request) Successful in 1m30s
android / android (pull_request) Canceled after 1m45s
apple / swift (pull_request) Canceled after 1m41s
apple / screenshots (pull_request) Canceled after 0s
ci / rust (pull_request) Canceled after 1m43s
ci / rust-arm64 (pull_request) Canceled after 1m43s
nix / flake (pull_request) Canceled after 1m29s
windows-drivers / probe-and-proto (pull_request) Canceled after 0s
windows-drivers / driver-build (pull_request) Canceled after 1m25s
windows / build (aarch64-pc-windows-msvc) (pull_request) Canceled after 0s
windows / build (x86_64-pc-windows-msvc) (pull_request) Canceled after 0s
The tray leg builds punktfunk-core with default-features off, where lock_recover's only callers (the quic-gated punktfunk_connection_* entry points) do not exist — dead code under -D warnings. The helper takes the same feature gate. In pf-vkhdr-layer, rustfmt had reflowed destroy_surface's lookup into a multiline closure, leaving the SAFETY comment outside the closure that contains its unsafe block — the box's clippy rightly stopped accepting the adjacency. The comment moves inside, directly above the block. |
||
|
|
abec2a1457 |
chore(safety): nvenc_core — plain union-arm writes are safe by language rule
The .25 gate corrected the carve-out: rustc flags `unsafe { u.arm.field = x }`
as unused_unsafe — plain assignment through a union projection is safe
(writing an arm cannot itself be UB; the hazard is the mismatched READ).
The 11 plain writes go back to bare statements under their codec matches.
What stays in per-op unsafe blocks with arm-guard proofs is the real unsafe
surface: union reads, borrows, and the bindgen bitfield-setter calls — which
is exactly the surface the shipped 4:4:4 bug lived on (set_chromaFormatIDC
stamped under a wrong codec).
|
||
|
|
5f097d530d |
chore(safety): exempt the two bindings-only sys crates from the hoisted deny
Linux fallout from the hoist the mac could not see: bindgen emits unsafe blocks (layout tests/accessors) into OUT_DIR, where nobody hand-writes SAFETY proofs — pyrowave-sys failed clippy on .25 with 17 of them, and libvpl-sys would do the same on the Windows leg. Both crates are bindings-only by charter (the safe wrapper lives with the consumer), so the allow is crate-wide with the rationale at the crate root; the hand-written link-sanity tests keep their proofs by convention. |
||
|
|
2bfd1cd2d5 |
chore(safety): three unsafe-hygiene grep gates, blocking in ci.yml (WP2c gates)
scripts/ci/check-unsafe-hygiene.sh — textual gates for three classes no lint covers: A. unsafe fn markers carrying no contract. unsafe_op_in_unsafe_fn forces real ops into blocks, so an unsafe fn with no `unsafe` in its body is a marker with no contract ( |
||
|
|
dfebb9dfbb |
chore(safety): hoist the unsafe lints into the workspace tables (WP2c hoist)
undocumented_unsafe_blocks joins unsafe_op_in_unsafe_fn in
[workspace.lints], and the ~100 scattered per-file #![deny(...)] attributes
(85 files) are deleted — a new crate, or a new module in an old one, is now
covered on creation rather than on remembering. The per-file form is how
pf-vkhdr-layer, wdk-probe and half of pf-clipboard stayed uncovered.
There are THREE workspaces, so the claim is made three times: the main
Cargo.toml, packaging/windows/drivers (workspace table + [lints]
workspace = true in all seven members), and packaging/windows/pf-vkhdr-layer
(its [lints] table, previous commit). pf-update now opts into workspace
lints; the two vendored member snapshots (cros-codecs, usbip-sim) stay out
deliberately and now both say so.
Newly-covered fallout was two link-sanity tests (pyrowave-sys, libvpl-sys)
— proofs written. Stale prose that claimed the workspace held
unsafe_op_in_unsafe_fn at "warn" (it has been deny) or pointed at the
deleted attributes is corrected.
nvenc_core.rs is carved OUT of the unsafe_op_in_unsafe_fn fence: its
exemption rationale ("raw entry-table calls almost line for line") was
false — the file makes zero FFI calls. Its unsafe surface is C-union writes
whose soundness hangs on which codec arm is active, and its own 4:4:4 note
records the shipped bug (hevcConfig bytes stamped onto an AV1 config) that
per-operation blocks make visible. It now runs the strictest discipline in
the crate: clippy::multiple_unsafe_ops_per_block at deny, one union access
per block, each naming its codec guard.
Verified here: cargo fmt clean in all three workspaces; native clippy
-D warnings clean for everything that compiles on macOS (the three
pre-existing mac-native failures — pf-client-core wol.rs, pf-encode
dead-code/closure-call, probe mic_burst — reproduce on the clean tree).
Linux/Windows legs ride the .25/.133 gate.
|
||
|
|
f675b3710e |
chore(api): regenerate openapi.json — fcf4c9fd rewrote the unpairClient description without regenerating
|
||
|
|
23fa03b051 |
chore(safety): close the three crate-level lint gaps (WP2b)
pf-vkhdr-layer — the sharpest gap: an implicit layer injected into every Vulkan game process, 32 unsafe usages, zero SAFETY comments, own workspace so no lint table reached it, and an explicit missing_safety_doc allow. Now: a [lints] table (unsafe_op_in_unsafe_fn + clippy::undocumented_unsafe_blocks, both deny), the allow removed, every unsafe operation in an explicit block with a real proof (loader layer protocol / Vulkan valid-usage), # Safety docs on the contract-carrying fns, const layout asserts for the SurfaceFormat2Raw mirror, the five helpers with no caller-facing contract demoted to safe fns, and the two redundant `unsafe impl Send` deleted (fn pointers and vk handles are Send intrinsically — the type-check proves it). wdk-probe — 21 unsafe blocks, 12 proofs: the 9 missing SAFETY comments are written (the iddcx_rt.rs DDI slot-dispatch ones are about table population and PFN/index pairing, not pattern fill), the sibling denies added at the crate root, missing_safety_doc allow dropped, # Safety on DriverEntry, and the crate joins windows-drivers.yml's clippy list — it was the only driver crate not in it. pf-clipboard — the undocumented_unsafe_blocks deny moves from host/windows.rs to the crate root so host/wayland.rs (4 blocks), host/mutter.rs (2) and any future backend under host/ are covered on creation. All existing blocks already carry proofs; free today, structural tomorrow. Verified here: pf-vkhdr-layer cargo fmt --check + clippy --release -D warnings at x86_64-pc-windows-msvc. wdk-probe and pf-clipboard compile checks need the WDK/Linux boxes and ride the .133/.25 gate. |
||
|
|
6e4638dab5 |
ci(audit): interpret the FFI-free leaf crates under Miri, one at MSVC layout
Adds a non-blocking `miri` job to audit.yml, per rust-safety-programme.md §7. What it buys is one narrow, real thing: pf-driver-proto interpreted CROSS-COMPILED to x86_64-pc-windows-msvc, on a Linux runner, with no Windows box in the loop. That crate is `#![forbid(unsafe_code)]` and path-dep'd by BOTH the main workspace and the driver workspace, so it is the layout oracle for every frame and IOCTL crossing that boundary, and nothing else in CI checks it at MSVC layout. It is NOT unsafe coverage — Miri can execute on the order of 2% of the host's unsafe and cannot run ash, windows-rs, ffmpeg, CUDA or the WDK — so no "Miri coverage" number is reported anywhere. Three steps, every one of them measured on 192.168.1.25 with a cold target dir and cold sysroot cache, on the dated toolchain the job installs, BEFORE being committed: step A pf-driver-proto + pf-host-config + pf-gpu 21 + 12 + 4 pass 43 s step B pf-driver-proto @ x86_64-pc-windows-msvc 21 pass 26 s step C punktfunk-core fec::gf8 with +avx2,+ssse3 2 pass 63 s Four corrections to the §7.3 job spec, found while doing this and folded into comments: * `-p punktfunk-core fec packet crypto` does not parse — cargo rejects the extra positionals. Corrected (filters after `--`) it selects 63 tests and was killed at a 25-minute cap with not one test complete, so the bulk step is dropped entirely and only the narrow `fec::gf8` selection is kept, timed at 63 s. * `nightly-2026-08-10` resolves to rustc 1.99.0-nightly (969b803cb 2026-08-09), NOT the 12c36e253 2026-08-10 the doc cites: `nightly-<date>` names the day rustup PUBLISHED the build, which is compiled from the previous day's commit. The doc's hash came from the ROLLING `nightly` channel and was mislabelled. All three steps were re-run and are green on the dated pin actually installed here. * fec-rs dispatches its GF(2^8) multiply through RUNTIME `is_x86_feature_detected!`, so step C's RUSTFLAGS are load-bearing in both directions. Verified by probe: bare, avx2=false and the step would silently interpret the scalar fallback; with the flags, avx2=true and `_mm256_shuffle_epi8` genuinely executes under the interpreter. GFNI stays false either way, so that branch is simply not covered. * `RUSTC_WRAPPER: ""` is a guard, not a fix, and the comment says so — audit.yml sets no sccache today, and cargo-miri warns "Ignoring `RUSTC_WRAPPER`, Miri does not support wrapping" and carries on regardless. Non-blocking via a step-level `||`, not job-level continue-on-error, following the precedent audit.yml already documents for docs-site-audit. Each step additionally asserts a non-zero pass count, so a crate rename or a filter that stops matching surfaces as a warning rather than as a green zero-test run. Both paths were exercised directly: a failing run emits the annotation and still exits 0, and a zero-selection run trips the guard, while a green run with empty bin/doctest targets does not false-positive. Leak checking stays ON (no -Zmiri-ignore-leaks); the two deliberate leaks in the tree are named in a comment so whoever expands coverage annotates those sites instead of blanket- disabling the check. pf-bitstream and the FFI crates are excluded with the reasons inline so they are not helpfully re-added. `paths:` is deliberately not widened to crates/pf-driver-proto/** — that filter is workflow-level and would fire all six audit jobs on every driver-proto edit. |
||
|
|
0c2ac333ae |
Merge pull request 'Chore/rust safety programme' (#164) from chore/rust-safety-programme into main
apple / swift (push) Successful in 1m43s
ci / web (push) Successful in 1m33s
windows-drivers / probe-and-proto (push) Successful in 27s
ci / docs-site (push) Successful in 1m44s
ci / bun-nix (push) Successful in 21s
windows-drivers / driver-build (push) Successful in 1m45s
ci / rust-arm64 (push) Successful in 7m52s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 21s
deb / build-publish-client-arm64 (push) Successful in 2m35s
arch / build-publish (push) Successful in 11m28s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 18s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 19s
release / apple (push) Successful in 9m41s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 14s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 14s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 15s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 52s
ci / rust (push) Failing after 11m41s
android / android (push) Successful in 14m57s
deb / build-publish-host (push) Successful in 7m17s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 3m13s
apple / screenshots (push) Successful in 6m20s
docker / builders-arm64cross (push) Successful in 18s
docker / deploy-docs (push) Successful in 44s
nix / flake (push) Successful in 14m52s
windows-host / package (push) Successful in 20m38s
windows-host / winget-source (push) Skipped
deb / build-publish (push) Successful in 13m0s
windows-host / canary-manifest (push) Successful in 49s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 3m28s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 3m13s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 1m24s
flatpak / build-publish (push) Successful in 24m54s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 2m33s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 39m36s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 38m33s
|
||
|
|
bc70a58fb1 |
Merge main into chore/rust-safety-programme
windows-drivers / probe-and-proto (pull_request) Successful in 22s
ci / bun-nix (pull_request) Successful in 36s
ci / web (pull_request) Successful in 1m17s
apple / swift (pull_request) Successful in 1m39s
apple / screenshots (pull_request) Skipped
windows-drivers / driver-build (pull_request) Successful in 1m58s
ci / rust-arm64 (pull_request) Successful in 3m18s
ci / docs-site (pull_request) Successful in 3m55s
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m29s
android / android (pull_request) Successful in 4m46s
windows / build (x86_64-pc-windows-msvc) (pull_request) Successful in 2m30s
ci / rust (pull_request) Failing after 10m11s
nix / flake (pull_request) Successful in 15m6s
Two conflicts: the test-module import list in gamescope.rs (union — the branch's takeover-state tests and main's WSI opt-out tests both stay), and next_frame_timed_out in pf-capture, where the branch still carried the pre-#168 else-if chain — resolved to main's match-based refactor, which already embeds the same arm semantics plus the provisional-budget latch gate. |
||
|
|
ce25aca7bd |
Merge pull request 'Two black screens from the .41 field session — a NO_FOCUS window stole the composite, and one truncated timeout downgraded the host forever' (#168) from worktree-blackscreen-fixes into main
apple / swift (push) Successful in 1m42s
ci / web (push) Successful in 1m14s
ci / docs-site (push) Successful in 1m20s
ci / bun-nix (push) Successful in 19s
deb / build-publish-client-arm64 (push) Successful in 1m46s
deb / build-publish (push) Successful in 5m9s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 6s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 8s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 10s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 11s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 9s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 5s
apple / screenshots (push) Canceled after 1m18s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 42s
deb / build-publish-host (push) Successful in 7m18s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 1m28s
arch / build-publish (push) Successful in 11m28s
android / android (push) Canceled after 6m31s
ci / rust (push) Canceled after 2m21s
ci / rust-arm64 (push) Canceled after 1m13s
docker / builders-arm64cross (push) Successful in 11s
docker / deploy-docs (push) Canceled after 5s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 4m10s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 3m2s
windows-host / package (push) Canceled after 0s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
|
||
|
|
5587699a85 |
Merge pull request 'Every pinned card gets a library, and it launches with that card's profile' (#167) from worktree-console-pinned-profile-library into main
apple / swift (push) Successful in 1m40s
android / android (push) Canceled after 0s
apple / screenshots (push) Canceled after 0s
arch / build-publish (push) Canceled after 0s
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 1m47s
ci / web (push) Canceled after 0s
ci / docs-site (push) Canceled after 0s
ci / bun-nix (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 19s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 56s
deb / build-publish (push) Canceled after 0s
deb / build-publish-host (push) Canceled after 0s
deb / build-publish-client-arm64 (push) Canceled after 1m55s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 28s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 55s
docker / builders-arm64cross (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 11s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 11s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 3m34s
release / apple (push) Successful in 9m29s
flatpak / build-publish (push) Canceled after 13m45s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 2m59s
windows / build (aarch64-pc-windows-msvc) (push) Canceled after 7s
windows / build (x86_64-pc-windows-msvc) (push) Canceled after 0s
|
||
|
|
c946fcdcb5 |
Merge pull request 'build(web): silence rollup's "use client" directive warnings in the nitro pass' (#166) from build/web-silence-rollup-directive-warnings into main
arch / build-publish (push) Canceled after 47s
ci / bun-nix (push) Successful in 23s
ci / rust (push) Canceled after 42s
ci / docs-site (push) Canceled after 47s
ci / rust-arm64 (push) Canceled after 59s
ci / web (push) Canceled after 58s
deb / build-publish (push) Canceled after 5s
deb / build-publish-host (push) Canceled after 53s
deb / build-publish-client-arm64 (push) Canceled after 43s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 15s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Canceled after 2s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 5s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 0s
docker / deploy-docs (push) Canceled after 0s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 0s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 1m28s
windows-host / package (push) Canceled after 3m49s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
|
||
|
|
fcf4c9fd63 |
fix(mgmt): unpair now revokes a LIVE session on both planes
ci / bun-nix (pull_request) Successful in 37s
ci / web (pull_request) Successful in 1m38s
apple / swift (pull_request) Successful in 1m50s
apple / screenshots (pull_request) Skipped
ci / rust-arm64 (pull_request) Successful in 2m38s
ci / docs-site (pull_request) Successful in 2m32s
windows-drivers / driver-build (pull_request) Successful in 1m50s
windows / build (aarch64-pc-windows-msvc) (pull_request) Successful in 1m29s
android / android (pull_request) Successful in 6m31s
windows / build (x86_64-pc-windows-msvc) (pull_request) Successful in 2m54s
ci / rust (pull_request) Failing after 10m42s
nix / flake (pull_request) Canceled after 8m26s
windows-drivers / probe-and-proto (pull_request) Canceled after 0s
An unpair removed the certificate but left the revoked client's running
session streaming until the client chose to leave. Now it is a complete
revocation:
- GameStream: when the removed certificate owns the active launch, the
session is quit_session'd — the ENet control thread's ended-session arm
gives the client the standard TERMINATION+disconnect. (An owner-less
launch cannot be attributed and is left to the WP0 port teardown when the
last pairing goes.) The endpoint docstring's long-standing caveat
('removes the client from the listing without severing its ability to
reconnect') is retired: TLS handshakes complete by design, authorization
is per-request, and a live session no longer survives its own revocation.
- Native: session_status::stop_by_fingerprint signals the unpaired
client's live session(s) to tear down deliberately (quit+stop), matched
by the registry's client label — the fingerprint's 12-hex-char prefix for
every pairable client; anonymous/TOFU sessions carry IP labels and are
never touched (they have no pairing to revoke).
(The unpair-didn't-PERSIST half of 'unpairing was broken' was already fixed
in
|
||
|
|
cc8eb7df08 |
feat(clients): every pinned card gets a library, and it launches with that card's profile
ci / bun-nix (pull_request) Successful in 26s
ci / web (pull_request) Successful in 1m4s
ci / docs-site (pull_request) Successful in 1m13s
apple / swift (pull_request) Successful in 1m44s
apple / screenshots (pull_request) Skipped
ci / rust-arm64 (pull_request) Successful in 3m10s
windows / build (x86_64-pc-windows-msvc) (pull_request) Successful in 4m39s
android / android (pull_request) Successful in 7m12s
ci / rust (pull_request) Successful in 7m58s
windows / build (aarch64-pc-windows-msvc) (pull_request) Failing after 11m18s
The console fix before this one closed the leak on one client. The same question
has a different wrong answer on each of the others, so this closes it everywhere:
a pinned host+profile card can be browsed, and every title launched off a pinned
card's shelf streams with that card's profile.
Two shapes of bug, one per client:
**The library was not offered on a pinned card at all** — Apple (both UIs:
`hasLibrary: profile == nil` on the console tile, no menu item on the touch card),
Android (`hasLibrary` required `pinnedProfileId == null`, and the console host
options gated Library on `pin == null`), GTK (the pinned card's menu had Connect,
Copy link, Create shortcut, Unpin — no library) and Windows (pinned tiles had no
menu whatsoever). Each was justified in a comment as "a pin is a shortcut, not a
second host, so the host-level actions stay on the host's tile" — right about
wake, pair, edit and forget, wrong about the library. Browsing is not a property
of the machine: it is this card's connect with a title picked first, which is
exactly what a shortcut is for. So the library joins Connect on every pinned
surface, and the host-level actions stay where they were.
**The launch dropped the profile.** GTK already carried it (its library clones
the card's whole ConnectRequest) and Windows already carried it (its library page
launches through the shared target, which the tile parks). Apple did not: the
library was keyed on a bare `StoredHost`, so `launchTitle` connected with
`.inherit` and the host's binding won even from a pinned card. Android was worse
still, and not only for pins — `LibraryScreen` dialled `connectToHost` with the
RAW settings, so a library launch applied NO profile at all, not even the host's
binding, on every host. Its host list resolves
`settings.effectiveFor(profileStore.resolveFor(kh, oneOff))`; its library resolved
nothing.
So the shelf, not the host, is now the unit both clients navigate by. Apple gets
a `LibraryTarget` (host + `ProfileSelection`) threaded through `libraryTarget`,
the shell's screen enum, both presentations and `SessionModel`; Android passes
the pinned id into `LibraryScreen` and resolves it there through the same
`ProfileStore.resolveFor` rule the connect path uses. Falling out of that:
* a game that exits returns to the shelf it was launched from, pin and all,
rather than to the host's default one — `SessionModel.launchedShelf` on Apple,
`ActiveSession.libraryProfileId` → `LibraryReturn` on Android. Android also
drops a pin that was unpinned while the game ran, rather than reopening a card
that no longer exists.
* Android's stats overlay finally names the profile a library launch used
(`profileName` was never set on that path).
* Apple's `punktfunk://browse/<host>` honours `profile=`, which it parsed and
ignored — and refuses an unknown or ambiguous reference exactly as the connect
route does (§10.6) rather than degrading to the binding.
* every shelf says which one it is, in the card's own `host · profile` shape:
the console's title, GTK's page title, Android's ConsoleHeader, Apple's
navigation title and its console heading.
Verified per platform, none of it on trust:
* console + GTK: fmt, build, clippy `-D warnings` and 85 tests green in the
pf-lxcheck2 container (a Mac `cargo test -p pf-console-ui` compiles nothing).
* Apple: `swift build` green for macOS, iOS and tvOS. Worth all three — the tvOS
pass alone caught `navigationDestination(item:)` needing Hashable, and an
iOS-only screen was confirmed genuinely compiled by planting a type error.
* Android: `compileDebugKotlin` + unit tests, with HomeTilesTest's pin
expectation flipped to match.
* Windows: `cargo check --all-targets` + clippy `-D warnings` on the CI runner,
cold (3m10s) — that client cannot compile on a Mac.
|
||
|
|
6ca192b9ab |
fix(packaging/gamescope): +pfhdr6 — a GAMESCOPE_NO_FOCUS window can no longer steal the composite
ci / web (pull_request) Successful in 1m3s
ci / rust-arm64 (pull_request) Successful in 1m35s
apple / swift (pull_request) Successful in 1m40s
apple / screenshots (pull_request) Skipped
ci / docs-site (pull_request) Successful in 1m16s
ci / bun-nix (pull_request) Successful in 1m30s
ci / rust (pull_request) Successful in 4m52s
android / android (pull_request) Successful in 5m36s
Patch 0008: honor GAMESCOPE_NO_FOCUS in steamcompmgr's focus selection. hhd (Handheld Daemon) sets the atom once at init on its hhd-ui overlay window and never clears it; MangoHud sets it too; show/hide for these clients runs over the STEAM_OVERLAY protocol. NOTHING consumed the atom — not upstream gamescope, not Bazzite's fork (checked ba148 by strings) — so a mapped-but-unpainted hhd-ui window (it crash-loops under a headless punktfunk takeover and remaps on every respawn, stamping Steam's appid 769) was an ordinary focus candidate, and steamcompmgr picked it over Big Picture. The composite, and the stream fed from it, went black while every health signal stayed green: on .41 the client sat decoding 60 fps at 0.1 Mb/s of black, GAMESCOPE_FOCUSED_WINDOW named the hhd-ui window with GAMESCOPE_NO_FOCUS(CARDINAL)=1 on it, and killing hhd-ui brought the picture back the same second. The patch wires the atom exactly like GAMESCOPE_EXTERNAL_OVERLAY — read at map, PropertyNotify-tracked with MakeFocusDirty, skipped by both focus-candidate collectors (X11 and XDG) — and touches neither compositing nor appID, so a NO_FOCUS window still paints if the baselayer protocol brings it into view; it is only barred from being CHOSEN. Applies cleanly on the full 0001..0008 series from the bare 5fb8dce4 pin (verified with git am). Banner +pfhdr5 → +pfhdr6, PKGBUILD 3.16.25.pfhdr6-1; README gains the 0008 row, the missing +pfhdr5 ledger row, and the reconciled bump rule (a bugfix bumps the level only when field triage must read the difference off a box's banner — 0007's crash-loop, 0008's lost composite). |
||
|
|
022ede651f |
fix(pf-capture): the truncated first attempt no longer latches the sticky downgrades
The pipeline retry loop deliberately shortens its first attempt's first-frame wait to 2.5s so a stream bound during a gamescope re-init fails over quickly. But the portal capturer's timeout diagnosis treated EVERY expiry as a verdict: it latched whichever offer it implicated — HDR capture off for the source, the raw-dmabuf offer off, the EGL→CUDA offer off — process-wide and permanently, when the attempt was truncated by design and a gamescope cold start routinely delivers nothing inside that window while accepting every offer a few seconds later (observed on .41: pid 1962 hit the expiry at connect and every later session in that process ran silently degraded). This is bug #6 from the pf-capture sweep, verified then and unfixed until now. The truncated attempt is now declared PROVISIONAL end to end: a new `Capturer::next_frame_within_provisional` (default: delegates) lets the retry loop say "this budget is the schedule, not a verdict", and the portal capturer's timeout classification — split out as the pure `classify_first_frame_timeout` + `timeout_convicts`, with tests — names the same suspect in the error text but latches nothing unless the expired budget was full-length. |
||
|
|
9c6e06d3b9 |
feat(host): GameStream is now a cargo feature — WP19, compile-time isolation
A new 'gamestream' feature (default ON — every stock package is behaviorally identical, and GameStream stays runtime-opt-in via --gamestream / PUNKTFUNK_GAMESTREAM) gates the whole Moonlight-protocol surface: control (the ENet plane), rtsp, nvhttp, pairing, serverinfo, the _nvstream mDNS advert, the compat media path (stream/video/audio), pen/gamepad/input decode, apps, crypto, cert (the RSA identity), and tls's Moonlight-client-cert leniency. AppState keeps the shared vocabulary unconditional and cfg-gates the Moonlight-only fields; the mgmt API's PIN endpoints (routes, handlers, OpenAPI entries, lane classifications, tests) exist only under the feature. Building --no-default-features --features pyrowave yields the hardened NATIVE-ONLY host: no rusty_enet (the c2rust-transpiled C ENet stack, 158 unsafe sites) and no rsa (the identity split's legacy fallback became a pem-only read — rustls/ring serves an existing RSA cert without the crate — so the accepted Marvin advisory no longer applies to native-only builds). Both claims are ASSERTED, not assumed: a new CI leg keeps the native-only flavor clippy-clean and fails if cargo tree finds either crate in its graph. serve --gamestream (or the env knob) against such a binary refuses to start with a clear error rather than serving less than the operator configured. En route: the logs-paging test assumed a quiet process-global log ring between its cursors and raced other tests' legitimate log lines (the identity tests added new emitters) — it now asserts on its own markers within the page. Gates: Linux amd64 — BOTH flavors clippy --all-targets -D warnings clean; default tests identity 3/3, mgmt 37/37, gamestream 59/59; native-only tests identity 3/3, mgmt 35/35, residue 4/4; rusty_enet+rsa absent native-only, present default. .133 Windows — both flavors clippy clean (clean-first, sentinel-checked), tree claims hold, and the WP0 port-lifecycle functional gate PASSES on the default build. |
||
|
|
f5fa9649b7 |
fix(console): a pinned card's library launches with that card's profile
Pinning a profile onto a host gives it its own card on the console home, and pressing A on that card has always connected with the pinned profile as the one-off the resolver prefers over the host's binding. Y on the same card opens a library — it is paired and saved, which is the only thing the hint bar asks — and every title launched off that shelf went out with no profile at all, so the host's default binding won. Connecting straight from the card honoured the profile; going through its library did not, which is the shape a user reads as "the pin works until I pick a game". The screen was the leak: LibraryScreen copied the row's address, port, fingerprint and mgmt port, and dropped `pin` — so its launch had nothing to send and hardcoded `profile: None`, under a comment asserting that game launches follow the binding. They should follow the card: a launch off a pinned card's shelf is that card's connect with a title attached. The screen now carries the row's pin and sends its id as the one-off. It also says so, in the card's own `host · profile` shape: the shelf's title names the profile, and so does the connecting card, so which of a host's cards you came in on is legible from the screen rather than inferred from the tile you pressed two screens ago. Off the host's primary tile there is no pin and nothing changes — `None`, and the binding decides. Console-only. The Apple and Android consoles keep Y off pinned cards outright (`hasLibrary: profile == nil`), the GTK client clones the card's whole ConnectRequest — profile included — into its library, and the Windows client offers "Browse library" from the primary tile only. The console's own copy-link and wake-then-connect paths already carried the pin. Both directions are tested, and the pinned one was checked against a reverted fix: it fails with exactly the reported symptom (left: None, right: "hdr"). |
||
|
|
1009e14a44 |
build(web): silence rollup's "use client" directive warnings in the nitro pass
The nitro server build re-bundles the whole dep tree (`noExternals: true`), so every React package shipping a `"use client"` banner earns a MODULE_LEVEL_DIRECTIVE warning — ~150 locally, ~800 in CI — which buries the warnings worth reading. Ignoring the banner is correct rather than papered over: this bundle is the Bun/Nitro server, not an RSC module graph, and TanStack Start splits client from server with its own transform, so nothing downstream consults it. Supplying `onwarn` replaces nitro's own handler, so its three filters (CIRCULAR_DEPENDENCY, EVAL, "Unsupported source map comment") are restated. Verified: `bun run build` drops from 148 such lines to 0 with no other log delta; `tsc --noEmit` and `biome check` clean. |
||
|
|
e658ad726b |
feat(host): the identity split — the native planes get their own P-256 identity
One RSA-2048 identity served every plane, because Moonlight mandates RSA and the planes grew out of the GameStream host. The native punktfunk/1 QUIC plane and the management API now share a separate ECDSA P-256 identity (native-cert.pem/native-key.pem, src/identity.rs): ring-generated via rcgen (no rsa crate on the native path — the accepted Marvin advisory stops applying once WP19 gates the compat planes), real SANs (localhost, loopback, machine hostname — the legacy cert had none), and browser-compatible on purpose: Ed25519 was rejected because no mainstream browser accepts an Ed25519 server cert and /api/docs is opened in one. GameStream keeps the RSA identity untouched (Moonlight pins it; its pairing hashes bind its X.509 signature bytes). Migration is pin-preserving by construction. Clients TOFU-pin ONE leaf-DER SHA-256 for both QUIC and the mgmt/library API, so the identity is resolved ONCE in serve (the planes cannot race the first-run mint) under the rule: identity files exist → use them; else the native trust store is EMPTY → mint P-256 (fresh installs); else keep presenting the legacy RSA cert the paired clients pinned, and log the migration path (unpair all, restart, re-pair). Fingerprint pinning is algorithm-agnostic — existing shipped clients pair against P-256 hosts unchanged. Followers updated: the tray's loopback pin and the plugin SDK's mgmt CA prefer native-cert.pem → cert.pem; the Windows runner ACL grant lists both (the grant loop tolerates absent files). The in-process native tests now run on an EPHEMERAL identity — they previously read, and would newly have MINTED, identity files in the real config dir, which on a dev box that is also a live host would have switched its identity and stranded every pinned client. Gates: Linux amd64 clippy --all-targets -D warnings clean (host+tray); identity 2/2, mgmt 37/37, control 6/6, native 68/68 (C-ABI roundtrips over the ephemeral identity). .133 Windows clippy clean; the port-lifecycle gate re-run PASSES with the split live — the fresh host minted P-256 and served mgmt over it (curl 200/204), ports tracked the paired list as before. |
||
|
|
21f43d7f48 |
Merge pull request 'Games ran black in Nobara's Game Mode — the session script re-exports the WSI variable #144 cleared' (#165) from worktree-nobara-wsi-layer-clobber into main
apple / swift (push) Successful in 1m39s
ci / bun-nix (push) Successful in 55s
ci / web (push) Successful in 1m13s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Successful in 11s
ci / rust-arm64 (push) Successful in 1m43s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 12s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 11s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 9s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 9s
ci / docs-site (push) Successful in 2m22s
deb / build-publish-client-arm64 (push) Successful in 2m8s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Successful in 1m1s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 1m22s
ci / rust (push) Successful in 4m57s
android / android (push) Successful in 8m21s
deb / build-publish-host (push) Successful in 10m37s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Successful in 16s
arch / build-publish (push) Successful in 9m36s
docker / builders-arm64cross (push) Successful in 6s
docker / deploy-docs (push) Failing after 2m39s
apple / screenshots (push) Successful in 6m30s
deb / build-publish (push) Successful in 7m34s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 19m28s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 16m35s
windows-host / package (push) Successful in 15m1s
windows-host / winget-source (push) Skipped
windows-host / canary-manifest (push) Successful in 19s
Reviewed-on: #165 |
||
|
|
8d1e5ab5dd |
Merge pull request 'The Android console grows up — the desktop's real backdrop, Apple's drum, and the cross-client tables stop drifting in silence' (#163) from worktree-android-console-visual-refresh into main
audit / bun-audit (sdk) (push) Successful in 21s
audit / bun-audit (web) (push) Successful in 21s
audit / bun-audit (plugin-kit) (push) Successful in 42s
android / android (push) Canceled after 1m8s
arch / build-publish (push) Failing after 1m1s
apple / swift (push) Canceled after 1m23s
apple / screenshots (push) Canceled after 0s
ci / rust (push) Canceled after 0s
ci / rust-arm64 (push) Canceled after 0s
ci / web (push) Canceled after 47s
ci / docs-site (push) Canceled after 41s
ci / bun-nix (push) Canceled after 0s
docker / builders (ci/arch-ci.Dockerfile, punktfunk-arch-ci) (push) Successful in 14s
deb / build-publish (push) Canceled after 0s
deb / build-publish-client-arm64 (push) Canceled after 1m0s
deb / build-publish-host (push) Canceled after 1m0s
docker / builders (ci/rust-ci-noble.Dockerfile, punktfunk-rust-ci-noble) (push) Successful in 20s
docker / builders (--build-arg FEDORA_VERSION=44, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm, -f44) (push) Canceled after 0s
docker / builders (ci/android-ci.Dockerfile, punktfunk-android-ci) (push) Canceled after 0s
docker / builders (ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Canceled after 0s
docker / builders (ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Canceled after 0s
docker / builders-arm64cross (push) Canceled after 0s
docker / apps (., web/Dockerfile, punktfunk-web) (push) Canceled after 0s
docker / apps (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Canceled after 18s
docker / deploy-docs (push) Canceled after 0s
audit / docs-site-audit (push) Successful in 25s
audit / pnpm-audit (push) Successful in 16s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Canceled after 0s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Canceled after 0s
audit / cargo-audit (push) Successful in 47s
windows-host / package (push) Canceled after 1m57s
windows-host / canary-manifest (push) Canceled after 0s
windows-host / winget-source (push) Canceled after 0s
audit / license-gate (push) Successful in 5m32s
windows-msix / package (arm64, --no-default-features, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 4m16s
windows-msix / package (x64, , x86_64-pc-windows-msvc, C:\t) (push) Successful in 3m46s
release / apple (push) Successful in 10m18s
flatpak / build-publish (push) Successful in 9m20s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 3m51s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 5m46s
nix / flake (push) Failing after 16m5s
Reviewed-on: #163 |
||
|
|
23d0452157 |
feat(host): GameStream opt-in on every route; the native plane is deny(unsafe_code)-enforced
The user direction after WP0: ENet exists only for Moonlight, so the native
plane must be provably safe and the compat planes a deliberate choice.
Opt-in, everywhere. Windows already was (unchecked installer task). The three
opt-out surfaces are flipped: the shipped systemd user unit (deb/RPM/Arch/
sysext) no longer bakes --gamestream into ExecStart — a new
PUNKTFUNK_GAMESTREAM=1 host.env knob (pf-host-config, OR-ed with the CLI
flag) is the packaged opt-in; the NixOS module default goes true→false, with
a module-check assertion that unset = native-only; the Deck installer takes
--gamestream to opt in (--no-gamestream kept as explicit-off). Docs
(quickstart, running-as-a-service, moonlight, ubuntu/fedora/arch firewall
sections, gnome/sway, how-it-works) rewritten to the opt-in shape; the
CHANGELOG carries the upgrade note.
Enforced-safe. punktfunk-core is #![deny(unsafe_code)] crate-wide — every
module that parses network bytes is safe Rust as a compile error, not a
census result. Carve-outs are exactly two documented classes, neither of
which interprets attacker bytes: the client surface (abi, client) and the
transport syscall-batching shims (udp/{apple,linux,windows}, qos_windows).
In punktfunk-host, the modules a secure-default host exposes — native
(cfg-not-test: its tests exercise the client C ABI on purpose),
native_pairing, mgmt, mgmt_token, discovery, wol — are #[forbid(unsafe_code)].
Gates: Linux amd64 container clippy --all-targets -D warnings clean over
core+host-config+host; core 204 tests green under the deny; mgmt 46/46,
control 6/6. .133 Windows clippy (shipped features, clean-first,
sentinel-checked) clean — covers the qos_windows/udp-windows carve-outs.
macOS + iOS cargo check green (the apple.rs carve-out compiles for real).
|
||
|
|
9e28cd101c |
fix(pf-vdisplay): the WSI opt-out never reached the games — the session script re-exports it
ci / docs-site (pull_request) Successful in 1m23s
ci / web (pull_request) Successful in 1m24s
apple / swift (pull_request) Successful in 1m46s
ci / bun-nix (pull_request) Successful in 1m25s
apple / screenshots (pull_request) Skipped
ci / rust-arm64 (pull_request) Successful in 2m27s
android / android (pull_request) Successful in 5m53s
ci / rust (pull_request) Successful in 11m10s
A Nobara 44 field box on 0.27.0 got a working Game Mode takeover — right mode, right refresh, perf overlay in the stream — and then every game it launched played sound and took input over a BLACK PICTURE, with no error anywhere. #144 disabled the distro's `VkLayer_FROG_gamescope_wsi` with `--setenv=ENABLE_GAMESCOPE_WSI=0` on the transient unit, because that layer speaks the distro gamescope's `gamescope_swapchain` protocol and ours rejects its `swapchain_feedback`, killing the client. `gamescope-session-plus` then runs an unconditional `export ENABLE_GAMESCOPE_WSI=1` near the top of the script, before it launches anything — so the opt-out lived exactly as long as it took the script to start, and gamescope, Steam and every game got the layer back. The host logged that it had disabled it, which is what made this cost a field round-trip: the claim was true of the unit and false of everything in it. Nothing else looked wrong because the casualty is Vulkan clients specifically. Steam's Big Picture UI is not one, so the session came up looking perfectly healthy right up until a game started. Send `DISABLE_GAMESCOPE_WSI=1` as well. The Vulkan loader resolves an implicit layer's two manifest knobs in a fixed order (`loader_implicit_layer_is_enabled`): `enable_environment` must equal `"1"` to switch the layer on, and `disable_environment` is consulted last — "has priority over everything else" — where the mere PRESENCE of the variable, at any value, forces it off. The session script never mentions that one, so it is the only one that survives it. Both spellings now go out through one place, so the transient unit (`launch_session`) and the box's own session drop-in (`write_session_plus_dropin`) cannot drift apart — the same shape `SessionBind` already uses for the bind. `ENABLE_GAMESCOPE_WSI=0` stays alongside for a layer built without a `disable_environment`, and because it is what an operator reads the unit for. |