diff options
author | Scott Long <scottl@FreeBSD.org> | 2019-12-24 14:48:46 +0000 |
---|---|---|
committer | Scott Long <scottl@FreeBSD.org> | 2019-12-24 14:48:46 +0000 |
commit | 757d4fbaa75df6193ccd19e475f7b581081d5291 (patch) | |
tree | 4ac8c51c4757577afc27890bf748a116ec6ee17b /sys/x86 | |
parent | e30f025ff95d3bb03b19322e8a58e781881b2166 (diff) | |
download | src-757d4fbaa75df6193ccd19e475f7b581081d5291.tar.gz src-757d4fbaa75df6193ccd19e475f7b581081d5291.zip |
Introduce the concept of busdma tag templates. A template can be allocated
off the stack, initialized to default values, and then filled in with
driver-specific values, all without having to worry about the numerous
other fields in the tag. The resulting template is then passed into
busdma and the normal opaque tag object created. See the man page for
details on how to initialize a template.
Templates do not support tag filters. Filters have been broken for many
years, and only existed for an ancient make/model of hardware that had a
quirky DMA engine. Instead of breaking the ABI/API and changing the
arugment signature of bus_dma_tag_create() to remove the filter arguments,
templates allow us to ignore them, and also significantly reduce the
complexity of creating and managing tags.
Reviewed by: imp, kib
Differential Revision: https://reviews.freebsd.org/D22906
Notes
Notes:
svn path=/head/; revision=356050
Diffstat (limited to 'sys/x86')
-rw-r--r-- | sys/x86/x86/busdma_machdep.c | 54 |
1 files changed, 54 insertions, 0 deletions
diff --git a/sys/x86/x86/busdma_machdep.c b/sys/x86/x86/busdma_machdep.c index 152fec591417..36c8d1f78315 100644 --- a/sys/x86/x86/busdma_machdep.c +++ b/sys/x86/x86/busdma_machdep.c @@ -238,6 +238,60 @@ bus_dma_tag_create(bus_dma_tag_t parent, bus_size_t alignment, return (error); } +void +bus_dma_template_init(bus_dma_tag_template_t *t, bus_dma_tag_t parent) +{ + + if (t == NULL) + return; + + t->parent = parent; + t->alignment = 1; + t->boundary = 0; + t->lowaddr = t->highaddr = BUS_SPACE_MAXADDR; + t->maxsize = t->maxsegsize = BUS_SPACE_MAXSIZE; + t->nsegments = BUS_SPACE_UNRESTRICTED; + t->lockfunc = NULL; + t->lockfuncarg = NULL; + t->flags = 0; +} + +int +bus_dma_template_tag(bus_dma_tag_template_t *t, bus_dma_tag_t *dmat) +{ + + if (t == NULL || dmat == NULL) + return (EINVAL); + + return (bus_dma_tag_create(t->parent, t->alignment, t->boundary, + t->lowaddr, t->highaddr, NULL, NULL, t->maxsize, + t->nsegments, t->maxsegsize, t->flags, t->lockfunc, t->lockfuncarg, + dmat)); +} + +void +bus_dma_template_clone(bus_dma_tag_template_t *t, bus_dma_tag_t dmat) +{ + struct bus_dma_tag_common *common; + + if (t == NULL || dmat == NULL) + return; + + common = (struct bus_dma_tag_common *)dmat; + + t->parent = (bus_dma_tag_t)common->parent; + t->alignment = common->alignment; + t->boundary = common->boundary; + t->lowaddr = common->lowaddr; + t->highaddr = common->highaddr; + t->maxsize = common->maxsize; + t->nsegments = common->nsegments; + t->maxsegsize = common->maxsegsz; + t->flags = common->flags; + t->lockfunc = common->lockfunc; + t->lockfuncarg = common->lockfuncarg; +} + int bus_dma_tag_destroy(bus_dma_tag_t dmat) { |