Browse Source
Enhance BL3-1 entrypoint handling to support non-TF boot firmware - Phase 1pull/325/head
danh-arm
10 years ago
13 changed files with 371 additions and 406 deletions
@ -0,0 +1,256 @@ |
|||
/* |
|||
* Copyright (c) 2015, ARM Limited and Contributors. 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. |
|||
* |
|||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" |
|||
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
|||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE |
|||
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE |
|||
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR |
|||
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF |
|||
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS |
|||
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN |
|||
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) |
|||
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE |
|||
* POSSIBILITY OF SUCH DAMAGE. |
|||
*/ |
|||
|
|||
#ifndef __EL3_COMMON_MACROS_S__ |
|||
#define __EL3_COMMON_MACROS_S__ |
|||
|
|||
#include <arch.h> |
|||
#include <asm_macros.S> |
|||
|
|||
/* |
|||
* Helper macro to initialise EL3 registers we care about. |
|||
*/ |
|||
.macro el3_arch_init_common _exception_vectors |
|||
/* --------------------------------------------------------------------- |
|||
* Enable the instruction cache, stack pointer and data access alignment |
|||
* checks |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
mov x1, #(SCTLR_I_BIT | SCTLR_A_BIT | SCTLR_SA_BIT) |
|||
mrs x0, sctlr_el3 |
|||
orr x0, x0, x1 |
|||
msr sctlr_el3, x0 |
|||
isb |
|||
|
|||
#if IMAGE_BL31 |
|||
/* --------------------------------------------------------------------- |
|||
* Initialise the per-cpu cache pointer to the CPU. |
|||
* This is done early to enable crash reporting to have access to crash |
|||
* stack. Since crash reporting depends on cpu_data to report the |
|||
* unhandled exception, not doing so can lead to recursive exceptions |
|||
* due to a NULL TPIDR_EL3. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
bl init_cpu_data_ptr |
|||
#endif /* IMAGE_BL31 */ |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* Set the exception vectors. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
adr x0, \_exception_vectors |
|||
msr vbar_el3, x0 |
|||
isb |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* Enable the SError interrupt now that the exception vectors have been |
|||
* setup. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
msr daifclr, #DAIF_ABT_BIT |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* The initial state of the Architectural feature trap register |
|||
* (CPTR_EL3) is unknown and it must be set to a known state. All |
|||
* feature traps are disabled. Some bits in this register are marked as |
|||
* reserved and should not be modified. |
|||
* |
|||
* CPTR_EL3.TCPAC: This causes a direct access to the CPACR_EL1 from EL1 |
|||
* or the CPTR_EL2 from EL2 to trap to EL3 unless it is trapped at EL2. |
|||
* |
|||
* CPTR_EL3.TTA: This causes access to the Trace functionality to trap |
|||
* to EL3 when executed from EL0, EL1, EL2, or EL3. If system register |
|||
* access to trace functionality is not supported, this bit is RES0. |
|||
* |
|||
* CPTR_EL3.TFP: This causes instructions that access the registers |
|||
* associated with Floating Point and Advanced SIMD execution to trap |
|||
* to EL3 when executed from any exception level, unless trapped to EL1 |
|||
* or EL2. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
mrs x0, cptr_el3 |
|||
bic w0, w0, #TCPAC_BIT |
|||
bic w0, w0, #TTA_BIT |
|||
bic w0, w0, #TFP_BIT |
|||
msr cptr_el3, x0 |
|||
.endm |
|||
|
|||
/* ----------------------------------------------------------------------------- |
|||
* This is the super set of actions that need to be performed during a cold boot |
|||
* or a warm boot in EL3. This code is shared by BL1 and BL3-1. |
|||
* |
|||
* This macro will always perform reset handling, architectural initialisations |
|||
* and stack setup. The rest of the actions are optional because they might not |
|||
* be needed, depending on the context in which this macro is called. This is |
|||
* why this macro is parameterised ; each parameter allows to enable/disable |
|||
* some actions. |
|||
* |
|||
* _set_endian: |
|||
* Whether the macro needs to configure the endianness of data accesses. |
|||
* |
|||
* _warm_boot_mailbox: |
|||
* Whether the macro needs to detect the type of boot (cold/warm). The |
|||
* detection is based on the platform entrypoint address : if it is zero |
|||
* then it is a cold boot, otherwise it is a warm boot. In the latter case, |
|||
* this macro jumps on the platform entrypoint address. |
|||
* |
|||
* _secondary_cold_boot: |
|||
* Whether the macro needs to identify the CPU that is calling it: primary |
|||
* CPU or secondary CPU. The primary CPU will be allowed to carry on with |
|||
* the platform initialisations, while the secondaries will be put in a |
|||
* platform-specific state in the meantime. |
|||
* |
|||
* If the caller knows this macro will only be called by the primary CPU |
|||
* then this parameter can be defined to 0 to skip this step. |
|||
* |
|||
* _init_memory: |
|||
* Whether the macro needs to initialise the memory. |
|||
* |
|||
* _init_c_runtime: |
|||
* Whether the macro needs to initialise the C runtime environment. |
|||
* |
|||
* _exception_vectors: |
|||
* Address of the exception vectors to program in the VBAR_EL3 register. |
|||
* ----------------------------------------------------------------------------- |
|||
*/ |
|||
.macro el3_entrypoint_common \ |
|||
_set_endian, _warm_boot_mailbox, _secondary_cold_boot, \ |
|||
_init_memory, _init_c_runtime, _exception_vectors |
|||
|
|||
.if \_set_endian |
|||
/* ------------------------------------------------------------- |
|||
* Set the CPU endianness before doing anything that might |
|||
* involve memory reads or writes. |
|||
* ------------------------------------------------------------- |
|||
*/ |
|||
mrs x0, sctlr_el3 |
|||
bic x0, x0, #SCTLR_EE_BIT |
|||
msr sctlr_el3, x0 |
|||
isb |
|||
.endif /* _set_endian */ |
|||
|
|||
.if \_warm_boot_mailbox |
|||
/* ------------------------------------------------------------- |
|||
* This code will be executed for both warm and cold resets. |
|||
* Now is the time to distinguish between the two. |
|||
* Query the platform entrypoint address and if it is not zero |
|||
* then it means it is a warm boot so jump to this address. |
|||
* ------------------------------------------------------------- |
|||
*/ |
|||
mrs x0, mpidr_el1 |
|||
bl platform_get_entrypoint |
|||
cbz x0, do_cold_boot |
|||
br x0 |
|||
|
|||
do_cold_boot: |
|||
.endif /* _warm_boot_mailbox */ |
|||
|
|||
.if \_secondary_cold_boot |
|||
/* ------------------------------------------------------------- |
|||
* It is a cold boot. |
|||
* The primary CPU will set up the platform while the |
|||
* secondaries are placed in a platform-specific state until the |
|||
* primary CPU performs the necessary actions to bring them out |
|||
* of that state and allows entry into the OS. |
|||
* ------------------------------------------------------------- |
|||
*/ |
|||
mrs x0, mpidr_el1 |
|||
bl platform_is_primary_cpu |
|||
cbnz x0, do_primary_cold_boot |
|||
|
|||
/* This is a cold boot on a secondary CPU */ |
|||
bl plat_secondary_cold_boot_setup |
|||
/* plat_secondary_cold_boot_setup() is not supposed to return */ |
|||
secondary_panic: |
|||
b secondary_panic |
|||
|
|||
do_primary_cold_boot: |
|||
.endif /* _secondary_cold_boot */ |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* Perform any processor specific actions upon reset e.g. cache, TLB |
|||
* invalidations etc. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
bl reset_handler |
|||
|
|||
el3_arch_init_common \_exception_vectors |
|||
|
|||
.if \_init_memory |
|||
bl platform_mem_init |
|||
.endif /* _init_memory */ |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* Init C runtime environment: |
|||
* - Zero-initialise the NOBITS sections. There are 2 of them: |
|||
* - the .bss section; |
|||
* - the coherent memory section (if any). |
|||
* - Relocate the data section from ROM to RAM, if required. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
.if \_init_c_runtime |
|||
ldr x0, =__BSS_START__ |
|||
ldr x1, =__BSS_SIZE__ |
|||
bl zeromem16 |
|||
|
|||
#if USE_COHERENT_MEM |
|||
ldr x0, =__COHERENT_RAM_START__ |
|||
ldr x1, =__COHERENT_RAM_UNALIGNED_SIZE__ |
|||
bl zeromem16 |
|||
#endif |
|||
|
|||
#ifdef __DATA_ROM_START__ |
|||
ldr x0, =__DATA_RAM_START__ |
|||
ldr x1, =__DATA_ROM_START__ |
|||
ldr x2, =__DATA_SIZE__ |
|||
bl memcpy16 |
|||
#endif |
|||
.endif /* _init_c_runtime */ |
|||
|
|||
#if IMAGE_BL31 |
|||
/* --------------------------------------------------------------------- |
|||
* Use SP_EL0 for the C runtime stack. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
msr spsel, #0 |
|||
#endif /* IMAGE_BL31 */ |
|||
|
|||
/* --------------------------------------------------------------------- |
|||
* Allocate a stack whose memory will be marked as Normal-IS-WBWA when |
|||
* the MMU is enabled. There is no risk of reading stale stack memory |
|||
* after enabling the MMU as only the primary CPU is running at the |
|||
* moment. |
|||
* --------------------------------------------------------------------- |
|||
*/ |
|||
mrs x0, mpidr_el1 |
|||
bl platform_set_stack |
|||
.endm |
|||
|
|||
#endif /* __EL3_COMMON_MACROS_S__ */ |
Loading…
Reference in new issue