diff options
| author | riastradh <riastradh@NetBSD.org> | 2021-12-19 12:03:13 +0000 |
|---|---|---|
| committer | riastradh <riastradh@NetBSD.org> | 2021-12-19 12:03:13 +0000 |
| commit | 16c19ecda98c8c4edd313317b375e65c9ec623f4 (patch) | |
| tree | 660b32d8eafbd3984a812f6d54900c44fb87137a /sys/external/bsd/drm2/linux | |
| parent | 92957162ff3ac184f86da4cbddb7235592d6adc2 (diff) | |
linux: Accept multipage segments in sg_alloc_table_from_bus_dmamem.
Diffstat (limited to 'sys/external/bsd/drm2/linux')
| -rw-r--r-- | sys/external/bsd/drm2/linux/linux_sg.c | 21 |
1 files changed, 18 insertions, 3 deletions
diff --git a/sys/external/bsd/drm2/linux/linux_sg.c b/sys/external/bsd/drm2/linux/linux_sg.c index 22bccdb06d9..fb581364f6b 100644 --- a/sys/external/bsd/drm2/linux/linux_sg.c +++ b/sys/external/bsd/drm2/linux/linux_sg.c @@ -1,4 +1,4 @@ -/* $NetBSD: linux_sg.c,v 1.3 2021/12/19 11:38:04 riastradh Exp $ */ +/* $NetBSD: linux_sg.c,v 1.4 2021/12/19 12:03:13 riastradh Exp $ */ /*- * Copyright (c) 2021 The NetBSD Foundation, Inc. @@ -27,7 +27,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: linux_sg.c,v 1.3 2021/12/19 11:38:04 riastradh Exp $"); +__KERNEL_RCSID(0, "$NetBSD: linux_sg.c,v 1.4 2021/12/19 12:03:13 riastradh Exp $"); #include <sys/bus.h> #include <sys/errno.h> @@ -87,11 +87,26 @@ int sg_alloc_table_from_bus_dmamem(struct sg_table *sgt, bus_dma_tag_t dmat, const bus_dma_segment_t *seg, int nseg, gfp_t gfp) { + int i, npgs = 0; int ret; KASSERT(nseg >= 1); - ret = sg_alloc_table(sgt, nseg, gfp); + /* + * Count the number of pages. Some segments may span multiple + * contiguous pages. + */ + for (i = 0; i < nseg; i++) { + bus_size_t len = seg[i].ds_len; + for (; len >= PAGE_SIZE; len -= PAGE_SIZE, npgs++) { + if (npgs == INT_MAX) + return -ENOMEM; + } + KASSERTMSG(len == 0, "misaligned segment length: %ju\n", + (uintmax_t)seg[i].ds_len); + } + + ret = sg_alloc_table(sgt, npgs, gfp); if (ret) return ret; |
