diff options
author | Paul Mundt <lethal@linux-sh.org> | 2007-03-28 03:38:13 -0400 |
---|---|---|
committer | Paul Mundt <lethal@hera.kernel.org> | 2007-05-06 22:10:54 -0400 |
commit | 01066625e9ae39742c92e21163f7f2a818e02762 (patch) | |
tree | c5b8a2a2c9de29ed13094891fce2b7f5769ffca7 /arch/sh/kernel | |
parent | 759ab068c4d4216c4ad247bfa851601dfb6500dc (diff) |
sh: bootmem tidying for discontig/sparsemem preparation.
This reworks some of the node 0 bootmem initialization in
preparation for discontigmem and sparsemem support.
ARCH_POPULATES_NODE_MAP is switched to as a result of this.
Signed-off-by: Paul Mundt <lethal@linux-sh.org>
Diffstat (limited to 'arch/sh/kernel')
-rw-r--r-- | arch/sh/kernel/setup.c | 164 |
1 files changed, 95 insertions, 69 deletions
diff --git a/arch/sh/kernel/setup.c b/arch/sh/kernel/setup.c index 4d6d89115194..60cc2161438f 100644 --- a/arch/sh/kernel/setup.c +++ b/arch/sh/kernel/setup.c | |||
@@ -4,7 +4,7 @@ | |||
4 | * This file handles the architecture-dependent parts of initialization | 4 | * This file handles the architecture-dependent parts of initialization |
5 | * | 5 | * |
6 | * Copyright (C) 1999 Niibe Yutaka | 6 | * Copyright (C) 1999 Niibe Yutaka |
7 | * Copyright (C) 2002 - 2006 Paul Mundt | 7 | * Copyright (C) 2002 - 2007 Paul Mundt |
8 | */ | 8 | */ |
9 | #include <linux/screen_info.h> | 9 | #include <linux/screen_info.h> |
10 | #include <linux/ioport.h> | 10 | #include <linux/ioport.h> |
@@ -15,15 +15,18 @@ | |||
15 | #include <linux/seq_file.h> | 15 | #include <linux/seq_file.h> |
16 | #include <linux/root_dev.h> | 16 | #include <linux/root_dev.h> |
17 | #include <linux/utsname.h> | 17 | #include <linux/utsname.h> |
18 | #include <linux/nodemask.h> | ||
18 | #include <linux/cpu.h> | 19 | #include <linux/cpu.h> |
19 | #include <linux/pfn.h> | 20 | #include <linux/pfn.h> |
20 | #include <linux/fs.h> | 21 | #include <linux/fs.h> |
22 | #include <linux/mm.h> | ||
21 | #include <asm/uaccess.h> | 23 | #include <asm/uaccess.h> |
22 | #include <asm/io.h> | 24 | #include <asm/io.h> |
23 | #include <asm/sections.h> | 25 | #include <asm/sections.h> |
24 | #include <asm/irq.h> | 26 | #include <asm/irq.h> |
25 | #include <asm/setup.h> | 27 | #include <asm/setup.h> |
26 | #include <asm/clock.h> | 28 | #include <asm/clock.h> |
29 | #include <asm/mmu_context.h> | ||
27 | 30 | ||
28 | extern void * __rd_start, * __rd_end; | 31 | extern void * __rd_start, * __rd_end; |
29 | 32 | ||
@@ -202,53 +205,33 @@ static int __init sh_mv_setup(char **cmdline_p) | |||
202 | return 0; | 205 | return 0; |
203 | } | 206 | } |
204 | 207 | ||
205 | void __init setup_arch(char **cmdline_p) | 208 | /* |
209 | * Register fully available low RAM pages with the bootmem allocator. | ||
210 | */ | ||
211 | static void __init register_bootmem_low_pages(void) | ||
206 | { | 212 | { |
207 | unsigned long bootmap_size; | 213 | unsigned long curr_pfn, last_pfn, pages; |
208 | unsigned long start_pfn, max_pfn, max_low_pfn; | ||
209 | |||
210 | #ifdef CONFIG_CMDLINE_BOOL | ||
211 | strcpy(COMMAND_LINE, CONFIG_CMDLINE); | ||
212 | #endif | ||
213 | |||
214 | ROOT_DEV = old_decode_dev(ORIG_ROOT_DEV); | ||
215 | |||
216 | #ifdef CONFIG_BLK_DEV_RAM | ||
217 | rd_image_start = RAMDISK_FLAGS & RAMDISK_IMAGE_START_MASK; | ||
218 | rd_prompt = ((RAMDISK_FLAGS & RAMDISK_PROMPT_FLAG) != 0); | ||
219 | rd_doload = ((RAMDISK_FLAGS & RAMDISK_LOAD_FLAG) != 0); | ||
220 | #endif | ||
221 | |||
222 | if (!MOUNT_ROOT_RDONLY) | ||
223 | root_mountflags &= ~MS_RDONLY; | ||
224 | init_mm.start_code = (unsigned long) _text; | ||
225 | init_mm.end_code = (unsigned long) _etext; | ||
226 | init_mm.end_data = (unsigned long) _edata; | ||
227 | init_mm.brk = (unsigned long) _end; | ||
228 | |||
229 | code_resource.start = (unsigned long)virt_to_phys(_text); | ||
230 | code_resource.end = (unsigned long)virt_to_phys(_etext)-1; | ||
231 | data_resource.start = (unsigned long)virt_to_phys(_etext); | ||
232 | data_resource.end = (unsigned long)virt_to_phys(_edata)-1; | ||
233 | |||
234 | sh_mv_setup(cmdline_p); | ||
235 | |||
236 | 214 | ||
237 | /* | 215 | /* |
238 | * Find the highest page frame number we have available | 216 | * We are rounding up the start address of usable memory: |
239 | */ | 217 | */ |
240 | max_pfn = PFN_DOWN(__pa(memory_end)); | 218 | curr_pfn = PFN_UP(__MEMORY_START); |
241 | 219 | ||
242 | /* | 220 | /* |
243 | * Determine low and high memory ranges: | 221 | * ... and at the end of the usable range downwards: |
244 | */ | 222 | */ |
245 | max_low_pfn = max_pfn; | 223 | last_pfn = PFN_DOWN(__pa(memory_end)); |
246 | 224 | ||
247 | /* | 225 | if (last_pfn > max_low_pfn) |
248 | * Partially used pages are not usable - thus | 226 | last_pfn = max_low_pfn; |
249 | * we are rounding upwards: | 227 | |
250 | */ | 228 | pages = last_pfn - curr_pfn; |
251 | start_pfn = PFN_UP(__pa(_end)); | 229 | free_bootmem(PFN_PHYS(curr_pfn), PFN_PHYS(pages)); |
230 | } | ||
231 | |||
232 | void __init setup_bootmem_allocator(unsigned long start_pfn) | ||
233 | { | ||
234 | unsigned long bootmap_size; | ||
252 | 235 | ||
253 | /* | 236 | /* |
254 | * Find a proper area for the bootmem bitmap. After this | 237 | * Find a proper area for the bootmem bitmap. After this |
@@ -256,31 +239,11 @@ void __init setup_arch(char **cmdline_p) | |||
256 | * is intact) must be done via bootmem_alloc(). | 239 | * is intact) must be done via bootmem_alloc(). |
257 | */ | 240 | */ |
258 | bootmap_size = init_bootmem_node(NODE_DATA(0), start_pfn, | 241 | bootmap_size = init_bootmem_node(NODE_DATA(0), start_pfn, |
259 | __MEMORY_START>>PAGE_SHIFT, | 242 | min_low_pfn, max_low_pfn); |
260 | max_low_pfn); | ||
261 | /* | ||
262 | * Register fully available low RAM pages with the bootmem allocator. | ||
263 | */ | ||
264 | { | ||
265 | unsigned long curr_pfn, last_pfn, pages; | ||
266 | |||
267 | /* | ||
268 | * We are rounding up the start address of usable memory: | ||
269 | */ | ||
270 | curr_pfn = PFN_UP(__MEMORY_START); | ||
271 | /* | ||
272 | * ... and at the end of the usable range downwards: | ||
273 | */ | ||
274 | last_pfn = PFN_DOWN(__pa(memory_end)); | ||
275 | 243 | ||
276 | if (last_pfn > max_low_pfn) | 244 | register_bootmem_low_pages(); |
277 | last_pfn = max_low_pfn; | ||
278 | |||
279 | pages = last_pfn - curr_pfn; | ||
280 | free_bootmem_node(NODE_DATA(0), PFN_PHYS(curr_pfn), | ||
281 | PFN_PHYS(pages)); | ||
282 | } | ||
283 | 245 | ||
246 | node_set_online(0); | ||
284 | 247 | ||
285 | /* | 248 | /* |
286 | * Reserve the kernel text and | 249 | * Reserve the kernel text and |
@@ -289,14 +252,14 @@ void __init setup_arch(char **cmdline_p) | |||
289 | * case of us accidentally initializing the bootmem allocator with | 252 | * case of us accidentally initializing the bootmem allocator with |
290 | * an invalid RAM area. | 253 | * an invalid RAM area. |
291 | */ | 254 | */ |
292 | reserve_bootmem_node(NODE_DATA(0), __MEMORY_START+PAGE_SIZE, | 255 | reserve_bootmem(__MEMORY_START+PAGE_SIZE, |
293 | (PFN_PHYS(start_pfn)+bootmap_size+PAGE_SIZE-1)-__MEMORY_START); | 256 | (PFN_PHYS(start_pfn)+bootmap_size+PAGE_SIZE-1)-__MEMORY_START); |
294 | 257 | ||
295 | /* | 258 | /* |
296 | * reserve physical page 0 - it's a special BIOS page on many boxes, | 259 | * reserve physical page 0 - it's a special BIOS page on many boxes, |
297 | * enabling clean reboots, SMP operation, laptop functions. | 260 | * enabling clean reboots, SMP operation, laptop functions. |
298 | */ | 261 | */ |
299 | reserve_bootmem_node(NODE_DATA(0), __MEMORY_START, PAGE_SIZE); | 262 | reserve_bootmem(__MEMORY_START, PAGE_SIZE); |
300 | 263 | ||
301 | #ifdef CONFIG_BLK_DEV_INITRD | 264 | #ifdef CONFIG_BLK_DEV_INITRD |
302 | ROOT_DEV = MKDEV(RAMDISK_MAJOR, 0); | 265 | ROOT_DEV = MKDEV(RAMDISK_MAJOR, 0); |
@@ -310,8 +273,8 @@ void __init setup_arch(char **cmdline_p) | |||
310 | 273 | ||
311 | if (LOADER_TYPE && INITRD_START) { | 274 | if (LOADER_TYPE && INITRD_START) { |
312 | if (INITRD_START + INITRD_SIZE <= (max_low_pfn << PAGE_SHIFT)) { | 275 | if (INITRD_START + INITRD_SIZE <= (max_low_pfn << PAGE_SHIFT)) { |
313 | reserve_bootmem_node(NODE_DATA(0), INITRD_START + | 276 | reserve_bootmem(INITRD_START + __MEMORY_START, |
314 | __MEMORY_START, INITRD_SIZE); | 277 | INITRD_SIZE); |
315 | initrd_start = INITRD_START + PAGE_OFFSET + | 278 | initrd_start = INITRD_START + PAGE_OFFSET + |
316 | __MEMORY_START; | 279 | __MEMORY_START; |
317 | initrd_end = initrd_start + INITRD_SIZE; | 280 | initrd_end = initrd_start + INITRD_SIZE; |
@@ -324,6 +287,71 @@ void __init setup_arch(char **cmdline_p) | |||
324 | } | 287 | } |
325 | } | 288 | } |
326 | #endif | 289 | #endif |
290 | } | ||
291 | |||
292 | #ifndef CONFIG_NEED_MULTIPLE_NODES | ||
293 | static void __init setup_memory(void) | ||
294 | { | ||
295 | unsigned long start_pfn; | ||
296 | |||
297 | /* | ||
298 | * Partially used pages are not usable - thus | ||
299 | * we are rounding upwards: | ||
300 | */ | ||
301 | start_pfn = PFN_UP(__pa(_end)); | ||
302 | setup_bootmem_allocator(start_pfn); | ||
303 | } | ||
304 | #else | ||
305 | extern void __init setup_memory(void); | ||
306 | #endif | ||
307 | |||
308 | void __init setup_arch(char **cmdline_p) | ||
309 | { | ||
310 | enable_mmu(); | ||
311 | |||
312 | #ifdef CONFIG_CMDLINE_BOOL | ||
313 | strcpy(COMMAND_LINE, CONFIG_CMDLINE); | ||
314 | #endif | ||
315 | |||
316 | ROOT_DEV = old_decode_dev(ORIG_ROOT_DEV); | ||
317 | |||
318 | #ifdef CONFIG_BLK_DEV_RAM | ||
319 | rd_image_start = RAMDISK_FLAGS & RAMDISK_IMAGE_START_MASK; | ||
320 | rd_prompt = ((RAMDISK_FLAGS & RAMDISK_PROMPT_FLAG) != 0); | ||
321 | rd_doload = ((RAMDISK_FLAGS & RAMDISK_LOAD_FLAG) != 0); | ||
322 | #endif | ||
323 | |||
324 | if (!MOUNT_ROOT_RDONLY) | ||
325 | root_mountflags &= ~MS_RDONLY; | ||
326 | init_mm.start_code = (unsigned long) _text; | ||
327 | init_mm.end_code = (unsigned long) _etext; | ||
328 | init_mm.end_data = (unsigned long) _edata; | ||
329 | init_mm.brk = (unsigned long) _end; | ||
330 | |||
331 | code_resource.start = virt_to_phys(_text); | ||
332 | code_resource.end = virt_to_phys(_etext)-1; | ||
333 | data_resource.start = virt_to_phys(_etext); | ||
334 | data_resource.end = virt_to_phys(_edata)-1; | ||
335 | |||
336 | parse_early_param(); | ||
337 | |||
338 | sh_mv_setup(cmdline_p); | ||
339 | |||
340 | /* | ||
341 | * Find the highest page frame number we have available | ||
342 | */ | ||
343 | max_pfn = PFN_DOWN(__pa(memory_end)); | ||
344 | |||
345 | /* | ||
346 | * Determine low and high memory ranges: | ||
347 | */ | ||
348 | max_low_pfn = max_pfn; | ||
349 | min_low_pfn = __MEMORY_START >> PAGE_SHIFT; | ||
350 | |||
351 | nodes_clear(node_online_map); | ||
352 | setup_memory(); | ||
353 | paging_init(); | ||
354 | sparse_init(); | ||
327 | 355 | ||
328 | #ifdef CONFIG_DUMMY_CONSOLE | 356 | #ifdef CONFIG_DUMMY_CONSOLE |
329 | conswitchp = &dummy_con; | 357 | conswitchp = &dummy_con; |
@@ -332,8 +360,6 @@ void __init setup_arch(char **cmdline_p) | |||
332 | /* Perform the machine specific initialisation */ | 360 | /* Perform the machine specific initialisation */ |
333 | if (likely(sh_mv.mv_setup)) | 361 | if (likely(sh_mv.mv_setup)) |
334 | sh_mv.mv_setup(cmdline_p); | 362 | sh_mv.mv_setup(cmdline_p); |
335 | |||
336 | paging_init(); | ||
337 | } | 363 | } |
338 | 364 | ||
339 | struct sh_machine_vector* __init get_mv_byname(const char* name) | 365 | struct sh_machine_vector* __init get_mv_byname(const char* name) |