166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer/* 266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * linux/arch/m68k/mm/init.c 366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * 466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * Copyright (C) 1995 Hamish Macdonald 566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * 666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * Contains common initialization routines, specific init code moved 766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * to motorola.c and sun3mmu.c 866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer */ 966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 1066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/module.h> 1166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/signal.h> 1266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/sched.h> 1366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/mm.h> 1466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/swap.h> 1566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/kernel.h> 1666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/string.h> 1766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/types.h> 1866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/init.h> 1966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/bootmem.h> 2066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <linux/gfp.h> 2166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 2266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/setup.h> 2366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/uaccess.h> 2466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/page.h> 2566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/pgalloc.h> 26e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#include <asm/traps.h> 2766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/machdep.h> 2866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/io.h> 2966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#ifdef CONFIG_ATARI 3066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/atari_stram.h> 3166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#endif 3266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/sections.h> 3366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#include <asm/tlb.h> 3466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 3566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungererpg_data_t pg_data_map[MAX_NUMNODES]; 3666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg UngererEXPORT_SYMBOL(pg_data_map); 3766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 3866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungererint m68k_virt_to_node_shift; 3966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 4066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#ifndef CONFIG_SINGLE_MEMORY_CHUNK 4166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungererpg_data_t *pg_data_table[65]; 4266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg UngererEXPORT_SYMBOL(pg_data_table); 4366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#endif 4466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 4566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerervoid __init m68k_setup_node(int node) 4666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer{ 4766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#ifndef CONFIG_SINGLE_MEMORY_CHUNK 4866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer struct mem_info *info = m68k_memory + node; 4966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int i, end; 5066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 5166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer i = (unsigned long)phys_to_virt(info->addr) >> __virt_to_node_shift(); 5266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer end = (unsigned long)phys_to_virt(info->addr + info->size - 1) >> __virt_to_node_shift(); 5366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer for (; i <= end; i++) { 5466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer if (pg_data_table[i]) 5566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer printk("overlap at %u for chunk %u\n", i, node); 5666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer pg_data_table[i] = pg_data_map + node; 5766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer } 5866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#endif 5966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer pg_data_map[node].bdata = bootmem_node_data + node; 6066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer node_set_online(node); 6166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer} 6266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 6366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 6466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer/* 6566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * ZERO_PAGE is a special page that is used for zero-initialized 6666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer * data and COW. 6766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer */ 6866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 6966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerervoid *empty_zero_page; 7066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg UngererEXPORT_SYMBOL(empty_zero_page); 7166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 7266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungererextern void init_pointer_table(unsigned long ptable); 7366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 7466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer/* References to section boundaries */ 7566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 7666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungererextern pmd_t *zero_pgtable; 7766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 78e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#if defined(CONFIG_MMU) && !defined(CONFIG_COLDFIRE) 79e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define VECTORS &vectors[0] 80e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#else 81e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define VECTORS _ramvec 82e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#endif 83e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer 84e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerervoid __init print_memmap(void) 85e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer{ 86e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define UL(x) ((unsigned long) (x)) 87e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define MLK(b, t) UL(b), UL(t), (UL(t) - UL(b)) >> 10 88e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define MLM(b, t) UL(b), UL(t), (UL(t) - UL(b)) >> 20 89e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer#define MLK_ROUNDUP(b, t) b, t, DIV_ROUND_UP(((t) - (b)), 1024) 90e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer 91e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer pr_notice("Virtual kernel memory layout:\n" 92e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " vector : 0x%08lx - 0x%08lx (%4ld KiB)\n" 93e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " kmap : 0x%08lx - 0x%08lx (%4ld MiB)\n" 94e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " vmalloc : 0x%08lx - 0x%08lx (%4ld MiB)\n" 95e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " lowmem : 0x%08lx - 0x%08lx (%4ld MiB)\n" 96e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " .init : 0x%p" " - 0x%p" " (%4d KiB)\n" 97e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " .text : 0x%p" " - 0x%p" " (%4d KiB)\n" 98e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " .data : 0x%p" " - 0x%p" " (%4d KiB)\n" 99e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer " .bss : 0x%p" " - 0x%p" " (%4d KiB)\n", 100e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLK(VECTORS, VECTORS + 256), 101e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLM(KMAP_START, KMAP_END), 102e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLM(VMALLOC_START, VMALLOC_END), 103e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLM(PAGE_OFFSET, (unsigned long)high_memory), 104e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLK_ROUNDUP(__init_begin, __init_end), 105e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLK_ROUNDUP(_stext, _etext), 106e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLK_ROUNDUP(_sdata, _edata), 107e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer MLK_ROUNDUP(_sbss, _ebss)); 108e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer} 109e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer 11066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerervoid __init mem_init(void) 11166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer{ 11266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer pg_data_t *pgdat; 11366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int codepages = 0; 11466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int datapages = 0; 11566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int initpages = 0; 11666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int i; 11766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 11866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer /* this will put all memory onto the freelists */ 11966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer totalram_pages = num_physpages = 0; 12066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer for_each_online_pgdat(pgdat) { 12166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer num_physpages += pgdat->node_present_pages; 12266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 12366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer totalram_pages += free_all_bootmem_node(pgdat); 12466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer for (i = 0; i < pgdat->node_spanned_pages; i++) { 12566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer struct page *page = pgdat->node_mem_map + i; 12666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer char *addr = page_to_virt(page); 12766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 12866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer if (!PageReserved(page)) 12966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer continue; 13066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer if (addr >= _text && 13166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer addr < _etext) 13266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer codepages++; 13366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer else if (addr >= __init_begin && 13466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer addr < __init_end) 13566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer initpages++; 13666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer else 13766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer datapages++; 13866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer } 13966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer } 14066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 141fbe3364ac4fa82caa585f98e4a525946d2cc21f4Greg Ungerer#if !defined(CONFIG_SUN3) && !defined(CONFIG_COLDFIRE) 14266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer /* insert pointer tables allocated so far into the tablelist */ 14366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer init_pointer_table((unsigned long)kernel_pg_dir); 14466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer for (i = 0; i < PTRS_PER_PGD; i++) { 14566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer if (pgd_present(kernel_pg_dir[i])) 14666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer init_pointer_table(__pgd_page(kernel_pg_dir[i])); 14766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer } 14866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 14966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer /* insert also pointer table that we used to unmap the zero page */ 15066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer if (zero_pgtable) 15166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer init_pointer_table((unsigned long)zero_pgtable); 15266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#endif 15366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 15466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer printk("Memory: %luk/%luk available (%dk kernel code, %dk data, %dk init)\n", 15566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer nr_free_pages() << (PAGE_SHIFT-10), 15666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer totalram_pages << (PAGE_SHIFT-10), 15766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer codepages << (PAGE_SHIFT-10), 15866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer datapages << (PAGE_SHIFT-10), 15966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer initpages << (PAGE_SHIFT-10)); 160e87c09a899d38d1b6858e010c22a1200fb77965dGreg Ungerer print_memmap(); 16166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer} 16266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer 16366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#ifdef CONFIG_BLK_DEV_INITRD 16466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerervoid free_initrd_mem(unsigned long start, unsigned long end) 16566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer{ 16666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer int pages = 0; 16766d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer for (; start < end; start += PAGE_SIZE) { 16866d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer ClearPageReserved(virt_to_page(start)); 16966d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer init_page_count(virt_to_page(start)); 17066d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer free_page(start); 17166d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer totalram_pages++; 17266d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer pages++; 17366d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer } 17466d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer printk ("Freeing initrd memory: %dk freed\n", pages); 17566d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer} 17666d857b08b8c3ed5c72c361f863cce77d2a978d7Greg Ungerer#endif 177