fix(android): hold BOTH Wi-Fi locks while streaming — HIGH_PERF alone is a no-op
apple / swift (push) Successful in 1m10s
android / android (push) Successful in 5m40s
arch / build-publish (push) Successful in 6m0s
audit / bun-audit (push) Failing after 17s
audit / cargo-audit (push) Failing after 1m40s
windows-host / package (push) Successful in 7m41s
ci / web (push) Successful in 59s
windows-msix / package (arm64, C:\Users\Public\ffmpeg-arm64, aarch64-pc-windows-msvc, C:\t-a64) (push) Successful in 1m21s
ci / docs-site (push) Successful in 1m23s
windows-msix / package (x64, C:\Users\Public\ffmpeg, x86_64-pc-windows-msvc, C:\t) (push) Successful in 1m14s
release / apple (push) Successful in 9m12s
windows / build (aarch64-pc-windows-msvc) (push) Successful in 52s
windows / build (x86_64-pc-windows-msvc) (push) Successful in 56s
ci / bench (push) Successful in 4m51s
ci / rust (push) Successful in 9m59s
decky / build-publish (push) Successful in 24s
apple / screenshots (push) Successful in 7m10s
deb / build-publish (push) Successful in 4m50s
docker / build-push (--build-arg FEDORA_VERSION=44, ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora44-rpm) (push) Successful in 2m42s
docker / build-push (., web/Dockerfile, punktfunk-web) (push) Successful in 34s
docker / build-push (ci, ci/fedora-rpm.Dockerfile, punktfunk-fedora-rpm) (push) Successful in 2m32s
docker / build-push (ci, ci/rust-ci.Dockerfile, punktfunk-rust-ci) (push) Successful in 2m23s
docker / build-push (docs-site, docs-site/Dockerfile, punktfunk-docs) (push) Successful in 57s
flatpak / build-publish (push) Successful in 4m34s
rpm / build-publish (43, bazzite, punktfunk-fedora-rpm) (push) Successful in 11m47s
docker / deploy-docs (push) Successful in 23s
rpm / build-publish (44, fedora-44, punktfunk-fedora44-rpm) (push) Successful in 10m7s

The baseline stream held only WIFI_MODE_FULL_HIGH_PERF, which is deprecated
AND non-functional on recent Android — so with the low-latency toggle off (the
default) Wi-Fi power save stayed fully active: downlink delivery clumped at
beacon intervals (a few hundred ms of latency mush, sawtoothing bitrate) and
the AP's power-save buffer periodically overflowed, killing whole frames every
few seconds (the host log's alternating loss_ppm=0/50000). Now every stream
holds FULL_LOW_LATENCY (API 29+, the only effective power-save disable;
foreground + screen-on, which a stream always is) AND FULL_HIGH_PERF (covers
older releases) — the same pair Moonlight holds. The experimental toggle no
longer selects the lock mode.

Also: declare tracing's "log" feature explicitly in the native crate (core
transport warnings → logcat must not hinge on quinn's default features), and
align the low-latency toggle's copy with its actual scope.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
2026-07-07 07:34:56 +02:00
parent f992298da8
commit 8f06a4334e
6 changed files with 45 additions and 25 deletions
+8
View File
@@ -31,6 +31,14 @@ mdns-sd = "0.20"
# via `ndk`, the Opus codec) is only pulled in for the real `*-linux-android` targets.
[target.'cfg(target_os = "android")'.dependencies]
android_logger = "0.14"
# Feature bridge, no code here: punktfunk-core logs through `tracing`, but this client only
# installs `android_logger` (a `log` backend). Core transport warnings (e.g. "UDP socket buffer
# capped well below target") reach logcat only via tracing's "log" feature, which forwards events
# as `log` records when no tracing subscriber is set (always, here). Today that feature happens to
# be enabled transitively — quinn's default `log` feature unifies `tracing/log` onto the whole
# graph — but nothing about this client's logging should hinge on a QUIC crate's default feature
# set, so declare it explicitly.
tracing = { version = "0.1", default-features = false, features = ["std", "log"] }
# NDK bindings. "media" = AMediaCodec/ANativeWindow (video); "audio" = AAudio (audio playback).
# Pure-Rust FFI to libmediandk/libnativewindow/libaaudio — no C++/libc++_shared to bundle. Decode +
# audio run entirely in Rust on native threads (the "no async on the hot path" invariant).
+4 -1
View File
@@ -44,7 +44,10 @@ mod stats;
mod wol;
/// Initialize `android_logger` once when the JVM loads the library. Logs land in logcat under the
/// `punktfunk` tag. Android-only — there is no JVM (and no logcat) on the host build.
/// `punktfunk` tag. Core `tracing` events (transport warnings: socket-buffer clamp, QoS failures)
/// arrive here too: tracing's "log" feature — declared explicitly in Cargo.toml rather than relied
/// on via quinn's defaults — forwards them as `log` records since no tracing subscriber is ever
/// installed. Android-only — there is no JVM (and no logcat) on the host build.
#[cfg(target_os = "android")]
#[no_mangle]
pub extern "system" fn JNI_OnLoad(