After suspend and resume, the alsa driver is stopped. But if alsa-lib run
into snd_pcm_xxxx_drain(), it need to wait avail >= pcm->stop_threshold,
otherwise, it will not exit the loop, so finally it is blocked at poll() of
snd_pcm_wait_nocheck(pcm, -1).
This patch is to add state check after snd_pcm_wait_nocheck(pcm, -1), if
the state is SND_PCM_STATE_SUSPENDED, then return error.
Signed-off-by: Shengjiu Wang <shengjiu.wang@freescale.com>
Signed-off-by: Takashi Iwai <tiwai@suse.de>
snd_pcm_uframes_t stop_threshold;
int err;
+ switch (snd_pcm_state(dmix->spcm)) {
+ case SND_PCM_STATE_SUSPENDED:
+ return -ESTRPIPE;
+ default:
+ break;
+ }
+
if (dmix->state == SND_PCM_STATE_OPEN)
return -EBADFD;
if (pcm->mode & SND_PCM_NONBLOCK)
snd_pcm_dmix_sync_area(pcm);
snd_pcm_wait_nocheck(pcm, -1);
snd_pcm_direct_clear_timer_queue(dmix); /* force poll to wait */
+
+ switch (snd_pcm_state(dmix->spcm)) {
+ case SND_PCM_STATE_SUSPENDED:
+ return -ESTRPIPE;
+ default:
+ break;
+ }
}
} while (dmix->state == SND_PCM_STATE_DRAINING);
pcm->stop_threshold = stop_threshold;
snd_pcm_uframes_t stop_threshold;
int err;
+ switch (snd_pcm_state(dshare->spcm)) {
+ case SND_PCM_STATE_SUSPENDED:
+ return -ESTRPIPE;
+ default:
+ break;
+ }
+
if (dshare->state == SND_PCM_STATE_OPEN)
return -EBADFD;
if (pcm->mode & SND_PCM_NONBLOCK)
snd_pcm_dshare_sync_area(pcm);
snd_pcm_wait_nocheck(pcm, -1);
snd_pcm_direct_clear_timer_queue(dshare); /* force poll to wait */
+
+ switch (snd_pcm_state(dshare->spcm)) {
+ case SND_PCM_STATE_SUSPENDED:
+ return -ESTRPIPE;
+ default:
+ break;
+ }
}
} while (dshare->state == SND_PCM_STATE_DRAINING);
pcm->stop_threshold = stop_threshold;