From 361ec26f1029f32f21641431c135e12dac68d1d4 Mon Sep 17 00:00:00 2001 From: Alexander von Gluck IV Date: Thu, 24 May 2012 05:48:10 -0500 Subject: [PATCH] rPi MMU: Cleanup, add gPeripheralBase * gPeripheralBase keeps track of the device peripherals before and after mmu_init * Add ability to disable mmu for troubleshooting * Remove static FB_BASE, we actually don't know where the FB is yet. (depends on firmware used) --- headers/private/kernel/arch/arm/bcm2708.h | 4 +- .../boot/platform/raspberrypi_arm/mmu.cpp | 37 +++++++++++++------ .../boot/platform/raspberrypi_arm/serial.cpp | 7 ++-- .../boot/platform/raspberrypi_arm/start.c | 6 ++- 4 files changed, 34 insertions(+), 20 deletions(-) diff --git a/headers/private/kernel/arch/arm/bcm2708.h b/headers/private/kernel/arch/arm/bcm2708.h index 740837224b..e124ae6aa7 100644 --- a/headers/private/kernel/arch/arm/bcm2708.h +++ b/headers/private/kernel/arch/arm/bcm2708.h @@ -62,9 +62,7 @@ // SMI Base #define USB_BASE 0x980000 // USB Controller, 15.2, page 202 -#define FB_BASE 0x000000 - // Fake frame buffer -#define FB_SIZE SIZE_4K +// FB_BASE will depend on memory split // 7.5, page 112 diff --git a/src/system/boot/platform/raspberrypi_arm/mmu.cpp b/src/system/boot/platform/raspberrypi_arm/mmu.cpp index aa486f265c..b80ad8b79f 100644 --- a/src/system/boot/platform/raspberrypi_arm/mmu.cpp +++ b/src/system/boot/platform/raspberrypi_arm/mmu.cpp @@ -40,9 +40,14 @@ // You also need to define ENABLE_SERIAL in serial.cpp // for output to work. +//#define DEBUG_DISABLE_MMU + + extern uint8 __stack_start; extern uint8 __stack_end; +extern addr_t gPeripheralBase; + /* *defines a block in memory @@ -60,6 +65,7 @@ struct memblock { static struct memblock LOADER_MEMORYMAP[] = { + // We map this first so we can always find peripherals { "devices", PERIPHERAL_BASE, @@ -114,20 +120,20 @@ static struct memblock LOADER_MEMORYMAP[] = { //static const uint32 kDefaultPageTableFlags = MMU_FLAG_READWRITE; // not cached not buffered, R/W -static const size_t kMaxKernelSize = 0x200000; // 2 MB for the kernel +static const size_t kMaxKernelSize = 0x200000; // 2 MB for the kernel -static addr_t sNextPhysicalAddress = 0; //will be set by mmu_init +static addr_t sNextPhysicalAddress = 0; // will be set by mmu_init static addr_t sNextVirtualAddress = KERNEL_BASE + kMaxKernelSize; static addr_t sMaxVirtualAddress = KERNEL_BASE + kMaxKernelSize; static addr_t sNextPageTableAddress = 0; -//the page directory is in front of the pagetable +// the page directory is in front of the pagetable static uint32 kPageTableRegionEnd = 0; // working page directory and page table static uint32 *sPageDirectory = 0 ; -//page directory has to be on a multiple of 16MB for -//some arm processors +// page directory has to be on a multiple of 16MB for +// some arm processors static addr_t @@ -141,11 +147,13 @@ get_next_virtual_address(size_t size) static addr_t -get_next_virtual_address_alligned (size_t size, uint32 mask) +get_next_virtual_address_alligned(size_t size, uint32 mask) { - addr_t address = (sNextVirtualAddress) & mask; + addr_t address = sNextVirtualAddress & mask; sNextVirtualAddress = address + size; + TRACE("%s: %p\n", __func__, (void*)address); + return address; } @@ -190,7 +198,7 @@ get_next_physical_page(size_t pagesize) void mmu_set_TTBR(uint32 ttb) { - TRACE("%s: Set Translation Table Base to 0x%lx\n", __func__); + TRACE("%s: Set Translation Table Base to 0x%" B_PRIx32 "\n", __func__, ttb); ttb &= 0xffffc000; asm volatile("MRC p15, 0, %[adr], c2, c0, 0"::[adr] "r" (ttb)); } @@ -233,7 +241,8 @@ mmu_write_C1(uint32 value) void mmu_write_DACR(uint32 value) { - TRACE("%s: Set Domain Access Register to 0x%lx\n", __func__); + TRACE("%s: Set Domain Access Register to 0x%" B_PRIx32 "\n", + __func__, value); asm volatile("MCR p15, 0, %[c1in], c3, c0, 0"::[c1in] "r" (value)); } @@ -242,7 +251,7 @@ static uint32 * get_next_page_table(uint32 type) { TRACE("%s: sNextPageTableAddress %p, kPageTableRegionEnd %p, " - "type 0x%" B_PRIX32 "\n", __func__, sNextPageTableAddress, + "type 0x%" B_PRIx32 "\n", __func__, sNextPageTableAddress, kPageTableRegionEnd, type); size_t size = 0; @@ -289,7 +298,7 @@ init_page_directory() sPageDirectory[i] = 0; uint32 *pageTable = NULL; - for (uint32 i = 0; i < ARRAY_SIZE(LOADER_MEMORYMAP);i++) { + for (uint32 i = 0; i < ARRAY_SIZE(LOADER_MEMORYMAP); i++) { pageTable = get_next_page_table(MMU_L1_TYPE_COARSE); TRACE("BLOCK: %s START: %lx END %lx\n", LOADER_MEMORYMAP[i].name, @@ -328,12 +337,16 @@ init_page_directory() // TLB Flush mmu_flush_TLB(); - // Set domain access register + // Set domain access register, manager access to all mmu_write_DACR(0xFFFFFFFF); + #ifndef DEBUG_DISABLE_MMU TRACE("%s: Enable MMU...\n", __func__); mmu_write_C1(mmu_read_C1() | 0x1); + gPeripheralBase = sNextVirtualAddress; + #endif + TRACE("%s: Complete\n", __func__); } diff --git a/src/system/boot/platform/raspberrypi_arm/serial.cpp b/src/system/boot/platform/raspberrypi_arm/serial.cpp index b97d0b7a6a..c64f45bdad 100644 --- a/src/system/boot/platform/raspberrypi_arm/serial.cpp +++ b/src/system/boot/platform/raspberrypi_arm/serial.cpp @@ -23,6 +23,7 @@ DebugUART *gUART; static bool sSerialEnabled = false; +extern addr_t gPeripheralBase; static void @@ -88,10 +89,8 @@ serial_cleanup(void) extern "C" void serial_init(void) { - addr_t uart0 = mmu_map_physical_memory(PERIPHERAL_BASE + BOARD_UART_DEBUG, - 0x00004000, kDefaultPageFlags); - - gUART = arch_get_uart_pl011(uart0, BOARD_UART_CLOCK); + gUART = arch_get_uart_pl011(gPeripheralBase + BOARD_UART_DEBUG, + BOARD_UART_CLOCK); gUART->InitEarly(); gUART->InitPort(9600); diff --git a/src/system/boot/platform/raspberrypi_arm/start.c b/src/system/boot/platform/raspberrypi_arm/start.c index 6b3de48b38..8887e34276 100644 --- a/src/system/boot/platform/raspberrypi_arm/start.c +++ b/src/system/boot/platform/raspberrypi_arm/start.c @@ -37,6 +37,9 @@ extern uint8 __stack_end; extern int main(stage2_args *args); void _start(void); +// Adjusted during mmu_init +addr_t gPeripheralBase = PERIPHERAL_BASE; + static void clear_bss(void) @@ -112,8 +115,9 @@ pi_start(void) gpio_init(); // Flick on "OK" led, use pre-mmu firmware base - gpio_write(PERIPHERAL_BASE + GPIO_BASE, 16, 0); + gpio_write(gPeripheralBase + GPIO_BASE, 16, 0); + // To debug mmu, enable serial_init above me! mmu_init(); serial_init();