diff options
49 files changed, 949 insertions, 247 deletions
@@ -246,6 +246,12 @@ endif # over the sources. endif +################################################################################ +# Include libraries' Makefile that are used in all BL +################################################################################ + +include lib/stack_protector/stack_protector.mk + ################################################################################ # Include the platform specific Makefile after the SPD Makefile (the platform diff --git a/bl1/bl1.ld.S b/bl1/bl1.ld.S index b69065ee..2cfb24c1 100644 --- a/bl1/bl1.ld.S +++ b/bl1/bl1.ld.S @@ -111,14 +111,20 @@ SECTIONS ASSERT(__CPU_OPS_END__ > __CPU_OPS_START__, "cpu_ops not defined for this platform.") + . = BL1_RW_BASE; + ASSERT(BL1_RW_BASE == ALIGN(4096), + "BL1_RW_BASE address is not aligned on a page boundary.") + /* * The .data section gets copied from ROM to RAM at runtime. - * Its LMA must be 16-byte aligned. + * Its LMA should be 16-byte aligned to allow efficient copying of 16-bytes + * aligned regions in it. * Its VMA must be page-aligned as it marks the first read/write page. + * + * It must be placed at a lower address than the stacks if the stack + * protector is enabled. Alternatively, the .data.stack_protector_canary + * section can be placed independently of the main .data section. */ - . = BL1_RW_BASE; - ASSERT(. == ALIGN(4096), - "BL1_RW_BASE address is not aligned on a page boundary.") .data . : ALIGN(16) { __DATA_RAM_START__ = .; *(.data*) diff --git a/bl2/aarch32/bl2_entrypoint.S b/bl2/aarch32/bl2_entrypoint.S index bb0b7f31..c82456f2 100644 --- a/bl2/aarch32/bl2_entrypoint.S +++ b/bl2/aarch32/bl2_entrypoint.S @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2016-2017, 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: @@ -122,6 +122,15 @@ func bl2_entrypoint bl plat_set_my_stack /* --------------------------------------------- + * Initialize the stack protector canary before + * any C code is called. + * --------------------------------------------- + */ +#if STACK_PROTECTOR_ENABLED + bl update_stack_protector_canary +#endif + + /* --------------------------------------------- * Perform early platform setup & platform * specific early arch. setup e.g. mmu setup * --------------------------------------------- diff --git a/bl2/aarch64/bl2_entrypoint.S b/bl2/aarch64/bl2_entrypoint.S index 31f77879..15a217d0 100644 --- a/bl2/aarch64/bl2_entrypoint.S +++ b/bl2/aarch64/bl2_entrypoint.S @@ -113,6 +113,15 @@ func bl2_entrypoint bl plat_set_my_stack /* --------------------------------------------- + * Initialize the stack protector canary before + * any C code is called. + * --------------------------------------------- + */ +#if STACK_PROTECTOR_ENABLED + bl update_stack_protector_canary +#endif + + /* --------------------------------------------- * Perform early platform setup & platform * specific early arch. setup e.g. mmu setup * --------------------------------------------- diff --git a/bl2/bl2.ld.S b/bl2/bl2.ld.S index b9275f34..07e0bccd 100644 --- a/bl2/bl2.ld.S +++ b/bl2/bl2.ld.S @@ -99,6 +99,11 @@ SECTIONS */ __RW_START__ = . ; + /* + * .data must be placed at a lower address than the stacks if the stack + * protector is enabled. Alternatively, the .data.stack_protector_canary + * section can be placed independently of the main .data section. + */ .data . : { __DATA_START__ = .; *(.data*) diff --git a/bl2u/aarch64/bl2u_entrypoint.S b/bl2u/aarch64/bl2u_entrypoint.S index 9fa84bf4..81aabc77 100644 --- a/bl2u/aarch64/bl2u_entrypoint.S +++ b/bl2u/aarch64/bl2u_entrypoint.S @@ -107,6 +107,15 @@ func bl2u_entrypoint bl plat_set_my_stack /* --------------------------------------------- + * Initialize the stack protector canary before + * any C code is called. + * --------------------------------------------- + */ +#if STACK_PROTECTOR_ENABLED + bl update_stack_protector_canary +#endif + + /* --------------------------------------------- * Perform early platform setup & platform * specific early arch. setup e.g. mmu setup * --------------------------------------------- diff --git a/bl2u/bl2u.ld.S b/bl2u/bl2u.ld.S index 91e8556e..aebf84f4 100644 --- a/bl2u/bl2u.ld.S +++ b/bl2u/bl2u.ld.S @@ -86,6 +86,11 @@ SECTIONS */ __RW_START__ = . ; + /* + * .data must be placed at a lower address than the stacks if the stack + * protector is enabled. Alternatively, the .data.stack_protector_canary + * section can be placed independently of the main .data section. + */ .data . : { __DATA_START__ = .; *(.data*) diff --git a/bl31/bl31.ld.S b/bl31/bl31.ld.S index e5d6232e..3a3fbd9a 100644 --- a/bl31/bl31.ld.S +++ b/bl31/bl31.ld.S @@ -140,7 +140,12 @@ SECTIONS */ __RW_START__ = . ; - .data . : { + /* + * .data must be placed at a lower address than the stacks if the stack + * protector is enabled. Alternatively, the .data.stack_protector_canary + * section can be placed independently of the main .data section. + */ + .data . : { __DATA_START__ = .; *(.data*) __DATA_END__ = .; diff --git a/bl32/tsp/aarch64/tsp_entrypoint.S b/bl32/tsp/aarch64/tsp_entrypoint.S index 182f3148..3f281394 100644 --- a/bl32/tsp/aarch64/tsp_entrypoint.S +++ b/bl32/tsp/aarch64/tsp_entrypoint.S @@ -139,6 +139,15 @@ func tsp_entrypoint bl plat_set_my_stack /* --------------------------------------------- + * Initialize the stack protector canary before + * any C code is called. + * --------------------------------------------- + */ +#if STACK_PROTECTOR_ENABLED + bl update_stack_protector_canary +#endif + + /* --------------------------------------------- * Perform early platform setup & platform * specific early arch. setup e.g. mmu setup * --------------------------------------------- diff --git a/docs/porting-guide.md b/docs/porting-guide.md index 65518ffb..690f307a 100644 --- a/docs/porting-guide.md +++ b/docs/porting-guide.md @@ -920,6 +920,20 @@ kept aside to pass trusted firmware related information that next BL image needs. This function is currently invoked in BL2 to pass this information to the next BL image, when LOAD_IMAGE_V2 is enabled. +### Function : plat_get_stack_protector_canary() + Argument : void + Return : u_register_t + +This function returns a random value that is used to initialize the canary used +when the stack protector is enabled with ENABLE_STACK_PROTECTOR. A predictable +value will weaken the protection as the attacker could easily write the right +value as part of the attack most of the time. Therefore, it should return a +true random number. + +Note: For the protection to be effective, the global data need to be placed at +a lower address than the stack bases. Failure to do so would allow an attacker +to overwrite the canary as part of the stack buffer overflow attack. + ### Function : plat_flush_next_bl_params() Argument : void diff --git a/docs/user-guide.md b/docs/user-guide.md index 87c11519..a1df9652 100644 --- a/docs/user-guide.md +++ b/docs/user-guide.md @@ -301,6 +301,14 @@ performed. Currently, only PSCI is instrumented. Enabling this option enables the `ENABLE_PMF` build option as well. Default is 0. +* `ENABLE_STACK_PROTECTOR`: String option to enable the stack protection + checks in GCC. Allowed values are "all", "strong" and "0" (default). + "strong" is the recommended stack protection level if this feature is + desired. 0 disables the stack protection. For all values other than 0, the + `plat_get_stack_protector_canary()` platform hook needs to be implemented. + The value is passed as the last component of the option + `-fstack-protector-$ENABLE_STACK_PROTECTOR`. + * `ERROR_DEPRECATED`: This option decides whether to treat the usage of deprecated platform APIs, helper functions or drivers within Trusted Firmware as error. It can take the value 1 (flag the use of deprecated diff --git a/include/common/aarch32/el3_common_macros.S b/include/common/aarch32/el3_common_macros.S index f6b7527e..d7e0b3f5 100644 --- a/include/common/aarch32/el3_common_macros.S +++ b/include/common/aarch32/el3_common_macros.S @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2016-2017, 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: @@ -278,6 +278,12 @@ * --------------------------------------------------------------------- */ bl plat_set_my_stack + +#if STACK_PROTECTOR_ENABLED + .if \_init_c_runtime + bl update_stack_protector_canary + .endif /* _init_c_runtime */ +#endif .endm #endif /* __EL3_COMMON_MACROS_S__ */ diff --git a/include/common/aarch64/el3_common_macros.S b/include/common/aarch64/el3_common_macros.S index e085f9f1..5c6aa069 100644 --- a/include/common/aarch64/el3_common_macros.S +++ b/include/common/aarch64/el3_common_macros.S @@ -283,6 +283,12 @@ * --------------------------------------------------------------------- */ bl plat_set_my_stack + +#if STACK_PROTECTOR_ENABLED + .if \_init_c_runtime + bl update_stack_protector_canary + .endif /* _init_c_runtime */ +#endif .endm #endif /* __EL3_COMMON_MACROS_S__ */ diff --git a/include/common/debug.h b/include/common/debug.h index 41c8df0c..c6f211f3 100644 --- a/include/common/debug.h +++ b/include/common/debug.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2013-2016, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2013-2017, 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: @@ -84,6 +84,9 @@ void __dead2 do_panic(void); #define panic() do_panic() +/* Function called when stack protection check code detects a corrupted stack */ +void __dead2 __stack_chk_fail(void); + void tf_printf(const char *fmt, ...) __printflike(1, 2); #endif /* __ASSEMBLY__ */ diff --git a/include/lib/utils.h b/include/lib/utils.h index 69bbb430..279c9135 100644 --- a/include/lib/utils.h +++ b/include/lib/utils.h @@ -42,6 +42,20 @@ #define BIT(nr) (1UL << (nr)) +#define MIN(x, y) __extension__ ({ \ + __typeof__(x) _x = (x); \ + __typeof__(y) _y = (y); \ + (void)(&_x == &_y); \ + _x < _y ? _x : _y; \ +}) + +#define MAX(x, y) __extension__ ({ \ + __typeof__(x) _x = (x); \ + __typeof__(y) _y = (y); \ + (void)(&_x == &_y); \ + _x > _y ? _x : _y; \ +}) + /* * The round_up() macro rounds up a value to the given boundary in a * type-agnostic yet type-safe manner. The boundary must be a power of two. diff --git a/include/plat/arm/board/common/board_css_def.h b/include/plat/arm/board/common/board_css_def.h index 65e3d32d..4b5e84dd 100644 --- a/include/plat/arm/board/common/board_css_def.h +++ b/include/plat/arm/board/common/board_css_def.h @@ -33,6 +33,7 @@ #include <common_def.h> #include <soc_css_def.h> +#include <utils.h> #include <v2m_def.h> /* diff --git a/include/plat/arm/common/arm_def.h b/include/plat/arm/common/arm_def.h index 8ce718af..43e0eb89 100644 --- a/include/plat/arm/common/arm_def.h +++ b/include/plat/arm/common/arm_def.h @@ -34,6 +34,7 @@ #include <common_def.h> #include <platform_def.h> #include <tbbr_img_def.h> +#include <utils.h> #include <xlat_tables_defs.h> diff --git a/include/plat/arm/soc/common/soc_css_def.h b/include/plat/arm/soc/common/soc_css_def.h index e83144ec..3b4cc79f 100644 --- a/include/plat/arm/soc/common/soc_css_def.h +++ b/include/plat/arm/soc/common/soc_css_def.h @@ -32,6 +32,7 @@ #define __SOC_CSS_DEF_H__ #include <common_def.h> +#include <utils.h> /* diff --git a/include/plat/common/platform.h b/include/plat/common/platform.h index 73bb6431..f13b30d8 100644 --- a/include/plat/common/platform.h +++ b/include/plat/common/platform.h @@ -72,6 +72,16 @@ uintptr_t plat_get_ns_image_entrypoint(void); unsigned int plat_my_core_pos(void); int plat_core_pos_by_mpidr(u_register_t mpidr); +#if STACK_PROTECTOR_ENABLED +/* + * Return a new value to be used for the stack protection's canary. + * + * Ideally, this value is a random number that is impossible to predict by an + * attacker. + */ +u_register_t plat_get_stack_protector_canary(void); +#endif /* STACK_PROTECTOR_ENABLED */ + /******************************************************************************* * Mandatory interrupt management functions ******************************************************************************/ @@ -326,7 +336,7 @@ int platform_setup_pm(const plat_pm_ops_t **); unsigned int plat_get_aff_count(unsigned int, unsigned long); unsigned int plat_get_aff_state(unsigned int, unsigned long); -#else +#else /* __ENABLE_PLAT_COMPAT__ */ /* * The below function enable Trusted Firmware components like SPDs which * haven't migrated to the new platform API to compile on platforms which @@ -335,4 +345,6 @@ unsigned int plat_get_aff_state(unsigned int, unsigned long); unsigned int platform_get_core_pos(unsigned long mpidr) __deprecated; #endif /* __ENABLE_PLAT_COMPAT__ */ + #endif /* __PLATFORM_H__ */ + diff --git a/lib/stack_protector/aarch32/asm_stack_protector.S b/lib/stack_protector/aarch32/asm_stack_protector.S new file mode 100644 index 00000000..9d2d77dc --- /dev/null +++ b/lib/stack_protector/aarch32/asm_stack_protector.S @@ -0,0 +1,58 @@ +/* + * Copyright (c) 2017, 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 <assert_macros.S> + + .globl update_stack_protector_canary + +/* ----------------------------------------------------------------------- + * void update_stack_protector_canary(void) + * + * Change the value of the canary used for stack smashing attacks protection. + * Note: This must be called when it is safe to call C code, but this cannot be + * called by C code. Doing this will make the check fail when the calling + * function returns. + * ----------------------------------------------------------------------- + */ + +func update_stack_protector_canary + /* Use r4 as it is callee-saved */ + mov r4, lr + bl plat_get_stack_protector_canary + + /* Update the canary with the returned value */ + ldr r1, =__stack_chk_guard + str r0, [r1] + bx r4 +endfunc update_stack_protector_canary + + diff --git a/lib/stack_protector/aarch64/asm_stack_protector.S b/lib/stack_protector/aarch64/asm_stack_protector.S new file mode 100644 index 00000000..36f8f068 --- /dev/null +++ b/lib/stack_protector/aarch64/asm_stack_protector.S @@ -0,0 +1,58 @@ +/* + * Copyright (c) 2017, 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 <assert_macros.S> + + .globl update_stack_protector_canary + +/* ----------------------------------------------------------------------- + * void update_stack_protector_canary(void) + * + * Change the value of the canary used for stack smashing attacks protection. + * Note: This must be called when it is safe to call C code, but this cannot be + * called by C code. Doing this will make the check fail when the calling + * function returns. + * ----------------------------------------------------------------------- + */ + +func update_stack_protector_canary + /* Use x19 as it is callee-saved */ + mov x19, x30 + bl plat_get_stack_protector_canary + + /* Update the canary with the returned value */ + adrp x1, __stack_chk_guard + str x0, [x1, #:lo12:__stack_chk_guard] + ret x19 +endfunc update_stack_protector_canary + + diff --git a/lib/stack_protector/stack_protector.c b/lib/stack_protector/stack_protector.c new file mode 100644 index 00000000..ccf2af48 --- /dev/null +++ b/lib/stack_protector/stack_protector.c @@ -0,0 +1,54 @@ +/* + * Copyright (c) 2017, 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 <debug.h> +#include <platform.h> +#include <stdint.h> + +/* + * Canary value used by the compiler runtime checks to detect stack corruption. + * + * Force the canary to be in .data to allow predictable memory layout relatively + * to the stacks. + */ +u_register_t __attribute__((section(".data.stack_protector_canary"))) + __stack_chk_guard = (u_register_t) 3288484550995823360ULL; + +/* + * Function called when the stack's canary check fails, which means the stack + * was corrupted. It must not return. + */ +void __dead2 __stack_chk_fail(void) +{ +#if DEBUG + ERROR("Stack corruption detected\n"); +#endif + panic(); +} + diff --git a/lib/stack_protector/stack_protector.mk b/lib/stack_protector/stack_protector.mk new file mode 100644 index 00000000..03d47c47 --- /dev/null +++ b/lib/stack_protector/stack_protector.mk @@ -0,0 +1,43 @@ +# +# Copyright (c) 2017, 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. +# + +# Boolean macro to be used in C code +STACK_PROTECTOR_ENABLED := 0 + +ifneq (${ENABLE_STACK_PROTECTOR},0) +STACK_PROTECTOR_ENABLED := 1 +BL_COMMON_SOURCES += lib/stack_protector/stack_protector.c \ + lib/stack_protector/${ARCH}/asm_stack_protector.S + +TF_CFLAGS += -fstack-protector-${ENABLE_STACK_PROTECTOR} +endif + +$(eval $(call add_define,STACK_PROTECTOR_ENABLED)) + diff --git a/make_helpers/defaults.mk b/make_helpers/defaults.mk index de506be5..e66f5112 100644 --- a/make_helpers/defaults.mk +++ b/make_helpers/defaults.mk @@ -90,6 +90,9 @@ ENABLE_PSCI_STAT := 0 # Flag to enable runtime instrumentation using PMF ENABLE_RUNTIME_INSTRUMENTATION := 0 +# Flag to enable stack corruption protection +ENABLE_STACK_PROTECTOR := 0 + # Build flag to treat usage of deprecated platform and framework APIs as error. ERROR_DEPRECATED := 0 diff --git a/plat/arm/board/fvp/fvp_stack_protector.c b/plat/arm/board/fvp/fvp_stack_protector.c new file mode 100644 index 00000000..0375c1e2 --- /dev/null +++ b/plat/arm/board/fvp/fvp_stack_protector.c @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2017, 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_helpers.h> +#include <platform.h> +#include <stdint.h> + +#define RANDOM_CANARY_VALUE ((u_register_t) 3288484550995823360ULL) + +u_register_t plat_get_stack_protector_canary(void) +{ + /* + * Ideally, a random number should be returned instead of the + * combination of a timer's value and a compile-time constant. As the + * FVP does not have any random number generator, this is better than + * nothing but not necessarily really secure. + */ + return RANDOM_CANARY_VALUE ^ read_cntpct_el0(); +} + diff --git a/plat/arm/board/fvp/include/platform_def.h b/plat/arm/board/fvp/include/platform_def.h index bf5e03b0..4088e986 100644 --- a/plat/arm/board/fvp/include/platform_def.h +++ b/plat/arm/board/fvp/include/platform_def.h @@ -35,6 +35,7 @@ #include <board_arm_def.h> #include <common_def.h> #include <tzc400.h> +#include <utils.h> #include <v2m_def.h> #include "../fvp_def.h" diff --git a/plat/arm/board/fvp/platform.mk b/plat/arm/board/fvp/platform.mk index 9b827a6b..8bac0be9 100644 --- a/plat/arm/board/fvp/platform.mk +++ b/plat/arm/board/fvp/platform.mk @@ -1,5 +1,5 @@ # -# Copyright (c) 2013-2016, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2013-2017, 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: @@ -157,5 +157,9 @@ BL31_SOURCES += plat/arm/board/fvp/fvp_bl31_setup.c \ # Disable the PSCI platform compatibility layer ENABLE_PLAT_COMPAT := 0 +ifneq (${ENABLE_STACK_PROTECTOR},0) +PLAT_BL_COMMON_SOURCES += plat/arm/board/fvp/fvp_stack_protector.c +endif + include plat/arm/board/common/board_common.mk include plat/arm/common/arm_common.mk diff --git a/plat/arm/board/juno/juno_decl.h b/plat/arm/board/juno/juno_decl.h new file mode 100644 index 00000000..75ed5b03 --- /dev/null +++ b/plat/arm/board/juno/juno_decl.h @@ -0,0 +1,36 @@ +/* + * Copyright (c) 2017, 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 __JUNO_DECL_H__ +#define __JUNO_DECL_H__ + +int juno_getentropy(void *buf, size_t len); + +#endif /* __JUNO_DECL_H__ */ diff --git a/plat/arm/board/juno/juno_def.h b/plat/arm/board/juno/juno_def.h index f27bbb22..a8e9872b 100644 --- a/plat/arm/board/juno/juno_def.h +++ b/plat/arm/board/juno/juno_def.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2014-2016, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2014-2017, 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: @@ -75,6 +75,17 @@ #define TZC400_NSAID_CORESIGHT 12 /******************************************************************************* + * TRNG related constants + ******************************************************************************/ +#define TRNG_BASE 0x7FE60000ULL +#define TRNG_NOUTPUTS 4 +#define TRNG_STATUS 0x10 +#define TRNG_INTMASK 0x14 +#define TRNG_CONFIG 0x18 +#define TRNG_CONTROL 0x1C +#define TRNG_NBYTES 16 /* Number of bytes generated per round. */ + +/******************************************************************************* * MMU-401 related constants ******************************************************************************/ #define MMU401_SSD_OFFSET 0x4000 diff --git a/plat/arm/board/juno/juno_stack_protector.c b/plat/arm/board/juno/juno_stack_protector.c new file mode 100644 index 00000000..720a522e --- /dev/null +++ b/plat/arm/board/juno/juno_stack_protector.c @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2017, 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_helpers.h> +#include <debug.h> +#include <utils.h> +#include "juno_decl.h" +#include "juno_def.h" + +u_register_t plat_get_stack_protector_canary(void) +{ + u_register_t c[TRNG_NBYTES / sizeof(u_register_t)]; + u_register_t ret = 0; + size_t i; + + if (juno_getentropy(c, sizeof(c)) != 0) { + ERROR("Not enough entropy to initialize canary value\n"); + panic(); + } + + /* + * On Juno we get 128-bits of entropy in one round. + * Fuse the values together to form the canary. + */ + for (i = 0; i < ARRAY_SIZE(c); i++) + ret ^= c[i]; + return ret; +} diff --git a/plat/arm/board/juno/juno_trng.c b/plat/arm/board/juno/juno_trng.c new file mode 100644 index 00000000..2fcddcdb --- /dev/null +++ b/plat/arm/board/juno/juno_trng.c @@ -0,0 +1,104 @@ +/* + * Copyright (c) 2017, 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 <mmio.h> +#include <string.h> +#include <utils.h> +#include "juno_def.h" + +#define NSAMPLE_CLOCKS 1 /* min 1 cycle, max 231 cycles */ +#define NRETRIES 5 + +static inline int output_valid(void) +{ + int i; + + for (i = 0; i < NRETRIES; i++) { + uint32_t val; + + val = mmio_read_32(TRNG_BASE + TRNG_STATUS); + if (val & 1U) + break; + } + if (i >= NRETRIES) + return 0; /* No output data available. */ + return 1; +} + +/* + * This function fills `buf` with `len` bytes of entropy. + * It uses the Trusted Entropy Source peripheral on Juno. + * Returns 0 when the buffer has been filled with entropy + * successfully and -1 otherwise. + */ +int juno_getentropy(void *buf, size_t len) +{ + uint8_t *bp = buf; + + assert(buf); + assert(len); + assert(!check_uptr_overflow((uintptr_t)bp, len)); + + /* Disable interrupt mode. */ + mmio_write_32(TRNG_BASE + TRNG_INTMASK, 0); + /* Program TRNG to sample for `NSAMPLE_CLOCKS`. */ + mmio_write_32(TRNG_BASE + TRNG_CONFIG, NSAMPLE_CLOCKS); + + while (len > 0) { + int i; + + /* Start TRNG. */ + mmio_write_32(TRNG_BASE + TRNG_CONTROL, 1); + + /* Check if output is valid. */ + if (!output_valid()) + return -1; + + /* Fill entropy buffer. */ + for (i = 0; i < TRNG_NOUTPUTS; i++) { + size_t n; + uint32_t val; + + val = mmio_read_32(TRNG_BASE + i * sizeof(uint32_t)); + n = MIN(len, sizeof(uint32_t)); + memcpy(bp, &val, n); + bp += n; + len -= n; + if (len == 0) + break; + } + + /* Reset TRNG outputs. */ + mmio_write_32(TRNG_BASE + TRNG_STATUS, 1); + } + + return 0; +} diff --git a/plat/arm/board/juno/platform.mk b/plat/arm/board/juno/platform.mk index bac8de17..39977240 100644 --- a/plat/arm/board/juno/platform.mk +++ b/plat/arm/board/juno/platform.mk @@ -1,5 +1,5 @@ # -# Copyright (c) 2013-2016, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2013-2017, 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: @@ -39,8 +39,12 @@ JUNO_INTERCONNECT_SOURCES := drivers/arm/cci/cci.c \ JUNO_SECURITY_SOURCES := drivers/arm/tzc/tzc400.c \ plat/arm/board/juno/juno_security.c \ + plat/arm/board/juno/juno_trng.c \ plat/arm/common/arm_tzc400.c +ifneq (${ENABLE_STACK_PROTECTOR}, 0) +JUNO_SECURITY_SOURCES += plat/arm/board/juno/juno_stack_protector.c +endif PLAT_INCLUDES := -Iplat/arm/board/juno/include @@ -51,7 +55,8 @@ BL1_SOURCES += lib/cpus/aarch64/cortex_a53.S \ lib/cpus/aarch64/cortex_a72.S \ plat/arm/board/juno/juno_bl1_setup.c \ plat/arm/board/juno/juno_err.c \ - ${JUNO_INTERCONNECT_SOURCES} + ${JUNO_INTERCONNECT_SOURCES} \ + ${JUNO_SECURITY_SOURCES} BL2_SOURCES += plat/arm/board/juno/juno_err.c \ ${JUNO_SECURITY_SOURCES} diff --git a/plat/mediatek/mt6795/bl31.ld.S b/plat/mediatek/mt6795/bl31.ld.S index 472cd2e0..73d5fdf9 100644 --- a/plat/mediatek/mt6795/bl31.ld.S +++ b/plat/mediatek/mt6795/bl31.ld.S @@ -95,6 +95,11 @@ SECTIONS */ __RW_START__ = . ; + /* + * .data must be placed at a lower address than the stacks if the stack + * protector is enabled. Alternatively, the .data.stack_protector_canary + * section can be placed independently of the main .data section. + */ .data . : { __DATA_START__ = .; *(.data*) diff --git a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c b/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c index c4170504..859ecd53 100644 --- a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c +++ b/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c @@ -43,7 +43,7 @@ #define GPU_RESET_BIT (1 << 24) /* Video Memory base and size (live values) */ -static uintptr_t video_mem_base; +static uint64_t video_mem_base; static uint64_t video_mem_size; /* @@ -85,7 +85,9 @@ void tegra_memctrl_setup(void) (void)tegra_mc_read_32(MC_SMMU_CONFIG_0); /* read to flush writes */ /* video memory carveout */ - tegra_mc_write_32(MC_VIDEO_PROTECT_BASE, video_mem_base); + tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_HI, + (uint32_t)(video_mem_base >> 32)); + tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_LO, (uint32_t)video_mem_base); tegra_mc_write_32(MC_VIDEO_PROTECT_SIZE_MB, video_mem_size); } @@ -208,7 +210,8 @@ void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes) enable_mmu_el3(0); done: - tegra_mc_write_32(MC_VIDEO_PROTECT_BASE, phys_base); + tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_HI, (uint32_t)(phys_base >> 32)); + tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_LO, (uint32_t)phys_base); tegra_mc_write_32(MC_VIDEO_PROTECT_SIZE_MB, size_in_bytes >> 20); /* store new values */ diff --git a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c b/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c index bd16b991..fb57b2b7 100644 --- a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c +++ b/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c @@ -136,7 +136,7 @@ const static mc_streamid_security_cfg_t sec_cfgs[] = { mc_make_sec_cfg(TSECSRDB, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(AXISW, SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(SDMMCWAB, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(AONDMAW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(AONDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(GPUSWR2, SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(SATAW, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(UFSHCW, NON_SECURE, OVERRIDE, ENABLE), @@ -178,8 +178,8 @@ const static mc_streamid_security_cfg_t sec_cfgs[] = { mc_make_sec_cfg(SCER, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(XUSB_HOSTR, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(VICSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AONDMAR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(AONW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(AONDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(AONW, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(SDMMCRA, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(HOST1XDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(EQOSR, NON_SECURE, OVERRIDE, ENABLE), @@ -188,24 +188,17 @@ const static mc_streamid_security_cfg_t sec_cfgs[] = { mc_make_sec_cfg(HDAR, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(SDMMCRAB, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(ETRR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(AONR, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(AONR, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(SESRD, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(NVENCSRD, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(GPUSWR, SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(TSECSWRB, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(ISPWB, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(GPUSRD2, SECURE, NO_OVERRIDE, DISABLE), -#if ENABLE_CHIP_VERIFICATION_HARNESS - mc_make_sec_cfg(APEDMAW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(APER, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(APEW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(APEDMAR, NON_SECURE, OVERRIDE, ENABLE), -#else mc_make_sec_cfg(APEDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(APER, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(APEW, NON_SECURE, NO_OVERRIDE, ENABLE), mc_make_sec_cfg(APEDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), -#endif }; const static mc_txn_override_cfg_t mc_override_cfgs[] = { @@ -623,6 +616,20 @@ void tegra_memctrl_tzdram_setup(uint64_t phys_base, uint32_t size_in_bytes) tegra_mc_write_32(MC_SECURITY_CFG1_0, size_in_bytes >> 20); /* + * When TZ encryption enabled, + * We need setup TZDRAM before CPU to access TZ Carveout, + * otherwise CPU will fetch non-decrypted data. + * So save TZDRAM setting for retore by SC7 resume FW. + */ + + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV55_LO, + tegra_mc_read_32(MC_SECURITY_CFG0_0)); + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV55_HI, + tegra_mc_read_32(MC_SECURITY_CFG3_0)); + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV54_HI, + tegra_mc_read_32(MC_SECURITY_CFG1_0)); + + /* * MCE propogates the security configuration values across the * CCPLEX. */ diff --git a/plat/nvidia/tegra/include/drivers/memctrl_v1.h b/plat/nvidia/tegra/include/drivers/memctrl_v1.h index e44a9ea9..b504594b 100644 --- a/plat/nvidia/tegra/include/drivers/memctrl_v1.h +++ b/plat/nvidia/tegra/include/drivers/memctrl_v1.h @@ -60,14 +60,6 @@ #define MC_SMMU_TRANSLATION_ENABLE_4_0 0xb98 #define MC_SMMU_TRANSLATION_ENABLE (~0) -/* TZDRAM carveout configuration registers */ -#define MC_SECURITY_CFG0_0 0x70 -#define MC_SECURITY_CFG1_0 0x74 - -/* Video Memory carveout configuration registers */ -#define MC_VIDEO_PROTECT_BASE 0x648 -#define MC_VIDEO_PROTECT_SIZE_MB 0x64c - static inline uint32_t tegra_mc_read_32(uint32_t off) { return mmio_read_32(TEGRA_MC_BASE + off); diff --git a/plat/nvidia/tegra/include/drivers/memctrl_v2.h b/plat/nvidia/tegra/include/drivers/memctrl_v2.h index e1abe143..559ea2c5 100644 --- a/plat/nvidia/tegra/include/drivers/memctrl_v2.h +++ b/plat/nvidia/tegra/include/drivers/memctrl_v2.h @@ -353,51 +353,6 @@ typedef struct mc_streamid_security_cfg { #endif /* __ASSEMBLY__ */ /******************************************************************************* - * TZDRAM carveout configuration registers - ******************************************************************************/ -#define MC_SECURITY_CFG0_0 0x70 -#define MC_SECURITY_CFG1_0 0x74 -#define MC_SECURITY_CFG3_0 0x9BC - -/******************************************************************************* - * Video Memory carveout configuration registers - ******************************************************************************/ -#define MC_VIDEO_PROTECT_BASE_HI 0x978 -#define MC_VIDEO_PROTECT_BASE_LO 0x648 -#define MC_VIDEO_PROTECT_SIZE_MB 0x64c - -/******************************************************************************* - * TZRAM carveout (MC_SECURITY_CARVEOUT11) configuration registers - ******************************************************************************/ -#define MC_TZRAM_BASE_LO 0x2194 -#define TZRAM_BASE_LO_SHIFT 12 -#define TZRAM_BASE_LO_MASK 0xFFFFF -#define MC_TZRAM_BASE_HI 0x2198 -#define TZRAM_BASE_HI_SHIFT 0 -#define TZRAM_BASE_HI_MASK 3 -#define MC_TZRAM_SIZE 0x219C -#define TZRAM_SIZE_RANGE_4KB_SHIFT 27 - -#define MC_TZRAM_CARVEOUT_CFG 0x2190 -#define TZRAM_LOCK_CFG_SETTINGS_BIT (1 << 1) -#define TZRAM_ENABLE_TZ_LOCK_BIT (1 << 0) -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG0 0x21A0 -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG1 0x21A4 -#define TZRAM_CARVEOUT_CPU_WRITE_ACCESS_BIT (1 << 25) -#define TZRAM_CARVEOUT_CPU_READ_ACCESS_BIT (1 << 7) -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG2 0x21A8 -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG3 0x21AC -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG4 0x21B0 -#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG5 0x21B4 - -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS0 0x21B8 -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS1 0x21BC -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS2 0x21C0 -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS3 0x21C4 -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS4 0x21C8 -#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS5 0x21CC - -/******************************************************************************* * Memory Controller Reset Control registers ******************************************************************************/ #define MC_CLIENT_HOTRESET_CTRL0 0x200 @@ -438,43 +393,6 @@ typedef struct mc_streamid_security_cfg { #define MC_CLIENT_HOTRESET_STATUS1 0x974 /******************************************************************************* - * TSA configuration registers - ******************************************************************************/ -#define TSA_CONFIG_STATIC0_CSW_SESWR 0x4010 -#define TSA_CONFIG_STATIC0_CSW_SESWR_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_ETRW 0x4038 -#define TSA_CONFIG_STATIC0_CSW_ETRW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_SDMMCWAB 0x5010 -#define TSA_CONFIG_STATIC0_CSW_SDMMCWAB_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_AXISW 0x7008 -#define TSA_CONFIG_STATIC0_CSW_AXISW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_HDAW 0xA008 -#define TSA_CONFIG_STATIC0_CSW_HDAW_RESET 0x100 -#define TSA_CONFIG_STATIC0_CSW_AONDMAW 0xB018 -#define TSA_CONFIG_STATIC0_CSW_AONDMAW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_SCEDMAW 0xD018 -#define TSA_CONFIG_STATIC0_CSW_SCEDMAW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_BPMPDMAW 0xD028 -#define TSA_CONFIG_STATIC0_CSW_BPMPDMAW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_APEDMAW 0x12018 -#define TSA_CONFIG_STATIC0_CSW_APEDMAW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_UFSHCW 0x13008 -#define TSA_CONFIG_STATIC0_CSW_UFSHCW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_AFIW 0x13018 -#define TSA_CONFIG_STATIC0_CSW_AFIW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_SATAW 0x13028 -#define TSA_CONFIG_STATIC0_CSW_SATAW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_EQOSW 0x13038 -#define TSA_CONFIG_STATIC0_CSW_EQOSW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_XUSB_DEVW 0x15008 -#define TSA_CONFIG_STATIC0_CSW_XUSB_DEVW_RESET 0x1100 -#define TSA_CONFIG_STATIC0_CSW_XUSB_HOSTW 0x15018 -#define TSA_CONFIG_STATIC0_CSW_XUSB_HOSTW_RESET 0x1100 - -#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK (0x3 << 11) -#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU (0 << 11) - -/******************************************************************************* * Memory Controller's PCFIFO client configuration registers ******************************************************************************/ #define MC_PCFIFO_CLIENT_CONFIG1 0xdd4 diff --git a/plat/nvidia/tegra/include/t132/tegra_def.h b/plat/nvidia/tegra/include/t132/tegra_def.h index 314b7007..4ba4f12c 100644 --- a/plat/nvidia/tegra/include/t132/tegra_def.h +++ b/plat/nvidia/tegra/include/t132/tegra_def.h @@ -104,6 +104,16 @@ ******************************************************************************/ #define TEGRA_MC_BASE 0x70019000 +/* TZDRAM carveout configuration registers */ +#define MC_SECURITY_CFG0_0 0x70 +#define MC_SECURITY_CFG1_0 0x74 +#define MC_SECURITY_CFG3_0 0x9BC + +/* Video Memory carveout configuration registers */ +#define MC_VIDEO_PROTECT_BASE_HI 0x978 +#define MC_VIDEO_PROTECT_BASE_LO 0x648 +#define MC_VIDEO_PROTECT_SIZE_MB 0x64c + /******************************************************************************* * Tegra TZRAM constants ******************************************************************************/ diff --git a/plat/nvidia/tegra/include/t186/tegra_def.h b/plat/nvidia/tegra/include/t186/tegra_def.h index e0eddfd3..6bac0d71 100644 --- a/plat/nvidia/tegra/include/t186/tegra_def.h +++ b/plat/nvidia/tegra/include/t186/tegra_def.h @@ -32,6 +32,36 @@ #define __TEGRA_DEF_H__ /******************************************************************************* + * MCE apertures used by the ARI interface + * + * Aperture 0 - Cpu0 (ARM Cortex A-57) + * Aperture 1 - Cpu1 (ARM Cortex A-57) + * Aperture 2 - Cpu2 (ARM Cortex A-57) + * Aperture 3 - Cpu3 (ARM Cortex A-57) + * Aperture 4 - Cpu4 (Denver15) + * Aperture 5 - Cpu5 (Denver15) + ******************************************************************************/ +#define MCE_ARI_APERTURE_0_OFFSET 0x0 +#define MCE_ARI_APERTURE_1_OFFSET 0x10000 +#define MCE_ARI_APERTURE_2_OFFSET 0x20000 +#define MCE_ARI_APERTURE_3_OFFSET 0x30000 +#define MCE_ARI_APERTURE_4_OFFSET 0x40000 +#define MCE_ARI_APERTURE_5_OFFSET 0x50000 +#define MCE_ARI_APERTURE_OFFSET_MAX MCE_APERTURE_5_OFFSET + +/* number of apertures */ +#define MCE_ARI_APERTURES_MAX 6 + +/* each ARI aperture is 64KB */ +#define MCE_ARI_APERTURE_SIZE 0x10000 + +/******************************************************************************* + * CPU core id macros for the MCE_ONLINE_CORE ARI + ******************************************************************************/ +#define MCE_CORE_ID_MAX 8 +#define MCE_CORE_ID_MASK 0x7 + +/******************************************************************************* * These values are used by the PSCI implementation during the `CPU_SUSPEND` * and `SYSTEM_SUSPEND` calls as the `state-id` field in the 'power state' * parameter. @@ -85,11 +115,87 @@ #define TEGRA_TSA_BASE 0x02400000 /******************************************************************************* + * TSA configuration registers + ******************************************************************************/ +#define TSA_CONFIG_STATIC0_CSW_SESWR 0x4010 +#define TSA_CONFIG_STATIC0_CSW_SESWR_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_ETRW 0x4038 +#define TSA_CONFIG_STATIC0_CSW_ETRW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_SDMMCWAB 0x5010 +#define TSA_CONFIG_STATIC0_CSW_SDMMCWAB_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_AXISW 0x7008 +#define TSA_CONFIG_STATIC0_CSW_AXISW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_HDAW 0xA008 +#define TSA_CONFIG_STATIC0_CSW_HDAW_RESET 0x100 +#define TSA_CONFIG_STATIC0_CSW_AONDMAW 0xB018 +#define TSA_CONFIG_STATIC0_CSW_AONDMAW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_SCEDMAW 0xD018 +#define TSA_CONFIG_STATIC0_CSW_SCEDMAW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_BPMPDMAW 0xD028 +#define TSA_CONFIG_STATIC0_CSW_BPMPDMAW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_APEDMAW 0x12018 +#define TSA_CONFIG_STATIC0_CSW_APEDMAW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_UFSHCW 0x13008 +#define TSA_CONFIG_STATIC0_CSW_UFSHCW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_AFIW 0x13018 +#define TSA_CONFIG_STATIC0_CSW_AFIW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_SATAW 0x13028 +#define TSA_CONFIG_STATIC0_CSW_SATAW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_EQOSW 0x13038 +#define TSA_CONFIG_STATIC0_CSW_EQOSW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_XUSB_DEVW 0x15008 +#define TSA_CONFIG_STATIC0_CSW_XUSB_DEVW_RESET 0x1100 +#define TSA_CONFIG_STATIC0_CSW_XUSB_HOSTW 0x15018 +#define TSA_CONFIG_STATIC0_CSW_XUSB_HOSTW_RESET 0x1100 + +#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK (0x3 << 11) +#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU (0 << 11) + +/******************************************************************************* * Tegra Memory Controller constants ******************************************************************************/ #define TEGRA_MC_STREAMID_BASE 0x02C00000 #define TEGRA_MC_BASE 0x02C10000 +/* TZDRAM carveout configuration registers */ +#define MC_SECURITY_CFG0_0 0x70 +#define MC_SECURITY_CFG1_0 0x74 +#define MC_SECURITY_CFG3_0 0x9BC + +/* Video Memory carveout configuration registers */ +#define MC_VIDEO_PROTECT_BASE_HI 0x978 +#define MC_VIDEO_PROTECT_BASE_LO 0x648 +#define MC_VIDEO_PROTECT_SIZE_MB 0x64c + +/* TZRAM carveout (MC_SECURITY_CARVEOUT11) configuration registers */ +#define MC_TZRAM_BASE_LO 0x2194 +#define TZRAM_BASE_LO_SHIFT 12 +#define TZRAM_BASE_LO_MASK 0xFFFFF +#define MC_TZRAM_BASE_HI 0x2198 +#define TZRAM_BASE_HI_SHIFT 0 +#define TZRAM_BASE_HI_MASK 3 +#define MC_TZRAM_SIZE 0x219C +#define TZRAM_SIZE_RANGE_4KB_SHIFT 27 + +#define MC_TZRAM_CARVEOUT_CFG 0x2190 +#define TZRAM_LOCK_CFG_SETTINGS_BIT (1 << 1) +#define TZRAM_ENABLE_TZ_LOCK_BIT (1 << 0) +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG0 0x21A0 +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG1 0x21A4 +#define TZRAM_CARVEOUT_CPU_WRITE_ACCESS_BIT (1 << 25) +#define TZRAM_CARVEOUT_CPU_READ_ACCESS_BIT (1 << 7) +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG2 0x21A8 +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG3 0x21AC +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG4 0x21B0 +#define MC_TZRAM_CARVEOUT_CLIENT_ACCESS_CFG5 0x21B4 + +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS0 0x21B8 +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS1 0x21BC +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS2 0x21C0 +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS3 0x21C4 +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS4 0x21C8 +#define MC_TZRAM_CARVEOUT_FORCE_INTERNAL_ACCESS5 0x21CC + /******************************************************************************* * Tegra UART Controller constants ******************************************************************************/ @@ -148,6 +254,9 @@ #define SECURE_SCRATCH_RSV11_HI 0x6AC #define SECURE_SCRATCH_RSV53_LO 0x7F8 #define SECURE_SCRATCH_RSV53_HI 0x7FC +#define SECURE_SCRATCH_RSV54_HI 0x804 +#define SECURE_SCRATCH_RSV55_LO 0x808 +#define SECURE_SCRATCH_RSV55_HI 0x80C /******************************************************************************* * Tegra Memory Mapped Control Register Access Bus constants diff --git a/plat/nvidia/tegra/include/t210/tegra_def.h b/plat/nvidia/tegra/include/t210/tegra_def.h index d24377da..09613551 100644 --- a/plat/nvidia/tegra/include/t210/tegra_def.h +++ b/plat/nvidia/tegra/include/t210/tegra_def.h @@ -129,6 +129,16 @@ ******************************************************************************/ #define TEGRA_MC_BASE 0x70019000 +/* TZDRAM carveout configuration registers */ +#define MC_SECURITY_CFG0_0 0x70 +#define MC_SECURITY_CFG1_0 0x74 +#define MC_SECURITY_CFG3_0 0x9BC + +/* Video Memory carveout configuration registers */ +#define MC_VIDEO_PROTECT_BASE_HI 0x978 +#define MC_VIDEO_PROTECT_BASE_LO 0x648 +#define MC_VIDEO_PROTECT_SIZE_MB 0x64c + /******************************************************************************* * Tegra TZRAM constants ******************************************************************************/ diff --git a/plat/nvidia/tegra/soc/t186/drivers/include/mce.h b/plat/nvidia/tegra/soc/t186/drivers/include/mce.h index 66e212bf..441a2c1b 100644 --- a/plat/nvidia/tegra/soc/t186/drivers/include/mce.h +++ b/plat/nvidia/tegra/soc/t186/drivers/include/mce.h @@ -35,67 +35,28 @@ #include <tegra_def.h> /******************************************************************************* - * MCE apertures used by the ARI interface - * - * Aperture 0 - Cpu0 (ARM Cortex A-57) - * Aperture 1 - Cpu1 (ARM Cortex A-57) - * Aperture 2 - Cpu2 (ARM Cortex A-57) - * Aperture 3 - Cpu3 (ARM Cortex A-57) - * Aperture 4 - Cpu4 (Denver15) - * Aperture 5 - Cpu5 (Denver15) - ******************************************************************************/ -#define MCE_ARI_APERTURE_0_OFFSET 0x0 -#define MCE_ARI_APERTURE_1_OFFSET 0x10000 -#define MCE_ARI_APERTURE_2_OFFSET 0x20000 -#define MCE_ARI_APERTURE_3_OFFSET 0x30000 -#define MCE_ARI_APERTURE_4_OFFSET 0x40000 -#define MCE_ARI_APERTURE_5_OFFSET 0x50000 -#define MCE_ARI_APERTURE_OFFSET_MAX MCE_APERTURE_5_OFFSET - -/* number of apertures */ -#define MCE_ARI_APERTURES_MAX 6 - -/* each ARI aperture is 64KB */ -#define MCE_ARI_APERTURE_SIZE 0x10000 - -/******************************************************************************* - * CPU core ids - used by the MCE_ONLINE_CORE ARI - ******************************************************************************/ -typedef enum mce_core_id { - MCE_CORE_ID_DENVER_15_0, - MCE_CORE_ID_DENVER_15_1, - /* 2 and 3 are reserved */ - MCE_CORE_ID_A57_0 = 4, - MCE_CORE_ID_A57_1, - MCE_CORE_ID_A57_2, - MCE_CORE_ID_A57_3, - MCE_CORE_ID_MAX -} mce_core_id_t; - -#define MCE_CORE_ID_MASK 0x7 - -/******************************************************************************* * MCE commands ******************************************************************************/ typedef enum mce_cmd { MCE_CMD_ENTER_CSTATE = 0, - MCE_CMD_UPDATE_CSTATE_INFO, - MCE_CMD_UPDATE_CROSSOVER_TIME, - MCE_CMD_READ_CSTATE_STATS, - MCE_CMD_WRITE_CSTATE_STATS, - MCE_CMD_IS_SC7_ALLOWED, - MCE_CMD_ONLINE_CORE, - MCE_CMD_CC3_CTRL, - MCE_CMD_ECHO_DATA, - MCE_CMD_READ_VERSIONS, - MCE_CMD_ENUM_FEATURES, - MCE_CMD_ROC_FLUSH_CACHE_TRBITS, - MCE_CMD_ENUM_READ_MCA, - MCE_CMD_ENUM_WRITE_MCA, - MCE_CMD_ROC_FLUSH_CACHE, - MCE_CMD_ROC_CLEAN_CACHE, - MCE_CMD_ENABLE_LATIC, - MCE_CMD_UNCORE_PERFMON_REQ, + MCE_CMD_UPDATE_CSTATE_INFO = 1, + MCE_CMD_UPDATE_CROSSOVER_TIME = 2, + MCE_CMD_READ_CSTATE_STATS = 3, + MCE_CMD_WRITE_CSTATE_STATS = 4, + MCE_CMD_IS_SC7_ALLOWED = 5, + MCE_CMD_ONLINE_CORE = 6, + MCE_CMD_CC3_CTRL = 7, + MCE_CMD_ECHO_DATA = 8, + MCE_CMD_READ_VERSIONS = 9, + MCE_CMD_ENUM_FEATURES = 10, + MCE_CMD_ROC_FLUSH_CACHE_TRBITS = 11, + MCE_CMD_ENUM_READ_MCA = 12, + MCE_CMD_ENUM_WRITE_MCA = 13, + MCE_CMD_ROC_FLUSH_CACHE = 14, + MCE_CMD_ROC_CLEAN_CACHE = 15, + MCE_CMD_ENABLE_LATIC = 16, + MCE_CMD_UNCORE_PERFMON_REQ = 17, + MCE_CMD_MISC_CCPLEX = 18, MCE_CMD_IS_CCX_ALLOWED = 0xFE, MCE_CMD_MAX = 0xFF, } mce_cmd_t; @@ -337,9 +298,7 @@ typedef struct arch_mce_ops { * This ARI request allows updating the reset vector register for * D15 and A57 CPUs. */ - int (*update_reset_vector)(uint32_t ari_base, - uint32_t addr_low, - uint32_t addr_high); + int (*update_reset_vector)(uint32_t ari_base); /* * This ARI request instructs the ROC to flush A57 data caches in * order to maintain coherency with the Denver cluster. @@ -386,11 +345,17 @@ typedef struct arch_mce_ops { */ int (*read_write_uncore_perfmon)(uint32_t ari_base, uncore_perfmon_req_t req, uint64_t *data); + /* + * This ARI implements ARI_MISC_CCPLEX commands. This can be + * used to enable/disable coresight clock gating. + */ + void (*misc_ccplex)(uint32_t ari_base, uint32_t index, + uint32_t value); } arch_mce_ops_t; int mce_command_handler(mce_cmd_t cmd, uint64_t arg0, uint64_t arg1, uint64_t arg2); -int mce_update_reset_vector(uint32_t addr_lo, uint32_t addr_hi); +int mce_update_reset_vector(void); int mce_update_gsc_videomem(void); int mce_update_gsc_tzdram(void); int mce_update_gsc_tzram(void); @@ -411,7 +376,7 @@ int ari_is_ccx_allowed(uint32_t ari_base, uint32_t state, uint32_t wake_time); int ari_is_sc7_allowed(uint32_t ari_base, uint32_t state, uint32_t wake_time); int ari_online_core(uint32_t ari_base, uint32_t core); int ari_cc3_ctrl(uint32_t ari_base, uint32_t freq, uint32_t volt, uint8_t enable); -int ari_reset_vector_update(uint32_t ari_base, uint32_t lo, uint32_t hi); +int ari_reset_vector_update(uint32_t ari_base); int ari_roc_flush_cache_trbits(uint32_t ari_base); int ari_roc_flush_cache(uint32_t ari_base); int ari_roc_clean_cache(uint32_t ari_base); @@ -420,6 +385,7 @@ int ari_update_ccplex_gsc(uint32_t ari_base, uint32_t gsc_idx); void ari_enter_ccplex_state(uint32_t ari_base, uint32_t state_idx); int ari_read_write_uncore_perfmon(uint32_t ari_base, uncore_perfmon_req_t req, uint64_t *data); +void ari_misc_ccplex(uint32_t ari_base, uint32_t index, uint32_t value); int nvg_enter_cstate(uint32_t ari_base, uint32_t state, uint32_t wake_time); int nvg_update_cstate_info(uint32_t ari_base, uint32_t cluster, uint32_t ccplex, diff --git a/plat/nvidia/tegra/soc/t186/drivers/include/t18x_ari.h b/plat/nvidia/tegra/soc/t186/drivers/include/t18x_ari.h index 3e6054bd..cb48de62 100644 --- a/plat/nvidia/tegra/soc/t186/drivers/include/t18x_ari.h +++ b/plat/nvidia/tegra/soc/t186/drivers/include/t18x_ari.h @@ -40,8 +40,8 @@ */ enum { - TEGRA_ARI_VERSION_MAJOR = 2, - TEGRA_ARI_VERSION_MINOR = 19, + TEGRA_ARI_VERSION_MAJOR = 3, + TEGRA_ARI_VERSION_MINOR = 0, }; typedef enum { @@ -107,15 +107,15 @@ typedef enum { typedef enum { TEGRA_ARI_CCPLEX_CCP0 = 0, TEGRA_ARI_CCPLEX_CCP1 = 1, - TEGRA_ARI_CCPLEX_CCP3 = 3, + TEGRA_ARI_CCPLEX_CCP3 = 3, /* obsoleted */ } tegra_ari_ccplex_sleep_state_t; typedef enum { TEGRA_ARI_SYSTEM_SC0 = 0, - TEGRA_ARI_SYSTEM_SC1 = 1, - TEGRA_ARI_SYSTEM_SC2 = 2, - TEGRA_ARI_SYSTEM_SC3 = 3, - TEGRA_ARI_SYSTEM_SC4 = 4, + TEGRA_ARI_SYSTEM_SC1 = 1, /* obsoleted */ + TEGRA_ARI_SYSTEM_SC2 = 2, /* obsoleted */ + TEGRA_ARI_SYSTEM_SC3 = 3, /* obsoleted */ + TEGRA_ARI_SYSTEM_SC4 = 4, /* obsoleted */ TEGRA_ARI_SYSTEM_SC7 = 7, TEGRA_ARI_SYSTEM_SC8 = 8, } tegra_ari_system_sleep_state_t; @@ -124,21 +124,22 @@ typedef enum { TEGRA_ARI_CROSSOVER_C1_C6 = 0, TEGRA_ARI_CROSSOVER_CC1_CC6 = 1, TEGRA_ARI_CROSSOVER_CC1_CC7 = 2, - TEGRA_ARI_CROSSOVER_CCP1_CCP3 = 3, - TEGRA_ARI_CROSSOVER_CCP3_SC2 = 4, - TEGRA_ARI_CROSSOVER_CCP3_SC3 = 5, - TEGRA_ARI_CROSSOVER_CCP3_SC4 = 6, - TEGRA_ARI_CROSSOVER_CCP3_SC7 = 7, - TEGRA_ARI_CROSSOVER_CCP3_SC1 = 8, + TEGRA_ARI_CROSSOVER_CCP1_CCP3 = 3, /* obsoleted */ + TEGRA_ARI_CROSSOVER_CCP3_SC2 = 4, /* obsoleted */ + TEGRA_ARI_CROSSOVER_CCP3_SC3 = 5, /* obsoleted */ + TEGRA_ARI_CROSSOVER_CCP3_SC4 = 6, /* obsoleted */ + TEGRA_ARI_CROSSOVER_CCP3_SC7 = 7, /* obsoleted */ + TEGRA_ARI_CROSSOVER_SC0_SC7 = 7, + TEGRA_ARI_CROSSOVER_CCP3_SC1 = 8, /* obsoleted */ } tegra_ari_crossover_index_t; typedef enum { TEGRA_ARI_CSTATE_STATS_CLEAR = 0, - TEGRA_ARI_CSTATE_STATS_SC7_ENTRIES = 1, - TEGRA_ARI_CSTATE_STATS_SC4_ENTRIES, - TEGRA_ARI_CSTATE_STATS_SC3_ENTRIES, - TEGRA_ARI_CSTATE_STATS_SC2_ENTRIES, - TEGRA_ARI_CSTATE_STATS_CCP3_ENTRIES, + TEGRA_ARI_CSTATE_STATS_SC7_ENTRIES, + TEGRA_ARI_CSTATE_STATS_SC4_ENTRIES, /* obsoleted */ + TEGRA_ARI_CSTATE_STATS_SC3_ENTRIES, /* obsoleted */ + TEGRA_ARI_CSTATE_STATS_SC2_ENTRIES, /* obsoleted */ + TEGRA_ARI_CSTATE_STATS_CCP3_ENTRIES, /* obsoleted */ TEGRA_ARI_CSTATE_STATS_A57_CC6_ENTRIES, TEGRA_ARI_CSTATE_STATS_A57_CC7_ENTRIES, TEGRA_ARI_CSTATE_STATS_D15_CC6_ENTRIES, @@ -403,17 +404,18 @@ typedef enum { TEGRA_NVG_CHANNEL_CROSSOVER_C1_C6 = 5, TEGRA_NVG_CHANNEL_CROSSOVER_CC1_CC6 = 6, TEGRA_NVG_CHANNEL_CROSSOVER_CC1_CC7 = 7, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP1_CCP3 = 8, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC2 = 9, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC3 = 10, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC4 = 11, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC7 = 12, + TEGRA_NVG_CHANNEL_CROSSOVER_CCP1_CCP3 = 8, /* obsoleted */ + TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC2 = 9, /* obsoleted */ + TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC3 = 10, /* obsoleted */ + TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC4 = 11, /* obsoleted */ + TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC7 = 12, /* obsoleted */ + TEGRA_NVG_CHANNEL_CROSSOVER_SC0_SC7 = 12, TEGRA_NVG_CHANNEL_CSTATE_STATS_CLEAR = 13, TEGRA_NVG_CHANNEL_CSTATE_STATS_SC7_ENTRIES = 14, - TEGRA_NVG_CHANNEL_CSTATE_STATS_SC4_ENTRIES = 15, - TEGRA_NVG_CHANNEL_CSTATE_STATS_SC3_ENTRIES = 16, - TEGRA_NVG_CHANNEL_CSTATE_STATS_SC2_ENTRIES = 17, - TEGRA_NVG_CHANNEL_CSTATE_STATS_CCP3_ENTRIES = 18, + TEGRA_NVG_CHANNEL_CSTATE_STATS_SC4_ENTRIES = 15, /* obsoleted */ + TEGRA_NVG_CHANNEL_CSTATE_STATS_SC3_ENTRIES = 16, /* obsoleted */ + TEGRA_NVG_CHANNEL_CSTATE_STATS_SC2_ENTRIES = 17, /* obsoleted */ + TEGRA_NVG_CHANNEL_CSTATE_STATS_CCP3_ENTRIES = 18, /* obsoleted */ TEGRA_NVG_CHANNEL_CSTATE_STATS_A57_CC6_ENTRIES = 19, TEGRA_NVG_CHANNEL_CSTATE_STATS_A57_CC7_ENTRIES = 20, TEGRA_NVG_CHANNEL_CSTATE_STATS_D15_CC6_ENTRIES = 21, @@ -432,7 +434,7 @@ typedef enum { TEGRA_NVG_CHANNEL_CSTATE_STATS_A57_3_C7_ENTRIES = 34, TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_D15_0 = 35, TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_D15_1 = 36, - TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_D15_2 = 37, /* Reserved (for Denver15 core 2) */ + TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_D15_2 = 37, /* Reserved (for Denver15 core 2) */ TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_D15_3 = 38, /* Reserved (for Denver15 core 3) */ TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_A57_0 = 39, TEGRA_NVG_CHANNEL_CSTATE_STATS_LAST_CSTATE_ENTRY_A57_1 = 40, @@ -441,10 +443,8 @@ typedef enum { TEGRA_NVG_CHANNEL_IS_SC7_ALLOWED = 43, TEGRA_NVG_CHANNEL_ONLINE_CORE = 44, TEGRA_NVG_CHANNEL_CC3_CTRL = 45, - TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC1 = 46, + TEGRA_NVG_CHANNEL_CROSSOVER_CCP3_SC1 = 46, /* obsoleted */ TEGRA_NVG_CHANNEL_LAST_INDEX, } tegra_nvg_channel_id_t; #endif /* T18X_TEGRA_ARI_H */ - - diff --git a/plat/nvidia/tegra/soc/t186/drivers/mce/ari.c b/plat/nvidia/tegra/soc/t186/drivers/mce/ari.c index e11d1600..7597c12b 100644 --- a/plat/nvidia/tegra/soc/t186/drivers/mce/ari.c +++ b/plat/nvidia/tegra/soc/t186/drivers/mce/ari.c @@ -129,6 +129,9 @@ int ari_enter_cstate(uint32_t ari_base, uint32_t state, uint32_t wake_time) return EINVAL; } + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* Enter the cstate, to be woken up after wake_time (TSC ticks) */ return ari_request_wait(ari_base, ARI_EVT_MASK_STANDBYWFI_BIT, TEGRA_ARI_ENTER_CSTATE, state, wake_time); @@ -140,6 +143,9 @@ int ari_update_cstate_info(uint32_t ari_base, uint32_t cluster, uint32_t ccplex, { uint32_t val = 0; + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* update CLUSTER_CSTATE? */ if (cluster) val |= (cluster & CLUSTER_CSTATE_MASK) | @@ -172,6 +178,9 @@ int ari_update_crossover_time(uint32_t ari_base, uint32_t type, uint32_t time) (type > TEGRA_ARI_CROSSOVER_CCP3_SC1)) return EINVAL; + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* update crossover threshold time */ return ari_request_wait(ari_base, 0, TEGRA_ARI_UPDATE_CROSSOVER, type, time); @@ -185,6 +194,9 @@ uint64_t ari_read_cstate_stats(uint32_t ari_base, uint32_t state) if (state == 0) return EINVAL; + /* clean the previous response state */ + ari_clobber_response(ari_base); + ret = ari_request_wait(ari_base, 0, TEGRA_ARI_CSTATE_STATS, state, 0); if (ret != 0) return EINVAL; @@ -194,6 +206,9 @@ uint64_t ari_read_cstate_stats(uint32_t ari_base, uint32_t state) int ari_write_cstate_stats(uint32_t ari_base, uint32_t state, uint32_t stats) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* write the cstate stats */ return ari_request_wait(ari_base, 0, TEGRA_ARI_WRITE_CSTATE_STATS, state, stats); @@ -226,6 +241,9 @@ int ari_is_ccx_allowed(uint32_t ari_base, uint32_t state, uint32_t wake_time) { int ret; + /* clean the previous response state */ + ari_clobber_response(ari_base); + ret = ari_request_wait(ari_base, 0, TEGRA_ARI_IS_CCX_ALLOWED, state & 0x7, wake_time); if (ret) { @@ -248,6 +266,9 @@ int ari_is_sc7_allowed(uint32_t ari_base, uint32_t state, uint32_t wake_time) return EINVAL; } + /* clean the previous response state */ + ari_clobber_response(ari_base); + ret = ari_request_wait(ari_base, 0, TEGRA_ARI_IS_SC7_ALLOWED, state, wake_time); if (ret) { @@ -283,6 +304,9 @@ int ari_online_core(uint32_t ari_base, uint32_t core) return EINVAL; } + /* clean the previous response state */ + ari_clobber_response(ari_base); + return ari_request_wait(ari_base, 0, TEGRA_ARI_ONLINE_CORE, core, 0); } @@ -290,6 +314,9 @@ int ari_cc3_ctrl(uint32_t ari_base, uint32_t freq, uint32_t volt, uint8_t enable { int val; + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* * If the enable bit is cleared, Auto-CC3 will be disabled by setting * the SW visible voltage/frequency request registers for all non @@ -307,31 +334,43 @@ int ari_cc3_ctrl(uint32_t ari_base, uint32_t freq, uint32_t volt, uint8_t enable return ari_request_wait(ari_base, 0, TEGRA_ARI_CC3_CTRL, val, 0); } -int ari_reset_vector_update(uint32_t ari_base, uint32_t lo, uint32_t hi) +int ari_reset_vector_update(uint32_t ari_base) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* * Need to program the CPU reset vector one time during cold boot * and SC7 exit */ - ari_request_wait(ari_base, 0, TEGRA_ARI_COPY_MISCREG_AA64_RST, lo, hi); + ari_request_wait(ari_base, 0, TEGRA_ARI_COPY_MISCREG_AA64_RST, 0, 0); return 0; } int ari_roc_flush_cache_trbits(uint32_t ari_base) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + return ari_request_wait(ari_base, 0, TEGRA_ARI_ROC_FLUSH_CACHE_TRBITS, 0, 0); } int ari_roc_flush_cache(uint32_t ari_base) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + return ari_request_wait(ari_base, 0, TEGRA_ARI_ROC_FLUSH_CACHE_ONLY, 0, 0); } int ari_roc_clean_cache(uint32_t ari_base) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + return ari_request_wait(ari_base, 0, TEGRA_ARI_ROC_CLEAN_CACHE_ONLY, 0, 0); } @@ -372,6 +411,9 @@ int ari_update_ccplex_gsc(uint32_t ari_base, uint32_t gsc_idx) if (gsc_idx > TEGRA_ARI_GSC_VPR_IDX) return EINVAL; + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* * The MCE code will read the GSC carveout value, corrseponding to * the ID, from the MC registers and update the internal GSC registers @@ -384,6 +426,9 @@ int ari_update_ccplex_gsc(uint32_t ari_base, uint32_t gsc_idx) void ari_enter_ccplex_state(uint32_t ari_base, uint32_t state_idx) { + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* * The MCE will shutdown or restart the entire system */ @@ -396,6 +441,9 @@ int ari_read_write_uncore_perfmon(uint32_t ari_base, int ret; uint32_t val; + /* clean the previous response state */ + ari_clobber_response(ari_base); + /* sanity check input parameters */ if (req.perfmon_command.cmd == UNCORE_PERFMON_CMD_READ && !data) { ERROR("invalid parameters\n"); @@ -427,3 +475,22 @@ int ari_read_write_uncore_perfmon(uint32_t ari_base, return (int)req.perfmon_status.val; } + +void ari_misc_ccplex(uint32_t ari_base, uint32_t index, uint32_t value) +{ + /* + * This invokes the ARI_MISC_CCPLEX commands. This can be + * used to enable/disable coresight clock gating. + */ + + if ((index > TEGRA_ARI_MISC_CCPLEX_CORESIGHT_CG_CTRL) || + ((index == TEGRA_ARI_MISC_CCPLEX_CORESIGHT_CG_CTRL) && + (value > 1))) { + ERROR("%s: invalid parameters \n", __func__); + return; + } + + /* clean the previous response state */ + ari_clobber_response(ari_base); + (void)ari_request_wait(ari_base, 0, TEGRA_ARI_MISC_CCPLEX, index, value); +} diff --git a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c index f87dfa4d..3a0edfb9 100644 --- a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c +++ b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c @@ -63,7 +63,8 @@ static arch_mce_ops_t nvg_mce_ops = { .read_write_mca = ari_read_write_mca, .update_ccplex_gsc = ari_update_ccplex_gsc, .enter_ccplex_state = ari_enter_ccplex_state, - .read_write_uncore_perfmon = ari_read_write_uncore_perfmon + .read_write_uncore_perfmon = ari_read_write_uncore_perfmon, + .misc_ccplex = ari_misc_ccplex }; /* ARI functions handlers */ @@ -85,7 +86,8 @@ static arch_mce_ops_t ari_mce_ops = { .read_write_mca = ari_read_write_mca, .update_ccplex_gsc = ari_update_ccplex_gsc, .enter_ccplex_state = ari_enter_ccplex_state, - .read_write_uncore_perfmon = ari_read_write_uncore_perfmon + .read_write_uncore_perfmon = ari_read_write_uncore_perfmon, + .misc_ccplex = ari_misc_ccplex }; typedef struct mce_config { @@ -307,14 +309,12 @@ int mce_command_handler(mce_cmd_t cmd, uint64_t arg0, uint64_t arg1, break; case MCE_CMD_ENUM_FEATURES: - ret = ops->call_enum_misc(cpu_ari_base, + ret64 = ops->call_enum_misc(cpu_ari_base, TEGRA_ARI_MISC_FEATURE_LEAF_0, arg0); /* update context to return features value */ write_ctx_reg(gp_regs, CTX_GPREG_X1, ret64); - ret = 0; - break; case MCE_CMD_ROC_FLUSH_CACHE_TRBITS: @@ -387,6 +387,11 @@ int mce_command_handler(mce_cmd_t cmd, uint64_t arg0, uint64_t arg1, write_ctx_reg(gp_regs, CTX_GPREG_X1, arg1); break; + case MCE_CMD_MISC_CCPLEX: + ops->misc_ccplex(cpu_ari_base, arg0, arg1); + + break; + default: ERROR("unknown MCE command (%d)\n", cmd); return EINVAL; @@ -398,11 +403,11 @@ int mce_command_handler(mce_cmd_t cmd, uint64_t arg0, uint64_t arg1, /******************************************************************************* * Handler to update the reset vector for CPUs ******************************************************************************/ -int mce_update_reset_vector(uint32_t addr_lo, uint32_t addr_hi) +int mce_update_reset_vector(void) { arch_mce_ops_t *ops = mce_get_curr_cpu_ops(); - ops->update_reset_vector(mce_get_curr_cpu_ari_base(), addr_lo, addr_hi); + ops->update_reset_vector(mce_get_curr_cpu_ari_base()); return 0; } diff --git a/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c index 35828787..a170b994 100644 --- a/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c +++ b/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c @@ -55,7 +55,7 @@ extern uint32_t __tegra186_cpu_reset_handler_data, /* state id mask */ #define TEGRA186_STATE_ID_MASK 0xF /* constants to get power state's wake time */ -#define TEGRA186_WAKE_TIME_MASK 0xFFFFFF +#define TEGRA186_WAKE_TIME_MASK 0x0FFFFFF0 #define TEGRA186_WAKE_TIME_SHIFT 4 /* default core wake mask for CPU_SUSPEND */ #define TEGRA186_CORE_WAKE_MASK 0x180c @@ -63,7 +63,9 @@ extern uint32_t __tegra186_cpu_reset_handler_data, #define TEGRA186_SE_CONTEXT_SIZE 3 static uint32_t se_regs[TEGRA186_SE_CONTEXT_SIZE]; -static unsigned int wake_time[PLATFORM_CORE_COUNT]; +static struct t18x_psci_percpu_data { + unsigned int wake_time; +} __aligned(CACHE_WRITEBACK_GRANULE) percpu_data[PLATFORM_CORE_COUNT]; /* System power down state */ uint32_t tegra186_system_powerdn_state = TEGRA_ARI_MISC_CCPLEX_SHUTDOWN_POWER_OFF; @@ -74,9 +76,19 @@ int32_t tegra_soc_validate_power_state(unsigned int power_state, int state_id = psci_get_pstate_id(power_state) & TEGRA186_STATE_ID_MASK; int cpu = plat_my_core_pos(); - /* save the core wake time (us) */ - wake_time[cpu] = (power_state >> TEGRA186_WAKE_TIME_SHIFT) & - TEGRA186_WAKE_TIME_MASK; + /* save the core wake time (in TSC ticks)*/ + percpu_data[cpu].wake_time = (power_state & TEGRA186_WAKE_TIME_MASK) + << TEGRA186_WAKE_TIME_SHIFT; + + /* + * Clean percpu_data[cpu] to DRAM. This needs to be done to ensure that + * the correct value is read in tegra_soc_pwr_domain_suspend(), which + * is called with caches disabled. It is possible to read a stale value + * from DRAM in that function, because the L2 cache is not flushed + * unless the cluster is entering CC6/CC7. + */ + clean_dcache_range((uint64_t)&percpu_data[cpu], + sizeof(percpu_data[cpu])); /* Sanity check the requested state id */ switch (state_id) { @@ -121,7 +133,7 @@ int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) val = (stateid_afflvl0 == PSTATE_ID_CORE_IDLE) ? TEGRA_ARI_CORE_C6 : TEGRA_ARI_CORE_C7; (void)mce_command_handler(MCE_CMD_ENTER_CSTATE, val, - wake_time[cpu], 0); + percpu_data[cpu].wake_time, 0); } else if (stateid_afflvl2 == PSTATE_ID_SOC_POWERDN) { @@ -193,7 +205,8 @@ plat_local_state_t tegra_soc_get_target_pwr_state(unsigned int lvl, /* Check if CCx state is allowed. */ ret = mce_command_handler(MCE_CMD_IS_CCX_ALLOWED, - TEGRA_ARI_CORE_C7, wake_time[cpu], 0); + TEGRA_ARI_CORE_C7, percpu_data[cpu].wake_time, + 0); if (ret) return PSTATE_ID_CORE_POWERDN; } diff --git a/plat/nvidia/tegra/soc/t186/plat_secondary.c b/plat/nvidia/tegra/soc/t186/plat_secondary.c index 406c1e08..6576db11 100644 --- a/plat/nvidia/tegra/soc/t186/plat_secondary.c +++ b/plat/nvidia/tegra/soc/t186/plat_secondary.c @@ -91,5 +91,5 @@ void plat_secondary_setup(void) addr_high); /* update reset vector address to the CCPLEX */ - mce_update_reset_vector(addr_low, addr_high); + mce_update_reset_vector(); } diff --git a/plat/nvidia/tegra/soc/t186/plat_sip_calls.c b/plat/nvidia/tegra/soc/t186/plat_sip_calls.c index 8e337184..31e903eb 100644 --- a/plat/nvidia/tegra/soc/t186/plat_sip_calls.c +++ b/plat/nvidia/tegra/soc/t186/plat_sip_calls.c @@ -66,6 +66,7 @@ extern uint32_t tegra186_system_powerdn_state; #define TEGRA_SIP_MCE_CMD_ROC_CLEAN_CACHE 0x82FFFF0F #define TEGRA_SIP_MCE_CMD_ENABLE_LATIC 0x82FFFF10 #define TEGRA_SIP_MCE_CMD_UNCORE_PERFMON_REQ 0x82FFFF11 +#define TEGRA_SIP_MCE_CMD_MISC_CCPLEX 0x82FFFF12 /******************************************************************************* * This function is responsible for handling all T186 SiP calls @@ -104,6 +105,7 @@ int plat_sip_handler(uint32_t smc_fid, case TEGRA_SIP_MCE_CMD_ROC_CLEAN_CACHE: case TEGRA_SIP_MCE_CMD_ENABLE_LATIC: case TEGRA_SIP_MCE_CMD_UNCORE_PERFMON_REQ: + case TEGRA_SIP_MCE_CMD_MISC_CCPLEX: /* clean up the high bits */ smc_fid &= MCE_CMD_MASK; diff --git a/plat/nvidia/tegra/soc/t186/plat_trampoline.S b/plat/nvidia/tegra/soc/t186/plat_trampoline.S index 7619ed0c..21393d9b 100644 --- a/plat/nvidia/tegra/soc/t186/plat_trampoline.S +++ b/plat/nvidia/tegra/soc/t186/plat_trampoline.S @@ -42,18 +42,14 @@ /* CPU reset handler routine */ func tegra186_cpu_reset_handler /* - * The Memory Controller loses state during System Suspend. We - * use this information to decide if the reset handler is running - * after a System Suspend. Resume from system suspend requires - * restoring the entire state from TZDRAM to TZRAM. + * The TZRAM loses state during System Suspend. We use this + * information to decide if the reset handler is running after a + * System Suspend. Resume from system suspend requires restoring + * the entire state from TZDRAM to TZRAM. */ - mov x1, #TEGRA_MC_BASE - ldr w0, [x1, #MC_SECURITY_CFG3_0] - lsl x0, x0, #32 - ldr w0, [x1, #MC_SECURITY_CFG0_0] - adr x1, tegra186_cpu_reset_handler - cmp x0, x1 - beq boot_cpu + mov x0, #BL31_BASE + ldr x0, [x0] + cbnz x0, boot_cpu /* resume from system suspend */ mov x0, #BL31_BASE diff --git a/plat/rockchip/common/plat_pm.c b/plat/rockchip/common/plat_pm.c index 09c5397c..2d4dc99a 100644 --- a/plat/rockchip/common/plat_pm.c +++ b/plat/rockchip/common/plat_pm.c @@ -391,15 +391,6 @@ static void __dead2 rockchip_system_poweroff(void) rockchip_soc_system_off(); } -static void __dead2 rockchip_pd_pwr_down_wfi( - const psci_power_state_t *target_state) -{ - if (RK_SYSTEM_PWR_STATE(target_state) == PLAT_MAX_OFF_STATE) - rockchip_soc_sys_pd_pwr_dn_wfi(); - else - rockchip_soc_cores_pd_pwr_dn_wfi(target_state); -} - /******************************************************************************* * Export the platform handlers via plat_rockchip_psci_pm_ops. The rockchip * standard |