mirror of
https://github.com/alsa-project/alsa-lib.git
synced 2025-11-03 09:01:52 -05:00
Fix poll after XRUN with dmix
Fix the behavior of poll after XRUN with dmix plugin. Poll should return immediately with an XRUN stream.
This commit is contained in:
parent
b0ee34e757
commit
4c6809bf30
2 changed files with 8 additions and 6 deletions
|
|
@ -456,12 +456,12 @@ int snd_pcm_direct_poll_revents(snd_pcm_t *pcm, struct pollfd *pfds, unsigned in
|
||||||
{
|
{
|
||||||
snd_pcm_direct_t *dmix = pcm->private_data;
|
snd_pcm_direct_t *dmix = pcm->private_data;
|
||||||
unsigned short events;
|
unsigned short events;
|
||||||
|
int empty = 0;
|
||||||
|
|
||||||
assert(pfds && nfds == 1 && revents);
|
assert(pfds && nfds == 1 && revents);
|
||||||
events = pfds[0].revents;
|
events = pfds[0].revents;
|
||||||
if (events & POLLIN) {
|
if (events & POLLIN) {
|
||||||
snd_pcm_uframes_t avail;
|
snd_pcm_uframes_t avail;
|
||||||
int empty;
|
|
||||||
snd_pcm_avail_update(pcm);
|
snd_pcm_avail_update(pcm);
|
||||||
if (pcm->stream == SND_PCM_STREAM_PLAYBACK) {
|
if (pcm->stream == SND_PCM_STREAM_PLAYBACK) {
|
||||||
events |= POLLOUT;
|
events |= POLLOUT;
|
||||||
|
|
@ -471,10 +471,6 @@ int snd_pcm_direct_poll_revents(snd_pcm_t *pcm, struct pollfd *pfds, unsigned in
|
||||||
avail = snd_pcm_mmap_capture_avail(pcm);
|
avail = snd_pcm_mmap_capture_avail(pcm);
|
||||||
}
|
}
|
||||||
empty = avail < pcm->avail_min;
|
empty = avail < pcm->avail_min;
|
||||||
if (empty) {
|
|
||||||
snd_pcm_direct_clear_timer_queue(dmix);
|
|
||||||
events &= ~(POLLOUT|POLLIN);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
switch (snd_pcm_state(dmix->spcm)) {
|
switch (snd_pcm_state(dmix->spcm)) {
|
||||||
case SND_PCM_STATE_XRUN:
|
case SND_PCM_STATE_XRUN:
|
||||||
|
|
@ -482,6 +478,10 @@ int snd_pcm_direct_poll_revents(snd_pcm_t *pcm, struct pollfd *pfds, unsigned in
|
||||||
events |= POLLERR;
|
events |= POLLERR;
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
|
if (empty) {
|
||||||
|
snd_pcm_direct_clear_timer_queue(dmix);
|
||||||
|
events &= ~(POLLOUT|POLLIN);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
*revents = events;
|
*revents = events;
|
||||||
|
|
|
||||||
|
|
@ -312,7 +312,7 @@ static int _snd_pcm_dmix_sync_ptr(snd_pcm_t *pcm, int do_slave_sync)
|
||||||
dmix->avail_max = avail;
|
dmix->avail_max = avail;
|
||||||
if (avail >= pcm->stop_threshold) {
|
if (avail >= pcm->stop_threshold) {
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
snd_pcm_direct_timer_stop(dmix);
|
snd_timer_stop(dmix->timer);
|
||||||
gettimeofday(&tv, 0);
|
gettimeofday(&tv, 0);
|
||||||
dmix->trigger_tstamp.tv_sec = tv.tv_sec;
|
dmix->trigger_tstamp.tv_sec = tv.tv_sec;
|
||||||
dmix->trigger_tstamp.tv_nsec = tv.tv_usec * 1000L;
|
dmix->trigger_tstamp.tv_nsec = tv.tv_usec * 1000L;
|
||||||
|
|
@ -321,6 +321,8 @@ static int _snd_pcm_dmix_sync_ptr(snd_pcm_t *pcm, int do_slave_sync)
|
||||||
return -EPIPE;
|
return -EPIPE;
|
||||||
}
|
}
|
||||||
dmix->state = SND_PCM_STATE_SETUP;
|
dmix->state = SND_PCM_STATE_SETUP;
|
||||||
|
/* clear queue to remove pending poll events */
|
||||||
|
snd_pcm_direct_clear_timer_queue(dmix);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue