Skip to content

fix(linux): bound feedback sound playback so a wedged output device cannot lock the mic/sink - #2148

Open
tahakotil wants to merge 1 commit into
cjpais:mainfrom
tahakotil:fix/linux-audio-feedback-lock
Open

tahakotil wants to merge 1 commit into
cjpais:mainfrom
tahakotil:fix/linux-audio-feedback-lock

Conversation

@tahakotil

Copy link
Copy Markdown

Problem (Linux)

The audio-feedback path opens a cpal output stream and waits with sink.sleep_until_end(). On ALSA, when the output device wedges (stale/hung open handle), that call can park the thread forever while the stream keeps holding /dev/snd/pcmC2D0p (mmap mode). Consequences on a PipeWire system:

  • pipewire logs spa.alsa front:2: playback open failed: Device or resource busy every ~5 s (thousands of entries),
  • the default sink stays unavailable to every other app (system sounds, browser/video) for as long as Handy lives,
  • dropped/unfocused streams (e.g. after the app crashes mid-playback) can leave the handle leaked onward.

Observed live on Kubuntu 26.04 (PipeWire 1.6.2, GNOME/KDE Wayland): the AppImage process held /dev/snd/pcmC2D0p in mmap mode for ~20 h while the loop above repeated.

Fix

Poll for completion with a 30 s hard cap instead of an indefinite sleep_until_end(). On cap, log a warning and drop the sink/output stream — the ALSA handle is released, so the rest of the audio stack recovers even if the device itself is wedged.

Verification

  • cargo check passes (rustc 1.98.1, tauri 2.11.5 deps; only 2 pre-existing handy lib warnings)
  • on-device confirmation that the patched drop releases the ALSA handle (fuser /dev/snd/pcmC2D0p empty after force-killing the wedge)

Notes

  • Bug/stability contribution scoped per CONTRIBUTING (feature freeze).
  • A related system-level workaround (route ALSA front:CARD=... into PipeWire via /etc/asound.conf) currently masks the issue on this machine, but the root cause — an unbounded feedback wait occupying the output stream — stands.

Happy to adjust the cap (e.g. make it settings-based) if the maintainers prefer another constant.

…annot lock the mic/sink

On Linux the feedback path opens a cpal output stream and waits with
sink.sleep_until_end(). If the device wedges (ALSA keeps a stale open
handle), that call parks the worker thread forever while the stream keeps
the device output side locked: PipeWire (or any other consumer) then gets
EBUSY on the default sink for as long as the app lives, so e.g. system
audio and the browser cannot open the sink at all.

Poll for completion with a 30 s hard cap instead. Returning early drops
the sink and the output stream, releasing the ALSA handle; a wedged
device no longer blocks the rest of the audio stack.

Observed on Kubuntu 26.04 (PipeWire 1.6.2): the AppImage held
/dev/snd/pcmC2D0p in mmap mode for ~20 h, while pipewire logged
*spa.alsa front:2: playback open failed: Device or resource busy*
every 5 s (~1400 h keeping the default sink unavailable).
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant