Author: wmb Date: Sat Oct 22 12:40:13 2011 New Revision: 2644 URL: http://tracker.coreboot.org/trac/openfirmware/changeset/2644
Log: OLPC XO-1.75 - Fixed emacs by revamping the DMA allocation code, separating the DMA memory list from the physical memlist. DMA memory is mapped uncached, while other memory is cacheable, so conflating them is not a good idea.
Modified: cpu/arm/linux.fth cpu/arm/mmp2/rootnode.fth cpu/arm/olpc/1.75/fw.bth cpu/arm/olpc/1.75/probemem.fth
Modified: cpu/arm/linux.fth ============================================================================== --- cpu/arm/linux.fth Sat Oct 22 12:40:07 2011 (r2643) +++ cpu/arm/linux.fth Sat Oct 22 12:40:13 2011 (r2644) @@ -9,8 +9,9 @@
0 value linux-memtop
+defer memory-limit \ Find the end of the largest piece of memory -: memory-limit ( -- limit ) +: (memory-limit) ( -- limit ) \ If we have already loaded a RAMdisk in high memory, its base is the memory limit ramdisk-adr ?dup if exit then
@@ -30,6 +31,7 @@ 2drop ( size base ) + ( limit ) ; +' (memory-limit) to memory-limit \ Override by platform code if necessary
\ see http://www.simtec.co.uk/products/SWLINUX/files/booting_article.html
Modified: cpu/arm/mmp2/rootnode.fth ============================================================================== --- cpu/arm/mmp2/rootnode.fth Sat Oct 22 12:40:07 2011 (r2643) +++ cpu/arm/mmp2/rootnode.fth Sat Oct 22 12:40:13 2011 (r2644) @@ -34,54 +34,14 @@ 2drop ;
-: dma-range ( -- start end ) dma-mem-va >physical dup /dma-mem + ; - +[ifdef] virtual-mode h# 0 constant dma-map-mode \ XXX what should this be? - -\ Used with "find-node" to locate a physical memory node containing -\ enough memory in the DMA range. -\ We first compute the intersection between the memory piece and the -\ range reachable by DMA. If the regions are disjoint, then ok-high -\ will be (unsigned) less than ok-low. We then subtract ok-low from -\ ok-high to give the (possibly negative) size of the intersection. -: in-range? ( size mem-low mem-high range-low range-high -- flag ) - rot umin -rot ( size min-high mem-low mem-high ) - umax ( size min-high max-low ) - - <= ( flag ) -; - -: dma-ok? ( size node-adr -- size flag ) - node-range ( size mem-adr mem-len ) - over + ( size mem-adr mem-end ) - - 3dup dma-range in-range? if ( size mem-adr mem-end ) - 2drop true exit ( size true ) - then ( size mem-adr mem-end ) - - 2drop false ( size false ) -; - -\ Find an available physical address range suitable for DMA. This word -\ doesn't actually claim the memory (that is done later), but simply locates -\ a suitable range that can be successfully claimed. -: find-dma-address ( size -- true | adr false ) - " physavail" memory-node @ $call-method ( list ) - ['] dma-ok? find-node is next-node drop ( size' ) - next-node 0= if drop true exit then ( size' ) - next-end ( size mem-end ) - dma-range ( size mem-end range-l,h ) - nip umin swap - false ( adr false ) -; +[then]
headers : dma-alloc ( size -- virt ) - pagesize round-up - - \ Locate a suitable physical range - dup find-dma-address throw ( size' phys ) - - \ Claim it - over 0 mem-claim ( size' phys ) + \ Allocate the physical memory + dup " allocate-dma-phys" $call-mem-method ( size' phys )
[ifdef] virtual-mode \ Get a virtual range @@ -111,7 +71,7 @@ swap >physical swap ( virt ) [then] [then] - mem-release ( ) + " free-dma-phys" $call-mem-method ( ) ;
: dma-map-in ( virt size cacheable -- devaddr )
Modified: cpu/arm/olpc/1.75/fw.bth ============================================================================== --- cpu/arm/olpc/1.75/fw.bth Sat Oct 22 12:40:07 2011 (r2643) +++ cpu/arm/olpc/1.75/fw.bth Sat Oct 22 12:40:13 2011 (r2644) @@ -27,6 +27,11 @@
fload ${BP}/cpu/arm/linux.fth
+\ The bottom of extra-mem is the top of DMA memory. +\ We give everything up to that address to Linux. +: olpc-memory-limit ( -- adr ) extra-mem-va >physical ; +' olpc-memory-limit to memory-limit + : usb-quiet ( -- ) [ ' linux-hook behavior compile, ] \ Chain to old behavior unload-crypto
Modified: cpu/arm/olpc/1.75/probemem.fth ============================================================================== --- cpu/arm/olpc/1.75/probemem.fth Sat Oct 22 12:40:07 2011 (r2643) +++ cpu/arm/olpc/1.75/probemem.fth Sat Oct 22 12:40:13 2011 (r2644) @@ -8,18 +8,28 @@
headerless
-h# ffff.ffff value low -h# 0 value high +list: dmaavail 0 dmaavail !
-: log&release ( adr len -- ) - over low umin to low ( adr len ) - 2dup + high umax to high ( adr len ) - release +headers +: allocate-dma-phys ( size -- phys ) + \ Minumum granularity of memory chunks is 1 page + pagesize round-up ( size' ) + + pagesize over dmaavail ( size alignment size list ) + allocate-memrange ( size [ adr ] error? ) + abort" Insufficient DMA memory" ( size adr ) + dup rot clear-mem ( phys ) +; + +: free-dma-phys ( phys size -- ) + >page-boundaries ( adr' size' ) + ['] 2drop is ?splice ( adr' size' ) + dmaavail free-memrange ;
headers : probe ( -- ) - 0 fb-mem-va >physical /fb-mem + log&release + 0 fb-mem-va >physical /fb-mem + release
0 0 encode-bytes ( adr 0 ) physavail ['] make-phys-memlist find-node ( adr len prev 0 ) @@ -29,6 +39,9 @@ fb-mem-va >physical /fb-mem 0 claim drop fw-mem-va >physical /fw-mem 0 claim drop extra-mem-va >physical /extra-mem 0 claim drop + dma-mem-va >physical /dma-mem 0 claim drop + + dma-mem-va >physical /dma-mem free-dma-phys
0 pagesize 0 claim drop \ Vector table ;
openfirmware@openfirmware.info