At Sun, 22 Feb 2009 04:14:53 +0100, Lennart Poettering wrote:
On Sat, 21.02.09 17:36, Takashi Iwai (tiwai@suse.de) wrote:
At Fri, 20 Feb 2009 21:34:17 +0100, Lennart Poettering wrote:
On Fri, 20.02.09 08:26, Takashi Iwai (tiwai@suse.de) wrote:
Yes, I am. But ignore that part for now. I have now commented the use of that call. Now I certainly get more POLLOUTs as expected, but the real problem stays: after a few minutes _avail() will suddenly jump from next to zero to more then the hwbuf size in less than 1ms without any further inteference and with a buffer size of 350ms! There is something really wrong with the behaviour of _avail().
I can reproduce this only on ens1371 for now.
The ens1371 driver itself is damn simple. The pointer callback just returns the read value. So, it implies that it's basically a hardware issue.
Does the patch below have any influence?
No. It doesn't appear to have any effect whatsoever. Still, from time to time the value returned by _avail() is off by once the buffer size, sometimes upwards, sometimes downwards.
Moreover I can now reproduce the same issue on snd-intel8x0, albeit it takes more than a couple of minutes to make snd_pcm_avail() return bogus data.
Somehow I get the feeling the problem is not so much the inaccuracy of the pointer the kernel reports but in what alsa-libs does ith it.
Hrm... both cases the pointer calculation is relatively simple, and for "hw" PCM, the avail calculation is also very straightforward. So, my first suspect is about the pointer calculation. But, of course we should check all possibilities.
Can you give a small testcase?
Ok, here's a little test case:
http://git.0pointer.de/?p=pulseaudio.git;a=blob_plain;f=src/tests/alsa-time-...
Finally have time to go back to this issue again now.
With your test case, indeed I get abort(), too. However, checking through the code, you set stop_threshold to the boundary size like:
r = snd_pcm_sw_params_get_boundary(swparams, &boundary); r = snd_pcm_sw_params_set_stop_threshold(pcm, swparams, boundary);
This means essentially you are disabling the XRUN detection in the driver and keep it free-running. So, no wonder avail gets over buffer_size. It's actually an XRUN condition, but just ignored due to this setup. (Usually, stop_threshould == buffer_size.)
Or do I misunderstand the intention of your testcase?
thanks,
Takashi