diff options
-rw-r--r-- | Makefile | 5 | ||||
-rw-r--r-- | bl1/bl1_context_mgmt.c | 14 | ||||
-rw-r--r-- | bl31/bl31_main.c | 13 | ||||
-rw-r--r-- | common/aarch64/context.S | 66 | ||||
-rw-r--r-- | common/bl_common.c | 33 | ||||
-rw-r--r-- | docs/user-guide.md | 6 | ||||
-rw-r--r-- | include/common/context.h | 82 | ||||
-rw-r--r-- | include/lib/cpus/aarch64/cortex_a73.h | 44 | ||||
-rw-r--r-- | include/lib/xlat_tables.h | 6 | ||||
-rw-r--r-- | lib/cpus/aarch64/cortex_a73.S | 155 | ||||
-rw-r--r-- | plat/arm/board/common/board_arm_trusted_boot.c | 10 | ||||
-rw-r--r-- | plat/arm/board/fvp/fvp_common.c | 2 | ||||
-rw-r--r-- | plat/arm/board/fvp/fvp_trusted_boot.c | 68 | ||||
-rw-r--r-- | plat/arm/board/fvp/platform.mk | 5 | ||||
-rw-r--r-- | plat/arm/common/aarch64/arm_common.c | 2 |
15 files changed, 417 insertions, 94 deletions
@@ -62,6 +62,9 @@ NS_TIMER_SWITCH := 0 RESET_TO_BL31 := 0 # Include FP registers in cpu context CTX_INCLUDE_FPREGS := 0 +# Build flag to include AArch32 registers in cpu context save and restore +# during world switch. This flag must be set to 0 for AArch64-only platforms. +CTX_INCLUDE_AARCH32_REGS := 1 # Determine the version of ARM GIC architecture to use for interrupt management # in EL3. The platform port can change this value if needed. ARM_GIC_ARCH := 2 @@ -396,6 +399,7 @@ $(eval $(call assert_boolean,DEBUG)) $(eval $(call assert_boolean,NS_TIMER_SWITCH)) $(eval $(call assert_boolean,RESET_TO_BL31)) $(eval $(call assert_boolean,CTX_INCLUDE_FPREGS)) +$(eval $(call assert_boolean,CTX_INCLUDE_AARCH32_REGS)) $(eval $(call assert_boolean,ASM_ASSERTION)) $(eval $(call assert_boolean,USE_COHERENT_MEM)) $(eval $(call assert_boolean,DISABLE_PEDANTIC)) @@ -423,6 +427,7 @@ $(eval $(call add_define,SPD_${SPD})) $(eval $(call add_define,NS_TIMER_SWITCH)) $(eval $(call add_define,RESET_TO_BL31)) $(eval $(call add_define,CTX_INCLUDE_FPREGS)) +$(eval $(call add_define,CTX_INCLUDE_AARCH32_REGS)) $(eval $(call add_define,ARM_GIC_ARCH)) $(eval $(call add_define,ARM_CCI_PRODUCT_ID)) $(eval $(call add_define,ASM_ASSERTION)) diff --git a/bl1/bl1_context_mgmt.c b/bl1/bl1_context_mgmt.c index bd40608b..972c7f68 100644 --- a/bl1/bl1_context_mgmt.c +++ b/bl1/bl1_context_mgmt.c @@ -32,6 +32,7 @@ #include <assert.h> #include <context.h> #include <context_mgmt.h> +#include <debug.h> #include <platform.h> /* @@ -66,6 +67,19 @@ void bl1_prepare_next_image(unsigned int image_id) image_desc_t *image_desc; entry_point_info_t *next_bl_ep; +#if CTX_INCLUDE_AARCH32_REGS + /* + * Ensure that the build flag to save AArch32 system registers in CPU + * context is not set for AArch64-only platforms. + */ + if (((read_id_aa64pfr0_el1() >> ID_AA64PFR0_EL1_SHIFT) + & ID_AA64PFR0_ELX_MASK) == 0x1) { + ERROR("EL1 supports AArch64-only. Please set build flag " + "CTX_INCLUDE_AARCH32_REGS = 0"); + panic(); + } +#endif + /* Get the image descriptor. */ image_desc = bl1_plat_get_image_desc(image_id); assert(image_desc); diff --git a/bl31/bl31_main.c b/bl31/bl31_main.c index 835d41e8..7f04d218 100644 --- a/bl31/bl31_main.c +++ b/bl31/bl31_main.c @@ -145,6 +145,19 @@ void bl31_prepare_next_image_entry(void) entry_point_info_t *next_image_info; uint32_t image_type; +#if CTX_INCLUDE_AARCH32_REGS + /* + * Ensure that the build flag to save AArch32 system registers in CPU + * context is not set for AArch64-only platforms. + */ + if (((read_id_aa64pfr0_el1() >> ID_AA64PFR0_EL1_SHIFT) + & ID_AA64PFR0_ELX_MASK) == 0x1) { + ERROR("EL1 supports AArch64-only. Please set build flag " + "CTX_INCLUDE_AARCH32_REGS = 0"); + panic(); + } +#endif + /* Determine which image to execute next */ image_type = bl31_get_next_image_type(); diff --git a/common/aarch64/context.S b/common/aarch64/context.S index 0baa9b2f..d51daa78 100644 --- a/common/aarch64/context.S +++ b/common/aarch64/context.S @@ -57,14 +57,6 @@ func el1_sysregs_context_save mrs x10, elr_el1 stp x9, x10, [x0, #CTX_SPSR_EL1] - mrs x11, spsr_abt - mrs x12, spsr_und - stp x11, x12, [x0, #CTX_SPSR_ABT] - - mrs x13, spsr_irq - mrs x14, spsr_fiq - stp x13, x14, [x0, #CTX_SPSR_IRQ] - mrs x15, sctlr_el1 mrs x16, actlr_el1 stp x15, x16, [x0, #CTX_SCTLR_EL1] @@ -93,10 +85,6 @@ func el1_sysregs_context_save mrs x10, tpidrro_el0 stp x9, x10, [x0, #CTX_TPIDR_EL0] - mrs x11, dacr32_el2 - mrs x12, ifsr32_el2 - stp x11, x12, [x0, #CTX_DACR32_EL2] - mrs x13, par_el1 mrs x14, far_el1 stp x13, x14, [x0, #CTX_PAR_EL1] @@ -109,6 +97,24 @@ func el1_sysregs_context_save mrs x9, vbar_el1 stp x17, x9, [x0, #CTX_CONTEXTIDR_EL1] + /* Save AArch32 system registers if the build has instructed so */ +#if CTX_INCLUDE_AARCH32_REGS + mrs x11, spsr_abt + mrs x12, spsr_und + stp x11, x12, [x0, #CTX_SPSR_ABT] + + mrs x13, spsr_irq + mrs x14, spsr_fiq + stp x13, x14, [x0, #CTX_SPSR_IRQ] + + mrs x15, dacr32_el2 + mrs x16, ifsr32_el2 + stp x15, x16, [x0, #CTX_DACR32_EL2] + + mrs x17, fpexc32_el2 + str x17, [x0, #CTX_FP_FPEXC32_EL2] +#endif + /* Save NS timer registers if the build has instructed so */ #if NS_TIMER_SWITCH mrs x10, cntp_ctl_el0 @@ -123,9 +129,6 @@ func el1_sysregs_context_save str x14, [x0, #CTX_CNTKCTL_EL1] #endif - mrs x15, fpexc32_el2 - str x15, [x0, #CTX_FP_FPEXC32_EL2] - ret endfunc el1_sysregs_context_save @@ -143,14 +146,6 @@ func el1_sysregs_context_restore msr spsr_el1, x9 msr elr_el1, x10 - ldp x11, x12, [x0, #CTX_SPSR_ABT] - msr spsr_abt, x11 - msr spsr_und, x12 - - ldp x13, x14, [x0, #CTX_SPSR_IRQ] - msr spsr_irq, x13 - msr spsr_fiq, x14 - ldp x15, x16, [x0, #CTX_SCTLR_EL1] msr sctlr_el1, x15 msr actlr_el1, x16 @@ -179,10 +174,6 @@ func el1_sysregs_context_restore msr tpidr_el0, x9 msr tpidrro_el0, x10 - ldp x11, x12, [x0, #CTX_DACR32_EL2] - msr dacr32_el2, x11 - msr ifsr32_el2, x12 - ldp x13, x14, [x0, #CTX_PAR_EL1] msr par_el1, x13 msr far_el1, x14 @@ -195,6 +186,23 @@ func el1_sysregs_context_restore msr contextidr_el1, x17 msr vbar_el1, x9 + /* Restore AArch32 system registers if the build has instructed so */ +#if CTX_INCLUDE_AARCH32_REGS + ldp x11, x12, [x0, #CTX_SPSR_ABT] + msr spsr_abt, x11 + msr spsr_und, x12 + + ldp x13, x14, [x0, #CTX_SPSR_IRQ] + msr spsr_irq, x13 + msr spsr_fiq, x14 + + ldp x15, x16, [x0, #CTX_DACR32_EL2] + msr dacr32_el2, x15 + msr ifsr32_el2, x16 + + ldr x17, [x0, #CTX_FP_FPEXC32_EL2] + msr fpexc32_el2, x17 +#endif /* Restore NS timer registers if the build has instructed so */ #if NS_TIMER_SWITCH ldp x10, x11, [x0, #CTX_CNTP_CTL_EL0] @@ -209,11 +217,7 @@ func el1_sysregs_context_restore msr cntkctl_el1, x14 #endif - ldr x15, [x0, #CTX_FP_FPEXC32_EL2] - msr fpexc32_el2, x15 - /* No explict ISB required here as ERET covers it */ - ret endfunc el1_sysregs_context_restore diff --git a/common/bl_common.c b/common/bl_common.c index 2e23fbf3..7cafe635 100644 --- a/common/bl_common.c +++ b/common/bl_common.c @@ -189,12 +189,20 @@ unsigned long image_size(unsigned int image_id) } /******************************************************************************* - * Generic function to load an image at a specific address given a name and - * extents of free memory. It updates the memory layout if the load is - * successful, as well as the image information and the entry point information. - * The caller might pass a NULL pointer for the entry point if it is not - * interested in this information, e.g. because the image just needs to be - * loaded in memory but won't ever be executed. + * Generic function to load an image at a specific address given an image ID and + * extents of free memory. + * + * If the load is successful then the image information is updated. + * + * If the entry_point_info argument is not NULL then this function also updates: + * - the memory layout to mark the memory as reserved; + * - the entry point information. + * + * The caller might pass a NULL pointer for the entry point if they are not + * interested in this information. This is typically the case for non-executable + * images (e.g. certificates) and executable images that won't ever be executed + * on the application processor (e.g. additional microcontroller firmware). + * * Returns 0 on success, a negative error code otherwise. ******************************************************************************/ int load_image(meminfo_t *mem_layout, @@ -259,6 +267,9 @@ int load_image(meminfo_t *mem_layout, goto exit; } + image_data->image_base = image_base; + image_data->image_size = image_size; + /* * Update the memory usage info. * This is done after the actual loading so that it is not updated when @@ -269,20 +280,16 @@ int load_image(meminfo_t *mem_layout, if (entry_point_info != NULL) { reserve_mem(&mem_layout->free_base, &mem_layout->free_size, image_base, image_size); + entry_point_info->pc = image_base; } else { INFO("Skip reserving memory: %p - %p\n", (void *) image_base, (void *) (image_base + image_size)); } - image_data->image_base = image_base; - image_data->image_size = image_size; - - if (entry_point_info != NULL) - entry_point_info->pc = image_base; - /* * File has been successfully loaded. - * Flush the image in TZRAM so that the next EL can see it. + * Flush the image in Trusted SRAM so that the next exception level can + * see it. */ flush_dcache_range(image_base, image_size); diff --git a/docs/user-guide.md b/docs/user-guide.md index ce0390d8..0bdedf90 100644 --- a/docs/user-guide.md +++ b/docs/user-guide.md @@ -380,6 +380,12 @@ performed. any register that is not part of the SBSA generic UART specification. Default value is 0 (a full PL011 compliant UART is present). +* `CTX_INCLUDE_AARCH32_REGS` : Boolean option that, when set to 1, will cause + the AArch32 system registers to be included when saving and restoring the + CPU context. The option must be set to 0 for AArch64-only platforms (that + is on hardware that does not implement AArch32, or at least not at EL1 and + higher ELs). Default value is 1. + * `CTX_INCLUDE_FPREGS`: Boolean option that, when set to 1, will cause the FP registers to be included when saving and restoring the CPU context. Default is 0. diff --git a/include/common/context.h b/include/common/context.h index 0dfebe0b..ec47f2ad 100644 --- a/include/common/context.h +++ b/include/common/context.h @@ -91,48 +91,58 @@ #define CTX_SYSREGS_OFFSET (CTX_EL3STATE_OFFSET + CTX_EL3STATE_END) #define CTX_SPSR_EL1 0x0 #define CTX_ELR_EL1 0x8 -#define CTX_SPSR_ABT 0x10 -#define CTX_SPSR_UND 0x18 -#define CTX_SPSR_IRQ 0x20 -#define CTX_SPSR_FIQ 0x28 -#define CTX_SCTLR_EL1 0x30 -#define CTX_ACTLR_EL1 0x38 -#define CTX_CPACR_EL1 0x40 -#define CTX_CSSELR_EL1 0x48 -#define CTX_SP_EL1 0x50 -#define CTX_ESR_EL1 0x58 -#define CTX_TTBR0_EL1 0x60 -#define CTX_TTBR1_EL1 0x68 -#define CTX_MAIR_EL1 0x70 -#define CTX_AMAIR_EL1 0x78 -#define CTX_TCR_EL1 0x80 -#define CTX_TPIDR_EL1 0x88 -#define CTX_TPIDR_EL0 0x90 -#define CTX_TPIDRRO_EL0 0x98 -#define CTX_DACR32_EL2 0xa0 -#define CTX_IFSR32_EL2 0xa8 -#define CTX_PAR_EL1 0xb0 -#define CTX_FAR_EL1 0xb8 -#define CTX_AFSR0_EL1 0xc0 -#define CTX_AFSR1_EL1 0xc8 -#define CTX_CONTEXTIDR_EL1 0xd0 -#define CTX_VBAR_EL1 0xd8 +#define CTX_SCTLR_EL1 0x10 +#define CTX_ACTLR_EL1 0x18 +#define CTX_CPACR_EL1 0x20 +#define CTX_CSSELR_EL1 0x28 +#define CTX_SP_EL1 0x30 +#define CTX_ESR_EL1 0x38 +#define CTX_TTBR0_EL1 0x40 +#define CTX_TTBR1_EL1 0x48 +#define CTX_MAIR_EL1 0x50 +#define CTX_AMAIR_EL1 0x58 +#define CTX_TCR_EL1 0x60 +#define CTX_TPIDR_EL1 0x68 +#define CTX_TPIDR_EL0 0x70 +#define CTX_TPIDRRO_EL0 0x78 +#define CTX_PAR_EL1 0x80 +#define CTX_FAR_EL1 0x88 +#define CTX_AFSR0_EL1 0x90 +#define CTX_AFSR1_EL1 0x98 +#define CTX_CONTEXTIDR_EL1 0xa0 +#define CTX_VBAR_EL1 0xa8 + +/* + * If the platform is AArch64-only, there is no need to save and restore these + * AArch32 registers. + */ +#if CTX_INCLUDE_AARCH32_REGS +#define CTX_SPSR_ABT 0xb0 +#define CTX_SPSR_UND 0xb8 +#define CTX_SPSR_IRQ 0xc0 +#define CTX_SPSR_FIQ 0xc8 +#define CTX_DACR32_EL2 0xd0 +#define CTX_IFSR32_EL2 0xd8 +#define CTX_FP_FPEXC32_EL2 0xe0 +#define CTX_TIMER_SYSREGS_OFF 0xf0 /* Align to the next 16 byte boundary */ +#else +#define CTX_TIMER_SYSREGS_OFF 0xb0 +#endif /* __CTX_INCLUDE_AARCH32_REGS__ */ + /* * If the timer registers aren't saved and restored, we don't have to reserve * space for them in the context */ #if NS_TIMER_SWITCH -#define CTX_CNTP_CTL_EL0 0xe0 -#define CTX_CNTP_CVAL_EL0 0xe8 -#define CTX_CNTV_CTL_EL0 0xf0 -#define CTX_CNTV_CVAL_EL0 0xf8 -#define CTX_CNTKCTL_EL1 0x100 -#define CTX_FP_FPEXC32_EL2 0x108 -#define CTX_SYSREGS_END 0x110 +#define CTX_CNTP_CTL_EL0 (CTX_TIMER_SYSREGS_OFF + 0x0) +#define CTX_CNTP_CVAL_EL0 (CTX_TIMER_SYSREGS_OFF + 0x8) +#define CTX_CNTV_CTL_EL0 (CTX_TIMER_SYSREGS_OFF + 0x10) +#define CTX_CNTV_CVAL_EL0 (CTX_TIMER_SYSREGS_OFF + 0x18) +#define CTX_CNTKCTL_EL1 (CTX_TIMER_SYSREGS_OFF + 0x20) +#define CTX_SYSREGS_END (CTX_TIMER_SYSREGS_OFF + 0x30) /* Align to the next 16 byte boundary */ #else -#define CTX_FP_FPEXC32_EL2 0xe0 -#define CTX_SYSREGS_END 0xf0 -#endif +#define CTX_SYSREGS_END CTX_TIMER_SYSREGS_OFF +#endif /* __NS_TIMER_SWITCH__ */ /******************************************************************************* * Constants that allow assembler code to access members of and the 'fp_regs' diff --git a/include/lib/cpus/aarch64/cortex_a73.h b/include/lib/cpus/aarch64/cortex_a73.h new file mode 100644 index 00000000..2ad04677 --- /dev/null +++ b/include/lib/cpus/aarch64/cortex_a73.h @@ -0,0 +1,44 @@ +/* + * Copyright (c) 2016, 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 __CORTEX_A73_H__ +#define __CORTEX_A73_H__ + +/* Cortex-A73 midr for revision 0 */ +#define CORTEX_A73_MIDR 0x410FD090 + +/******************************************************************************* + * CPU Extended Control register specific definitions. + ******************************************************************************/ +#define CORTEX_A73_CPUECTLR_EL1 S3_1_C15_C2_1 /* Instruction def. */ + +#define CORTEX_A73_CPUECTLR_SMP_BIT (1 << 6) + +#endif /* __CORTEX_A73_H__ */ diff --git a/include/lib/xlat_tables.h b/include/lib/xlat_tables.h index abe46ed9..7d57521b 100644 --- a/include/lib/xlat_tables.h +++ b/include/lib/xlat_tables.h @@ -150,12 +150,6 @@ typedef enum { MT_MEMORY, /* Values up to 7 are reserved to add new memory types in the future */ - /* - * The following values are organised so that a clear bit gives a more - * restrictive mapping than a set bit, that way a bitwise-and of two - * sets of attributes will never give an attribute which has greater - * access rights than any of the original attributes. - */ MT_RO = 0 << MT_PERM_SHIFT, MT_RW = 1 << MT_PERM_SHIFT, diff --git a/lib/cpus/aarch64/cortex_a73.S b/lib/cpus/aarch64/cortex_a73.S new file mode 100644 index 00000000..70b4c6a5 --- /dev/null +++ b/lib/cpus/aarch64/cortex_a73.S @@ -0,0 +1,155 @@ +/* + * Copyright (c) 2016, 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. + */ +#include <arch.h> +#include <asm_macros.S> +#include <bl_common.h> +#include <cortex_a73.h> +#include <cpu_macros.S> +#include <plat_macros.S> + + /* --------------------------------------------- + * Disable L1 data cache + * --------------------------------------------- + */ +func cortex_a73_disable_dcache + mrs x1, sctlr_el3 + bic x1, x1, #SCTLR_C_BIT + msr sctlr_el3, x1 + isb + ret +endfunc cortex_a73_disable_dcache + + /* --------------------------------------------- + * Disable intra-cluster coherency + * --------------------------------------------- + */ +func cortex_a73_disable_smp + mrs x0, CORTEX_A73_CPUECTLR_EL1 + bic x0, x0, #CORTEX_A73_CPUECTLR_SMP_BIT + msr CORTEX_A73_CPUECTLR_EL1, x0 + isb + dsb sy + ret +endfunc cortex_a73_disable_smp + +func cortex_a73_reset_func + /* --------------------------------------------- + * Enable the SMP bit. + * Clobbers : x0 + * --------------------------------------------- + */ + mrs x0, CORTEX_A73_CPUECTLR_EL1 + orr x0, x0, #CORTEX_A73_CPUECTLR_SMP_BIT + msr CORTEX_A73_CPUECTLR_EL1, x0 + isb + ret +endfunc cortex_a73_reset_func + +func cortex_a73_core_pwr_dwn + mov x18, x30 + + /* --------------------------------------------- + * Turn off caches. + * --------------------------------------------- + */ + bl cortex_a73_disable_dcache + + /* --------------------------------------------- + * Flush L1 caches. + * --------------------------------------------- + */ + mov x0, #DCCISW + bl dcsw_op_level1 + + /* --------------------------------------------- + * Come out of intra cluster coherency + * --------------------------------------------- + */ + mov x30, x18 + b cortex_a73_disable_smp +endfunc cortex_a73_core_pwr_dwn + +func cortex_a73_cluster_pwr_dwn + mov x18, x30 + + /* --------------------------------------------- + * Turn off caches. + * --------------------------------------------- + */ + bl cortex_a73_disable_dcache + + /* --------------------------------------------- + * Flush L1 caches. + * --------------------------------------------- + */ + mov x0, #DCCISW + bl dcsw_op_level1 + + /* --------------------------------------------- + * Disable the optional ACP. + * --------------------------------------------- + */ + bl plat_disable_acp + + /* --------------------------------------------- + * Flush L2 caches. + * --------------------------------------------- + */ + mov x0, #DCCISW + bl dcsw_op_level2 + + /* --------------------------------------------- + * Come out of intra cluster coherency + * --------------------------------------------- + */ + mov x30, x18 + b cortex_a73_disable_smp +endfunc cortex_a73_cluster_pwr_dwn + + /* --------------------------------------------- + * This function provides cortex_a73 specific + * register information for crash reporting. + * It needs to return with x6 pointing to + * a list of register names in ascii and + * x8 - x15 having values of registers to be + * reported. + * --------------------------------------------- + */ +.section .rodata.cortex_a73_regs, "aS" +cortex_a73_regs: /* The ascii list of register names to be reported */ + .asciz "cpuectlr_el1", "" + +func cortex_a73_cpu_reg_dump + adr x6, cortex_a73_regs + mrs x8, CORTEX_A73_CPUECTLR_EL1 + ret +endfunc cortex_a73_cpu_reg_dump + +declare_cpu_ops cortex_a73, CORTEX_A73_MIDR diff --git a/plat/arm/board/common/board_arm_trusted_boot.c b/plat/arm/board/common/board_arm_trusted_boot.c index 7ae00cce..fd9e9f62 100644 --- a/plat/arm/board/common/board_arm_trusted_boot.c +++ b/plat/arm/board/common/board_arm_trusted_boot.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2016, 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: @@ -180,10 +180,10 @@ int plat_get_nv_ctr(void *cookie, unsigned int *nv_ctr) } /* - * Store a new non-volatile counter value. On Juno and FVP, the non-volatile - * counters are RO and cannot be modified. We expect the values in the - * certificates to always match the RO values so that this function is never - * called. + * Store a new non-volatile counter value. By default on ARM development + * platforms, the non-volatile counters are RO and cannot be modified. We expect + * the values in the certificates to always match the RO values so that this + * function is never called. * * Return: 0 = success, Otherwise = error */ diff --git a/plat/arm/board/fvp/fvp_common.c b/plat/arm/board/fvp/fvp_common.c index eb67dab2..0f557af2 100644 --- a/plat/arm/board/fvp/fvp_common.c +++ b/plat/arm/board/fvp/fvp_common.c @@ -62,7 +62,7 @@ arm_config_t arm_config; #define MAP_DEVICE2 MAP_REGION_FLAT(DEVICE2_BASE, \ DEVICE2_SIZE, \ - MT_DEVICE | MT_RO | MT_SECURE) + MT_DEVICE | MT_RW | MT_SECURE) /* diff --git a/plat/arm/board/fvp/fvp_trusted_boot.c b/plat/arm/board/fvp/fvp_trusted_boot.c new file mode 100644 index 00000000..7db5051b --- /dev/null +++ b/plat/arm/board/fvp/fvp_trusted_boot.c @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2016, 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. + */ + +#include <assert.h> +#include <platform_oid.h> +#include <stdint.h> +#include <string.h> +#include "fvp_def.h" + +/* + * Store a new non-volatile counter value. On some FVP versions, the + * non-volatile counters are RO. On these versions we expect the values in the + * certificates to always match the RO values so that this function is never + * called. + * + * Return: 0 = success, Otherwise = error + */ +int plat_set_nv_ctr(void *cookie, unsigned int nv_ctr) +{ + const char *oid; + uint32_t *nv_ctr_addr; + + assert(cookie != NULL); + + oid = (const char *)cookie; + if (strcmp(oid, TRUSTED_FW_NVCOUNTER_OID) == 0) { + nv_ctr_addr = (uint32_t *)TFW_NVCTR_BASE; + } else if (strcmp(oid, NON_TRUSTED_FW_NVCOUNTER_OID) == 0) { + nv_ctr_addr = (uint32_t *)NTFW_CTR_BASE; + } else { + return 1; + } + + *(unsigned int *)nv_ctr_addr = nv_ctr; + + /* Verify that the current value is the one we just wrote. */ + if (nv_ctr != (unsigned int)(*nv_ctr_addr)) + return 1; + + return 0; +} diff --git a/plat/arm/board/fvp/platform.mk b/plat/arm/board/fvp/platform.mk index 6456cdea..1ea98222 100644 --- a/plat/arm/board/fvp/platform.mk +++ b/plat/arm/board/fvp/platform.mk @@ -102,7 +102,8 @@ FVP_CPU_LIBS := lib/cpus/aarch64/aem_generic.S \ lib/cpus/aarch64/cortex_a35.S \ lib/cpus/aarch64/cortex_a53.S \ lib/cpus/aarch64/cortex_a57.S \ - lib/cpus/aarch64/cortex_a72.S + lib/cpus/aarch64/cortex_a72.S \ + lib/cpus/aarch64/cortex_a73.S BL1_SOURCES += drivers/io/io_semihosting.c \ lib/semihosting/semihosting.c \ @@ -111,6 +112,7 @@ BL1_SOURCES += drivers/io/io_semihosting.c \ plat/arm/board/fvp/fvp_bl1_setup.c \ plat/arm/board/fvp/fvp_err.c \ plat/arm/board/fvp/fvp_io_storage.c \ + plat/arm/board/fvp/fvp_trusted_boot.c \ ${FVP_CPU_LIBS} \ ${FVP_INTERCONNECT_SOURCES} @@ -122,6 +124,7 @@ BL2_SOURCES += drivers/io/io_semihosting.c \ plat/arm/board/fvp/fvp_bl2_setup.c \ plat/arm/board/fvp/fvp_err.c \ plat/arm/board/fvp/fvp_io_storage.c \ + plat/arm/board/fvp/fvp_trusted_boot.c \ ${FVP_SECURITY_SOURCES} ifeq (${FVP_USE_SP804_TIMER},1) diff --git a/plat/arm/common/aarch64/arm_common.c b/plat/arm/common/aarch64/arm_common.c index 616edc92..c4cc80e6 100644 --- a/plat/arm/common/aarch64/arm_common.c +++ b/plat/arm/common/aarch64/arm_common.c @@ -176,7 +176,7 @@ const mmap_region_t *plat_arm_get_mmap(void) #if ERROR_DEPRECATED unsigned int plat_get_syscnt_freq2(void) { - unsigned int counter_base_frequency + unsigned int counter_base_frequency; #else unsigned long long plat_get_syscnt_freq(void) { |