https://bugs.winehq.org/show_bug.cgi?id=39814
--- Comment #12 from Andrew Eikum aeikum@codeweavers.com --- Thanks for the nice bug report!
This actually looks like a bug in Reaper that the large buffer size was covering up.
Reaper asks for a buffer of length 0x1a0ab REFERENCE_TIMEs, which is 0.0106667 seconds. I'm not sure how this number is derived, but it at least uses the result of GetDevicePeriod.
0034:trace:pulse:AudioClient_Initialize (0x17d450)->(0, 40000, 1a0ab, 0, 0x192a0fc, (null))
And PA honors this, giving us a buffer of the same size (expressed here in bytes at 8bps and 48 kHz):
0034:trace:pulse:dump_attr tlength: 4104
Then Reaper grabs the buffer size and fills the whole buffer:
0034:trace:pulse:AudioClient_GetBufferSize (0x17d450)->(0xc83e910) 0034:trace:pulse:AudioRenderClient_GetBuffer (0x17d450)->(512, 0xc83e8c4)
But, next time it tries to write:
0034:trace:pulse:AudioClient_GetCurrentPadding 0x17d450 Pad: 11 ms (512) 0034:trace:pulse:AudioRenderClient_GetBuffer (0x17d450)->(512, 0xc83e8c4) 0034:warn:pulse:AudioRenderClient_GetBuffer Wanted to write 512, but only 1 available
winepulse is telling the application "512 samples of our 512 sample buffer are occupied," but then Repear tries to write 512 samples into the full buffer! That can't work. They're mistakenly using the size of the data in the buffer as the amount of free space in the buffer.
You see the same bug with each GetBuffer call after that until the buffer is less than half full, at which point the request succeeds. But that's just ~0.005 seconds of data in the buffer, so we hear underruns.
I tested Reaper out with PULSE_LATENCY_MSEC=60 and saw the same broken behavior. The reason it sounds better is because the period size is larger, so the requested buffer size is much larger, which means the half-full buffer doesn't underrun.
So, this is an application bug exposed by our support for very low buffer sizes. I suspect in practice Windows devices don't claim the low latency that winepulse does, or somehow otherwise mask this bug.