; ; Copyright (c) 2012, ARM Limited. All rights reserved. ; ; Redistribution and use in source and binary forms, with ; or without modification, are permitted provided that the ; following conditions are met: ; ; Redistributions of source code must retain the above ; copyright notice, this list of conditions and the ; following disclaimer. ; ; Redistributions in binary form must reproduce the ; above copyright notice, this list of conditions and ; the following disclaimer in the documentation ; and/or other materials provided with the distribution. ; ; Neither the name of ARM nor the names of its ; contributors may be used to endorse or promote products ; derived from this software without specific prior written ; permission. ; AREA |boot|, CODE, ALIGN=2 PRESERVE8 INCLUDE emubuild.s IMPORT __use_no_semihosting_swi IMPORT __use_no_heap_region IMPORT output_string IMPORT c_start IMPORT enable_coherency IMPORT stack IMPORT stack_size IMPORT hexword IMPORT read_sctlr IMPORT write_sctlr IMPORT get_sp IMPORT inv_icache_all EXPORT start EXPORT dabort EXPORT fiq EXPORT irq EXPORT pabort EXPORT swi EXPORT undef EXPORT unused EXPORT dead ;------------------------------------------------------------------------------ ; Boot code starts here - identify the CPU type, set up stacks and call c_start ;------------------------------------------------------------------------------ start bl inv_icache_all ;------------------------------------------------------------------ ; Enable ICache, branch predictor and alignment ;------------------------------------------------------------------ bl read_sctlr bic r0, r0, #CR_C orr r0, r0, #CR_Z orr r0, r0, #CR_I ;------------------------------------------------------------------ ; Set U bit - the C compiler produces non-64-bit-aligned LDRD/STRDs ;------------------------------------------------------------------ orr r0, #CR_U bl write_sctlr ;------------------------------------------------------------------ ; Give yourself a stack to make things easier ;------------------------------------------------------------------ ldr r0, =stack ldr r1, =stack_size ldr r1, [r1] bl get_sp mov sp, r0 ;------------------------------------------------------------------ ; Caches are inavlidated at reset & MMU is off. So its safe to ; enable coherency ;------------------------------------------------------------------ ;; bl enable_coherency ;------------------------------------------------------------------ ; TODO: Enable MMU & coherency here ;------------------------------------------------------------------ ;------------------------------------------------------------------ ; Jump to the C handler ;------------------------------------------------------------------ bl c_start ;------------------------------------------------------------------ ; Should never come here ;------------------------------------------------------------------ kernel_returned b kernel_returned ; ============================================================================== ; End of main code ; ============================================================================== ; ============================================================================== ; Message strings, etc. ; ============================================================================== LTORG ALIGN dabort_string DCB " Emubuild-DAB!", 0 undef_string DCB " Emubuild-UND!", 0 pabort_string DCB " Emubuild-PAB!", 0 swi_string DCB " Emubuild-SWI!", 0 irq_string DCB " Emubuild-IRQ!", 0 fiq_string DCB " Emubuild-FIQ!", 0 unused_string DCB " Emubuild-UNU!", 0 ALIGN ; ============================================================================== ; Exception handlers - for most exceptions we spin ; ============================================================================== dabort mov r12, lr ; save lr, just in case it's interesting mov r0, r12 bl hexword mrc p15,0,r0,c5,c0,0 ; DFSR bl hexword mrc p15,0,r0,c6,c0,0 ; DFAR bl hexword ldr r0, =dabort_string bl output_string b dead undef push {r0-r1} ldr r0, [lr,#-4] ; load undeffing instruction ldr r1, =0xf57ff000 ; ignore unimplemented DSB/DMB/ISB/CLRX bic r0, r0, #0x000000ff cmp r0, r1 popeq {r0-r1} bxeq lr mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =undef_string bl output_string b dead pabort mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =pabort_string bl output_string b dead swi mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =swi_string bl output_string b dead irq mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =irq_string bl output_string b dead fiq mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =fiq_string bl output_string b dead unused mov r0, lr ; print lr, just in case it's interesting bl hexword ldr r0, =unused_string bl output_string b dead dead B dead END