[Bug 297155] LinuxKPI: swapped busdma sync operations in the DMA_TO_DEVICE / DMA_FROM_DEVICE PRE-sync path break streaming DMA when a mapping bounces (breaks ath10k QCA6174 on >4GB machines)
[email protected] Thu, 30 Jul 2026 03:19:52 +0000
| Newsgroups | gmane.os.freebsd.bugs |
|---|---|
| Message-ID | <[email protected]/bugzilla/> |
https://bugs.freebsd.org/bugzilla/show_bug.cgi?id=3D297155
Bug ID: 297155
Summary: LinuxKPI: swapped busdma sync operations in the
DMA_TO_DEVICE / DMA_FROM_DEVICE PRE-sync path break
streaming DMA when a mapping bounces (breaks ath10k
QCA6174 on >4GB machines)
Product: Base System
Version: CURRENT
Hardware: amd64
OS: Any
Status: New
Severity: Affects Some People
Priority: ---
Component: kern
Assignee: [email protected]
Reporter: [email protected]
Created attachment 273303
--> https://bugs.freebsd.org/bugzilla/attachment.cgi?id=3D273303&action=
=3Dedit
swapped busdma sync operations in the DMA_TO_DEVICE / DMA_FROM_DEVICE
LinuxKPI: fix swapped busdma sync ops in DMA_TO_DEVICE/FROM_DEVICE PRE-sync=
=20=20=20=20=20
dma_sync_single_for_device() and the PRE-sync switch in=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20
linux_dma_map_sg_attrs() transpose the busdma sync operations for the=20=20=
=20=20=20=20=20=20=20=20=20
DMA_TO_DEVICE and DMA_FROM_DEVICE directions.=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20
Per the Linux DMA API, dma_sync_single_for_device() on a DMA_TO_DEVICE=20=
=20=20=20=20=20=20=20=20=20
mapping must make the CPU's writes visible to the device before it reads=20=
=20=20=20=20=20=20=20
the buffer. For a bounce buffer that means copying the client buffer into=
=20=20=20=20=20=20=20
the bounce page, which busdma performs on BUS_DMASYNC_PREWRITE (see=20=20=
=20=20=20=20=20=20=20=20=20=20=20
bounce_bus_dmamap_sync() in sys/x86/x86/busdma_bounce.c: PREWRITE does=20=
=20=20=20=20=20=20=20=20=20
bcopy(client -> bounce); PREREAD moves no data). The code instead issued=20=
=20=20=20=20=20=20=20
BUS_DMASYNC_PREREAD for DMA_TO_DEVICE (a no-op) and BUS_DMASYNC_PREWRITE=20=
=20=20=20=20=20=20=20
for DMA_FROM_DEVICE.=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20
The bug is only observable when a streaming mapping actually bounces,=20=20=
=20=20=20=20=20=20=20=20=20
i.e. a device with a sub-64-bit DMA mask on a machine with RAM above the=20=
=20=20=20=20=20=20=20
mask limit. Most LinuxKPI drivers use a 64-bit mask and never bounce, so=20=
=20=20=20=20=20=20=20
the wrong op was a harmless no-op. ath10k(4) (QCA6174) forces a 32-bit=20=
=20=20=20=20=20=20=20=20=20
mask via dma_set_mask_and_coherent(DMA_BIT_MASK(32)); on a >4GB machine=20=
=20=20=20=20=20=20=20=20
its BMI request buffer (DMA_TO_DEVICE) is never copied into the bounce=20=
=20=20=20=20=20=20=20=20=20
page, the target never sees the command, and firmware probe fails with:=20=
=20=20=20=20=20=20=20=20
ath10k0: bmi cmd took 3009 jiffies hz 1000 ret -60=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20
ath10k0: could not get target info (-60)=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=
=20
ath10k0: could not probe fw (-60)=20=20=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=
=20=20=20=20=20=20
Capping physmem below 4GB (no bounce) or applying this patch both resolve=
=20=20=20=20=20=20=20
it; with the patch ath10k attaches and scans normally at full 16GB.=20=20=
=20=20=20=20=20=20=20=20=20=20=20
The POST-sync paths (dma_sync_single_for_cpu(), linux_dma_unmap_sg_attrs())=
=20=20=20=20=20
already use the conventional DMA_TO_DEVICE->POSTWRITE /=20=20=20=20=20=20=
=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20=20
DMA_FROM_DEVICE->POSTREAD mapping; only the two PRE switches were swapped.=
=20=20=20=20=20=20
This change makes PRE match. DMA_BIDIRECTIONAL (PREWRITE) is unchanged.
--=20
You are receiving this mail because:
You are the assignee for the bug.=