Skip to content

Commit 1e8b5d8

Browse files
committed
docs: dma-api: document __dma_from_device_group_begin()/end()
Document the __dma_from_device_group_begin()/end() annotations. Message-ID: <01ea88055ded4d70cac70ba557680fd5fa7d9ff5.1767601130.git.mst@redhat.com> Acked-by: Marek Szyprowski <m.szyprowski@samsung.com> Reviewed-by: Petr Tesarik <ptesarik@suse.com> Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
1 parent ca085fa commit 1e8b5d8

1 file changed

Lines changed: 52 additions & 0 deletions

File tree

Documentation/core-api/dma-api-howto.rst

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -146,6 +146,58 @@ What about block I/O and networking buffers? The block I/O and
146146
networking subsystems make sure that the buffers they use are valid
147147
for you to DMA from/to.
148148

149+
__dma_from_device_group_begin/end annotations
150+
=============================================
151+
152+
As explained previously, when a structure contains a DMA_FROM_DEVICE /
153+
DMA_BIDIRECTIONAL buffer (device writes to memory) alongside fields that the
154+
CPU writes to, cache line sharing between the DMA buffer and CPU-written fields
155+
can cause data corruption on CPUs with DMA-incoherent caches.
156+
157+
The ``__dma_from_device_group_begin(GROUP)/__dma_from_device_group_end(GROUP)``
158+
macros ensure proper alignment to prevent this::
159+
160+
struct my_device {
161+
spinlock_t lock1;
162+
__dma_from_device_group_begin();
163+
char dma_buffer1[16];
164+
char dma_buffer2[16];
165+
__dma_from_device_group_end();
166+
spinlock_t lock2;
167+
};
168+
169+
To isolate a DMA buffer from adjacent fields, use
170+
``__dma_from_device_group_begin(GROUP)`` before the first DMA buffer
171+
field and ``__dma_from_device_group_end(GROUP)`` after the last DMA
172+
buffer field (with the same GROUP name). This protects both the head
173+
and tail of the buffer from cache line sharing.
174+
175+
The GROUP parameter is an optional identifier that names the DMA buffer group
176+
(in case you have several in the same structure)::
177+
178+
struct my_device {
179+
spinlock_t lock1;
180+
__dma_from_device_group_begin(buffer1);
181+
char dma_buffer1[16];
182+
__dma_from_device_group_end(buffer1);
183+
spinlock_t lock2;
184+
__dma_from_device_group_begin(buffer2);
185+
char dma_buffer2[16];
186+
__dma_from_device_group_end(buffer2);
187+
};
188+
189+
On cache-coherent platforms these macros expand to zero-length array markers.
190+
On non-coherent platforms, they also ensure the minimal DMA alignment, which
191+
can be as large as 128 bytes.
192+
193+
.. note::
194+
195+
It is allowed (though somewhat fragile) to include extra fields, not
196+
intended for DMA from the device, within the group (in order to pack the
197+
structure tightly) - but only as long as the CPU does not write these
198+
fields while any fields in the group are mapped for DMA_FROM_DEVICE or
199+
DMA_BIDIRECTIONAL.
200+
149201
DMA addressing capabilities
150202
===========================
151203

0 commit comments

Comments
 (0)