I keep spending hours and hours debugging. It always works afterward. But in the end, it’s not really a solution to the root cause. Sooner or later, in a few weeks, I’ll be stuck with another audio problem like this. It happened again yesterday. After hours of it, I’d had enough and put dom0 into suspend.
Today I noticed that, miraculously, the audio is working in all the AppVMs.
My system:
Qubes OS 4.2
Apps all debian 13
no sys-usb
no sys-audio
The current solution is probably to suspend dom0 and then resume it.
About the problem: It was even more complicated because the audio on YouTube in Firefox was working. Only espeak-ng was stuttering. But as soon as espeak-ng was running while YouTube was playing, YouTube started stuttering too.
So basically, the audio wasn’t completely broken, just partially.
And on top of that, it’s impossible to reproduce this problem.
A few weeks ago, this problem also occurred during a Zoom webinar (via Firefox).
So Firefox with YouTube must be doing something differently than Firefox with Zoom.
Summary:
On AppVM1:
espeak-ng: stutters
On AppVM2:
espeak-ng: stutters
Firefox YouTube: works fine
espeak-ng + Firefox YouTube: both stutter
On AppVM a few weeks earlier:
Firefox YouTube: I don’t remember
Firefox Zoom: stutters
Firefox YouTube + Firefox Zoom: I don’t remember
Zoom native app: stutters
The AI says it’s a “PulseAudio buffer latency creep.” Can anyone confirm or deny this?
The audio issue is so difficult to identify because several factors interact with each other.
#1 The underlying problem is this bug:
The workaround “suspending the system and then waking it up” always works with the apps I’ve tested: mpv, espeak-ng
I put marmarek’s code into a script (test.sh) and ran it in a loop.
test.sh
#!/usr/bin/env bash
# Measures how fast VLC can decode audio, to track the post-S3 slowdown from
# https://github.com/QubesOS/qubes-issues/issues/10616
#
# X ms of audio decoded in Y ms -> Y << X is healthy, Y approaching X is the bug.
# Reference (marmarek): 1018 ms in 7 ms fresh after S3, in 335 ms degraded,
# 4088 ms in 9062 ms while stuttering.
#
# Needs a 44.1 kHz compressed file: wav or 48 kHz opus/webm will not reproduce.
set -uo pipefail
if ! command -v cvlc >/dev/null 2>&1; then
echo "vlc not found, installing..."
sudo apt install -y vlc --no-install-recommends
fi
# Default sample lives next to this script, not in the caller's cwd.
DIR="$(cd -- "$(dirname -- "${BASH_SOURCE[0]}")" && pwd)"
FILE="${1:-$DIR/melodigne-quiz-test-187137.mp3}"
if [ ! -r "$FILE" ]; then
echo "error: cannot read '$FILE'" >&2
echo "download the default sample from https://pixabay.com/music/beats-quiz-test-187137/" >&2
exit 1
fi
VLC_VERBOSE=3 cvlc -A afile --audiofile-file=/dev/null \
--no-loop --play-and-exit --run-time 10 "$FILE" 2>&1 |
awk -v ts="$(date '+%Y-%m-%d %H:%M:%S')" -v file="$FILE" '
match($0, /samplerate:[0-9]+/) {
rate = substr($0, RSTART + 11, RLENGTH - 11)
}
match($0, /buffering done \([^)]*\)/) {
split(substr($0, RSTART, RLENGTH), paren, /[()]/)
split(paren[2], f, " ") # f = (X, ms, in, Y, ms)
audio = f[1]; decode = f[4]
if (decode > 0)
speed = sprintf("%.1fx realtime", audio / decode)
else
speed = ">1000x realtime"
printf "%s %s Hz %s ms audio decoded in %s ms (%s)\n", \
ts, rate, audio, decode, speed
found = 1
}
END {
if (!found) {
print ts " no measurement - VLC produced no buffering line; " \
"is \"" file "\" a decodable audio file?"
exit 1
}
}
'
As you can see from the numbers here, the “realtime” value gets worse and worse over time.
Slight stuttering starts when the value drops below 2 and after a suspend/wakeup, the sound quality is back to its best.
before suspend:
$ ./test.sh
2026-09-02 11:34:59 44100 Hz 1018 ms audio decoded in 246 ms (4.1x realtime)
dom0: systemctl suspend
then after waking up:
$ ./test.sh && sleep 1380 && while true; do ./test.sh; sleep 3592; done
2026-09-02 11:35:38 44100 Hz 1018 ms audio decoded in 3 ms (339.3x realtime)
2026-09-02 12:00:00 44100 Hz 1018 ms audio decoded in 17 ms (59.9x realtime)
2026-09-02 13:00:01 44100 Hz 1018 ms audio decoded in 56 ms (18.2x realtime)
2026-09-02 14:00:02 44100 Hz 1018 ms audio decoded in 111 ms (9.2x realtime)
2026-09-02 15:00:04 44100 Hz 1018 ms audio decoded in 138 ms (7.4x realtime)
2026-09-02 16:00:05 44100 Hz 1018 ms audio decoded in 175 ms (5.8x realtime)
2026-09-02 17:00:06 44100 Hz 1018 ms audio decoded in 217 ms (4.7x realtime)
2026-09-02 18:00:09 44100 Hz 1018 ms audio decoded in 265 ms (3.8x realtime)
2026-09-02 19:00:10 44100 Hz 1018 ms audio decoded in 306 ms (3.3x realtime)
2026-09-02 20:00:11 44100 Hz 1018 ms audio decoded in 337 ms (3.0x realtime)
2026-09-02 21:00:13 44100 Hz 1018 ms audio decoded in 385 ms (2.6x realtime)
2026-09-02 22:00:14 44100 Hz 1018 ms audio decoded in 422 ms (2.4x realtime)
2026-09-02 23:00:16 44100 Hz 1018 ms audio decoded in 446 ms (2.3x realtime)
2026-09-03 00:00:17 44100 Hz 1018 ms audio decoded in 495 ms (2.1x realtime)
2026-09-03 01:00:19 44100 Hz 1018 ms audio decoded in 527 ms (1.9x realtime)
2026-09-03 02:00:21 44100 Hz 1018 ms audio decoded in 559 ms (1.8x realtime)
2026-09-03 03:00:22 44100 Hz 1018 ms audio decoded in 595 ms (1.7x realtime)
2026-09-03 04:00:24 44100 Hz 1018 ms audio decoded in 653 ms (1.6x realtime)
2026-09-03 05:00:26 44100 Hz 1018 ms audio decoded in 683 ms (1.5x realtime)
2026-09-03 06:00:28 44100 Hz 1018 ms audio decoded in 716 ms (1.4x realtime)
2026-09-03 07:00:30 44100 Hz 1018 ms audio decoded in 780 ms (1.3x realtime)
2026-09-03 08:00:31 44100 Hz 1018 ms audio decoded in 790 ms (1.3x realtime)
2026-09-03 09:00:33 44100 Hz 1018 ms audio decoded in 865 ms (1.2x realtime)
2026-09-03 10:00:35 44100 Hz 1018 ms audio decoded in 875 ms (1.2x realtime)
2026-09-03 11:00:37 44100 Hz 1018 ms audio decoded in 921 ms (1.1x realtime)
2026-09-03 12:00:40 44100 Hz 1018 ms audio decoded in 947 ms (1.1x realtime)
2026-09-03 13:00:42 44100 Hz 1018 ms audio decoded in 991 ms (1.0x realtime)
2026-09-03 14:00:44 44100 Hz 1018 ms audio decoded in 1023 ms (1.0x realtime)
2026-09-03 15:00:46 44100 Hz 1018 ms audio decoded in 1105 ms (0.9x realtime)
2026-09-03 16:00:49 44100 Hz 1018 ms audio decoded in 1103 ms (0.9x realtime)
2026-09-03 17:00:52 44100 Hz 1018 ms audio decoded in 1146 ms (0.9x realtime)
2026-09-03 17:00:52 44100 Hz 391 ms audio decoded in 435 ms (0.9x realtime)
dom0: systemctl suspend
then after waking up:
$ ./test.sh
2026-09-03 17:07:40 44100 Hz 1018 ms audio decoded in 2 ms (509.0x realtime)
#2 File 48000Hz/44100Hz/Opus/AAC or App mpv/espeak-ng
None of that matters. I tested these audio formats. Either they all worked, or they all stuttered.
Depending on what the “realtime” value was, as described in #1 above.
In cases where the realtime value is below 2, mpv and espeak-ng cause stuttering when run individually.
When Firefox was playing YouTube, the sound was flawless despite a realtime value of 0.9.
But when I then started espeak-ng, Firefox also started stuttering.
And the opposite was true with mpv. When I ran mpv, it stuttered, but as soon as I ran YouTube in Firefox, the simultaneous audio from mpv was also flawless. Even though the realtime value was 0.9!
Conclusion
On Qubes OS 4.2, the only solution is to suspend and wake up the system.
On Qubes OS 4.3, the fix should already be included in the updates, so the problem shouldn’t occur.
P.S.:
All of my tests were conducted without the sys-audio VM and sys-usb VM, using a USB sound card connected directly to dom0.