From ba057abe909df7e2b9fba57e0db989e7ea47951b Mon Sep 17 00:00:00 2001 From: Daniel Drake Date: Tue, 21 May 2013 13:02:39 -0600 Subject: [PATCH] ALSA: HDA: handle FIFO errors The HDA code was listening for the FIFO error interrupt but not handling it. Such condition would tend to indicate an xrun. On OLPC XO-1.75 (VIA VX855) this interrupt seems to be erroneously raised on occasion, resulting in a halt of sound playback and the application hanging as no sound buffer space becomes available. Signed-off-by: Daniel Drake --- sound/pci/hda/hda_intel.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-) diff --git a/sound/pci/hda/hda_intel.c b/sound/pci/hda/hda_intel.c index de65fa8..c3ef376 100644 --- a/sound/pci/hda/hda_intel.c +++ b/sound/pci/hda/hda_intel.c @@ -1237,8 +1237,20 @@ static irqreturn_t azx_interrupt(int irq, void *dev_id) if (status & azx_dev->sd_int_sta_mask) { sd_status = azx_sd_readb(azx_dev, SD_STS); azx_sd_writeb(azx_dev, SD_STS, SD_INT_MASK); - if (!azx_dev->substream || !azx_dev->running || - !(sd_status & SD_INT_COMPLETE)) + if (!azx_dev->substream || !azx_dev->running) + continue; + + if (sd_status & SD_INT_FIFO_ERR) { + snd_pcm_stream_lock(azx_dev->substream); + spin_unlock(&chip->reg_lock); + snd_pcm_stop(azx_dev->substream, + SNDRV_PCM_STATE_XRUN); + spin_lock(&chip->reg_lock); + snd_pcm_stream_unlock(azx_dev->substream); + continue; + } + + if (!(sd_status & SD_INT_COMPLETE)) continue; /* check whether this IRQ is really acceptable */ ok = azx_position_ok(chip, azx_dev); -- 1.8.1.4