* is remap_pfn_range should align to 2(n) * (page size) ?
@ 2008-05-09 6:54 zhuzhenhua
2008-05-09 9:56 ` Ralf Baechle
0 siblings, 1 reply; 8+ messages in thread
From: zhuzhenhua @ 2008-05-09 6:54 UTC (permalink / raw)
To: linux-mips
[-- Attachment #1: Type: text/plain, Size: 391 bytes --]
hello all
i have a sensor driver want to malloc 2.xM SDRAM to capture
data(using DMA), so i used remap_pfn_range to malloc 3M.
But in /proc/meminfo, it showes free memory reduce 4M. i also check the
/proc/buddyinfo, it seemes too.
(i am looking inside kernel code, but not get clear at now).
is remap_pfn_range should align to 2(n) * (page size) ?
thanks for any hints
zzh
[-- Attachment #2: Type: text/html, Size: 500 bytes --]
^ permalink raw reply [flat|nested] 8+ messages in thread* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-09 6:54 is remap_pfn_range should align to 2(n) * (page size) ? zhuzhenhua @ 2008-05-09 9:56 ` Ralf Baechle 2008-05-12 2:18 ` zhuzhenhua 0 siblings, 1 reply; 8+ messages in thread From: Ralf Baechle @ 2008-05-09 9:56 UTC (permalink / raw) To: zhuzhenhua; +Cc: linux-mips On Fri, May 09, 2008 at 02:54:29PM +0800, zhuzhenhua wrote: > i have a sensor driver want to malloc 2.xM SDRAM to capture > data(using DMA), so i used remap_pfn_range to malloc 3M. > But in /proc/meminfo, it showes free memory reduce 4M. i also check the > /proc/buddyinfo, it seemes too. > (i am looking inside kernel code, but not get clear at now). > > is remap_pfn_range should align to 2(n) * (page size) ? This has nothing to do with remap_pfn_range but with the power of two sized buckets used by the global free page pool. Any allocation with get_free_pages will be rounded up to the next power of two. If that's a real concern for you you could allocate a 4MB page then split the page into a 2MB and two 1MB pages and free the 1MB page again. Ralf ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-09 9:56 ` Ralf Baechle @ 2008-05-12 2:18 ` zhuzhenhua 2008-05-12 11:22 ` Ralf Baechle 0 siblings, 1 reply; 8+ messages in thread From: zhuzhenhua @ 2008-05-12 2:18 UTC (permalink / raw) To: Ralf Baechle; +Cc: linux-mips [-- Attachment #1: Type: text/plain, Size: 1165 bytes --] On 5/9/08, Ralf Baechle <ralf@linux-mips.org> wrote: > > On Fri, May 09, 2008 at 02:54:29PM +0800, zhuzhenhua wrote: > > > i have a sensor driver want to malloc 2.xM SDRAM to capture > > data(using DMA), so i used remap_pfn_range to malloc 3M. > > But in /proc/meminfo, it showes free memory reduce 4M. i also check the > > /proc/buddyinfo, it seemes too. > > (i am looking inside kernel code, but not get clear at now). > > > > is remap_pfn_range should align to 2(n) * (page size) ? > > > This has nothing to do with remap_pfn_range but with the power of two > sized buckets used by the global free page pool. Any allocation with > get_free_pages will be rounded up to the next power of two. If that's a > real concern for you you could allocate a 4MB page then split the page > into a 2MB and two 1MB pages and free the 1MB page again. > > > Ralf thanks for your reply , i see in get_frree_pages and free_pages there is a get_order(size). but i don't understand " allocate a 4MB page then split the page into a 2MB and two 1MB pages and free the 1MB page again." is there any function to split it? thanks for any hints Best Regards zzh [-- Attachment #2: Type: text/html, Size: 1764 bytes --] ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-12 2:18 ` zhuzhenhua @ 2008-05-12 11:22 ` Ralf Baechle 2008-05-13 11:44 ` zhuzhenhua 0 siblings, 1 reply; 8+ messages in thread From: Ralf Baechle @ 2008-05-12 11:22 UTC (permalink / raw) To: zhuzhenhua; +Cc: linux-mips On Mon, May 12, 2008 at 10:18:27AM +0800, zhuzhenhua wrote: > > This has nothing to do with remap_pfn_range but with the power of two > > sized buckets used by the global free page pool. Any allocation with > > get_free_pages will be rounded up to the next power of two. If that's a > > real concern for you you could allocate a 4MB page then split the page > > into a 2MB and two 1MB pages and free the 1MB page again. > thanks for your reply , i see in get_frree_pages and free_pages there is a > get_order(size). > but i don't understand " allocate a 4MB page then split the page > into a 2MB and two 1MB pages and free the 1MB page again." > is there any function to split it? No, you'd have to code that yourself. Take a look at split_page() which splits an order n page into order 0 pages. You'd want something similar but splitting for some non-zero order. Ralf ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-12 11:22 ` Ralf Baechle @ 2008-05-13 11:44 ` zhuzhenhua 2008-05-13 17:23 ` Ralf Baechle 0 siblings, 1 reply; 8+ messages in thread From: zhuzhenhua @ 2008-05-13 11:44 UTC (permalink / raw) To: Ralf Baechle; +Cc: linux-mips [-- Attachment #1: Type: text/plain, Size: 4385 bytes --] On 5/12/08, Ralf Baechle <ralf@linux-mips.org> wrote: > > On Mon, May 12, 2008 at 10:18:27AM +0800, zhuzhenhua wrote: > > > > This has nothing to do with remap_pfn_range but with the power of two > > > sized buckets used by the global free page pool. Any allocation with > > > get_free_pages will be rounded up to the next power of two. If that's > a > > > real concern for you you could allocate a 4MB page then split the page > > > into a 2MB and two 1MB pages and free the 1MB page again. > > > > thanks for your reply , i see in get_frree_pages and free_pages there is > a > > get_order(size). > > but i don't understand " allocate a 4MB page then split the page > > into a 2MB and two 1MB pages and free the 1MB page again." > > is there any function to split it? > > > No, you'd have to code that yourself. Take a look at split_page() which > splits an order n page into order 0 pages. You'd want something similar > but splitting for some non-zero order. > > > Ralf thanks for your advice, i found in newest kernel version, in some arch , the dma_alloc_coherent will call split_page. because my kernel version is 2.6.14, so i first patch a split_page patch as follow: http://www.kernel.org/pub/linux/kernel/people/npiggin/patches/lockless/2.6.16-rc5/broken-out/mm-split-highorder.patch but it seemes that there is still no split_page in dma_alloc_coherent/dma_alloc_noncoherent so i copy from other arch code to arch/mips/mm/dma-noncoherent.c (attach at the end of mail) and now my driver just use dma_alloc_coherent malloc 3M directly, and it seemes ok. i just wonder why mips arch dma_alloc_coherent/dma_alloc_nocoherent do not call split_page while other arch calling. thanks for any hints. Best Regards zzh modify on dma-noncoherent.c --- dma-noncoherent.c 2008-05-13 19:31:58.131375500 +0800 +++ dma-noncoherent-split.c 2008-05-13 19:31:51.039745500 +0800 @@ -16,27 +16,59 @@ #include <asm/cache.h> #include <asm/io.h> + +static struct page *__dma_alloc(struct device *dev, size_t size, + dma_addr_t *handle, gfp_t gfp) +{ + struct page *page, *free, *end; + int order; + + size = PAGE_ALIGN(size); + order = get_order(size); + page = alloc_pages(gfp, order); + if (!page) + return NULL; + split_page(page, order); + + *handle = page_to_phys(page); + free = page + (size >> PAGE_SHIFT); + end = page + (1 << order); -/* - * Warning on the terminology - Linux calls an uncached area coherent; - * MIPS terminology calls memory areas with hardware maintained coherency - * coherent. - */ + /* + * Free any unused pages + */ + while (free < end) { + __free_page(free); + free++; + } + + return page; +} + +static void __dma_free(struct device *dev, size_t size, + struct page *page, dma_addr_t handle) +{ + struct page *end = page + (PAGE_ALIGN(size) >> PAGE_SHIFT); + while (page < end) + __free_page(page++); +} void *dma_alloc_noncoherent(struct device *dev, size_t size, dma_addr_t * dma_handle, unsigned int __nocast gfp) { + struct page *page; void *ret; /* ignore region specifiers */ gfp &= ~(__GFP_DMA | __GFP_HIGHMEM); if (dev == NULL || (dev->coherent_dma_mask < 0xffffffff)) gfp |= GFP_DMA; - ret = (void *) __get_free_pages(gfp, get_order(size)); - + page = __dma_alloc(dev, size, dma_handle, gfp); + if (page) + ret = KSEG1ADDR(page_to_phys(page)); + printk("ret in dma_alloc_noncoherent = 0x%x\n",ret); if (ret != NULL) { memset(ret, 0, size); - *dma_handle = virt_to_phys(ret); } return ret; @@ -63,19 +95,17 @@ void dma_free_noncoherent(struct device *dev, size_t size, void *vaddr, dma_addr_t dma_handle) { - free_pages((unsigned long) vaddr, get_order(size)); + void *addr = KSEG0ADDR(vaddr); + struct page *page; + BUG_ON(!virt_addr_valid(addr)); + page = virt_to_page(addr); + __dma_free(dev, size, page, dma_handle); } EXPORT_SYMBOL(dma_free_noncoherent); void dma_free_coherent(struct device *dev, size_t size, void *vaddr, - dma_addr_t dma_handle) -{ - unsigned long addr = (unsigned long) vaddr; - - addr = CAC_ADDR(addr); - free_pages(addr, get_order(size)); -} + dma_addr_t dma_handle) __attribute__((alias("dma_free_noncoherent"))); EXPORT_SYMBOL(dma_free_coherent); [-- Attachment #2: Type: text/html, Size: 6926 bytes --] ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-13 11:44 ` zhuzhenhua @ 2008-05-13 17:23 ` Ralf Baechle 2008-05-14 1:19 ` zhuzhenhua 0 siblings, 1 reply; 8+ messages in thread From: Ralf Baechle @ 2008-05-13 17:23 UTC (permalink / raw) To: zhuzhenhua; +Cc: linux-mips On Tue, May 13, 2008 at 07:44:06PM +0800, zhuzhenhua wrote: > thanks for your advice, i found in newest kernel version, in some arch , the > dma_alloc_coherent will call split_page. > because my kernel version is 2.6.14, so i first patch a split_page patch as > follow: > http://www.kernel.org/pub/linux/kernel/people/npiggin/patches/lockless/2.6.16-rc5/broken-out/mm-split-highorder.patch > > but it seemes that there is still no split_page in > dma_alloc_coherent/dma_alloc_noncoherent > so i copy from other arch code to arch/mips/mm/dma-noncoherent.c (attach at > the end of mail) > and now my driver just use dma_alloc_coherent malloc 3M directly, and it > seemes ok. > i just wonder why mips arch dma_alloc_coherent/dma_alloc_nocoherent do not > call split_page while other arch calling. I have not identified the waste of memory as a big problem for typical MIPS systems yet. The 3MB requirement of your device is sort of odd because it's not a power of two. Have you considered splitting the allocation into a 2MB and a 1MB allocation or would that be undersirable? Ralf ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-13 17:23 ` Ralf Baechle @ 2008-05-14 1:19 ` zhuzhenhua 2008-05-14 7:33 ` Geert Uytterhoeven 0 siblings, 1 reply; 8+ messages in thread From: zhuzhenhua @ 2008-05-14 1:19 UTC (permalink / raw) To: Ralf Baechle; +Cc: linux-mips [-- Attachment #1: Type: text/plain, Size: 1761 bytes --] On Wed, May 14, 2008 at 1:23 AM, Ralf Baechle <ralf@linux-mips.org> wrote: > On Tue, May 13, 2008 at 07:44:06PM +0800, zhuzhenhua wrote: > > > thanks for your advice, i found in newest kernel version, in some arch , > the > > dma_alloc_coherent will call split_page. > > because my kernel version is 2.6.14, so i first patch a split_page patch > as > > follow: > > > http://www.kernel.org/pub/linux/kernel/people/npiggin/patches/lockless/2.6.16-rc5/broken-out/mm-split-highorder.patch > > > > but it seemes that there is still no split_page in > > dma_alloc_coherent/dma_alloc_noncoherent > > so i copy from other arch code to arch/mips/mm/dma-noncoherent.c (attach > at > > the end of mail) > > and now my driver just use dma_alloc_coherent malloc 3M directly, and it > > seemes ok. > > i just wonder why mips arch dma_alloc_coherent/dma_alloc_nocoherent do > not > > call split_page while other arch calling. > > I have not identified the waste of memory as a big problem for typical > MIPS systems yet. > > The 3MB requirement of your device is sort of odd because it's not a power > of two. Have you considered splitting the allocation into a 2MB and a 1MB > allocation or would that be undersirable? > > Ralf > Thanks for your reply. Our board is for embedded system , It only have 32M sdram and we don't want to waste 1M sdram. My sensor driver need about 2.5xM memory to capture a picture by DMA (our DMA controller do not support scatter/gather). I also can use bootargs "mem=29M" to keep 3M sdram. but it's not flexible as passing a param to driver module(calling dma_alloc_coherent). maybe my situation is not common for MIPS arch. so that's is no split_page in dma_alloc_coherent. and now after patch,it seemes ok for me. Best Regards zzh [-- Attachment #2: Type: text/html, Size: 2393 bytes --] ^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: is remap_pfn_range should align to 2(n) * (page size) ? 2008-05-14 1:19 ` zhuzhenhua @ 2008-05-14 7:33 ` Geert Uytterhoeven 0 siblings, 0 replies; 8+ messages in thread From: Geert Uytterhoeven @ 2008-05-14 7:33 UTC (permalink / raw) To: zhuzhenhua; +Cc: Ralf Baechle, linux-mips On Wed, 14 May 2008, zhuzhenhua wrote: > On Wed, May 14, 2008 at 1:23 AM, Ralf Baechle <ralf@linux-mips.org> wrote: > > On Tue, May 13, 2008 at 07:44:06PM +0800, zhuzhenhua wrote: > > > thanks for your advice, i found in newest kernel version, in some arch , > > the > > > dma_alloc_coherent will call split_page. > > > because my kernel version is 2.6.14, so i first patch a split_page patch > > as > > > follow: > > > > > http://www.kernel.org/pub/linux/kernel/people/npiggin/patches/lockless/2.6.16-rc5/broken-out/mm-split-highorder.patch > > > > > > but it seemes that there is still no split_page in > > > dma_alloc_coherent/dma_alloc_noncoherent > > > so i copy from other arch code to arch/mips/mm/dma-noncoherent.c (attach > > at > > > the end of mail) > > > and now my driver just use dma_alloc_coherent malloc 3M directly, and it > > > seemes ok. > > > i just wonder why mips arch dma_alloc_coherent/dma_alloc_nocoherent do > > not > > > call split_page while other arch calling. > > > > I have not identified the waste of memory as a big problem for typical > > MIPS systems yet. > > > > The 3MB requirement of your device is sort of odd because it's not a power > > of two. Have you considered splitting the allocation into a 2MB and a 1MB > > allocation or would that be undersirable? > > > > Thanks for your reply. > Our board is for embedded system , It only have 32M sdram and we don't want > to > waste 1M sdram. My sensor driver need about 2.5xM memory to capture a > picture > by DMA (our DMA controller do not support scatter/gather). > > I also can use bootargs "mem=29M" to keep 3M sdram. but it's not flexible > as > passing a param to driver module(calling dma_alloc_coherent). maybe my > situation > is not common for MIPS arch. so that's is no split_page in > dma_alloc_coherent. > and now after patch,it seemes ok for me. One other issue is that bootargs "mem=29M" is guaranteed to give you 3 MiB for your device, while dma_alloc_coherent() may fail if memory is too fragmented. Gr{oetje,eeting}s, Geert -- Geert Uytterhoeven -- There's lots of Linux beyond ia32 -- geert@linux-m68k.org In personal conversations with technical people, I call myself a hacker. But when I'm talking to journalists I just say "programmer" or something like that. -- Linus Torvalds ^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2008-05-14 7:34 UTC | newest] Thread overview: 8+ messages (download: mbox.gz follow: Atom feed -- links below jump to the message on this page -- 2008-05-09 6:54 is remap_pfn_range should align to 2(n) * (page size) ? zhuzhenhua 2008-05-09 9:56 ` Ralf Baechle 2008-05-12 2:18 ` zhuzhenhua 2008-05-12 11:22 ` Ralf Baechle 2008-05-13 11:44 ` zhuzhenhua 2008-05-13 17:23 ` Ralf Baechle 2008-05-14 1:19 ` zhuzhenhua 2008-05-14 7:33 ` Geert Uytterhoeven
This is a public inbox, see mirroring instructions for how to clone and mirror all data and code used for this inbox