diff options
author | scottl <scottl@FreeBSD.org> | 2003-01-29 07:25:27 +0000 |
---|---|---|
committer | scottl <scottl@FreeBSD.org> | 2003-01-29 07:25:27 +0000 |
commit | 27cbbd88a297ee95096971d969fc28f1f2c7a09c (patch) | |
tree | d21203bdfa9f1d0c2ea53afbd752b1326d109e6c /sys/sparc64/include/bus.h | |
parent | 1bc11f23c6b4c14967b2c1745df47caa7147c66e (diff) | |
download | FreeBSD-src-27cbbd88a297ee95096971d969fc28f1f2c7a09c.zip FreeBSD-src-27cbbd88a297ee95096971d969fc28f1f2c7a09c.tar.gz |
Implement bus_dmamem_alloc_size() and bus_dmamem_free_size() as
counterparts to bus_dmamem_alloc() and bus_dmamem_free(). This allows
the caller to specify the size of the allocation instead of it defaulting
to the max_size field of the busdma tag.
This is intended to aid in converting drivers to busdma. Lots of
hardware cannot understand scatter/gather lists, which forces the
driver to copy the i/o buffers to a single contiguous region
before sending it to the hardware. Without these new methods, this
would require a new busdma tag for each operation, or a complex
internal allocator/cache for each driver.
Allocations greater than PAGE_SIZE are rounded up to the next
PAGE_SIZE by contigmalloc(), so this is not suitable for multiple
static allocations that would be better served by a single
fixed-length subdivided allocation.
Reviewed by: jake (sparc64)
Diffstat (limited to 'sys/sparc64/include/bus.h')
-rw-r--r-- | sys/sparc64/include/bus.h | 30 |
1 files changed, 30 insertions, 0 deletions
diff --git a/sys/sparc64/include/bus.h b/sys/sparc64/include/bus.h index 95089fa..2a90c01 100644 --- a/sys/sparc64/include/bus.h +++ b/sys/sparc64/include/bus.h @@ -971,8 +971,12 @@ struct bus_dma_tag { /* * DMA memory utility functions. */ + int (*dt_dmamem_alloc_size)(bus_dma_tag_t, bus_dma_tag_t, void **, + int, bus_dmamap_t *, bus_size_t size); int (*dt_dmamem_alloc)(bus_dma_tag_t, bus_dma_tag_t, void **, int, bus_dmamap_t *); + void (*dt_dmamem_free_size)(bus_dma_tag_t, bus_dma_tag_t, void *, + bus_dmamap_t, bus_size_t size); void (*dt_dmamem_free)(bus_dma_tag_t, bus_dma_tag_t, void *, bus_dmamap_t); }; @@ -1084,6 +1088,19 @@ sparc64_dmamap_sync(bus_dma_tag_t pt, bus_dma_tag_t dt, bus_dmamap_t m, sparc64_dmamap_sync((t), (t), (m), (op)) static __inline int +sparc64_dmamem_alloc_size(bus_dma_tag_t pt, bus_dma_tag_t dt, void **v, int f, + bus_dmamap_t *m, bus_size_t s) +{ + bus_dma_tag_t lt; + + for (lt = pt; lt->dmamem_alloc == NULL; lt = lt->parent) + ; + return ((*lt->dmamem_alloc_size)(lt, dt, v, f, m, s)); +} +#define bus_dmamem_alloc_size(t, v, f, m, s) \ + sparc64_dmamem_alloc_size((t), (t), (v), (f), (m), (s)) + +static __inline int sparc64_dmamem_alloc(bus_dma_tag_t pt, bus_dma_tag_t dt, void **v, int f, bus_dmamap_t *m) { @@ -1097,6 +1114,19 @@ sparc64_dmamem_alloc(bus_dma_tag_t pt, bus_dma_tag_t dt, void **v, int f, sparc64_dmamem_alloc((t), (t), (v), (f), (m)) static __inline void +sparc64_dmamem_free_size(bus_dma_tag_t pt, bus_dma_tag_t dt, void *v, + bus_dmamap_t m, bus_size_t s) +{ + bus_dma_tag_t lt; + + for (lt = pt; lt->dmamem_free == NULL; lt = lt->parent) + ; + (*lt->dmamem_free_size)(lt, dt, v, m, s); +} +#define bus_dmamem_free_size(t, v, m, s) \ + sparc64_dmamem_free_size((t), (t), (v), (m), (s)) + +static __inline void sparc64_dmamem_free(bus_dma_tag_t pt, bus_dma_tag_t dt, void *v, bus_dmamap_t m) { |