contigmalloc() breaking Xorg
John Baldwin
jhb at freebsd.org
Thu Jul 12 12:35:11 UTC 2012
[ Adding alc@ for VM stuff, Warner for arm/mips bus dma brokenness ]
On Sunday, July 08, 2012 7:05:16 am Peter Jeremy wrote:
> On 2012-Jul-03 21:17:53 +1000, Peter Jeremy <peter at server.rulingia.com>
wrote:
> >I have a reasonably recent 8-stable/amd64 system (r237444) with a "ATI
> >Radeon HD 2400 Pro", xorg-server-1.10.6,1 and xf86-video-ati-6.14.3_1
> >8GB RAM and ZFS. I'm seeing fairly consistent problems with Xorg
> ...
> >How difficult would it be to modify bus_dmamem_alloc() [at least on
> >x86] to handle multi-segment allocations?
>
> I think I've managed to create an amd64 bus_dmamem_alloc() that allows
> page-sized allocations as long as no boundary condition is specified
> and no more than page-sized alignment is required (porting it to other
> architectures would be trivial). I've given it a quick whirl inside a
> VBox and no smoke came out but I'd appreciate someone with a better
> understanding of bus_dma(9) and vm/vm_contig.c giving
> http://www.rulingia.com/bugs/patch-wiredmalloc a once-over. Note that
> this patch is against 8.x but there's only a trivial difference to head.
>
> BTW, the comment in busdma_machdep.c:bus_dmamem_alloc()
> * XXX Use Contigmalloc until it is merged into this facility
> * and handles multi-seg allocations. Nobody is doing
> * multi-seg allocations yet though.
> * XXX Certain AGP hardware does.
> does not appear to be accurate. Apart from drm, quite a few drivers
> call bus_dma_tag_create(9) with multiple segments and also call
> bus_dmamem_alloc(9) [though I haven't verified that the calls share
> the same bus_dma_tag, so I can't be absolutely certain].
I do think that all tags currently used with bus_dmamem_alloc() only use a
single segment. It's a bit of an unfortunate part of the bus_dmamem API
that the size of the allocate is determined by the tag (the tag should be
used for determining the features and constraints of a DMA engine, not really
the amount of memory to allocate).
However, rather add a wiredmalloc(), I think you should just have
bus_dmamem_alloc() call kmem_alloc_attr() directly in this case. One of the
things I've been meaning to add to bus_dma is a way to allocate other memory
types (e.g. WC memory), and in that case it would be best to just call
kmem_alloc_attr() directly instead.
> BTW(2): Whilst studying busdma_machdep.c for arm and mips, I've
> noticed they appear to potentially allocate substantial kernel stack
> under some conditions as several bus_dma(9) functions include:
> bus_dma_segment_t dm_segments[dmat->nsegments];
> What prevents this overflowing the kernel stack?
That does seem dubious. x86 stores the array in the tag instead.
--
John Baldwin
More information about the freebsd-hackers
mailing list