Add a quick hack to ensure that bus_dmamem_alloc properly aligns
small allocations with large alignment requirements. Add a panic to detect cases where we've still failed to properly align.
This commit is contained in:
parent
39e2bd0bdb
commit
0d65566db8
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=159011
@ -495,7 +495,16 @@ bus_dmamem_alloc(bus_dma_tag_t dmat, void** vaddr, int flags,
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* XXX:
|
||||
* (dmat->alignment < dmat->maxsize) is just a quick hack; the exact
|
||||
* alignment guarantees of malloc need to be nailed down, and the
|
||||
* code below should be rewritten to take that into account.
|
||||
*
|
||||
* In the meantime, we'll panic if malloc gets it wrong.
|
||||
*/
|
||||
if ((dmat->maxsize <= PAGE_SIZE) &&
|
||||
(dmat->alignment < dmat->maxsize) &&
|
||||
dmat->lowaddr >= ptoa((vm_paddr_t)Maxmem)) {
|
||||
*vaddr = malloc(dmat->maxsize, M_DEVBUF, mflags);
|
||||
} else {
|
||||
@ -513,6 +522,8 @@ bus_dmamem_alloc(bus_dma_tag_t dmat, void** vaddr, int flags,
|
||||
CTR4(KTR_BUSDMA, "%s: tag %p tag flags 0x%x error %d",
|
||||
__func__, dmat, dmat->flags, ENOMEM);
|
||||
return (ENOMEM);
|
||||
} else if ((uintptr_t)*vaddr & (dmat->alignment - 1)) {
|
||||
panic("bus_dmamem_alloc failed to align memory properly.");
|
||||
}
|
||||
CTR4(KTR_BUSDMA, "%s: tag %p tag flags 0x%x error %d",
|
||||
__func__, dmat, dmat->flags, ENOMEM);
|
||||
@ -532,8 +543,9 @@ bus_dmamem_free(bus_dma_tag_t dmat, void *vaddr, bus_dmamap_t map)
|
||||
*/
|
||||
if (map != NULL)
|
||||
panic("bus_dmamem_free: Invalid map freed\n");
|
||||
if ((dmat->maxsize <= PAGE_SIZE)
|
||||
&& dmat->lowaddr >= ptoa((vm_paddr_t)Maxmem))
|
||||
if ((dmat->maxsize <= PAGE_SIZE) &&
|
||||
(dmat->alignment < dmat->maxsize) &&
|
||||
dmat->lowaddr >= ptoa((vm_paddr_t)Maxmem))
|
||||
free(vaddr, M_DEVBUF);
|
||||
else {
|
||||
contigfree(vaddr, dmat->maxsize, M_DEVBUF);
|
||||
|
Loading…
Reference in New Issue
Block a user