Maarten Lankhorst wrote:
That was about the relationship between GCP and GetPosition. Now what about GetPosition and wall time (as seen by the HighPerformanceTimer)? The largest delta is 8ms, which suggests that your GetPosition is not particularly regular, but as it stays below one 10ms period, it's presumably good enough. By contrast, native's largest delta is < 1ms.
Delta shouldn't be so high, are you using the timestamps from IAudioClock2::GetPosition ?
I'm using the data that you sent me, nothing invisible. So it's simply GetPosition vs. the HighPerformanceTimer output, as seen in: render.c:1194: hpctime 481 pcpos 492 render.c:1199: padding 1250 position 510000/21250 slept 470ms iteration 0
If you say jitter is 8 ms (which I find very high), you wouldn't notice that extra 10 ms..
I simply compared GetPosition advancement with wall time as reported by the HPC (relying on file buffering to ignore delays introduced by logging output).
I prefer to just report the values from pulseaudio directly.
Reasonable and probably good enough.
Some interruption of the audio stream, that sleep(i % 10) is suspect... what are you really testing there?
That sleep serves to prove my hypothesis that upon receiving an event from mmdevapi, any app has nearly one period time to feed (at least) one period worth of samples to mmdevapi. I.e. conceptually, mmdevapi calls SetEvent() after performing one round of mixing and decrementing padding. It then goes to sleep until the next period tick.
Native plays that test glitch free on real hardware.
And that test seems to be sensitive to not being run in realtime, it seems to work slightly better if I change that to if I set THREAD_PRIORITY_TIME_CRITICAL on the thread
RT probably helps, however I claim that *IF* Linux is able to deliver a sustained 10ms rate to any app without RT, then Wine (as an app) should be able to feed data to the audio every 10ms. The mmdevapi design is such that the client app has nearly 10ms to feed new data -- by design! That is why the sleep(8ms) is perfectly valid -- given a 10ms period -- albeit stressing (and sensitive to the Linux scheduler delaying execution of the client thread).
What I want to emphasize is that there would be a design bug in a wineXYZ.drv mmdevapi driver if it would depend on a client app to react within say 2ms upon SetEvent. I repeat that the app has nearly 10ms time, e.g. DSound can consume nearly 10ms to perform its mixing and HQ resampling in mmdevapi event based mode. I think this is a nice property of mmdevapi.
That is why we've the silence lead-in in winealsa.drv... It shall guarantee that ALSA has enough samples to play until the next period tick (if the Linux scheduler then calls the driver in time).
Here and then I've also reported that since the introduction of the completely fair scheduler, Linux appears *UNABLE* to sustain a periodic 10ms or even a 50ms rate without RT. This affects not only audio. The former scheduler found IIRC in 2.6.18 performed much better at games, both audio and video glitches. If you are a gamer, use one of the old kernels!
Sleep(0) (for i%10 = 0) looks kind of wrong though
That's just ok and the typical scenario where the client app react immediately to SetEvent.
I may also be hitting some pulseaudio bug though, if I play some music on the background when one [...] that would explain why I'm getting interruptions like the +14 ms above..
I'm sorry but I did not understand that whole paragraph.
Regards, Jörg Höhle