Skip to content

Commit 293dfe2

Browse files
tlaudajajanusz
authored andcommitted
hda-dma: refactor xrun handling
Changes behaviour of HDA Link overruns and underruns handling. Let's no longer stop the stream, but just report an error. It might happen that just after the release buffer is still full/not yet empty after the previous run, but it shouldn't affect the data, since stream has been paused anyway. Also adds additional bit to better reflect hardware registers. Signed-off-by: Tomasz Lauda <tomasz.lauda@linux.intel.com>
1 parent 8e5ab9c commit 293dfe2

File tree

1 file changed

+10
-13
lines changed

1 file changed

+10
-13
lines changed

src/drivers/intel/cavs/hda-dma.c

Lines changed: 10 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -50,7 +50,9 @@
5050
#define DGCS_GEN BIT(26)
5151
#define DGCS_FWCB BIT(23)
5252
#define DGCS_BSC BIT(11)
53-
#define DGCS_BOR BIT(10) /* buffer overrun */
53+
/* NOTE: both XRUN bits are the same, just direction is different */
54+
#define DGCS_BOR BIT(10) /* buffer overrun (input streams) */
55+
#define DGCS_BUR BIT(10) /* buffer underrun (output streams) */
5456
#define DGCS_BF BIT(9) /* buffer full */
5557
#define DGCS_BNE BIT(8) /* buffer not empty */
5658
#define DGCS_FIFORDY BIT(5) /* enable FIFO */
@@ -778,19 +780,14 @@ static int hda_dma_remove(struct dma *dma)
778780

779781
static int hda_dma_link_check_xrun(struct dma_chan_data *chan)
780782
{
781-
uint32_t dgcs;
783+
uint32_t dgcs = dma_chan_reg_read(chan, DGCS);
782784

783-
if (chan->direction == DMA_DIR_MEM_TO_DEV ||
784-
chan->direction == DMA_DIR_DEV_TO_MEM) {
785-
/* check for link xruns */
786-
dgcs = dma_chan_reg_read(chan, DGCS);
787-
if (dgcs & DGCS_BOR) {
788-
trace_hddma_error("hda_dma_link_check_xrun() error: "
789-
"xrun detected");
790-
dma_chan_reg_update_bits(chan, DGCS, DGCS_BOR,
791-
DGCS_BOR);
792-
return -ENODATA;
793-
}
785+
if (chan->direction == DMA_DIR_MEM_TO_DEV && dgcs & DGCS_BUR) {
786+
trace_hddma_error("hda_dma_link_check_xrun() error: underrun detected");
787+
dma_chan_reg_update_bits(chan, DGCS, DGCS_BUR, DGCS_BUR);
788+
} else if (chan->direction == DMA_DIR_DEV_TO_MEM && dgcs & DGCS_BOR) {
789+
trace_hddma_error("hda_dma_link_check_xrun() error: overrun detected");
790+
dma_chan_reg_update_bits(chan, DGCS, DGCS_BOR, DGCS_BOR);
794791
}
795792

796793
return 0;

0 commit comments

Comments
 (0)