Messages in this thread | | | Date | Mon, 9 Nov 2009 22:13:40 +0200 | Subject | Re: [PATCH 07/10] bootmem: add free_bootmem_late | From | Pekka Enberg <> |
| |
On Wed, Oct 28, 2009 at 8:47 AM, FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp> wrote: > @@ -151,7 +151,9 @@ unsigned long __init init_bootmem(unsigned long start, unsigned long pages) > * > * This will free the pages in the range @start to @end, making them > * available to the page allocator. The @map will be used to skip > - * reserved pages. Returns the count of pages freed. > + * reserved pages. In the case that @map is NULL, the bootmem allocator > + * is already free and the range is contiguous. Returns the count of > + * pages freed. > */ > static unsigned long __init free_bootmem_pages(unsigned long start, > unsigned long end, > @@ -164,13 +166,23 @@ static unsigned long __init free_bootmem_pages(unsigned long start, > * If the start is aligned to the machines wordsize, we might > * be able to free pages in bulks of that order. > */ > - aligned = !(start & (BITS_PER_LONG - 1)); > + if (map) > + aligned = !(start & (BITS_PER_LONG - 1)); > + else > + aligned = 1;
Why do we need this special casing here? Isn't start always aligned properly for callers with map == NULL?
> > for (cursor = start; cursor < end; cursor += BITS_PER_LONG) { > - unsigned long idx, vec; > + unsigned long vec; > > - idx = cursor - start; > - vec = ~map[idx / BITS_PER_LONG]; > + if (map) { > + unsigned long idx = cursor - start; > + vec = ~map[idx / BITS_PER_LONG]; > + } else { > + if (end - cursor >= BITS_PER_LONG) > + vec = ~0UL;
Why do we need the above?
> + else > + vec = (1UL << (end - cursor)) - 1; > + } > > if (aligned && vec == ~0UL && cursor + BITS_PER_LONG < end) { > int order = ilog2(BITS_PER_LONG); > @@ -387,6 +399,27 @@ void __init free_bootmem(unsigned long addr, unsigned long size) > } > > /** > + * free_bootmem_late - free bootmem pages directly to page allocator > + * @addr: starting address of the range > + * @size: size of the range in bytes > + * > + * This is only useful when the bootmem allocator has already been torn > + * down, but we are still initializing the system. Pages are given directly > + * to the page allocator, no bootmem metadata is updated because it is gone. > + */ > +void __init free_bootmem_late(unsigned long addr, unsigned long size) > +{ > + unsigned long start, end; > + > + kmemleak_free_part(__va(addr), size); > + > + start = PFN_UP(addr); > + end = PFN_DOWN(addr + size); > + > + totalram_pages += free_bootmem_pages(start, end, NULL); > +} > + > +/** > * reserve_bootmem_node - mark a page range as reserved > * @pgdat: node the range resides on > * @physaddr: starting address of the range > -- > 1.5.6.5 > > -- > To unsubscribe from this list: send the line "unsubscribe linux-kernel" in > the body of a message to majordomo@vger.kernel.org > More majordomo info at http://vger.kernel.org/majordomo-info.html > Please read the FAQ at http://www.tux.org/lkml/ > -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/
| |