xref: /dragonfly/share/man/man9/bus_dma.9 (revision 32efd857)
1.\"
2.\" Copyright (c) 2002, 2003, 2004 The DragonFly Project.  All rights reserved.
3.\"
4.\" This code is derived from software contributed to The DragonFly Project
5.\" by Hiten Pandya <hmp@backplane.com>.
6.\"
7.\" Redistribution and use in source and binary forms, with or without
8.\" modification, are permitted provided that the following conditions
9.\" are met:
10.\"
11.\" 1. Redistributions of source code must retain the above copyright
12.\"    notice, this list of conditions and the following disclaimer.
13.\" 2. Redistributions in binary form must reproduce the above copyright
14.\"    notice, this list of conditions and the following disclaimer in
15.\"    the documentation and/or other materials provided with the
16.\"    distribution.
17.\" 3. Neither the name of The DragonFly Project nor the names of its
18.\"    contributors may be used to endorse or promote products derived
19.\"    from this software without specific, prior written permission.
20.\"
21.\" THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23.\" LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24.\" FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
25.\" COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26.\" INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
27.\" BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
28.\" LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29.\" AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30.\" OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31.\" OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
32.\" SUCH DAMAGE.
33.\"
34.\" Copyright (c) 1996, 1997, 1998, 2001 The NetBSD Foundation, Inc.
35.\" All rights reserved.
36.\"
37.\" This code is derived from software contributed to The NetBSD Foundation
38.\" by Jason R. Thorpe of the Numerical Aerospace Simulation Facility,
39.\" NASA Ames Research Center.
40.\"
41.\" Redistribution and use in source and binary forms, with or without
42.\" modification, are permitted provided that the following conditions
43.\" are met:
44.\" 1. Redistributions of source code must retain the above copyright
45.\"    notice, this list of conditions and the following disclaimer.
46.\" 2. Redistributions in binary form must reproduce the above copyright
47.\"    notice, this list of conditions and the following disclaimer in the
48.\"    documentation and/or other materials provided with the distribution.
49.\" 3. All advertising materials mentioning features or use of this software
50.\"    must display the following acknowledgment:
51.\" 	This product includes software developed by the NetBSD
52.\" 	Foundation, Inc. and its contributors.
53.\" 4. Neither the name of The NetBSD Foundation nor the names of its
54.\"    contributors may be used to endorse or promote products derived
55.\"    from this software without specific prior written permission.
56.\"
57.\" THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
58.\" ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
59.\" TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
60.\" PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
61.\" BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
62.\" CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
63.\" SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
64.\" INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
65.\" CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
66.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
67.\" POSSIBILITY OF SUCH DAMAGE.
68.\"
69.\" $FreeBSD: /repoman/r/ncvs/src/share/man/man9/bus_dma.9,v 1.7 2003/07/27 14:05:29 mux Exp $
70.\" $NetBSD: bus_dma.9,v 1.25 2002/10/14 13:43:16 wiz Exp $
71.\"
72.Dd January 27, 2018
73.Dt BUS_DMA 9
74.Os
75.Sh NAME
76.Nm bus_dma ,
77.Nm bus_dma_tag_create ,
78.Nm bus_dma_tag_destroy ,
79.Nm bus_dmamap_create ,
80.Nm bus_dmamap_destroy ,
81.Nm bus_dmamap_load ,
82.Nm bus_dmamap_load_ccb ,
83.Nm bus_dmamap_load_mbuf ,
84.Nm bus_dmamap_load_mbuf_segment ,
85.Nm bus_dmamap_load_mbuf_defrag ,
86.Nm bus_dmamap_load_uio ,
87.Nm bus_dmamap_unload ,
88.Nm bus_dmamap_sync ,
89.Nm bus_dmamem_alloc ,
90.Nm bus_dmamem_coherent ,
91.Nm bus_dmamem_coherent_any ,
92.Nm bus_dmamem_free
93.Nd Bus and Machine Independent DMA Mapping Interface
94.Sh SYNOPSIS
95.In sys/bus.h
96.Ft int
97.Fn bus_dma_tag_create "bus_dma_tag_t parent" "bus_size_t alignment" \
98"bus_size_t boundary" "bus_addr_t lowaddr" "bus_addr_t highaddr" \
99"bus_dma_filter_t *filtfunc" "void *filtfuncarg" "bus_size_t maxsize" \
100"int nsegments" "bus_size_t maxsegsz" "int flags" "bus_dma_tag_t *dmat"
101.Ft int
102.Fn bus_dma_tag_destroy "bus_dma_tag_t dmat"
103.Ft int
104.Fn bus_dmamap_create "bus_dma_tag_t dmat" "int flags" "bus_dmamap_t *mapp"
105.Ft int
106.Fn bus_dmamap_destroy "bus_dma_tag_t dmat" "bus_dmamap_t map"
107.Ft int
108.Fn bus_dmamap_load "bus_dma_tag_t dmat" "bus_dmamap_t map" "void *buf" \
109"bus_size_t buflen" "bus_dmamap_callback_t *callback" "void *callback_arg" \
110"int flags"
111.Ft int
112.Fn bus_dmamap_load_ccb "bus_dma_tag_t dmat" "bus_dmamap_t map" \
113"union ccb *ccb" "bus_dmamap_callback_t *callback" "void *callback_arg" \
114"int flags"
115.Ft int
116.Fn bus_dmamap_load_mbuf "bus_dma_tag_t dmat" "bus_dmamap_t map" \
117"struct mbuf *mbuf" "bus_dmamap_callback2_t *callback" "void *callback_arg" \
118"int flags"
119.Ft int
120.Fn bus_dmamap_load_mbuf_segment "bus_dma_tag_t dmat" "bus_dmamap_t map" \
121"struct mbuf *mbuf" "bus_dma_segment_t *segs" "int maxsegs" "int *nsegs" \
122"int flags"
123.Ft int
124.Fn bus_dmamap_load_mbuf_defrag "bus_dma_tag_t dmat" "bus_dmamap_t map" \
125"struct mbuf **mbuf" "bus_dma_segment_t *segs" "int maxsegs" "int *nsegs" \
126"int flags"
127.Ft int
128.Fn bus_dmamap_load_uio "bus_dma_tag_t dmat" "bus_dmamap_t map" \
129"struct uio *uio" "bus_dmamap_callback2_t *callback" "void *callback_arg" \
130"int flags"
131.Ft int
132.Fn bus_dmamem_alloc "bus_dma_tag_t dmat" "void **vaddr" \
133"int flags" "bus_dmamap_t *mapp"
134.Ft int
135.Fn bus_dmamem_coherent "bus_dma_tag_t parent" "bus_size_t alignment" \
136"bus_size_t boundary" "bus_addr_t lowaddr" "bus_addr_t highaddr" \
137"bus_size_t maxsize" "int flags" "bus_dmamem_t *dmem"
138.Ft void *
139.Fn bus_dmamem_coherent_any "bus_dma_tag_t parent" "bus_size_t alignment" \
140"bus_size_t maxsize" "int flags" "bus_dma_tag_t *dtag" "bus_dmamap_t *dmap" \
141"bus_addr_t *busaddr"
142.Ft void
143.Fn bus_dmamap_unload "bus_dma_tag_t dmat" "bus_dmamap_t map"
144.Ft void
145.Fn bus_dmamap_sync "bus_dma_tag_t dmat" "bus_dmamap_t map" \
146"bus_dmasync_op_t op"
147.Ft void
148.Fn bus_dmamem_free "bus_dma_tag_t dmat" "void *vaddr" \
149"bus_dmamap_t map"
150.Sh DESCRIPTION
151Direct Memory Access (DMA) is a method of transferring data
152without involving the CPU, thus providing higher performance.
153A DMA transaction can be achieved between device to memory,
154device to device, or memory to memory.
155.Pp
156The
157.Nm
158API is a bus, device, and machine-independent (MI) interface to
159DMA mechanisms.
160It provides the client with flexibility and simplicity by
161abstracting machine dependent issues like setting up
162DMA mappings, handling cache issues, bus specific features
163and limitations.
164.Sh STRUCTURES AND TYPES
165.Bl -tag -width compact
166.It Vt bus_dma_tag_t
167A machine-dependent (MD) opaque type that describes the
168characteristics of DMA transactions.
169DMA tags are organized into a hierarchy, with each child
170tag inheriting the restrictions of its parent.
171This allows all devices along the path of DMA transactions
172to contribute to the constraints of those transactions.
173.It Vt bus_dma_filter_t
174Client specified address filter having the format:
175.Bl -tag -width compact
176.It Ft int
177.Fn "client_filter" "void *filtarg" "bus_addr_t testaddr"
178.El
179.sp
180Address filters can be specified during tag creation to allow
181for devices who's DMA address restrictions cannot be specified
182by a single window.
183The
184.Fa filtarg
185is client specified during tag creation to be passed to all
186invocations of the callback.
187The
188.Fa testaddr
189argument contains a potential starting address of a DMA mapping.
190The filter function operates on the set of addresses from
191.Fa testaddr
192to
193.Ql trunc_page(testaddr) + PAGE_SIZE - 1 ,
194inclusive.
195The filter function should return zero for any mapping in this range
196that can be accommodated by the device and non-zero otherwise.
197.It Vt bus_dma_segment_t
198A machine-dependent type that describes individual
199DMA segments.
200.Bd -literal
201	bus_addr_t	ds_addr;
202	bus_size_t	ds_len;
203.Ed
204.sp
205The
206.Fa ds_addr
207field contains the device visible address of the DMA segment, and
208.Fa ds_len
209contains the length of the DMA segment.
210Although the DMA segments returned by a mapping call will adhere to
211all restrictions necessary for a successful DMA operation, some conversion
212(e.g. a conversion from host byte order to the device's byte order) is
213almost always required when presenting segment information to the device.
214.It Vt bus_dmamap_t
215A machine-dependent opaque type describing an individual mapping.
216Multiple DMA maps can be associated with one DMA tag.
217.It Vt bus_dmamem_t
218A machine-dependent type that describes DMA memory created by
219.Fn bus_dmamem_coherent .
220.Bd -literal
221	bus_dma_tag_t	dmem_tag;
222	bus_dmamap_t	dmem_map;
223	void		*dmem_addr;
224	bus_addr_t	dmem_busaddr;
225.Ed
226.sp
227The
228.Fa dmem_tag
229field contains the DMA tag of the DMA memory and
230.Fa dmem_map
231field contains the DMA map of the DMA memory.
232The
233.Fa dmem_addr
234field points to the allocated DMA memory in kernel virtual address space.
235The
236.Fa dmem_busaddr
237field contains the device visible address of the DMA memory.
238.It Vt bus_dmamap_callback_t
239Client specified callback for receiving mapping information resulting from
240the load of a
241.Vt bus_dmamap_t
242via
243.Fn bus_dmamap_load
244or
245.Fn bus_dmamap_load_ccb .
246Callbacks are of the format:
247.Bl -tag -width compact
248.It Ft void
249.Fn "client_callback" "void *callback_arg" "bus_dma_segment_t *segs" \
250"int nseg" "int error"
251.El
252.sp
253The
254.Fa callback_arg
255is the callback argument passed to dmamap load functions.
256The
257.Fa segs
258and
259.Fa nseg
260parameters describe an array of
261.Vt bus_dma_segment_t
262structures that represent the mapping.
263This array is only valid within the scope of the callback function.
264The success or failure of the mapping is indicated by the
265.Fa error
266parameter.
267More information on the use of callbacks can be found in the
268description of the individual dmamap load functions.
269.It Vt bus_dmamap_callback2_t
270Client specified callback for receiving mapping information resulting from
271the load of a
272.Vt bus_dmamap_t
273via
274.Fn bus_dmamap_load_uio
275or
276.Fn bus_dmamap_load_mbuf .
277.sp
278Callback2s are of the format:
279.Bl -tag -width compact
280.It Ft void
281.Fn "client_callback2" "void *callback_arg" "bus_dma_segment_t *segs" \
282"int nseg" "bus_size_t mapsize" "int error"
283.El
284.sp
285Callback2's behavior is the same as
286.Vt bus_dmamap_callback_t
287with the addition that the length of the data mapped is provided via
288.Fa mapsize .
289.It Vt bus_dmasync_op_t
290Memory synchronization operation specifier.
291Bus DMA requires explicit synchronization of memory with its device
292visible mapping in order to guarantee memory coherency.
293The
294.Vt bus_dmasync_op_t
295allows the type of DMA operation that will be or has been performed
296to be communicated to the system so that the correct coherency measures
297are taken.
298All operations specified below are performed from the DMA engine's
299point of view:
300.Bl -tag -width BUS_DMASYNC_POSTWRITE
301.It Dv BUS_DMASYNC_PREREAD
302Perform any synchronization required after an update of memory by the CPU
303but prior to DMA read operations.
304.It Dv BUS_DMASYNC_PREWRITE
305Perform any synchronization required after an update of memory by the CPU
306but prior to DMA write operations.
307.It Dv BUS_DMASYNC_POSTREAD
308Perform any synchronization required after DMA read operations, but prior
309to CPU access of the memory.
310.It Dv BUS_DMASYNC_POSTWRITE
311Perform any synchronization required after DMA write operations, but prior
312to CPU access of the memory.
313.El
314.El
315.sp
316.Sh FUNCTIONS
317.Bl -tag -width compact
318.It Fn bus_dma_tag_create "parent" "alignment" "boundary" "lowaddr" \
319"highaddr" "*filtfunc" "*filtfuncarg" "maxsize" "nsegments" "maxsegsz" \
320"flags" "*dmat"
321Allocates a device specific DMA tag, and initializes it according to
322the arguments provided:
323.Bl -tag -width *filtfuncarg -compact
324.It Fa parent
325Indicates restrictions between the parent bridge, CPU memory, and the
326device.
327May be NULL, if no DMA restrictions are to be inherited.
328.It Fa alignment
329Alignment constraint, in bytes, of any mappings created using this tag.
330The alignment must be a power of 2.
331Hardware that can DMA starting at any address would specify
332.Em 1
333for byte alignment.
334Hardware requiring DMA transfers to start on a multiple of 4K
335would specify
336.Em 4096 .
337.It Fa boundary
338Boundary constraint, in bytes, of the target DMA memory region.
339The boundary indicates the set of addresses, all multiples of the
340boundary argument, that cannot be crossed by a single
341.Vt bus_dma_segment_t .
342The boundary must be either a power of 2 or 0.
343.Ql 0
344indicates that there are no boundary restrictions.
345.It Fa lowaddr
346.It Fa highaddr
347Bounds of the window of bus address space that
348.Em cannot
349be directly accessed by the device.
350The window contains all address greater than lowaddr and
351less than or equal to highaddr.
352For example, a device incapable of DMA above 4GB, would specify
353a highaddr of
354.Dv BUS_SPACE_MAXADDR
355and a lowaddr of
356.Dv BUS_SPACE_MAXADDR_32BIT .
357Similarly a device that can only dma to addresses below 16MB would
358specify a highaddr of
359.Dv BUS_SPACE_MAXADDR
360and a lowaddr of
361.Dv BUS_SPACE_MAXADDR_24BIT .
362Some implementations requires that some region of device visible
363address space, overlapping available host memory, be outside the
364window.
365This area of
366.Ql safe memory
367is used to bounce requests that would otherwise conflict with
368the exclusion window.
369.It Fa filtfunc
370Optional filter function (may be NULL) to be called for any attempt to
371map memory into the window described by
372.Fa lowaddr
373and
374.Fa highaddr .
375A filter function is only required when the single window described
376by
377.Fa lowaddr
378and
379.Fa highaddr
380cannot adequately describe the constraints of the device.
381The filter function will be called for every machine page
382that overlaps the exclusion window.
383.It Fa filtfuncarg
384Argument passed to all calls to the filter function for this tag.
385May be NULL.
386.It Fa maxsize
387Maximum size, in bytes, of the sum of all segment lengths in a given
388DMA mapping associated with this tag.
389.It Fa nsegments
390Number of discontinuities (scatter/gather segments) allowed
391in a DMA mapped region.
392If there is no restriction,
393.Dv BUS_SPACE_UNRESTRICTED
394may be specified for the tag intended to be used as the parent.
395.Dv BUS_SPACE_UNRESTRICTED
396must not be specified for the tags
397which will be used to create maps.
398For tags which will be used to create maps,
399this argument must be less than 16384 on x86_64.
400.It Fa maxsegsz
401Maximum size, in bytes, of a segment in any DMA mapped region associated
402with
403.Fa dmat .
404.It Fa flags
405Are as follows:
406.Bl -tag -width ".Dv BUS_DMA_PRIVBZONE" -compact
407.It Dv BUS_DMA_ALLOCNOW
408Allocate the minimum resources necessary to guarantee that all map load
409operations associated with this tag may not block.
410If sufficient resources are not available,
411.Er ENOMEM
412is returned.
413.It Dv BUS_DMA_WAITOK
414Indicates that it is OK to wait for resources.
415However,
416unlike
417.Xr kmalloc 9 ,
418it is not guaranteed that the resource allocation will succeed.
419This flag is the default one,
420if
421.Dv BUS_DMA_NOWAIT
422is not supplied.
423.It Dv BUS_DMA_NOWAIT
424If the resource allocation request cannot be immediately fulfilled,
425.Er ENOMEM
426is returned.
427.It Dv BUS_DMA_ONEBPAGE
428Allocte one bounce page at most,
429even if the
430.Fa maxsize
431indicates that multiple bounce pages are needed.
432.It Dv BUS_DMA_ALIGNED
433Indicates that all memory to be loaded into the DMA maps associated
434with this DMA tag is properly aligned according to
435.Fa alignment
436constraint.
437No resources,
438e.g. bounce pages,
439will be allocated due to the
440.Fa alignment
441constraint.
442If unaligned memory was loaded into the DMA maps associated with this DMA tag,
443system will panic.
444.It Dv BUS_DMA_PRIVBZONE
445Uses a private bounce zone instead of a shared one.
446A private bounce zone will vanish if the DMA tag is destroyed.
447.It Dv BUS_DMA_ALLOCALL
448Allocate all required resources (mainly the bounce buffer).
449If any allocation fails,
450.Fn bus_dma_tag_create
451fails.
452.It Dv BUS_DMA_PROTECTED
453All of the functions called with the DMA tag are already protected by the
454caller, so the
455.Nm
456code need not protect the internal data structures.
457.El
458.It Fa dmat
459Pointer to a bus_dma_tag_t where the resulting DMA tag will
460be stored.
461.El
462.Pp
463Returns
464.Er ENOMEM
465if sufficient memory is not available for tag creation
466or allocating mapping resources.
467.It Fn bus_dma_tag_destroy "dmat"
468Deallocate the DMA tag
469.Fa dmat
470that was created by
471.Fn bus_dma_tag_create .
472.Pp
473Returns
474.Er EBUSY
475if any DMA maps remain associated with
476.Fa dmat
477or
478.Ql 0
479on success.
480.It Fn bus_dmamap_create "dmat" "flags" "*mapp"
481Allocates and initializes a DMA map.
482Arguments are as follows:
483.Bl -tag -width nsegments -compact
484.It Fa dmat
485DMA tag.
486.It Fa flags
487Are as follows:
488.Bl -tag -width ".Dv BUS_DMA_ONEBPAGE" -compact
489.It Dv BUS_DMA_WAITOK
490Indicates that it is OK to wait for resources.
491However,
492unlike
493.Xr kmalloc 9 ,
494it is not guaranteed that the resource allocation will succeed.
495This flag is the default one,
496if
497.Dv BUS_DMA_NOWAIT
498is not supplied.
499.It Dv BUS_DMA_NOWAIT
500If the resource allocation request cannot be immediately fulfilled,
501.Er ENOMEM
502is returned.
503.It Dv BUS_DMA_ONEBPAGE
504Allocte one bounce page at most,
505even if the
506.Fa maxsize
507used to create the
508.Fa dmat
509indicates that multiple bounce pages are needed.
510.El
511.It Fa mapp
512Pointer to a
513.Vt bus_dmamap_t
514where the resulting DMA map will be stored.
515.El
516.Pp
517Returns
518.Er ENOMEM
519if sufficient memory is not available for creating the
520map or allocating mapping resources.
521.It Fn bus_dmamap_destroy "dmat" "map"
522Frees all resources associated with a given DMA map.
523Arguments are as follows:
524.Bl -tag -width dmat -compact
525.It Fa dmat
526DMA tag used to allocate
527.Fa map .
528.It Fa map
529The DMA map to destroy.
530.El
531.Pp
532Returns
533.Er EBUSY
534if a mapping is still active for
535.Fa map .
536.It Fn bus_dmamap_load "dmat" "map" "buf" "buflen" "*callback" "..."
537Creates a mapping in device visible address space of
538.Fa buflen
539bytes of
540.Fa buf ,
541associated with the DMA map
542.Fa map .
543Arguments are as follows:
544.Bl -tag -width buflen -compact
545.It Fa dmat
546DMA tag used to allocate
547.Fa map .
548.It Fa map
549A DMA map without a currently active mapping.
550.It Fa buf
551A kernel virtual address pointer to a contiguous (in KVA) buffer, to be
552mapped into device visible address space.
553.It Fa buflen
554The size of the buffer.
555.It Fa callback Fa callback_arg
556The callback function, and its argument.
557.It Fa flags
558The value of this argument is currently undefined, and should be
559specified as
560.Ql 0 .
561.El
562.Pp
563Return values to the caller are as follows:
564.Bl -tag -width ".Er EINPROGRESS" -compact
565.It 0
566The callback has been called and completed.
567The status of the mapping has been delivered to the callback.
568.It Er EINPROGRESS
569The mapping has been deferred for lack of resources.
570The callback will be called as soon as resources are available.
571Callbacks are serviced in FIFO order.
572DMA maps created from DMA tags that are allocated with
573the
574.Dv BUS_DMA_ALLOCNOW
575flag will never return this status for a load operation.
576.It Er EINVAL
577The load request was invalid.
578The callback has not, and will not be called.
579This error value may indicate that
580.Fa dmat ,
581.Fa map ,
582.Fa buf ,
583or
584.Fa callback
585were invalid, or
586.Fa buslen
587was larger than the
588.Fa maxsize
589argument used to create the dma tag
590.Fa dmat .
591.El
592.Pp
593When the callback is called, it is presented with an error value
594indicating the disposition of the mapping.
595Error may be one of the following:
596.Bl -tag -width ".Er EINPROGRESS" -compact
597.It 0
598The mapping was successful and the
599.Fa dm_segs
600callback argument contains an array of
601.Vt bus_dma_segment_t
602elements describing the mapping.
603This array is only valid during the scope of the callback function.
604.It Er EFBIG
605A mapping could not be achieved within the segment constraints provided
606in the tag even though the requested allocation size was less than maxsize.
607.El
608.It Fn bus_dmamap_load_ccb "dmat" "map" "ccb" "callback" "callback_arg" "flags"
609This is a variation of
610.Fn bus_dmamap_load
611which maps data pointed to by
612.Fa ccb
613for DMA transfers.
614.It Fn bus_dmamap_load_mbuf "dmat" "map" "mbuf" "callback2" "callback_arg" \
615"flags"
616This is a variation of
617.Fn bus_dmamap_load
618which maps mbuf chains
619for DMA transfers.
620A
621.Vt bus_size_t
622argument is also passed to the callback routine, which
623contains the mbuf chain's packet header length.
624.Pp
625Mbuf chains are assumed to be in kernel virtual address space.
626.Pp
627Returns
628.Er EINVAL
629if the size of the mbuf chain exceeds the maximum limit of the
630DMA tag.
631.It Fn bus_dmamap_load_mbuf_segment "dmat" "map" "mbuf" "*segs" "maxsegs" \
632"*nsegs" "flags"
633It is like
634.Fn bus_dmamap_load_mbuf
635without callback.
636Segmentation information are saved in the
637.Fa segs
638and
639.Fa nsegs
640if the loading is successful.
641The
642.Fa maxsegs ,
643which indicates the number of elements in the
644.Fa segs ,
645must be set by the caller and must be at least 1 and at most equal the
646.Fa nsegments
647used to create the
648.Fa dmat .
649The
650.Fa flags
651must have
652.Dv BUS_DMA_NOWAIT
653turned on.
654.Pp
655This function will not block.
656When system is short of DMA resources,
657this function will return
658.Er ENOMEM ,
659instead of
660.Er EINPROGRESS .
661.It Fn bus_dmamap_load_mbuf_defrag "dmat" "map" "*mbuf" "*segs" "maxsegs" \
662"*nsegs" "flags"
663This function is like
664.Fn bus_dmamap_load_mbuf_segment ,
665but it will call
666.Fn m_defrag
667on the
668.Fa *mbuf
669and try reloading,
670if low level code indicates too many fragments in the
671.Fa *mbuf ;
672the
673.Fa mbuf
674will be updated under this situation.
675However,
676.Fa *mbuf
677would not be freed by this function,
678even if
679.Fn m_defrag
680failed.
681.Pp
682Return
683.Er ENOBUFS ,
684if the calling of
685.Fn m_defrag
686failed.
687.It Fn bus_dmamap_load_uio "dmat" "map" "uio" "callback2" "callback_arg" "flags"
688This is a variation of
689.Fn bus_dmamap_load
690which maps buffers pointed to by
691.Fa uio
692for DMA transfers.
693A
694.Vt bus_size_t
695argument is also passed to the callback routine, which contains the size of
696.Fa uio ,
697i.e.
698.Fa uio->uio_resid .
699.Pp
700If
701.Fa uio->uio_segflg
702is
703.Dv UIO_USERSPACE ,
704then it is assumed that the buffer,
705.Fa uio
706is in
707.Fa "uio->uio_td->td_proc" Ns 's
708address space.
709User space memory must be in-core and wired prior to attempting a map
710load operation.
711.It Fn bus_dmamap_unload "dmat" "map"
712Unloads a DMA map.
713Arguments are as follows:
714.Bl -tag -width dmam -compact
715.It Fa dmat
716DMA tag used to allocate
717.Fa map .
718.It Fa map
719The DMA map that is to be unloaded.
720.El
721.Pp
722.Fn bus_dmamap_unload
723will not perform any implicit synchronization of DMA buffers.
724This must be done explicitly by a call to
725.Fn bus_dmamap_sync
726prior to unloading the map.
727.It Fn bus_dmamap_sync "dmat" "map" "op"
728Performs synchronization of a device visible mapping with the CPU visible
729memory referenced by that mapping.
730Arguments are as follows:
731.Bl -tag -width dmat -compact
732.It Fa dmat
733DMA tag used to allocate
734.Fa map .
735.It Fa map
736The DMA mapping to be synchronized.
737.It Fa op
738Type of synchronization operation to perform.
739See the definition of
740.Vt bus_dmasync_op_t
741for a description of the acceptable values for
742.Fa op .
743.El
744.Pp
745.Fn bus_dmamap_sync
746is the method used to ensure that CPU and device DMA access to shared
747memory is coherent.
748For example, the CPU might be used to setup the contents of a buffer
749that is to be DMA'ed into a device.
750To ensure that the data are visible via the device's mapping of that
751memory, the buffer must be loaded and a dma sync operation of
752.Dv BUS_DMASYNC_PREREAD
753must be performed.
754Additional sync operations must be performed after every CPU write
755to this memory if additional DMA reads are to be performed.
756Conversely, for the DMA write case, the buffer must be loaded,
757and a dma sync operation of
758.Dv BUS_DMASYNC_PREWRITE
759must be performed.
760The CPU will only be able to see the results of this DMA write
761once the DMA has completed and a
762.Dv BUS_DMASYNC_POSTWRITE
763operation has been performed.
764.Pp
765If DMA read and write operations are not preceded and followed by the
766appropriate synchronization operations, behavior is undefined.
767.It Fn bus_dmamem_alloc "dmat" "**vaddr" "flags" "mapp"
768Allocates memory that is mapped into KVA at the address returned
769in
770.Fa vaddr
771that is permanently loaded into the newly created
772.Vt bus_dmamap_t
773returned via
774.Fa mapp .
775Arguments are as follows:
776.Bl -tag -width alignment -compact
777.It Fa dmat
778DMA tag describing the constraints of the DMA mapping.
779.It Fa vaddr
780Pointer to a pointer that will hold the returned KVA mapping of
781the allocated region.
782.It Fa flags
783Flags are defined as follows:
784.Bl -tag -width ".Dv BUS_DMA_COHERENT" -compact
785.It Dv BUS_DMA_WAITOK
786The routine can safely wait (sleep) for resources.
787.It Dv BUS_DMA_NOWAIT
788The routine is not allowed to wait for resources.
789If resources are not available,
790.Er ENOMEM
791is returned.
792.It Dv BUS_DMA_COHERENT
793Attempt to map this memory such that cache sync operations are
794as cheap as possible.
795This flag is typically set on memory that will be accessed by both
796a CPU and a DMA engine, frequently.
797Use of this flag does not remove the requirement of using
798bus_dmamap_sync, but it may reduce the cost of performing
799these operations.
800.It Dv BUS_DMA_ZERO
801Causes the allocated memory to be set to all zeros.
802.It Dv BUS_DMA_NOCACHE
803The allocated memory will not be cached in the processor caches.
804All memory accesses appear on the bus and are executed
805without reordering.
806On x86_64, the
807.Dv BUS_DMA_NOCACHE
808flag results in the
809Strong Uncacheable PAT to be set for the allocated virtual address range.
810.El
811.It Fa mapp
812Pointer to storage for the returned DMA map.
813.El
814.Pp
815The size of memory to be allocated is
816.Fa maxsize
817as specified in
818.Fa dmat .
819.Pp
820The current implementation of
821.Fn bus_dmamem_alloc
822will allocate all requests as a single segment.
823.Pp
824Although no explicit loading is required to access the memory
825referenced by the returned map, the synchronization requirements
826as described in the
827.Fn bus_dmamap_sync
828section still apply.
829.Pp
830Returns
831.Er ENOMEM
832if sufficient memory is not available for completing
833the operation.
834.It Fn bus_dmamem_coherent "parent" "alignment" "boundary" "lowaddr" \
835"highaddr" "maxsize" "flags" "*dmem"
836This is a convenient function to create one segment of DMA memory.
837It combines following
838.Nm
839function calls:
840.Bd -literal
841	bus_dma_tag_create(..., dtag);
842	bus_dmamem_alloc(*dtag, vaddr, ..., dmap);
843	bus_dmamap_load(*dtag, *dmap, *vaddr, ..., \\
844			callback, busaddr, ...);
845.Ed
846.sp
847The final results of the above function calls are:
848DMA tag,
849DMA map,
850DMA memory's kernel virtual address and
851its device visible address.
852.Fn bus_dmamem_coherent
853saves the results in
854.Fa *dmem .
855.Pp
856The
857.Fa parent ,
858.Fa alignment ,
859.Fa boundary ,
860.Fa lowaddr
861and
862.Fa highaddr
863will be passed to
864.Fn bus_dma_tag_create
865as they are.
866The
867.Fa maxsize
868will be passed to
869.Fn bus_dma_tag_create
870as its
871.Fa maxsize
872and
873.Fa maxsegsz
874and
875.Ql 1
876will be passed to
877.Fn bus_dma_tag_create
878as its
879.Fa nsegments .
880When
881.Fn bus_dmamem_alloc
882is called,
883.Fa flags
884will be first or'ed with
885.Dv BUS_DMA_COHERENT
886then passed to it.
887The final results of the above three functions,
888i.e. DMA tag,
889DMA map,
890DMA memory's kernel virtual address and
891its device visible address,
892are saved in
893.Fa *dmem .
894If any of the three functions failed,
895this function will return the error code and the
896.Fa *dmem
897should not be used.
898.It Fn bus_dmamem_coherent_any "parent" "alignment" "maxsize" "flags" \
899"*dtag" "*dmap" "*busaddr"
900This function is a simplified version of
901.Fn bus_dmamem_coherent
902with
903its
904.Fa boundary
905set to
906.Ql 0 ,
907.Fa lowaddr
908set to
909.Dv BUS_SPACE_MAXADDR
910and
911.Fa highaddr
912set to
913.Dv BUS_SPACE_MAXADDR .
914The
915.Fa parent
916usually should not be NULL.
917.Pp
918Return the DMA memory's kernel virtual address.
919The DMA tag, DMA map and device visible address are returned in
920.Fa *dtag ,
921.Fa *dmap ,
922and
923.Fa *busaddr .
924If this function failed,
925NULL will be returned;
926.Fa *dtag ,
927.Fa *dmap ,
928and
929.Fa *busaddr
930are left unchanged.
931.It Fn bus_dmamem_free "dmat" "*vaddr" "map"
932Frees memory previously allocated by
933.Fn bus_dmamem_alloc .
934Any mappings
935will be invalidated.
936Arguments are as follows:
937.Bl -tag -width vaddr -compact
938.It Fa dmat
939DMA tag.
940.It Fa vaddr
941Kernel virtual address of the memory.
942.It Fa map
943DMA map to be invalidated.
944.El
945.El
946.Sh RETURN VALUES
947Behavior is undefined if invalid arguments are passed to
948any of the above functions.
949If sufficient resources cannot be allocated for a given
950transaction,
951.Er ENOMEM
952is returned.
953All
954routines that are not of type,
955.Vt void ,
956will return 0 on success or an error
957code, as discussed above.
958.Pp
959All
960.Vt void
961routines will succeed if provided with valid arguments.
962.Sh SEE ALSO
963.Xr devclass 9 ,
964.Xr device 9 ,
965.Xr driver 9 ,
966.Xr rman 9
967.Rs
968.%A "Jason R. Thorpe"
969.%T "A Machine-Independent DMA Framework for NetBSD"
970.%J "Proceedings of the Summer 1998 USENIX Technical Conference"
971.%Q "USENIX Association"
972.%D "June 1998"
973.Re
974.Sh HISTORY
975The
976.Nm
977interface first appeared in
978.Nx 1.3 .
979.Pp
980The
981.Nm
982API was adopted from
983.Nx
984for use in the CAM SCSI subsystem.
985The alterations to the original API were aimed to remove the need for
986a
987.Vt bus_dma_segment_t
988array stored in each
989.Vt bus_dmamap_t
990while allowing callers to queue up on scarce resources.
991.Sh AUTHORS
992The
993.Nm
994interface was designed and implemented by
995.An Jason R. Thorpe
996of the Numerical Aerospace Simulation Facility, NASA Ames Research Center.
997Additional input on the
998.Nm
999design was provided by
1000.An -nosplit
1001.An Chris Demetriou ,
1002.An Charles Hannum ,
1003.An Ross Harvey ,
1004.An Matthew Jacob ,
1005.An Jonathan Stone ,
1006and
1007.An Matt Thomas .
1008.Pp
1009This manual page was written by
1010.An Hiten Pandya
1011and
1012.An Justin T. Gibbs .
1013