diff options
author | David S. Miller <davem@sunset.davemloft.net> | 2005-09-22 04:08:57 -0400 |
---|---|---|
committer | David S. Miller <davem@sunset.davemloft.net> | 2005-09-22 04:08:57 -0400 |
commit | 2bdb3cb265830aee823444d115a8a84eca2b934e (patch) | |
tree | 967596d2e3ab18772761dd1202d67803d0830c85 | |
parent | 5085b4a5492f4f8bd32d0cc5b1cad4bf522c2e1a (diff) |
[SPARC64]: Remove unnecessary paging_init() cruft.
Because we don't access the PAGE_OFFSET linear mappings
any longer before we take over the trap table from the
firmware, we don't need to load dummy mappings there
into the TLB and we don't need the bootmap_base hack
any longer either.
While we are here, check for a larger than 8MB kernel
and halt the boot with an error message. We know that
doesn't work, so instead of failing mysteriously we
should let the user know exactly what's wrong.
Signed-off-by: David S. Miller <davem@davemloft.net>
-rw-r--r-- | arch/sparc64/mm/init.c | 114 |
1 files changed, 15 insertions, 99 deletions
diff --git a/arch/sparc64/mm/init.c b/arch/sparc64/mm/init.c index 598bfb3b0053..92d095802958 100644 --- a/arch/sparc64/mm/init.c +++ b/arch/sparc64/mm/init.c | |||
@@ -43,7 +43,7 @@ extern void device_scan(void); | |||
43 | 43 | ||
44 | struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; | 44 | struct sparc_phys_banks sp_banks[SPARC_PHYS_BANKS]; |
45 | 45 | ||
46 | unsigned long *sparc64_valid_addr_bitmap; | 46 | unsigned long *sparc64_valid_addr_bitmap __read_mostly; |
47 | 47 | ||
48 | /* Ugly, but necessary... -DaveM */ | 48 | /* Ugly, but necessary... -DaveM */ |
49 | unsigned long phys_base __read_mostly; | 49 | unsigned long phys_base __read_mostly; |
@@ -51,15 +51,6 @@ unsigned long kern_base __read_mostly; | |||
51 | unsigned long kern_size __read_mostly; | 51 | unsigned long kern_size __read_mostly; |
52 | unsigned long pfn_base __read_mostly; | 52 | unsigned long pfn_base __read_mostly; |
53 | 53 | ||
54 | /* This is even uglier. We have a problem where the kernel may not be | ||
55 | * located at phys_base. However, initial __alloc_bootmem() calls need to | ||
56 | * be adjusted to be within the 4-8Megs that the kernel is mapped to, else | ||
57 | * those page mappings wont work. Things are ok after inherit_prom_mappings | ||
58 | * is called though. Dave says he'll clean this up some other time. | ||
59 | * -- BenC | ||
60 | */ | ||
61 | static unsigned long bootmap_base; | ||
62 | |||
63 | /* get_new_mmu_context() uses "cache + 1". */ | 54 | /* get_new_mmu_context() uses "cache + 1". */ |
64 | DEFINE_SPINLOCK(ctx_alloc_lock); | 55 | DEFINE_SPINLOCK(ctx_alloc_lock); |
65 | unsigned long tlb_context_cache = CTX_FIRST_VERSION - 1; | 56 | unsigned long tlb_context_cache = CTX_FIRST_VERSION - 1; |
@@ -1415,8 +1406,6 @@ unsigned long __init bootmem_init(unsigned long *pages_avail) | |||
1415 | #endif | 1406 | #endif |
1416 | bootmap_size = init_bootmem_node(NODE_DATA(0), bootmap_pfn, pfn_base, end_pfn); | 1407 | bootmap_size = init_bootmem_node(NODE_DATA(0), bootmap_pfn, pfn_base, end_pfn); |
1417 | 1408 | ||
1418 | bootmap_base = bootmap_pfn << PAGE_SHIFT; | ||
1419 | |||
1420 | /* Now register the available physical memory with the | 1409 | /* Now register the available physical memory with the |
1421 | * allocator. | 1410 | * allocator. |
1422 | */ | 1411 | */ |
@@ -1475,89 +1464,22 @@ static unsigned long last_valid_pfn; | |||
1475 | void __init paging_init(void) | 1464 | void __init paging_init(void) |
1476 | { | 1465 | { |
1477 | extern pmd_t swapper_pmd_dir[1024]; | 1466 | extern pmd_t swapper_pmd_dir[1024]; |
1478 | unsigned long alias_base = kern_base + PAGE_OFFSET; | 1467 | unsigned long end_pfn, pages_avail, shift; |
1479 | unsigned long second_alias_page = 0; | ||
1480 | unsigned long pt, flags, end_pfn, pages_avail; | ||
1481 | unsigned long shift = alias_base - ((unsigned long)KERNBASE); | ||
1482 | unsigned long real_end; | 1468 | unsigned long real_end; |
1483 | 1469 | ||
1484 | set_bit(0, mmu_context_bmap); | 1470 | set_bit(0, mmu_context_bmap); |
1485 | 1471 | ||
1472 | shift = kern_base + PAGE_OFFSET - ((unsigned long)KERNBASE); | ||
1473 | |||
1486 | real_end = (unsigned long)_end; | 1474 | real_end = (unsigned long)_end; |
1487 | if ((real_end > ((unsigned long)KERNBASE + 0x400000))) | 1475 | if ((real_end > ((unsigned long)KERNBASE + 0x400000))) |
1488 | bigkernel = 1; | 1476 | bigkernel = 1; |
1489 | #ifdef CONFIG_BLK_DEV_INITRD | 1477 | if ((real_end > ((unsigned long)KERNBASE + 0x800000))) { |
1490 | if (sparc_ramdisk_image || sparc_ramdisk_image64) | 1478 | prom_printf("paging_init: Kernel > 8MB, too large.\n"); |
1491 | real_end = (PAGE_ALIGN(real_end) + PAGE_ALIGN(sparc_ramdisk_size)); | 1479 | prom_halt(); |
1492 | #endif | ||
1493 | |||
1494 | /* We assume physical memory starts at some 4mb multiple, | ||
1495 | * if this were not true we wouldn't boot up to this point | ||
1496 | * anyways. | ||
1497 | */ | ||
1498 | pt = kern_base | _PAGE_VALID | _PAGE_SZ4MB; | ||
1499 | pt |= _PAGE_CP | _PAGE_CV | _PAGE_P | _PAGE_L | _PAGE_W; | ||
1500 | local_irq_save(flags); | ||
1501 | if (tlb_type == spitfire) { | ||
1502 | __asm__ __volatile__( | ||
1503 | " stxa %1, [%0] %3\n" | ||
1504 | " stxa %2, [%5] %4\n" | ||
1505 | " membar #Sync\n" | ||
1506 | " flush %%g6\n" | ||
1507 | " nop\n" | ||
1508 | " nop\n" | ||
1509 | " nop\n" | ||
1510 | : /* No outputs */ | ||
1511 | : "r" (TLB_TAG_ACCESS), "r" (alias_base), "r" (pt), | ||
1512 | "i" (ASI_DMMU), "i" (ASI_DTLB_DATA_ACCESS), "r" (61 << 3) | ||
1513 | : "memory"); | ||
1514 | if (real_end >= KERNBASE + 0x340000) { | ||
1515 | second_alias_page = alias_base + 0x400000; | ||
1516 | __asm__ __volatile__( | ||
1517 | " stxa %1, [%0] %3\n" | ||
1518 | " stxa %2, [%5] %4\n" | ||
1519 | " membar #Sync\n" | ||
1520 | " flush %%g6\n" | ||
1521 | " nop\n" | ||
1522 | " nop\n" | ||
1523 | " nop\n" | ||
1524 | : /* No outputs */ | ||
1525 | : "r" (TLB_TAG_ACCESS), "r" (second_alias_page), "r" (pt + 0x400000), | ||
1526 | "i" (ASI_DMMU), "i" (ASI_DTLB_DATA_ACCESS), "r" (60 << 3) | ||
1527 | : "memory"); | ||
1528 | } | ||
1529 | } else if (tlb_type == cheetah || tlb_type == cheetah_plus) { | ||
1530 | __asm__ __volatile__( | ||
1531 | " stxa %1, [%0] %3\n" | ||
1532 | " stxa %2, [%5] %4\n" | ||
1533 | " membar #Sync\n" | ||
1534 | " flush %%g6\n" | ||
1535 | " nop\n" | ||
1536 | " nop\n" | ||
1537 | " nop\n" | ||
1538 | : /* No outputs */ | ||
1539 | : "r" (TLB_TAG_ACCESS), "r" (alias_base), "r" (pt), | ||
1540 | "i" (ASI_DMMU), "i" (ASI_DTLB_DATA_ACCESS), "r" ((0<<16) | (13<<3)) | ||
1541 | : "memory"); | ||
1542 | if (real_end >= KERNBASE + 0x340000) { | ||
1543 | second_alias_page = alias_base + 0x400000; | ||
1544 | __asm__ __volatile__( | ||
1545 | " stxa %1, [%0] %3\n" | ||
1546 | " stxa %2, [%5] %4\n" | ||
1547 | " membar #Sync\n" | ||
1548 | " flush %%g6\n" | ||
1549 | " nop\n" | ||
1550 | " nop\n" | ||
1551 | " nop\n" | ||
1552 | : /* No outputs */ | ||
1553 | : "r" (TLB_TAG_ACCESS), "r" (second_alias_page), "r" (pt + 0x400000), | ||
1554 | "i" (ASI_DMMU), "i" (ASI_DTLB_DATA_ACCESS), "r" ((0<<16) | (12<<3)) | ||
1555 | : "memory"); | ||
1556 | } | ||
1557 | } | 1480 | } |
1558 | local_irq_restore(flags); | 1481 | |
1559 | 1482 | /* Set kernel pgd to upper alias so physical page computations | |
1560 | /* Now set kernel pgd to upper alias so physical page computations | ||
1561 | * work. | 1483 | * work. |
1562 | */ | 1484 | */ |
1563 | init_mm.pgd += ((shift) / (sizeof(pgd_t))); | 1485 | init_mm.pgd += ((shift) / (sizeof(pgd_t))); |
@@ -1568,15 +1490,11 @@ void __init paging_init(void) | |||
1568 | pud_set(pud_offset(&swapper_pg_dir[0], 0), | 1490 | pud_set(pud_offset(&swapper_pg_dir[0], 0), |
1569 | swapper_pmd_dir + (shift / sizeof(pgd_t))); | 1491 | swapper_pmd_dir + (shift / sizeof(pgd_t))); |
1570 | 1492 | ||
1571 | swapper_pgd_zero = pgd_val(init_mm.pgd[0]); | 1493 | swapper_pgd_zero = pgd_val(swapper_pg_dir[0]); |
1572 | 1494 | ||
1573 | /* Inherit non-locked OBP mappings. */ | 1495 | /* Inherit non-locked OBP mappings. */ |
1574 | inherit_prom_mappings(); | 1496 | inherit_prom_mappings(); |
1575 | 1497 | ||
1576 | /* Setup bootmem... */ | ||
1577 | pages_avail = 0; | ||
1578 | last_valid_pfn = end_pfn = bootmem_init(&pages_avail); | ||
1579 | |||
1580 | /* Ok, we can use our TLB miss and window trap handlers safely. | 1498 | /* Ok, we can use our TLB miss and window trap handlers safely. |
1581 | * We need to do a quick peek here to see if we are on StarFire | 1499 | * We need to do a quick peek here to see if we are on StarFire |
1582 | * or not, so setup_tba can setup the IRQ globals correctly (it | 1500 | * or not, so setup_tba can setup the IRQ globals correctly (it |
@@ -1589,13 +1507,12 @@ void __init paging_init(void) | |||
1589 | 1507 | ||
1590 | inherit_locked_prom_mappings(1); | 1508 | inherit_locked_prom_mappings(1); |
1591 | 1509 | ||
1592 | /* We only created DTLB mapping of this stuff. */ | ||
1593 | spitfire_flush_dtlb_nucleus_page(alias_base); | ||
1594 | if (second_alias_page) | ||
1595 | spitfire_flush_dtlb_nucleus_page(second_alias_page); | ||
1596 | |||
1597 | __flush_tlb_all(); | 1510 | __flush_tlb_all(); |
1598 | 1511 | ||
1512 | /* Setup bootmem... */ | ||
1513 | pages_avail = 0; | ||
1514 | last_valid_pfn = end_pfn = bootmem_init(&pages_avail); | ||
1515 | |||
1599 | { | 1516 | { |
1600 | unsigned long zones_size[MAX_NR_ZONES]; | 1517 | unsigned long zones_size[MAX_NR_ZONES]; |
1601 | unsigned long zholes_size[MAX_NR_ZONES]; | 1518 | unsigned long zholes_size[MAX_NR_ZONES]; |
@@ -1757,8 +1674,7 @@ void __init mem_init(void) | |||
1757 | 1674 | ||
1758 | i = last_valid_pfn >> ((22 - PAGE_SHIFT) + 6); | 1675 | i = last_valid_pfn >> ((22 - PAGE_SHIFT) + 6); |
1759 | i += 1; | 1676 | i += 1; |
1760 | sparc64_valid_addr_bitmap = (unsigned long *) | 1677 | sparc64_valid_addr_bitmap = (unsigned long *) alloc_bootmem(i << 3); |
1761 | __alloc_bootmem(i << 3, SMP_CACHE_BYTES, bootmap_base); | ||
1762 | if (sparc64_valid_addr_bitmap == NULL) { | 1678 | if (sparc64_valid_addr_bitmap == NULL) { |
1763 | prom_printf("mem_init: Cannot alloc valid_addr_bitmap.\n"); | 1679 | prom_printf("mem_init: Cannot alloc valid_addr_bitmap.\n"); |
1764 | prom_halt(); | 1680 | prom_halt(); |