DF-5520 / fix.diff
--- a/sys/bus/isa/x86_64/isa_dma.c 2026-10-06 20:51:42.700616456 +0000 +++ b/sys/bus/isa/x86_64/isa_dma.c 2026-10-06 20:52:35.127935134 +0000 @@ -169,12 +169,12 @@ if (dma_busy & (1 << chan)) { dma_busy &= ~(1 << chan); - /* - * XXX We should also do "dma_bounced &= (1 << chan);" - * because we are acting on behalf of isa_dmadone() which - * was not called to end the last DMA operation. This does - * not matter now, but it may in the future. + /* + * We are acting on behalf of isa_dmadone() which was not + * called to end the last DMA operation; drop any stale + * bounce state so it cannot poison the next transfer. */ + dma_bounced &= ~(1 << chan); } dma_inuse &= ~(1 << chan); @@ -350,8 +350,17 @@ if (dma_bounced & (1 << chan)) { /* copy bounce buffer on read */ - if (flags & ISADMA_READ) - bcopy(dma_bouncebuf[chan], addr, nbytes); + if (flags & ISADMA_READ) { + u_int n = (u_int)nbytes; + + if (n > dma_bouncebufsize[chan]) { + kprintf("isa_dmadone: count %u exceeds bounce " + "buffer size %u, clamping\n", + n, dma_bouncebufsize[chan]); + n = dma_bouncebufsize[chan]; + } + bcopy(dma_bouncebuf[chan], addr, n); + } dma_bounced &= ~(1 << chan); } |