diff options
Diffstat (limited to 'sound/core/isadma.c')
-rw-r--r-- | sound/core/isadma.c | 10 |
1 files changed, 9 insertions, 1 deletions
diff --git a/sound/core/isadma.c b/sound/core/isadma.c index 79f0f16af339..950e19ba91fc 100644 --- a/sound/core/isadma.c +++ b/sound/core/isadma.c @@ -85,16 +85,24 @@ EXPORT_SYMBOL(snd_dma_disable); unsigned int snd_dma_pointer(unsigned long dma, unsigned int size) { unsigned long flags; - unsigned int result; + unsigned int result, result1; flags = claim_dma_lock(); clear_dma_ff(dma); if (!isa_dma_bridge_buggy) disable_dma(dma); result = get_dma_residue(dma); + /* + * HACK - read the counter again and choose higher value in order to + * avoid reading during counter lower byte roll over if the + * isa_dma_bridge_buggy is set. + */ + result1 = get_dma_residue(dma); if (!isa_dma_bridge_buggy) enable_dma(dma); release_dma_lock(flags); + if (unlikely(result < result1)) + result = result1; #ifdef CONFIG_SND_DEBUG if (result > size) snd_printk(KERN_ERR "pointer (0x%x) for DMA #%ld is greater than transfer size (0x%x)\n", result, dma, size); |