diff options
Diffstat (limited to 'plat/nvidia')
85 files changed, 4355 insertions, 4533 deletions
diff --git a/plat/nvidia/tegra/common/aarch64/tegra_helpers.S b/plat/nvidia/tegra/common/aarch64/tegra_helpers.S index 13ca6aaa2..6c8c4f018 100644 --- a/plat/nvidia/tegra/common/aarch64/tegra_helpers.S +++ b/plat/nvidia/tegra/common/aarch64/tegra_helpers.S @@ -1,14 +1,16 @@ /* * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ + #include <arch.h> #include <asm_macros.S> #include <assert_macros.S> -#include <cpu_macros.S> -#include <cortex_a53.h> #include <cortex_a57.h> +#include <cpu_macros.S> + #include <platform_def.h> #include <tegra_def.h> #include <tegra_platform.h> @@ -18,21 +20,16 @@ /******************************************************************************* * Implementation defined ACTLR_EL3 bit definitions ******************************************************************************/ -#define ACTLR_EL3_L2ACTLR_BIT (U(1) << 6) -#define ACTLR_EL3_L2ECTLR_BIT (U(1) << 5) -#define ACTLR_EL3_L2CTLR_BIT (U(1) << 4) -#define ACTLR_EL3_CPUECTLR_BIT (U(1) << 1) -#define ACTLR_EL3_CPUACTLR_BIT (U(1) << 0) -#define ACTLR_EL3_ENABLE_ALL_MASK (ACTLR_EL3_L2ACTLR_BIT | \ - ACTLR_EL3_L2ECTLR_BIT | \ - ACTLR_EL3_L2CTLR_BIT | \ - ACTLR_EL3_CPUECTLR_BIT | \ - ACTLR_EL3_CPUACTLR_BIT) -#define ACTLR_EL3_ENABLE_ALL_ACCESS (ACTLR_EL3_L2ACTLR_BIT | \ - ACTLR_EL3_L2ECTLR_BIT | \ - ACTLR_EL3_L2CTLR_BIT | \ - ACTLR_EL3_CPUECTLR_BIT | \ - ACTLR_EL3_CPUACTLR_BIT) +#define ACTLR_ELx_L2ACTLR_BIT (U(1) << 6) +#define ACTLR_ELx_L2ECTLR_BIT (U(1) << 5) +#define ACTLR_ELx_L2CTLR_BIT (U(1) << 4) +#define ACTLR_ELx_CPUECTLR_BIT (U(1) << 1) +#define ACTLR_ELx_CPUACTLR_BIT (U(1) << 0) +#define ACTLR_ELx_ENABLE_ALL_ACCESS (ACTLR_ELx_L2ACTLR_BIT | \ + ACTLR_ELx_L2ECTLR_BIT | \ + ACTLR_ELx_L2CTLR_BIT | \ + ACTLR_ELx_CPUECTLR_BIT | \ + ACTLR_ELx_CPUACTLR_BIT) /* Global functions */ .globl plat_is_my_cpu_primary @@ -43,6 +40,7 @@ .globl plat_crash_console_init .globl plat_crash_console_putc .globl plat_crash_console_flush + .weak plat_core_pos_by_mpidr .globl tegra_secure_entrypoint .globl plat_reset_handler @@ -93,15 +91,11 @@ * ------------------------------------------------------- */ mrs x0, actlr_el3 - mov x1, #ACTLR_EL3_ENABLE_ALL_MASK - bic x0, x0, x1 - mov x1, #ACTLR_EL3_ENABLE_ALL_ACCESS + mov x1, #ACTLR_ELx_ENABLE_ALL_ACCESS orr x0, x0, x1 msr actlr_el3, x0 mrs x0, actlr_el2 - mov x1, #ACTLR_EL3_ENABLE_ALL_MASK - bic x0, x0, x1 - mov x1, #ACTLR_EL3_ENABLE_ALL_ACCESS + mov x1, #ACTLR_ELx_ENABLE_ALL_ACCESS orr x0, x0, x1 msr actlr_el2, x0 isb @@ -148,17 +142,14 @@ endfunc plat_is_my_cpu_primary * unsigned int plat_my_core_pos(void); * * result: CorePos = CoreId + (ClusterId * cpus per cluster) + * Registers clobbered: x0, x8 * ---------------------------------------------------------- */ func plat_my_core_pos + mov x8, x30 mrs x0, mpidr_el1 - and x1, x0, #MPIDR_CPU_MASK - and x0, x0, #MPIDR_CLUSTER_MASK - lsr x0, x0, #MPIDR_AFFINITY_BITS - mov x2, #PLATFORM_MAX_CPUS_PER_CLUSTER - mul x0, x0, x2 - add x0, x1, x0 - ret + bl plat_core_pos_by_mpidr + ret x8 endfunc plat_my_core_pos /* ----------------------------------------------------- @@ -177,23 +168,6 @@ func plat_get_my_entrypoint endfunc plat_get_my_entrypoint /* ----------------------------------------------------- - * int platform_get_core_pos(int mpidr); - * - * result: CorePos = (ClusterId * cpus per cluster) + - * CoreId - * ----------------------------------------------------- - */ -func platform_get_core_pos - and x1, x0, #MPIDR_CPU_MASK - and x0, x0, #MPIDR_CLUSTER_MASK - lsr x0, x0, #MPIDR_AFFINITY_BITS - mov x2, #PLATFORM_MAX_CPUS_PER_CLUSTER - mul x0, x0, x2 - add x0, x1, x0 - ret -endfunc platform_get_core_pos - - /* ----------------------------------------------------- * void plat_secondary_cold_boot_setup (void); * * This function performs any platform specific actions @@ -241,7 +215,8 @@ func plat_reset_handler */ mov x0, x17 mov x1, x18 - mov x2, #BL31_SIZE + adr x2, __RELA_END__ + sub x2, x2, x18 _loop16: cmp x2, #16 b.lo _loop1 @@ -281,6 +256,42 @@ _end: mov x0, x20 ret endfunc plat_reset_handler + /* ------------------------------------------------------ + * int32_t plat_core_pos_by_mpidr(u_register_t mpidr) + * + * This function implements a part of the critical + * interface between the psci generic layer and the + * platform that allows the former to query the platform + * to convert an MPIDR to a unique linear index. An error + * code (-1) is returned in case the MPIDR is invalid. + * + * Clobbers: x0-x3 + * ------------------------------------------------------ + */ +func plat_core_pos_by_mpidr + lsr x1, x0, #MPIDR_AFF0_SHIFT + and x1, x1, #MPIDR_AFFLVL_MASK /* core id */ + lsr x2, x0, #MPIDR_AFF1_SHIFT + and x2, x2, #MPIDR_AFFLVL_MASK /* cluster id */ + + /* core_id >= PLATFORM_MAX_CPUS_PER_CLUSTER */ + mov x0, #-1 + cmp x1, #(PLATFORM_MAX_CPUS_PER_CLUSTER - 1) + b.gt 1f + + /* cluster_id >= PLATFORM_CLUSTER_COUNT */ + cmp x2, #(PLATFORM_CLUSTER_COUNT - 1) + b.gt 1f + + /* CorePos = CoreId + (ClusterId * cpus per cluster) */ + mov x3, #PLATFORM_MAX_CPUS_PER_CLUSTER + mul x3, x3, x2 + add x0, x1, x3 + +1: + ret +endfunc plat_core_pos_by_mpidr + /* ---------------------------------------- * Secure entrypoint function for CPU boot * ---------------------------------------- diff --git a/plat/nvidia/tegra/common/drivers/smmu/smmu.c b/plat/nvidia/tegra/common/drivers/smmu/smmu.c deleted file mode 100644 index 8c1b899f7..000000000 --- a/plat/nvidia/tegra/common/drivers/smmu/smmu.c +++ /dev/null @@ -1,177 +0,0 @@ -/* - * Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved. - * - * SPDX-License-Identifier: BSD-3-Clause - */ - -#include <assert.h> -#include <string.h> - -#include <platform_def.h> - -#include <common/bl_common.h> -#include <common/debug.h> - -#include <smmu.h> -#include <tegra_private.h> - -extern void memcpy16(void *dest, const void *src, unsigned int length); - -/* SMMU IDs currently supported by the driver */ -enum { - TEGRA_SMMU0 = 0U, - TEGRA_SMMU1, - TEGRA_SMMU2 -}; - -static uint32_t tegra_smmu_read_32(uint32_t smmu_id, uint32_t off) -{ - uint32_t ret = 0U; - -#if defined(TEGRA_SMMU0_BASE) - if (smmu_id == TEGRA_SMMU0) { - ret = mmio_read_32(TEGRA_SMMU0_BASE + (uint64_t)off); - } -#endif - -#if defined(TEGRA_SMMU1_BASE) - if (smmu_id == TEGRA_SMMU1) { - ret = mmio_read_32(TEGRA_SMMU1_BASE + (uint64_t)off); - } -#endif - -#if defined(TEGRA_SMMU2_BASE) - if (smmu_id == TEGRA_SMMU2) { - ret = mmio_read_32(TEGRA_SMMU2_BASE + (uint64_t)off); - } -#endif - - return ret; -} - -static void tegra_smmu_write_32(uint32_t smmu_id, - uint32_t off, uint32_t val) -{ -#if defined(TEGRA_SMMU0_BASE) - if (smmu_id == TEGRA_SMMU0) { - mmio_write_32(TEGRA_SMMU0_BASE + (uint64_t)off, val); - } -#endif - -#if defined(TEGRA_SMMU1_BASE) - if (smmu_id == TEGRA_SMMU1) { - mmio_write_32(TEGRA_SMMU1_BASE + (uint64_t)off, val); - } -#endif - -#if defined(TEGRA_SMMU2_BASE) - if (smmu_id == TEGRA_SMMU2) { - mmio_write_32(TEGRA_SMMU2_BASE + (uint64_t)off, val); - } -#endif -} - -/* - * Save SMMU settings before "System Suspend" to TZDRAM - */ -void tegra_smmu_save_context(uint64_t smmu_ctx_addr) -{ - uint32_t i, num_entries = 0; - smmu_regs_t *smmu_ctx_regs; - const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); - uint64_t tzdram_base = params_from_bl2->tzdram_base; - uint64_t tzdram_end = tzdram_base + params_from_bl2->tzdram_size; - uint32_t reg_id1, pgshift, cb_size; - - /* sanity check SMMU settings c*/ - reg_id1 = mmio_read_32((TEGRA_SMMU0_BASE + SMMU_GNSR0_IDR1)); - pgshift = ((reg_id1 & ID1_PAGESIZE) != 0U) ? 16U : 12U; - cb_size = ((uint32_t)2 << pgshift) * \ - ((uint32_t)1 << (((reg_id1 >> ID1_NUMPAGENDXB_SHIFT) & ID1_NUMPAGENDXB_MASK) + 1U)); - - assert(!((pgshift != PGSHIFT) || (cb_size != CB_SIZE))); - assert((smmu_ctx_addr >= tzdram_base) && (smmu_ctx_addr <= tzdram_end)); - - /* get SMMU context table */ - smmu_ctx_regs = plat_get_smmu_ctx(); - assert(smmu_ctx_regs != NULL); - - /* - * smmu_ctx_regs[0].val contains the size of the context table minus - * the last entry. Sanity check the table size before we start with - * the context save operation. - */ - while ((smmu_ctx_regs[num_entries].reg != 0xFFFFFFFFU)) { - num_entries++; - } - - /* panic if the sizes do not match */ - if (num_entries != smmu_ctx_regs[0].val) { - ERROR("SMMU context size mismatch!"); - panic(); - } - - /* save SMMU register values */ - for (i = 1U; i < num_entries; i++) { - smmu_ctx_regs[i].val = mmio_read_32(smmu_ctx_regs[i].reg); - } - - /* increment by 1 to take care of the last entry */ - num_entries++; - - /* Save SMMU config settings */ - (void)memcpy16((uint8_t *)smmu_ctx_addr, (uint8_t *)smmu_ctx_regs, - (sizeof(smmu_regs_t) * num_entries)); - - /* save the SMMU table address */ - mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_SMMU_TABLE_ADDR_LO, - (uint32_t)smmu_ctx_addr); - mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_SMMU_TABLE_ADDR_HI, - (uint32_t)(smmu_ctx_addr >> 32)); -} - -#define SMMU_NUM_CONTEXTS 64 -#define SMMU_CONTEXT_BANK_MAX_IDX 64 - -/* - * Init SMMU during boot or "System Suspend" exit - */ -void tegra_smmu_init(void) -{ - uint32_t val, cb_idx, smmu_id, ctx_base; - uint32_t smmu_counter = plat_get_num_smmu_devices(); - - for (smmu_id = 0U; smmu_id < smmu_counter; smmu_id++) { - /* Program the SMMU pagesize and reset CACHE_LOCK bit */ - val = tegra_smmu_read_32(smmu_id, SMMU_GSR0_SECURE_ACR); - val |= SMMU_GSR0_PGSIZE_64K; - val &= (uint32_t)~SMMU_ACR_CACHE_LOCK_ENABLE_BIT; - tegra_smmu_write_32(smmu_id, SMMU_GSR0_SECURE_ACR, val); - - /* reset CACHE LOCK bit for NS Aux. Config. Register */ - val = tegra_smmu_read_32(smmu_id, SMMU_GNSR_ACR); - val &= (uint32_t)~SMMU_ACR_CACHE_LOCK_ENABLE_BIT; - tegra_smmu_write_32(smmu_id, SMMU_GNSR_ACR, val); - - /* disable TCU prefetch for all contexts */ - ctx_base = (SMMU_GSR0_PGSIZE_64K * SMMU_NUM_CONTEXTS) - + SMMU_CBn_ACTLR; - for (cb_idx = 0; cb_idx < SMMU_CONTEXT_BANK_MAX_IDX; cb_idx++) { - val = tegra_smmu_read_32(smmu_id, - ctx_base + (SMMU_GSR0_PGSIZE_64K * cb_idx)); - val &= (uint32_t)~SMMU_CBn_ACTLR_CPRE_BIT; - tegra_smmu_write_32(smmu_id, ctx_base + - (SMMU_GSR0_PGSIZE_64K * cb_idx), val); - } - - /* set CACHE LOCK bit for NS Aux. Config. Register */ - val = tegra_smmu_read_32(smmu_id, SMMU_GNSR_ACR); - val |= (uint32_t)SMMU_ACR_CACHE_LOCK_ENABLE_BIT; - tegra_smmu_write_32(smmu_id, SMMU_GNSR_ACR, val); - - /* set CACHE LOCK bit for S Aux. Config. Register */ - val = tegra_smmu_read_32(smmu_id, SMMU_GSR0_SECURE_ACR); - val |= (uint32_t)SMMU_ACR_CACHE_LOCK_ENABLE_BIT; - tegra_smmu_write_32(smmu_id, SMMU_GSR0_SECURE_ACR, val); - } -} diff --git a/plat/nvidia/tegra/common/tegra_bl31_setup.c b/plat/nvidia/tegra/common/tegra_bl31_setup.c index cbe3377b0..cb4886f1a 100644 --- a/plat/nvidia/tegra/common/tegra_bl31_setup.c +++ b/plat/nvidia/tegra/common/tegra_bl31_setup.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -16,7 +17,6 @@ #include <bl31/bl31.h> #include <common/bl_common.h> #include <common/debug.h> -#include <cortex_a53.h> #include <cortex_a57.h> #include <denver.h> #include <drivers/console.h> @@ -27,6 +27,7 @@ #include <memctrl.h> #include <profiler.h> +#include <smmu.h> #include <tegra_def.h> #include <tegra_platform.h> #include <tegra_private.h> @@ -34,21 +35,12 @@ /* length of Trusty's input parameters (in bytes) */ #define TRUSTY_PARAMS_LEN_BYTES (4096*2) -extern void memcpy16(void *dest, const void *src, unsigned int length); - /******************************************************************************* * Declarations of linker defined symbols which will help us find the layout * of trusted SRAM ******************************************************************************/ - IMPORT_SYM(uint64_t, __RW_START__, BL31_RW_START); -static const uint64_t BL31_RW_END = BL_END; -static const uint64_t BL31_RODATA_BASE = BL_RO_DATA_BASE; -static const uint64_t BL31_RODATA_END = BL_RO_DATA_END; -static const uint64_t TEXT_START = BL_CODE_BASE; -static const uint64_t TEXT_END = BL_CODE_END; - extern uint64_t tegra_bl31_phys_base; static entry_point_info_t bl33_image_ep_info, bl32_image_ep_info; @@ -65,35 +57,6 @@ static aapcs64_params_t bl32_args; extern uint64_t ns_image_entrypoint; /******************************************************************************* - * The following platform setup functions are weakly defined. They - * provide typical implementations that will be overridden by a SoC. - ******************************************************************************/ -#pragma weak plat_early_platform_setup -#pragma weak plat_get_bl31_params -#pragma weak plat_get_bl31_plat_params -#pragma weak plat_late_platform_setup - -void plat_early_platform_setup(void) -{ - ; /* do nothing */ -} - -struct tegra_bl31_params *plat_get_bl31_params(void) -{ - return NULL; -} - -plat_params_from_bl2_t *plat_get_bl31_plat_params(void) -{ - return NULL; -} - -void plat_late_platform_setup(void) -{ - ; /* do nothing */ -} - -/******************************************************************************* * Return a pointer to the 'entry_point_info' structure of the next image for * security state specified. BL33 corresponds to the non-secure image type * while BL32 corresponds to the secure image type. @@ -130,15 +93,12 @@ void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1, { struct tegra_bl31_params *arg_from_bl2 = (struct tegra_bl31_params *) arg0; plat_params_from_bl2_t *plat_params = (plat_params_from_bl2_t *)arg1; - image_info_t bl32_img_info = { {0} }; - uint64_t tzdram_start, tzdram_end, bl32_start, bl32_end; int32_t ret; /* * For RESET_TO_BL31 systems, BL31 is the first bootloader to run so * there's no argument to relay from a previous bootloader. Platforms - * might use custom ways to get arguments, so provide handlers which - * they can override. + * might use custom ways to get arguments. */ if (arg_from_bl2 == NULL) { arg_from_bl2 = plat_get_bl31_params(); @@ -193,20 +153,17 @@ void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1, * location to store the boot profiler logs. Sanity check the * address and initialise the profiler library, if it looks ok. */ - if (plat_params->boot_profiler_shmem_base != 0ULL) { + ret = bl31_check_ns_address(plat_params->boot_profiler_shmem_base, + PROFILER_SIZE_BYTES); + if (ret == (int32_t)0) { - ret = bl31_check_ns_address(plat_params->boot_profiler_shmem_base, - PROFILER_SIZE_BYTES); - if (ret == (int32_t)0) { + /* store the membase for the profiler lib */ + plat_bl31_params_from_bl2.boot_profiler_shmem_base = + plat_params->boot_profiler_shmem_base; - /* store the membase for the profiler lib */ - plat_bl31_params_from_bl2.boot_profiler_shmem_base = - plat_params->boot_profiler_shmem_base; - - /* initialise the profiler library */ - boot_profiler_init(plat_params->boot_profiler_shmem_base, - TEGRA_TMRUS_BASE); - } + /* initialise the profiler library */ + boot_profiler_init(plat_params->boot_profiler_shmem_base, + TEGRA_TMRUS_BASE); } /* @@ -223,48 +180,6 @@ void bl31_early_platform_setup2(u_register_t arg0, u_register_t arg1, plat_early_platform_setup(); /* - * Do initial security configuration to allow DRAM/device access. - */ - tegra_memctrl_tzdram_setup(plat_bl31_params_from_bl2.tzdram_base, - (uint32_t)plat_bl31_params_from_bl2.tzdram_size); - - /* - * The previous bootloader might not have placed the BL32 image - * inside the TZDRAM. We check the BL32 image info to find out - * the base/PC values and relocate the image if necessary. - */ - if (arg_from_bl2->bl32_image_info != NULL) { - - bl32_img_info = *arg_from_bl2->bl32_image_info; - - /* Relocate BL32 if it resides outside of the TZDRAM */ - tzdram_start = plat_bl31_params_from_bl2.tzdram_base; - tzdram_end = plat_bl31_params_from_bl2.tzdram_base + - plat_bl31_params_from_bl2.tzdram_size; - bl32_start = bl32_img_info.image_base; - bl32_end = bl32_img_info.image_base + bl32_img_info.image_size; - - assert(tzdram_end > tzdram_start); - assert(bl32_end > bl32_start); - assert(bl32_image_ep_info.pc > tzdram_start); - assert(bl32_image_ep_info.pc < tzdram_end); - - /* relocate BL32 */ - if ((bl32_start >= tzdram_end) || (bl32_end <= tzdram_start)) { - - INFO("Relocate BL32 to TZDRAM\n"); - - (void)memcpy16((void *)(uintptr_t)bl32_image_ep_info.pc, - (void *)(uintptr_t)bl32_start, - bl32_img_info.image_size); - - /* clean up non-secure intermediate buffer */ - zeromem((void *)(uintptr_t)bl32_start, - bl32_img_info.image_size); - } - } - - /* * Add timestamp for platform early setup exit. */ boot_profiler_add_record("[TF] early setup exit"); @@ -318,12 +233,6 @@ void bl31_platform_setup(void) tegra_memctrl_setup(); /* - * Set up the TZRAM memory aperture to allow only secure world - * access - */ - tegra_memctrl_tzram_setup(TEGRA_TZRAM_BASE, TEGRA_TZRAM_SIZE); - - /* * Late setup handler to allow platforms to performs additional * functionality. * This handler gets called with MMU enabled. @@ -344,24 +253,9 @@ void bl31_platform_setup(void) void bl31_plat_runtime_setup(void) { /* - * During cold boot, it is observed that the arbitration - * bit is set in the Memory controller leading to false - * error interrupts in the non-secure world. To avoid - * this, clean the interrupt status register before - * booting into the non-secure world + * Platform specific runtime setup */ - tegra_memctrl_clear_pending_interrupts(); - - /* - * During boot, USB3 and flash media (SDMMC/SATA) devices need - * access to IRAM. Because these clients connect to the MC and - * do not have a direct path to the IRAM, the MC implements AHB - * redirection during boot to allow path to IRAM. In this mode - * accesses to a programmed memory address aperture are directed - * to the AHB bus, allowing access to the IRAM. This mode must be - * disabled before we jump to the non-secure world. - */ - tegra_memctrl_disable_ahb_redirection(); + plat_runtime_setup(); /* * Add final timestamp before exiting BL31. @@ -377,15 +271,12 @@ void bl31_plat_runtime_setup(void) void bl31_plat_arch_setup(void) { uint64_t rw_start = BL31_RW_START; - uint64_t rw_size = BL31_RW_END - BL31_RW_START; - uint64_t rodata_start = BL31_RODATA_BASE; - uint64_t rodata_size = BL31_RODATA_END - BL31_RODATA_BASE; - uint64_t code_base = TEXT_START; - uint64_t code_size = TEXT_END - TEXT_START; + uint64_t rw_size = BL_END - BL31_RW_START; + uint64_t rodata_start = BL_RO_DATA_BASE; + uint64_t rodata_size = BL_RO_DATA_END - BL_RO_DATA_BASE; + uint64_t code_base = BL_CODE_BASE; + uint64_t code_size = BL_CODE_END - BL_CODE_BASE; const mmap_region_t *plat_mmio_map = NULL; -#if USE_COHERENT_MEM - uint32_t coh_start, coh_size; -#endif const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); /* @@ -412,15 +303,6 @@ void bl31_plat_arch_setup(void) code_size, MT_CODE | MT_SECURE); -#if USE_COHERENT_MEM - coh_start = total_base + (BL_COHERENT_RAM_BASE - BL31_RO_BASE); - coh_size = BL_COHERENT_RAM_END - BL_COHERENT_RAM_BASE; - - mmap_add_region(coh_start, coh_start, - coh_size, - (uint8_t)MT_DEVICE | (uint8_t)MT_RW | (uint8_t)MT_SECURE); -#endif - /* map TZDRAM used by BL31 as coherent memory */ if (TEGRA_TZRAM_BASE == tegra_bl31_phys_base) { mmap_add_region(params_from_bl2->tzdram_base, @@ -449,7 +331,15 @@ void bl31_plat_arch_setup(void) int32_t bl31_check_ns_address(uint64_t base, uint64_t size_in_bytes) { uint64_t end = base + size_in_bytes - U(1); - int32_t ret = 0; + + /* + * Sanity check the input values + */ + if ((base == 0U) || (size_in_bytes == 0U)) { + ERROR("NS address 0x%llx (%lld bytes) is invalid\n", + base, size_in_bytes); + return -EINVAL; + } /* * Check if the NS DRAM address is valid @@ -458,7 +348,7 @@ int32_t bl31_check_ns_address(uint64_t base, uint64_t size_in_bytes) (end > TEGRA_DRAM_END)) { ERROR("NS address 0x%llx is out-of-bounds!\n", base); - ret = -EFAULT; + return -EFAULT; } /* @@ -467,9 +357,9 @@ int32_t bl31_check_ns_address(uint64_t base, uint64_t size_in_bytes) */ if ((base < (uint64_t)TZDRAM_END) && (end > tegra_bl31_phys_base)) { ERROR("NS address 0x%llx overlaps TZDRAM!\n", base); - ret = -ENOTSUP; + return -ENOTSUP; } /* valid NS address */ - return ret; + return 0; } diff --git a/plat/nvidia/tegra/common/tegra_common.mk b/plat/nvidia/tegra/common/tegra_common.mk index 34b5638ec..37910181c 100644 --- a/plat/nvidia/tegra/common/tegra_common.mk +++ b/plat/nvidia/tegra/common/tegra_common.mk @@ -1,37 +1,59 @@ # -# Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2020, NVIDIA Corporation. All rights reserved. # # SPDX-License-Identifier: BSD-3-Clause # PLAT_INCLUDES := -Iplat/nvidia/tegra/include/drivers \ -Iplat/nvidia/tegra/include/lib \ - -Iplat/nvidia/tegra/include \ - -Iplat/nvidia/tegra/include/${TARGET_SOC} + -Iplat/nvidia/tegra/include include lib/xlat_tables_v2/xlat_tables.mk PLAT_BL_COMMON_SOURCES += ${XLAT_TABLES_LIB_SRCS} -COMMON_DIR := plat/nvidia/tegra/common +TEGRA_COMMON := plat/nvidia/tegra/common +TEGRA_DRIVERS := plat/nvidia/tegra/drivers +TEGRA_LIBS := plat/nvidia/tegra/lib -TEGRA_GICv2_SOURCES := drivers/arm/gic/common/gic_common.c \ - drivers/arm/gic/v2/gicv2_main.c \ - drivers/arm/gic/v2/gicv2_helpers.c \ +# Include GICv3 driver files +include drivers/arm/gic/v3/gicv3.mk +TEGRA_GICv3_SOURCES := $(GICV3_SOURCES) \ + plat/common/plat_gicv3.c \ + ${TEGRA_COMMON}/tegra_gicv3.c + +# Include GICv2 driver files +include drivers/arm/gic/v2/gicv2.mk + +TEGRA_GICv2_SOURCES := ${GICV2_SOURCES} \ plat/common/plat_gicv2.c \ - ${COMMON_DIR}/tegra_gicv2.c + ${TEGRA_COMMON}/tegra_gicv2.c + +TEGRA_GICv3_SOURCES := drivers/arm/gic/common/gic_common.c \ + drivers/arm/gic/v3/arm_gicv3_common.c \ + drivers/arm/gic/v3/gicv3_main.c \ + drivers/arm/gic/v3/gicv3_helpers.c \ + plat/common/plat_gicv3.c \ + ${TEGRA_COMMON}/tegra_gicv3.c BL31_SOURCES += drivers/delay_timer/delay_timer.c \ drivers/io/io_storage.c \ plat/common/aarch64/crash_console_helpers.S \ - ${TEGRA_GICv2_SOURCES} \ - ${COMMON_DIR}/aarch64/tegra_helpers.S \ - ${COMMON_DIR}/drivers/pmc/pmc.c \ - ${COMMON_DIR}/lib/debug/profiler.c \ - ${COMMON_DIR}/tegra_bl31_setup.c \ - ${COMMON_DIR}/tegra_delay_timer.c \ - ${COMMON_DIR}/tegra_fiq_glue.c \ - ${COMMON_DIR}/tegra_io_storage.c \ - ${COMMON_DIR}/tegra_platform.c \ - ${COMMON_DIR}/tegra_pm.c \ - ${COMMON_DIR}/tegra_sip_calls.c \ - ${COMMON_DIR}/tegra_topology.c + ${TEGRA_LIBS}/debug/profiler.c \ + ${TEGRA_COMMON}/aarch64/tegra_helpers.S \ + ${TEGRA_LIBS}/debug/profiler.c \ + ${TEGRA_COMMON}/tegra_bl31_setup.c \ + ${TEGRA_COMMON}/tegra_delay_timer.c \ + ${TEGRA_COMMON}/tegra_fiq_glue.c \ + ${TEGRA_COMMON}/tegra_io_storage.c \ + ${TEGRA_COMMON}/tegra_platform.c \ + ${TEGRA_COMMON}/tegra_pm.c \ + ${TEGRA_COMMON}/tegra_sip_calls.c \ + ${TEGRA_COMMON}/tegra_sdei.c + +ifneq ($(ENABLE_STACK_PROTECTOR), 0) +BL31_SOURCES += ${TEGRA_COMMON}/tegra_stack_protector.c +endif +ifeq (${EL3_EXCEPTION_HANDLING},1) +BL31_SOURCES += plat/common/aarch64/plat_ehf.c +endif diff --git a/plat/nvidia/tegra/common/tegra_delay_timer.c b/plat/nvidia/tegra/common/tegra_delay_timer.c index 63dcf410c..d9547c4a3 100644 --- a/plat/nvidia/tegra/common/tegra_delay_timer.c +++ b/plat/nvidia/tegra/common/tegra_delay_timer.c @@ -1,31 +1,57 @@ /* * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ +#include <arch.h> + #include <drivers/delay_timer.h> #include <lib/mmio.h> +#include <lib/utils_def.h> +#include <plat/common/platform.h> #include <tegra_def.h> #include <tegra_private.h> -static uint32_t tegra_timerus_get_value(void) +static uint32_t tegra_timer_get_value(void) { - return mmio_read_32(TEGRA_TMRUS_BASE); + /* enable cntps_tval_el1 timer, mask interrupt */ + write_cntps_ctl_el1(CNTP_CTL_IMASK_BIT | CNTP_CTL_ENABLE_BIT); + + /* + * Generic delay timer implementation expects the timer to be a down + * counter. The value is clipped from 64 to 32 bits. + */ + return (uint32_t)(read_cntps_tval_el1()); } /* - * Initialise the on-chip free rolling us counter as the delay - * timer. + * Initialise the architecture provided counter as the delay timer. */ void tegra_delay_timer_init(void) { - static const timer_ops_t tegra_timer_ops = { - .get_timer_value = tegra_timerus_get_value, - .clk_mult = 1, - .clk_div = 1, - }; + static timer_ops_t tegra_timer_ops; + + /* Value in ticks */ + uint32_t multiplier = MHZ_TICKS_PER_SEC; + + /* Value in ticks per second (Hz) */ + uint32_t divider = plat_get_syscnt_freq2(); + + /* Reduce multiplier and divider by dividing them repeatedly by 10 */ + while (((multiplier % 10U) == 0U) && ((divider % 10U) == 0U)) { + multiplier /= 10U; + divider /= 10U; + } + + /* enable cntps_tval_el1 timer, mask interrupt */ + write_cntps_ctl_el1(CNTP_CTL_IMASK_BIT | CNTP_CTL_ENABLE_BIT); + /* register the timer */ + tegra_timer_ops.get_timer_value = tegra_timer_get_value; + tegra_timer_ops.clk_mult = multiplier; + tegra_timer_ops.clk_div = divider; timer_init(&tegra_timer_ops); } diff --git a/plat/nvidia/tegra/common/tegra_fiq_glue.c b/plat/nvidia/tegra/common/tegra_fiq_glue.c index 60b559556..5309d98cd 100644 --- a/plat/nvidia/tegra/common/tegra_fiq_glue.c +++ b/plat/nvidia/tegra/common/tegra_fiq_glue.c @@ -1,5 +1,6 @@ /* - * Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -8,11 +9,11 @@ #include <arch_helpers.h> #include <bl31/interrupt_mgmt.h> +#include <bl31/ehf.h> #include <common/bl_common.h> #include <common/debug.h> #include <context.h> #include <denver.h> -#include <lib/bakery_lock.h> #include <lib/el3_runtime/context_mgmt.h> #include <plat/common/platform.h> @@ -25,8 +26,6 @@ /* Legacy FIQ used by earlier Tegra platforms */ #define LEGACY_FIQ_PPI_WDT 28U -static DEFINE_BAKERY_LOCK(tegra_fiq_lock); - /******************************************************************************* * Static variables ******************************************************************************/ @@ -37,29 +36,18 @@ static pcpu_fiq_state_t fiq_state[PLATFORM_CORE_COUNT]; /******************************************************************************* * Handler for FIQ interrupts ******************************************************************************/ -static uint64_t tegra_fiq_interrupt_handler(uint32_t id, - uint32_t flags, - void *handle, - void *cookie) +static int tegra_fiq_interrupt_handler(unsigned int id, unsigned int flags, + void *handle, void *cookie) { cpu_context_t *ctx = cm_get_context(NON_SECURE); el3_state_t *el3state_ctx = get_el3state_ctx(ctx); uint32_t cpu = plat_my_core_pos(); - uint32_t irq; - (void)id; (void)flags; (void)handle; (void)cookie; /* - * Read the pending interrupt ID - */ - irq = plat_ic_get_pending_interrupt_id(); - - bakery_lock_get(&tegra_fiq_lock); - - /* * Jump to NS world only if the NS world's FIQ handler has * been registered */ @@ -94,7 +82,7 @@ static uint64_t tegra_fiq_interrupt_handler(uint32_t id, * disable the routing so that we can mark it as "complete" in the * GIC later. */ - if (irq == LEGACY_FIQ_PPI_WDT) { + if (id == LEGACY_FIQ_PPI_WDT) { tegra_fc_disable_fiq_to_ccplex_routing(); } #endif @@ -102,12 +90,7 @@ static uint64_t tegra_fiq_interrupt_handler(uint32_t id, /* * Mark this interrupt as complete to avoid a FIQ storm. */ - if (irq < 1022U) { - (void)plat_ic_acknowledge_interrupt(); - plat_ic_end_of_interrupt(irq); - } - - bakery_lock_release(&tegra_fiq_lock); + plat_ic_end_of_interrupt(id); return 0; } @@ -117,23 +100,13 @@ static uint64_t tegra_fiq_interrupt_handler(uint32_t id, ******************************************************************************/ void tegra_fiq_handler_setup(void) { - uint32_t flags; - int32_t rc; - /* return if already registered */ if (fiq_handler_active == 0U) { /* * Register an interrupt handler for FIQ interrupts generated for * NS interrupt sources */ - flags = 0U; - set_interrupt_rm_flag((flags), (NON_SECURE)); - rc = register_interrupt_type_handler(INTR_TYPE_EL3, - tegra_fiq_interrupt_handler, - flags); - if (rc != 0) { - panic(); - } + ehf_register_priority_handler(PLAT_TEGRA_WDT_PRIO, tegra_fiq_interrupt_handler); /* handler is now active */ fiq_handler_active = 1; @@ -155,7 +128,7 @@ int32_t tegra_fiq_get_intr_context(void) { cpu_context_t *ctx = cm_get_context(NON_SECURE); gp_regs_t *gpregs_ctx = get_gpregs_ctx(ctx); - const el1_sys_regs_t *el1state_ctx = get_sysregs_ctx(ctx); + const el1_sysregs_t *el1state_ctx = get_el1_sysregs_ctx(ctx); uint32_t cpu = plat_my_core_pos(); uint64_t val; diff --git a/plat/nvidia/tegra/common/tegra_gicv2.c b/plat/nvidia/tegra/common/tegra_gicv2.c index 293df8d4f..012107e3b 100644 --- a/plat/nvidia/tegra/common/tegra_gicv2.c +++ b/plat/nvidia/tegra/common/tegra_gicv2.c @@ -1,20 +1,23 @@ /* * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ #include <assert.h> - #include <platform_def.h> #include <common/bl_common.h> #include <drivers/arm/gicv2.h> #include <lib/utils.h> +#include <plat/common/platform.h> #include <tegra_private.h> #include <tegra_def.h> +static unsigned int tegra_target_masks[PLATFORM_CORE_COUNT]; + /****************************************************************************** * Tegra common helper to setup the GICv2 driver data. *****************************************************************************/ @@ -33,6 +36,8 @@ void tegra_gic_setup(const interrupt_prop_t *interrupt_props, tegra_gic_data.gicc_base = TEGRA_GICC_BASE; tegra_gic_data.interrupt_props = interrupt_props; tegra_gic_data.interrupt_props_num = interrupt_props_num; + tegra_gic_data.target_masks = tegra_target_masks; + tegra_gic_data.target_masks_num = ARRAY_SIZE(tegra_target_masks); gicv2_driver_init(&tegra_gic_data); } @@ -43,6 +48,7 @@ void tegra_gic_init(void) { gicv2_distif_init(); gicv2_pcpu_distif_init(); + gicv2_set_pe_target_mask(plat_my_core_pos()); gicv2_cpuif_enable(); } @@ -61,5 +67,6 @@ void tegra_gic_cpuif_deactivate(void) void tegra_gic_pcpu_init(void) { gicv2_pcpu_distif_init(); + gicv2_set_pe_target_mask(plat_my_core_pos()); gicv2_cpuif_enable(); } diff --git a/plat/nvidia/tegra/common/tegra_gicv3.c b/plat/nvidia/tegra/common/tegra_gicv3.c new file mode 100644 index 000000000..cba2f9b95 --- /dev/null +++ b/plat/nvidia/tegra/common/tegra_gicv3.c @@ -0,0 +1,79 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <assert.h> + +#include <common/bl_common.h> +#include <drivers/arm/gicv3.h> +#include <lib/utils.h> + +#include <plat/common/platform.h> +#include <platform_def.h> +#include <tegra_private.h> +#include <tegra_def.h> + +/* The GICv3 driver only needs to be initialized in EL3 */ +static uintptr_t rdistif_base_addrs[PLATFORM_CORE_COUNT]; + +static unsigned int plat_tegra_mpidr_to_core_pos(unsigned long mpidr) +{ + return (unsigned int)plat_core_pos_by_mpidr(mpidr); +} + +/****************************************************************************** + * Tegra common helper to setup the GICv3 driver data. + *****************************************************************************/ +void tegra_gic_setup(const interrupt_prop_t *interrupt_props, + unsigned int interrupt_props_num) +{ + /* + * Tegra GIC configuration settings + */ + static gicv3_driver_data_t tegra_gic_data; + + /* + * Register Tegra GICv3 driver + */ + tegra_gic_data.gicd_base = TEGRA_GICD_BASE; + tegra_gic_data.gicr_base = TEGRA_GICR_BASE; + tegra_gic_data.rdistif_num = PLATFORM_CORE_COUNT; + tegra_gic_data.rdistif_base_addrs = rdistif_base_addrs; + tegra_gic_data.mpidr_to_core_pos = plat_tegra_mpidr_to_core_pos; + tegra_gic_data.interrupt_props = interrupt_props; + tegra_gic_data.interrupt_props_num = interrupt_props_num; + gicv3_driver_init(&tegra_gic_data); + + /* initialize the GICD and GICR */ + tegra_gic_init(); +} + +/****************************************************************************** + * Tegra common helper to initialize the GICv3 only driver. + *****************************************************************************/ +void tegra_gic_init(void) +{ + gicv3_distif_init(); + gicv3_rdistif_init(plat_my_core_pos()); + gicv3_cpuif_enable(plat_my_core_pos()); +} + +/****************************************************************************** + * Tegra common helper to disable the GICv3 CPU interface + *****************************************************************************/ +void tegra_gic_cpuif_deactivate(void) +{ + gicv3_cpuif_disable(plat_my_core_pos()); +} + +/****************************************************************************** + * Tegra common helper to initialize the per cpu distributor interface + * in GICv3 + *****************************************************************************/ +void tegra_gic_pcpu_init(void) +{ + gicv3_rdistif_init(plat_my_core_pos()); + gicv3_cpuif_enable(plat_my_core_pos()); +} diff --git a/plat/nvidia/tegra/common/tegra_platform.c b/plat/nvidia/tegra/common/tegra_platform.c index c1e420959..d45d9886f 100644 --- a/plat/nvidia/tegra/common/tegra_platform.c +++ b/plat/nvidia/tegra/common/tegra_platform.c @@ -1,5 +1,6 @@ /* - * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2016-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -7,6 +8,8 @@ #include <arch_helpers.h> #include <assert.h> #include <lib/mmio.h> +#include <lib/smccc.h> +#include <services/arm_arch_svc.h> #include <tegra_def.h> #include <tegra_platform.h> #include <tegra_private.h> @@ -105,6 +108,13 @@ bool tegra_chipid_is_t210_b01(void) return (tegra_chipid_is_t210() && (tegra_get_chipid_major() == 0x2U)); } +bool tegra_chipid_is_t194(void) +{ + uint32_t chip_id = (tegra_get_chipid() >> CHIP_ID_SHIFT) & CHIP_ID_MASK; + + return (chip_id == TEGRA_CHIPID_TEGRA19); +} + /* * Read the chip ID value and derive the platform */ @@ -259,3 +269,47 @@ bool tegra_platform_is_virt_dev_kit(void) { return ((tegra_get_platform() == TEGRA_PLATFORM_VIRT_DEV_KIT) ? true : false); } + +/* + * This function returns soc version which mainly consist of below fields + * + * soc_version[30:24] = JEP-106 continuation code for the SiP + * soc_version[23:16] = JEP-106 identification code with parity bit for the SiP + * soc_version[0:15] = chip identification + */ +int32_t plat_get_soc_version(void) +{ + uint32_t chip_id = ((tegra_get_chipid() >> CHIP_ID_SHIFT) & CHIP_ID_MASK); + uint32_t manfid = (JEDEC_NVIDIA_BKID << 24) | (JEDEC_NVIDIA_MFID << 16); + + return (int32_t)(manfid | (chip_id & 0xFFFF)); +} + +/* + * This function returns soc revision in below format + * + * soc_revision[8:15] = major version number + * soc_revision[0:7] = minor version number + */ +int32_t plat_get_soc_revision(void) +{ + return (int32_t)((tegra_get_chipid_major() << 8) | tegra_get_chipid_minor()); +} + +/***************************************************************************** + * plat_is_smccc_feature_available() - This function checks whether SMCCC feature + * is availabile for the platform or not. + * @fid: SMCCC function id + * + * Return SMC_ARCH_CALL_SUCCESS if SMCCC feature is available and + * SMC_ARCH_CALL_NOT_SUPPORTED otherwise. + *****************************************************************************/ +int32_t plat_is_smccc_feature_available(u_register_t fid) +{ + switch (fid) { + case SMCCC_ARCH_SOC_ID: + return SMC_ARCH_CALL_SUCCESS; + default: + return SMC_ARCH_CALL_NOT_SUPPORTED; + } +} diff --git a/plat/nvidia/tegra/common/tegra_pm.c b/plat/nvidia/tegra/common/tegra_pm.c index 39dc42c5b..ec34a850d 100644 --- a/plat/nvidia/tegra/common/tegra_pm.c +++ b/plat/nvidia/tegra/common/tegra_pm.c @@ -1,5 +1,6 @@ /* - * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -27,104 +28,13 @@ extern uint64_t tegra_bl31_phys_base; extern uint64_t tegra_sec_entry_point; -/* - * The following platform setup functions are weakly defined. They - * provide typical implementations that will be overridden by a SoC. - */ -#pragma weak tegra_soc_pwr_domain_suspend_pwrdown_early -#pragma weak tegra_soc_cpu_standby -#pragma weak tegra_soc_pwr_domain_suspend -#pragma weak tegra_soc_pwr_domain_on -#pragma weak tegra_soc_pwr_domain_off -#pragma weak tegra_soc_pwr_domain_on_finish -#pragma weak tegra_soc_pwr_domain_power_down_wfi -#pragma weak tegra_soc_prepare_system_reset -#pragma weak tegra_soc_prepare_system_off -#pragma weak tegra_soc_get_target_pwr_state - -int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state) -{ - return PSCI_E_NOT_SUPPORTED; -} - -int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state) -{ - (void)cpu_state; - return PSCI_E_SUCCESS; -} - -int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) -{ - (void)target_state; - return PSCI_E_NOT_SUPPORTED; -} - -int32_t tegra_soc_pwr_domain_on(u_register_t mpidr) -{ - (void)mpidr; - return PSCI_E_SUCCESS; -} - -int32_t tegra_soc_pwr_domain_off(const psci_power_state_t *target_state) -{ - (void)target_state; - return PSCI_E_SUCCESS; -} - -int32_t tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) -{ - (void)target_state; - return PSCI_E_SUCCESS; -} - -int32_t tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state) -{ - (void)target_state; - return PSCI_E_SUCCESS; -} - -int32_t tegra_soc_prepare_system_reset(void) -{ - return PSCI_E_SUCCESS; -} - -__dead2 void tegra_soc_prepare_system_off(void) -{ - ERROR("Tegra System Off: operation not handled.\n"); - panic(); -} - -plat_local_state_t tegra_soc_get_target_pwr_state(uint32_t lvl, - const plat_local_state_t *states, - uint32_t ncpu) -{ - plat_local_state_t target = PLAT_MAX_OFF_STATE, temp; - uint32_t num_cpu = ncpu; - const plat_local_state_t *local_state = states; - - (void)lvl; - - assert(ncpu != 0U); - - do { - temp = *local_state; - if ((temp < target)) { - target = temp; - } - --num_cpu; - local_state++; - } while (num_cpu != 0U); - - return target; -} - /******************************************************************************* * This handler is called by the PSCI implementation during the `SYSTEM_SUSPEND` * call to get the `power_state` parameter. This allows the platform to encode * the appropriate State-ID field within the `power_state` parameter which can * be utilized in `pwr_domain_suspend()` to suspend to system affinity level. ******************************************************************************/ -void tegra_get_sys_suspend_power_state(psci_power_state_t *req_state) +static void tegra_get_sys_suspend_power_state(psci_power_state_t *req_state) { /* all affinities use system suspend state id */ for (uint32_t i = MPIDR_AFFLVL0; i <= PLAT_MAX_PWR_LVL; i++) { @@ -135,7 +45,7 @@ void tegra_get_sys_suspend_power_state(psci_power_state_t *req_state) /******************************************************************************* * Handler called when an affinity instance is about to enter standby. ******************************************************************************/ -void tegra_cpu_standby(plat_local_state_t cpu_state) +static void tegra_cpu_standby(plat_local_state_t cpu_state) { u_register_t saved_scr_el3; @@ -174,7 +84,7 @@ void tegra_cpu_standby(plat_local_state_t cpu_state) * Handler called when an affinity instance is about to be turned on. The * level and mpidr determine the affinity instance. ******************************************************************************/ -int32_t tegra_pwr_domain_on(u_register_t mpidr) +static int32_t tegra_pwr_domain_on(u_register_t mpidr) { return tegra_soc_pwr_domain_on(mpidr); } @@ -183,9 +93,12 @@ int32_t tegra_pwr_domain_on(u_register_t mpidr) * Handler called when a power domain is about to be turned off. The * target_state encodes the power state that each level should transition to. ******************************************************************************/ -void tegra_pwr_domain_off(const psci_power_state_t *target_state) +static void tegra_pwr_domain_off(const psci_power_state_t *target_state) { (void)tegra_soc_pwr_domain_off(target_state); + + /* disable GICC */ + tegra_gic_cpuif_deactivate(); } /******************************************************************************* @@ -203,17 +116,10 @@ void tegra_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_sta * Handler called when a power domain is about to be suspended. The * target_state encodes the power state that each level should transition to. ******************************************************************************/ -void tegra_pwr_domain_suspend(const psci_power_state_t *target_state) +static void tegra_pwr_domain_suspend(const psci_power_state_t *target_state) { (void)tegra_soc_pwr_domain_suspend(target_state); - /* Disable console if we are entering deep sleep. */ - if (target_state->pwr_domain_state[PLAT_MAX_PWR_LVL] == - PSTATE_ID_SOC_POWERDN) { - (void)console_flush(); - console_switch_state(0); - } - /* disable GICC */ tegra_gic_cpuif_deactivate(); } @@ -222,12 +128,20 @@ void tegra_pwr_domain_suspend(const psci_power_state_t *target_state) * Handler called at the end of the power domain suspend sequence. The * target_state encodes the power state that each level should transition to. ******************************************************************************/ -__dead2 void tegra_pwr_domain_power_down_wfi(const psci_power_state_t +static __dead2 void tegra_pwr_domain_power_down_wfi(const psci_power_state_t *target_state) { /* call the chip's power down handler */ (void)tegra_soc_pwr_domain_power_down_wfi(target_state); + /* Disable console if we are entering deep sleep. */ + if (target_state->pwr_domain_state[PLAT_MAX_PWR_LVL] == + PSTATE_ID_SOC_POWERDN) { + INFO("%s: complete. Entering System Suspend...\n", __func__); + console_flush(); + console_switch_state(0); + } + wfi(); panic(); } @@ -237,21 +151,23 @@ __dead2 void tegra_pwr_domain_power_down_wfi(const psci_power_state_t * being turned off earlier. The target_state encodes the low power state that * each level has woken up from. ******************************************************************************/ -void tegra_pwr_domain_on_finish(const psci_power_state_t *target_state) +static void tegra_pwr_domain_on_finish(const psci_power_state_t *target_state) { const plat_params_from_bl2_t *plat_params; /* - * Initialize the GIC cpu and distributor interfaces - */ - tegra_gic_pcpu_init(); - - /* * Check if we are exiting from deep sleep. */ if (target_state->pwr_domain_state[PLAT_MAX_PWR_LVL] == PSTATE_ID_SOC_POWERDN) { + /* + * On entering System Suspend state, the GIC loses power + * completely. Initialize the GIC global distributor and + * GIC cpu interfaces. + */ + tegra_gic_init(); + /* Restart console output. */ console_switch_state(CONSOLE_FLAG_RUNTIME); @@ -268,11 +184,11 @@ void tegra_pwr_domain_on_finish(const psci_power_state_t *target_state) tegra_memctrl_tzdram_setup(plat_params->tzdram_base, (uint32_t)plat_params->tzdram_size); + } else { /* - * Set up the TZRAM memory aperture to allow only secure world - * access + * Initialize the GIC cpu and distributor interfaces */ - tegra_memctrl_tzram_setup(TEGRA_TZRAM_BASE, TEGRA_TZRAM_SIZE); + tegra_gic_pcpu_init(); } /* @@ -286,7 +202,7 @@ void tegra_pwr_domain_on_finish(const psci_power_state_t *target_state) * having been suspended earlier. The target_state encodes the low power state * that each level has woken up from. ******************************************************************************/ -void tegra_pwr_domain_suspend_finish(const psci_power_state_t *target_state) +static void tegra_pwr_domain_suspend_finish(const psci_power_state_t *target_state) { tegra_pwr_domain_on_finish(target_state); } @@ -294,7 +210,7 @@ void tegra_pwr_domain_suspend_finish(const psci_power_state_t *target_state) /******************************************************************************* * Handler called when the system wants to be powered off ******************************************************************************/ -__dead2 void tegra_system_off(void) +static __dead2 void tegra_system_off(void) { INFO("Powering down system...\n"); @@ -304,23 +220,23 @@ __dead2 void tegra_system_off(void) /******************************************************************************* * Handler called when the system wants to be restarted. ******************************************************************************/ -__dead2 void tegra_system_reset(void) +static __dead2 void tegra_system_reset(void) { INFO("Restarting system...\n"); /* per-SoC system reset handler */ (void)tegra_soc_prepare_system_reset(); - /* - * Program the PMC in order to restart the system. - */ - tegra_pmc_system_reset(); + /* wait for the system to reset */ + for (;;) { + ; + } } /******************************************************************************* * Handler called to check the validity of the power state parameter. ******************************************************************************/ -int32_t tegra_validate_power_state(uint32_t power_state, +static int32_t tegra_validate_power_state(uint32_t power_state, psci_power_state_t *req_state) { assert(req_state != NULL); @@ -331,7 +247,7 @@ int32_t tegra_validate_power_state(uint32_t power_state, /******************************************************************************* * Platform handler called to check the validity of the non secure entrypoint. ******************************************************************************/ -int32_t tegra_validate_ns_entrypoint(uintptr_t entrypoint) +static int32_t tegra_validate_ns_entrypoint(uintptr_t entrypoint) { int32_t ret = PSCI_E_INVALID_ADDRESS; @@ -349,7 +265,7 @@ int32_t tegra_validate_ns_entrypoint(uintptr_t entrypoint) /******************************************************************************* * Export the platform handlers to enable psci to invoke them ******************************************************************************/ -static const plat_psci_ops_t tegra_plat_psci_ops = { +static plat_psci_ops_t tegra_plat_psci_ops = { .cpu_standby = tegra_cpu_standby, .pwr_domain_on = tegra_pwr_domain_on, .pwr_domain_off = tegra_pwr_domain_off, @@ -386,6 +302,14 @@ int plat_setup_psci_ops(uintptr_t sec_entrypoint, (void)tegra_soc_pwr_domain_on_finish(&target_state); /* + * Disable System Suspend if the platform does not + * support it + */ + if (!plat_supports_system_suspend()) { + tegra_plat_psci_ops.get_sys_suspend_power_state = NULL; + } + + /* * Initialize PSCI ops struct */ *psci_ops = &tegra_plat_psci_ops; diff --git a/plat/nvidia/tegra/common/tegra_sdei.c b/plat/nvidia/tegra/common/tegra_sdei.c new file mode 100644 index 000000000..9241b8172 --- /dev/null +++ b/plat/nvidia/tegra/common/tegra_sdei.c @@ -0,0 +1,56 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +/* SDEI configuration for Tegra platforms */ + +#include <platform_def.h> + +#include <bl31/ehf.h> +#include <common/bl_common.h> +#include <common/debug.h> +#include <lib/utils_def.h> +#include <services/sdei.h> + +/* Private event mappings */ +static sdei_ev_map_t tegra_sdei_private[] = { + /* Event 0 definition */ + SDEI_DEFINE_EVENT_0(TEGRA_SDEI_SGI_PRIVATE), + + /* Dynamic private events */ + SDEI_PRIVATE_EVENT(TEGRA_SDEI_DP_EVENT_0, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC), + SDEI_PRIVATE_EVENT(TEGRA_SDEI_DP_EVENT_1, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC), + SDEI_PRIVATE_EVENT(TEGRA_SDEI_DP_EVENT_2, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC), + + /* General purpose explicit events */ + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_0, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_1, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_2, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_3, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_4, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_5, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_6, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_7, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_8, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_9, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_10, SDEI_MAPF_CRITICAL), + SDEI_EXPLICIT_EVENT(TEGRA_SDEI_EP_EVENT_11, SDEI_MAPF_CRITICAL) +}; + +/* Shared event mappings */ +static sdei_ev_map_t tegra_sdei_shared[] = { + /* Dynamic shared events */ + SDEI_SHARED_EVENT(TEGRA_SDEI_DS_EVENT_0, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC), + SDEI_SHARED_EVENT(TEGRA_SDEI_DS_EVENT_1, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC), + SDEI_SHARED_EVENT(TEGRA_SDEI_DS_EVENT_2, SDEI_DYN_IRQ, SDEI_MAPF_DYNAMIC) +}; + +void plat_sdei_setup(void) +{ + INFO("SDEI platform setup\n"); +} + +/* Export Tegra SDEI events */ +REGISTER_SDEI_MAP(tegra_sdei_private, tegra_sdei_shared); diff --git a/plat/nvidia/tegra/common/tegra_sip_calls.c b/plat/nvidia/tegra/common/tegra_sip_calls.c index b8ba09562..80a2c4d0c 100644 --- a/plat/nvidia/tegra/common/tegra_sip_calls.c +++ b/plat/nvidia/tegra/common/tegra_sip_calls.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -26,32 +27,6 @@ #define TEGRA_SIP_FIQ_NS_GET_CONTEXT 0x82000006 /******************************************************************************* - * SoC specific SiP handler - ******************************************************************************/ -#pragma weak plat_sip_handler -int32_t plat_sip_handler(uint32_t smc_fid, - uint64_t x1, - uint64_t x2, - uint64_t x3, - uint64_t x4, - const void *cookie, - void *handle, - uint64_t flags) -{ - /* unused parameters */ - (void)smc_fid; - (void)x1; - (void)x2; - (void)x3; - (void)x4; - (void)cookie; - (void)handle; - (void)flags; - - return -ENOTSUP; -} - -/******************************************************************************* * This function is responsible for handling all SiP calls ******************************************************************************/ uintptr_t tegra_sip_handler(uint32_t smc_fid, @@ -77,6 +52,12 @@ uintptr_t tegra_sip_handler(uint32_t smc_fid, switch (smc_fid) { case TEGRA_SIP_NEW_VIDEOMEM_REGION: + /* Check whether Video memory resize is enabled */ + if (mmio_read_32(TEGRA_MC_BASE + MC_VIDEO_PROTECT_REG_CTRL) + != MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED) { + ERROR("Video Memory Resize isn't enabled! \n"); + SMC_RET1(handle, (uint64_t)-ENOTSUP); + } /* * Check if Video Memory overlaps TZDRAM (contains bl31/bl32) diff --git a/plat/nvidia/tegra/common/tegra_stack_protector.c b/plat/nvidia/tegra/common/tegra_stack_protector.c new file mode 100644 index 000000000..f6c459a8e --- /dev/null +++ b/plat/nvidia/tegra/common/tegra_stack_protector.c @@ -0,0 +1,28 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdint.h> + +#include <arch_helpers.h> +#include <lib/mmio.h> +#include <plat/common/platform.h> +#include <platform_def.h> + +u_register_t plat_get_stack_protector_canary(void) +{ + u_register_t seed; + + /* + * Ideally, a random number should be returned instead. As the + * platform does not have any random number generator, this is + * better than nothing, but not really secure. + */ + seed = mmio_read_32(TEGRA_MISC_BASE + HARDWARE_REVISION_OFFSET); + seed <<= 32; + seed |= mmio_read_32(TEGRA_TMRUS_BASE); + + return seed ^ read_cntpct_el0(); +} diff --git a/plat/nvidia/tegra/common/tegra_topology.c b/plat/nvidia/tegra/common/tegra_topology.c deleted file mode 100644 index 205b05165..000000000 --- a/plat/nvidia/tegra/common/tegra_topology.c +++ /dev/null @@ -1,48 +0,0 @@ -/* - * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. - * - * SPDX-License-Identifier: BSD-3-Clause - */ - -#include <platform_def.h> - -#include <arch.h> -#include <lib/psci/psci.h> -#include <plat/common/platform.h> - -#pragma weak plat_core_pos_by_mpidr - -/******************************************************************************* - * This function implements a part of the critical interface between the psci - * generic layer and the platform that allows the former to query the platform - * to convert an MPIDR to a unique linear index. An error code (-1) is returned - * in case the MPIDR is invalid. - ******************************************************************************/ -int32_t plat_core_pos_by_mpidr(u_register_t mpidr) -{ - u_register_t cluster_id, cpu_id; - int32_t result; - - cluster_id = (mpidr >> (u_register_t)MPIDR_AFF1_SHIFT) & - (u_register_t)MPIDR_AFFLVL_MASK; - cpu_id = (mpidr >> (u_register_t)MPIDR_AFF0_SHIFT) & - (u_register_t)MPIDR_AFFLVL_MASK; - - /* CorePos = CoreId + (ClusterId * cpus per cluster) */ - result = (int32_t)cpu_id + ((int32_t)cluster_id * - PLATFORM_MAX_CPUS_PER_CLUSTER); - - if (cluster_id >= (u_register_t)PLATFORM_CLUSTER_COUNT) { - result = PSCI_E_NOT_PRESENT; - } - - /* - * Validate cpu_id by checking whether it represents a CPU in - * one of the two clusters present on the platform. - */ - if (cpu_id >= (u_register_t)PLATFORM_MAX_CPUS_PER_CLUSTER) { - result = PSCI_E_NOT_PRESENT; - } - - return result; -} diff --git a/plat/nvidia/tegra/common/drivers/bpmp/bpmp.c b/plat/nvidia/tegra/drivers/bpmp/bpmp.c index d7db604cc..d7db604cc 100644 --- a/plat/nvidia/tegra/common/drivers/bpmp/bpmp.c +++ b/plat/nvidia/tegra/drivers/bpmp/bpmp.c diff --git a/plat/nvidia/tegra/common/drivers/bpmp_ipc/intf.c b/plat/nvidia/tegra/drivers/bpmp_ipc/intf.c index ae899c424..2e90d2547 100644 --- a/plat/nvidia/tegra/common/drivers/bpmp_ipc/intf.c +++ b/plat/nvidia/tegra/drivers/bpmp_ipc/intf.c @@ -175,44 +175,39 @@ static int32_t tegra_bpmp_ipc_send_req_atomic(uint32_t mrq, void *p_out, if ((p_out == NULL) || (size_out > IVC_DATA_SZ_BYTES) || (frame == NULL)) { ERROR("%s: invalid parameters, exiting\n", __func__); - ret = -EINVAL; + return -EINVAL; } - if (ret == 0) { - - /* prepare the command frame */ - frame->mrq = mrq; - frame->flags = FLAG_DO_ACK; - p_fdata = frame->data; - (void)memcpy(p_fdata, p_out, (size_t)size_out); + /* prepare the command frame */ + frame->mrq = mrq; + frame->flags = FLAG_DO_ACK; + p_fdata = frame->data; + (void)memcpy(p_fdata, p_out, (size_t)size_out); - /* signal the slave */ - tegra_bpmp_signal_slave(); + /* signal the slave */ + tegra_bpmp_signal_slave(); - /* wait for slave to ack */ - ret = tegra_bpmp_wait_for_slave_ack(); - if (ret != 0) { - ERROR("failed waiting for the slave to ack\n"); - } + /* wait for slave to ack */ + ret = tegra_bpmp_wait_for_slave_ack(); + if (ret < 0) { + ERROR("%s: wait for slave failed (%d)\n", __func__, ret); + return ret; + } - /* retrieve the response frame */ - if ((size_in <= IVC_DATA_SZ_BYTES) && (p_in != NULL) && - (ret == 0)) { + /* retrieve the response frame */ + if ((size_in <= IVC_DATA_SZ_BYTES) && (p_in != NULL)) { - f_in = tegra_bpmp_get_cur_in_frame(); - if (f_in != NULL) { - ERROR("Failed to get next input frame!\n"); - } else { - (void)memcpy(p_in, p_fdata, (size_t)size_in); - } + f_in = tegra_bpmp_get_cur_in_frame(); + if (f_in != NULL) { + ERROR("Failed to get next input frame!\n"); + } else { + (void)memcpy(p_in, p_fdata, (size_t)size_in); } + } - if (ret == 0) { - ret = tegra_bpmp_free_master(); - if (ret != 0) { - ERROR("Failed to free master\n"); - } - } + ret = tegra_bpmp_free_master(); + if (ret < 0) { + ERROR("%s: free master failed (%d)\n", __func__, ret); } return ret; @@ -316,7 +311,7 @@ int tegra_bpmp_ipc_enable_clock(uint32_t clk_id) /* prepare the MRQ_CLK command */ req.cmd_and_id = make_mrq_clk_cmd(CMD_CLK_ENABLE, clk_id); - ret = tegra_bpmp_ipc_send_req_atomic(MRQ_CLK, &req, sizeof(req), + ret = tegra_bpmp_ipc_send_req_atomic(MRQ_CLK, &req, (uint32_t)sizeof(req), NULL, 0); if (ret != 0) { ERROR("%s: failed for module %d with error %d\n", __func__, @@ -339,7 +334,7 @@ int tegra_bpmp_ipc_disable_clock(uint32_t clk_id) /* prepare the MRQ_CLK command */ req.cmd_and_id = make_mrq_clk_cmd(CMD_CLK_DISABLE, clk_id); - ret = tegra_bpmp_ipc_send_req_atomic(MRQ_CLK, &req, sizeof(req), + ret = tegra_bpmp_ipc_send_req_atomic(MRQ_CLK, &req, (uint32_t)sizeof(req), NULL, 0); if (ret != 0) { ERROR("%s: failed for module %d with error %d\n", __func__, diff --git a/plat/nvidia/tegra/common/drivers/bpmp_ipc/intf.h b/plat/nvidia/tegra/drivers/bpmp_ipc/intf.h index 7059c3701..d85b906b8 100644 --- a/plat/nvidia/tegra/common/drivers/bpmp_ipc/intf.h +++ b/plat/nvidia/tegra/drivers/bpmp_ipc/intf.h @@ -1,17 +1,17 @@ /* - * Copyright (c) 2017-2018, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ -#ifndef INTF_H -#define INTF_H +#ifndef BPMP_INTF_H +#define BPMP_INTF_H /** * Flags used in IPC req */ #define FLAG_DO_ACK (U(1) << 0) -#define FLAG_RING_DOORBELL (U(1) << 1) +#define FLAG_RING_DOORBELL (U(1) << 1) /* Bit 1 is designated for CCPlex in secure world */ #define HSP_MASTER_CCPLEX_BIT (U(1) << 1) @@ -77,16 +77,16 @@ struct __attribute__((packed)) mrq_reset_request { * */ enum { - CMD_CLK_GET_RATE = 1, - CMD_CLK_SET_RATE = 2, - CMD_CLK_ROUND_RATE = 3, - CMD_CLK_GET_PARENT = 4, - CMD_CLK_SET_PARENT = 5, - CMD_CLK_IS_ENABLED = 6, - CMD_CLK_ENABLE = 7, - CMD_CLK_DISABLE = 8, - CMD_CLK_GET_ALL_INFO = 14, - CMD_CLK_GET_MAX_CLK_ID = 15, + CMD_CLK_GET_RATE = U(1), + CMD_CLK_SET_RATE = U(2), + CMD_CLK_ROUND_RATE = U(3), + CMD_CLK_GET_PARENT = U(4), + CMD_CLK_SET_PARENT = U(5), + CMD_CLK_IS_ENABLED = U(6), + CMD_CLK_ENABLE = U(7), + CMD_CLK_DISABLE = U(8), + CMD_CLK_GET_ALL_INFO = U(14), + CMD_CLK_GET_MAX_CLK_ID = U(15), CMD_CLK_MAX, }; @@ -124,4 +124,4 @@ struct mrq_clk_request { */ #define make_mrq_clk_cmd(cmd, id) (((cmd) << 24) | (id & 0xFFFFFF)) -#endif /* INTF_H */ +#endif /* BPMP_INTF_H */ diff --git a/plat/nvidia/tegra/common/drivers/bpmp_ipc/ivc.c b/plat/nvidia/tegra/drivers/bpmp_ipc/ivc.c index 57daf6aeb..d964fc001 100644 --- a/plat/nvidia/tegra/common/drivers/bpmp_ipc/ivc.c +++ b/plat/nvidia/tegra/drivers/bpmp_ipc/ivc.c @@ -8,6 +8,7 @@ #include <assert.h> #include <common/debug.h> #include <errno.h> +#include <stdbool.h> #include <stddef.h> #include <string.h> diff --git a/plat/nvidia/tegra/common/drivers/bpmp_ipc/ivc.h b/plat/nvidia/tegra/drivers/bpmp_ipc/ivc.h index 42e6a1f7c..1b318213b 100644 --- a/plat/nvidia/tegra/common/drivers/bpmp_ipc/ivc.h +++ b/plat/nvidia/tegra/drivers/bpmp_ipc/ivc.h @@ -1,11 +1,11 @@ /* - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ -#ifndef IVC_H -#define IVC_H +#ifndef BPMP_IVC_H +#define BPMP_IVC_H #include <lib/utils_def.h> #include <stdint.h> @@ -15,22 +15,21 @@ #define IVC_CHHDR_TX_FIELDS U(16) #define IVC_CHHDR_RX_FIELDS U(16) -struct ivc; struct ivc_channel_header; -/* callback handler for notify on receiving a response */ -typedef void (* ivc_notify_function)(const struct ivc *); - struct ivc { struct ivc_channel_header *rx_channel; struct ivc_channel_header *tx_channel; uint32_t w_pos; uint32_t r_pos; - ivc_notify_function notify; + void (*notify)(const struct ivc *); uint32_t nframes; uint32_t frame_size; }; +/* callback handler for notify on receiving a response */ +typedef void (* ivc_notify_function)(const struct ivc *); + int32_t tegra_ivc_init(struct ivc *ivc, uintptr_t rx_base, uintptr_t tx_base, uint32_t nframes, uint32_t frame_size, ivc_notify_function notify); @@ -48,4 +47,4 @@ bool tegra_ivc_tx_empty(const struct ivc *ivc); bool tegra_ivc_can_write(const struct ivc *ivc); bool tegra_ivc_can_read(const struct ivc *ivc); -#endif /* IVC_H */ +#endif /* BPMP_IVC_H */ diff --git a/plat/nvidia/tegra/common/drivers/flowctrl/flowctrl.c b/plat/nvidia/tegra/drivers/flowctrl/flowctrl.c index 8f5555459..8f5555459 100644 --- a/plat/nvidia/tegra/common/drivers/flowctrl/flowctrl.c +++ b/plat/nvidia/tegra/drivers/flowctrl/flowctrl.c diff --git a/plat/nvidia/tegra/common/drivers/gpcdma/gpcdma.c b/plat/nvidia/tegra/drivers/gpcdma/gpcdma.c index d68cdfd4b..d68cdfd4b 100644 --- a/plat/nvidia/tegra/common/drivers/gpcdma/gpcdma.c +++ b/plat/nvidia/tegra/drivers/gpcdma/gpcdma.c diff --git a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c b/plat/nvidia/tegra/drivers/memctrl/memctrl_v1.c index 92fa273b5..b3dcd2a4b 100644 --- a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v1.c +++ b/plat/nvidia/tegra/drivers/memctrl/memctrl_v1.c @@ -1,5 +1,6 @@ /* - * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -92,20 +93,6 @@ 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); } -/* - * Secure the BL31 TZRAM aperture. - * - * phys_base = physical base of TZRAM aperture - * size_in_bytes = size of aperture in bytes - */ -void tegra_memctrl_tzram_setup(uint64_t phys_base, uint32_t size_in_bytes) -{ - /* - * The v1 hardware controller does not have any registers - * for setting up the on-chip TZRAM. - */ -} - static void tegra_clear_videomem(uintptr_t non_overlap_area_start, unsigned long long non_overlap_area_size) { @@ -117,7 +104,8 @@ static void tegra_clear_videomem(uintptr_t non_overlap_area_start, ret = mmap_add_dynamic_region(non_overlap_area_start, /* PA */ non_overlap_area_start, /* VA */ non_overlap_area_size, /* size */ - MT_NS | MT_RW | MT_EXECUTE_NEVER); /* attrs */ + MT_NS | MT_RW | MT_EXECUTE_NEVER | + MT_NON_CACHEABLE); /* attrs */ assert(ret == 0); zeromem((void *)non_overlap_area_start, non_overlap_area_size); diff --git a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c b/plat/nvidia/tegra/drivers/memctrl/memctrl_v2.c index 2f31906d8..92120b527 100644 --- a/plat/nvidia/tegra/common/drivers/memctrl/memctrl_v2.c +++ b/plat/nvidia/tegra/drivers/memctrl/memctrl_v2.c @@ -1,6 +1,6 @@ /* * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. - * Copyright (c) 2019, NVIDIA Corporation. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -21,59 +21,24 @@ #include <smmu.h> #include <tegra_def.h> #include <tegra_platform.h> +#include <tegra_private.h> /* Video Memory base and size (live values) */ static uint64_t video_mem_base; static uint64_t video_mem_size_mb; /* - * The following platform setup functions are weakly defined. They - * provide typical implementations that will be overridden by a SoC. - */ -#pragma weak plat_memctrl_tzdram_setup - -void plat_memctrl_tzdram_setup(uint64_t phys_base, uint64_t size_in_bytes) -{ - ; /* do nothing */ -} - -/* * Init Memory controller during boot. */ void tegra_memctrl_setup(void) { - uint32_t val; - const uint32_t *mc_streamid_override_regs; - uint32_t num_streamid_override_regs; - const mc_streamid_security_cfg_t *mc_streamid_sec_cfgs; - uint32_t num_streamid_sec_cfgs; - const tegra_mc_settings_t *plat_mc_settings = tegra_get_mc_settings(); - uint32_t i; - INFO("Tegra Memory Controller (v2)\n"); - /* Program the SMMU pagesize */ + /* Initialize the System memory management unit */ tegra_smmu_init(); - /* Get the settings from the platform */ - assert(plat_mc_settings != NULL); - mc_streamid_override_regs = plat_mc_settings->streamid_override_cfg; - num_streamid_override_regs = plat_mc_settings->num_streamid_override_cfgs; - mc_streamid_sec_cfgs = plat_mc_settings->streamid_security_cfg; - num_streamid_sec_cfgs = plat_mc_settings->num_streamid_security_cfgs; - - /* Program all the Stream ID overrides */ - for (i = 0; i < num_streamid_override_regs; i++) - tegra_mc_streamid_write_32(mc_streamid_override_regs[i], - MC_STREAM_ID_MAX); - - /* Program the security config settings for all Stream IDs */ - for (i = 0; i < num_streamid_sec_cfgs; i++) { - val = mc_streamid_sec_cfgs[i].override_enable << 16 | - mc_streamid_sec_cfgs[i].override_client_inputs << 8 | - mc_streamid_sec_cfgs[i].override_client_ns_flag << 0; - tegra_mc_streamid_write_32(mc_streamid_sec_cfgs[i].offset, val); - } + /* allow platforms to program custom memory controller settings */ + plat_memctrl_setup(); /* * All requests at boot time, and certain requests during @@ -90,21 +55,6 @@ void tegra_memctrl_setup(void) */ tegra_mc_write_32(MC_SMMU_BYPASS_CONFIG, MC_SMMU_BYPASS_CONFIG_SETTINGS); - - /* - * Re-configure MSS to allow ROC to deal with ordering of the - * Memory Controller traffic. This is needed as the Memory Controller - * boots with MSS having all control, but ROC provides a performance - * boost as compared to MSS. - */ - if (plat_mc_settings->reconfig_mss_clients != NULL) { - plat_mc_settings->reconfig_mss_clients(); - } - - /* Program overrides for MC transactions */ - if (plat_mc_settings->set_txn_overrides != NULL) { - plat_mc_settings->set_txn_overrides(); - } } /* @@ -112,32 +62,23 @@ void tegra_memctrl_setup(void) */ void tegra_memctrl_restore_settings(void) { - const tegra_mc_settings_t *plat_mc_settings = tegra_get_mc_settings(); - - assert(plat_mc_settings != NULL); - - /* - * Re-configure MSS to allow ROC to deal with ordering of the - * Memory Controller traffic. This is needed as the Memory Controller - * resets during System Suspend with MSS having all control, but ROC - * provides a performance boost as compared to MSS. - */ - if (plat_mc_settings->reconfig_mss_clients != NULL) { - plat_mc_settings->reconfig_mss_clients(); - } - - /* Program overrides for MC transactions */ - if (plat_mc_settings->set_txn_overrides != NULL) { - plat_mc_settings->set_txn_overrides(); - } + /* restore platform's memory controller settings */ + plat_memctrl_restore(); /* video memory carveout region */ if (video_mem_base != 0ULL) { tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_LO, (uint32_t)video_mem_base); + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_BASE_LO) + == (uint32_t)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_SIZE_MB, video_mem_size_mb); + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_BASE_HI) + == (uint32_t)(video_mem_base >> 32)); + tegra_mc_write_32(MC_VIDEO_PROTECT_SIZE_MB, + (uint32_t)video_mem_size_mb); + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_SIZE_MB) + == (uint32_t)video_mem_size_mb); /* * MCE propagates the VideoMem configuration values across the @@ -169,69 +110,62 @@ void tegra_memctrl_tzdram_setup(uint64_t phys_base, uint32_t size_in_bytes) */ void tegra_memctrl_tzram_setup(uint64_t phys_base, uint32_t size_in_bytes) { - uint32_t index; - uint32_t total_128kb_blocks = size_in_bytes >> 17; - uint32_t residual_4kb_blocks = (size_in_bytes & (uint32_t)0x1FFFF) >> 12; - uint32_t val; + ; /* do nothing */ +} - INFO("Configuring TrustZone SRAM Memory Carveout\n"); +/* + * Save MC settings before "System Suspend" to TZDRAM + */ +void tegra_mc_save_context(uint64_t mc_ctx_addr) +{ + uint32_t i, num_entries = 0; + mc_regs_t *mc_ctx_regs; + const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); + uint64_t tzdram_base = params_from_bl2->tzdram_base; + uint64_t tzdram_end = tzdram_base + params_from_bl2->tzdram_size; - /* - * Reset the access configuration registers to restrict access - * to the TZRAM aperture - */ - for (index = MC_TZRAM_CLIENT_ACCESS0_CFG0; - index < ((uint32_t)MC_TZRAM_CARVEOUT_CFG + (uint32_t)MC_GSC_CONFIG_REGS_SIZE); - index += 4U) { - tegra_mc_write_32(index, 0); - } + assert((mc_ctx_addr >= tzdram_base) && (mc_ctx_addr <= tzdram_end)); - /* - * Enable CPU access configuration registers to access the TZRAM aperture - */ - if (!tegra_chipid_is_t186()) { - val = tegra_mc_read_32(MC_TZRAM_CLIENT_ACCESS1_CFG0); - val |= TZRAM_ALLOW_MPCORER | TZRAM_ALLOW_MPCOREW; - tegra_mc_write_32(MC_TZRAM_CLIENT_ACCESS1_CFG0, val); - } + /* get MC context table */ + mc_ctx_regs = plat_memctrl_get_sys_suspend_ctx(); + assert(mc_ctx_regs != NULL); /* - * Set the TZRAM base. TZRAM base must be 4k aligned, at least. + * mc_ctx_regs[0].val contains the size of the context table minus + * the last entry. Sanity check the table size before we start with + * the context save operation. */ - assert((phys_base & (uint64_t)0xFFF) == 0U); - tegra_mc_write_32(MC_TZRAM_BASE_LO, (uint32_t)phys_base); - tegra_mc_write_32(MC_TZRAM_BASE_HI, - (uint32_t)(phys_base >> 32) & MC_GSC_BASE_HI_MASK); + while (mc_ctx_regs[num_entries].reg != 0xFFFFFFFFU) { + num_entries++; + } - /* - * Set the TZRAM size - * - * total size = (number of 128KB blocks) + (number of remaining 4KB - * blocks) - * - */ - val = (residual_4kb_blocks << MC_GSC_SIZE_RANGE_4KB_SHIFT) | - total_128kb_blocks; - tegra_mc_write_32(MC_TZRAM_SIZE, val); + /* panic if the sizes do not match */ + if (num_entries != mc_ctx_regs[0].val) { + ERROR("MC context size mismatch!"); + panic(); + } - /* - * Lock the configuration settings by disabling TZ-only lock - * and locking the configuration against any future changes - * at all. - */ - val = tegra_mc_read_32(MC_TZRAM_CARVEOUT_CFG); - val &= (uint32_t)~MC_GSC_ENABLE_TZ_LOCK_BIT; - val |= MC_GSC_LOCK_CFG_SETTINGS_BIT; - if (!tegra_chipid_is_t186()) { - val |= MC_GSC_ENABLE_CPU_SECURE_BIT; + /* save MC register values */ + for (i = 1U; i < num_entries; i++) { + mc_ctx_regs[i].val = mmio_read_32(mc_ctx_regs[i].reg); } - tegra_mc_write_32(MC_TZRAM_CARVEOUT_CFG, val); - /* - * MCE propagates the security configuration values across the - * CCPLEX. - */ - mce_update_gsc_tzram(); + /* increment by 1 to take care of the last entry */ + num_entries++; + + /* Save MC config settings */ + (void)memcpy((void *)mc_ctx_addr, mc_ctx_regs, + sizeof(mc_regs_t) * num_entries); + + /* save the MC table address */ + mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_MC_TABLE_ADDR_LO, + (uint32_t)mc_ctx_addr); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SCRATCH_MC_TABLE_ADDR_LO) + == (uint32_t)mc_ctx_addr); + mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_MC_TABLE_ADDR_HI, + (uint32_t)(mc_ctx_addr >> 32)); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SCRATCH_MC_TABLE_ADDR_HI) + == (uint32_t)(mc_ctx_addr >> 32)); } static void tegra_lock_videomem_nonoverlap(uint64_t phys_base, @@ -300,56 +234,33 @@ static void tegra_clear_videomem(uintptr_t non_overlap_area_start, { int ret; + INFO("Cleaning previous Video Memory Carveout\n"); + /* * Map the NS memory first, clean it and then unmap it. */ ret = mmap_add_dynamic_region(non_overlap_area_start, /* PA */ non_overlap_area_start, /* VA */ non_overlap_area_size, /* size */ - MT_NS | MT_RW | MT_EXECUTE_NEVER); /* attrs */ + MT_DEVICE | MT_RW | MT_NS); /* attrs */ assert(ret == 0); - zero_normalmem((void *)non_overlap_area_start, non_overlap_area_size); + zeromem((void *)non_overlap_area_start, non_overlap_area_size); flush_dcache_range(non_overlap_area_start, non_overlap_area_size); - (void)mmap_remove_dynamic_region(non_overlap_area_start, + ret = mmap_remove_dynamic_region(non_overlap_area_start, non_overlap_area_size); + assert(ret == 0); } -/* - * Program the Video Memory carveout region - * - * phys_base = physical base of aperture - * size_in_bytes = size of aperture in bytes - */ -void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes) +static void tegra_clear_videomem_nonoverlap(uintptr_t phys_base, + unsigned long size_in_bytes) { uintptr_t vmem_end_old = video_mem_base + (video_mem_size_mb << 20); uintptr_t vmem_end_new = phys_base + size_in_bytes; unsigned long long non_overlap_area_size; /* - * Setup the Memory controller to restrict CPU accesses to the Video - * Memory region - */ - INFO("Configuring Video Memory Carveout\n"); - - /* - * Configure Memory Controller directly for the first time. - */ - if (video_mem_base == 0U) - goto done; - - /* - * Lock the non overlapping memory being cleared so that other masters - * do not accidently write to it. The memory would be unlocked once - * the non overlapping region is cleared and the new memory - * settings take effect. - */ - tegra_lock_videomem_nonoverlap(video_mem_base, - video_mem_size_mb << 20); - - /* * Clear the old regions now being exposed. The following cases * can occur - * @@ -357,8 +268,6 @@ void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes) * 2. clear old sub-region below new base * 3. clear old sub-region above new end */ - INFO("Cleaning previous Video Memory Carveout\n"); - if ((phys_base > vmem_end_old) || (video_mem_base > vmem_end_new)) { tegra_clear_videomem(video_mem_base, video_mem_size_mb << 20U); @@ -372,26 +281,63 @@ void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes) tegra_clear_videomem(vmem_end_new, non_overlap_area_size); } } +} + +/* + * Program the Video Memory carveout region + * + * phys_base = physical base of aperture + * size_in_bytes = size of aperture in bytes + */ +void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes) +{ + /* + * Setup the Memory controller to restrict CPU accesses to the Video + * Memory region + */ + + INFO("Configuring Video Memory Carveout\n"); + + if (video_mem_base != 0U) { + /* + * Lock the non overlapping memory being cleared so that + * other masters do not accidently write to it. The memory + * would be unlocked once the non overlapping region is + * cleared and the new memory settings take effect. + */ + tegra_lock_videomem_nonoverlap(video_mem_base, + video_mem_size_mb << 20); + } -done: /* program the Videomem aperture */ tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_LO, (uint32_t)phys_base); tegra_mc_write_32(MC_VIDEO_PROTECT_BASE_HI, (uint32_t)(phys_base >> 32)); tegra_mc_write_32(MC_VIDEO_PROTECT_SIZE_MB, size_in_bytes >> 20); - /* unlock the previous locked nonoverlapping aperture */ - tegra_unlock_videomem_nonoverlap(); - - /* store new values */ - video_mem_base = phys_base; - video_mem_size_mb = size_in_bytes >> 20; + /* Redundancy check for Video Protect setting */ + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_BASE_LO) + == (uint32_t)phys_base); + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_BASE_HI) + == (uint32_t)(phys_base >> 32)); + assert(tegra_mc_read_32(MC_VIDEO_PROTECT_SIZE_MB) + == (size_in_bytes >> 20)); /* * MCE propagates the VideoMem configuration values across the * CCPLEX. */ - mce_update_gsc_videomem(); + (void)mce_update_gsc_videomem(); + + /* Clear the non-overlapping memory */ + if (video_mem_base != 0U) { + tegra_clear_videomem_nonoverlap(phys_base, size_in_bytes); + tegra_unlock_videomem_nonoverlap(); + } + + /* store new values */ + video_mem_base = phys_base; + video_mem_size_mb = (uint64_t)size_in_bytes >> 20; } /* diff --git a/plat/nvidia/tegra/common/drivers/pmc/pmc.c b/plat/nvidia/tegra/drivers/pmc/pmc.c index 6c5a73baf..6c5a73baf 100644 --- a/plat/nvidia/tegra/common/drivers/pmc/pmc.c +++ b/plat/nvidia/tegra/drivers/pmc/pmc.c diff --git a/plat/nvidia/tegra/drivers/smmu/smmu.c b/plat/nvidia/tegra/drivers/smmu/smmu.c new file mode 100644 index 000000000..4189b00b1 --- /dev/null +++ b/plat/nvidia/tegra/drivers/smmu/smmu.c @@ -0,0 +1,121 @@ +/* + * Copyright (c) 2016-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <assert.h> +#include <string.h> + +#include <platform_def.h> + +#include <common/bl_common.h> +#include <common/debug.h> + +#include <smmu.h> +#include <tegra_platform.h> +#include <tegra_private.h> + +extern void memcpy16(void *dest, const void *src, unsigned int length); + +#define SMMU_NUM_CONTEXTS 64U +#define SMMU_CONTEXT_BANK_MAX_IDX 64U + +#define MISMATCH_DETECTED 0x55AA55AAU + +/* + * Init SMMU during boot or "System Suspend" exit + */ +void tegra_smmu_init(void) +{ + uint32_t val, cb_idx, smmu_id, ctx_base; + uint32_t num_smmu_devices = plat_get_num_smmu_devices(); + + for (smmu_id = 0U; smmu_id < num_smmu_devices; smmu_id++) { + /* Program the SMMU pagesize and reset CACHE_LOCK bit */ + val = tegra_smmu_read_32(smmu_id, SMMU_GSR0_SECURE_ACR); + val |= SMMU_GSR0_PGSIZE_64K; + val &= (uint32_t)~SMMU_ACR_CACHE_LOCK_ENABLE_BIT; + tegra_smmu_write_32(smmu_id, SMMU_GSR0_SECURE_ACR, val); + + /* reset CACHE LOCK bit for NS Aux. Config. Register */ + val = tegra_smmu_read_32(smmu_id, SMMU_GNSR_ACR); + val &= (uint32_t)~SMMU_ACR_CACHE_LOCK_ENABLE_BIT; + tegra_smmu_write_32(smmu_id, SMMU_GNSR_ACR, val); + + /* disable TCU prefetch for all contexts */ + ctx_base = (SMMU_GSR0_PGSIZE_64K * SMMU_NUM_CONTEXTS) + + SMMU_CBn_ACTLR; + for (cb_idx = 0U; cb_idx < SMMU_CONTEXT_BANK_MAX_IDX; cb_idx++) { + val = tegra_smmu_read_32(smmu_id, + ctx_base + (SMMU_GSR0_PGSIZE_64K * cb_idx)); + val &= (uint32_t)~SMMU_CBn_ACTLR_CPRE_BIT; + tegra_smmu_write_32(smmu_id, ctx_base + + (SMMU_GSR0_PGSIZE_64K * cb_idx), val); + } + + /* set CACHE LOCK bit for NS Aux. Config. Register */ + val = tegra_smmu_read_32(smmu_id, SMMU_GNSR_ACR); + val |= (uint32_t)SMMU_ACR_CACHE_LOCK_ENABLE_BIT; + tegra_smmu_write_32(smmu_id, SMMU_GNSR_ACR, val); + + /* set CACHE LOCK bit for S Aux. Config. Register */ + val = tegra_smmu_read_32(smmu_id, SMMU_GSR0_SECURE_ACR); + val |= (uint32_t)SMMU_ACR_CACHE_LOCK_ENABLE_BIT; + tegra_smmu_write_32(smmu_id, SMMU_GSR0_SECURE_ACR, val); + } +} + +/* + * Verify SMMU settings have not been altered during boot + */ +void tegra_smmu_verify(void) +{ + uint32_t cb_idx, ctx_base, smmu_id, val; + uint32_t num_smmu_devices = plat_get_num_smmu_devices(); + uint32_t mismatch = 0U; + + for (smmu_id = 0U; smmu_id < num_smmu_devices; smmu_id++) { + /* check PGSIZE_64K bit inr S Aux. Config. Register */ + val = tegra_smmu_read_32(smmu_id, SMMU_GSR0_SECURE_ACR); + if (0U == (val & SMMU_GSR0_PGSIZE_64K)) { + ERROR("%s: PGSIZE_64K Mismatch - smmu_id=%d, GSR0_SECURE_ACR=%x\n", + __func__, smmu_id, val); + mismatch = MISMATCH_DETECTED; + } + + /* check CACHE LOCK bit in S Aux. Config. Register */ + if (0U == (val & SMMU_ACR_CACHE_LOCK_ENABLE_BIT)) { + ERROR("%s: CACHE_LOCK Mismatch - smmu_id=%d, GSR0_SECURE_ACR=%x\n", + __func__, smmu_id, val); + mismatch = MISMATCH_DETECTED; + } + + /* check CACHE LOCK bit in NS Aux. Config. Register */ + val = tegra_smmu_read_32(smmu_id, SMMU_GNSR_ACR); + if (0U == (val & SMMU_ACR_CACHE_LOCK_ENABLE_BIT)) { + ERROR("%s: Mismatch - smmu_id=%d, GNSR_ACR=%x\n", + __func__, smmu_id, val); + mismatch = MISMATCH_DETECTED; + } + + /* verify TCU prefetch for all contexts is disabled */ + ctx_base = (SMMU_GSR0_PGSIZE_64K * SMMU_NUM_CONTEXTS) + + SMMU_CBn_ACTLR; + for (cb_idx = 0U; cb_idx < SMMU_CONTEXT_BANK_MAX_IDX; cb_idx++) { + val = tegra_smmu_read_32(smmu_id, + ctx_base + (SMMU_GSR0_PGSIZE_64K * cb_idx)); + if (0U != (val & SMMU_CBn_ACTLR_CPRE_BIT)) { + ERROR("%s: Mismatch - smmu_id=%d, cb_idx=%d, GSR0_PGSIZE_64K=%x\n", + __func__, smmu_id, cb_idx, val); + mismatch = MISMATCH_DETECTED; + } + } + } + + /* Treat configuration mismatch as fatal */ + if ((mismatch == MISMATCH_DETECTED) && tegra_platform_is_silicon()) { + panic(); + } +} diff --git a/plat/nvidia/tegra/common/drivers/spe/shared_console.S b/plat/nvidia/tegra/drivers/spe/shared_console.S index a3e110ec9..d1b18dd44 100644 --- a/plat/nvidia/tegra/common/drivers/spe/shared_console.S +++ b/plat/nvidia/tegra/drivers/spe/shared_console.S @@ -1,16 +1,18 @@ /* - * Copyright (c) 2017-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ #include <asm_macros.S> +#include <assert_macros.S> #include <console_macros.S> #define CONSOLE_NUM_BYTES_SHIFT 24 #define CONSOLE_FLUSH_DATA_TO_PORT (1 << 26) #define CONSOLE_RING_DOORBELL (1 << 31) #define CONSOLE_IS_BUSY (1 << 31) -#define CONSOLE_WRITE (CONSOLE_RING_DOORBELL | CONSOLE_FLUSH_DATA_TO_PORT) +#define CONSOLE_TIMEOUT 0xC000 /* 50 ms */ /* * This file contains a driver implementation to make use of the @@ -30,24 +32,44 @@ .globl console_spe_flush .globl console_spe_register +.macro check_if_console_is_ready base, tmp1, tmp2, label + /* wait until spe is ready or timeout expires */ + mrs \tmp2, cntps_tval_el1 +1: ldr \tmp1, [\base] + and \tmp1, \tmp1, #CONSOLE_IS_BUSY + cbz \tmp1, 2f + mrs \tmp1, cntps_tval_el1 + sub \tmp1, \tmp2, \tmp1 + cmp \tmp1, #CONSOLE_TIMEOUT + b.lt 1b + b \label +2: +.endm + /* ------------------------------------------------- * int console_spe_register(uintptr_t baseaddr, * uint32_t clock, uint32_t baud, - * console_spe_t *console); + * console_t *console); * Function to initialize and register a new spe * console. Storage passed in for the console struct * *must* be persistent (i.e. not from the stack). * In: x0 - UART register base address * w1 - UART clock in Hz * w2 - Baud rate - * x3 - pointer to empty console_spe_t struct + * x3 - pointer to empty console_t struct * Out: return 1 on success, 0 on error * Clobber list : x0, x1, x2, x6, x7, x14 * ------------------------------------------------- */ func console_spe_register + /* Check the input base address */ + cbz x0, register_fail + + /* Dont use clock or baud rate, so ok to overwrite them */ + check_if_console_is_ready x0, x1, x2, register_fail + cbz x3, register_fail - str x0, [x3, #CONSOLE_T_DRVDATA] + str x0, [x3, #CONSOLE_T_BASE] mov x0, x3 finish_console_register spe putc=1, getc=1, flush=1 @@ -63,7 +85,7 @@ endfunc console_spe_register * In : w0 - character to be printed * x1 - console base address * Out : return -1 on error else return character. - * Clobber list : x2 + * Clobber list : x2, x3 * -------------------------------------------------------- */ func console_spe_core_putc @@ -72,29 +94,24 @@ func console_spe_core_putc /* Prepend '\r' to '\n' */ cmp w0, #0xA - b.ne 2f + b.ne not_eol - /* wait until spe is ready */ -1: ldr w2, [x1] - and w2, w2, #CONSOLE_IS_BUSY - cbnz w2, 1b + check_if_console_is_ready x1, x2, x3, putc_error /* spe is ready */ mov w2, #0xD /* '\r' */ and w2, w2, #0xFF - mov w3, #(CONSOLE_WRITE | (1 << CONSOLE_NUM_BYTES_SHIFT)) + mov w3, #(CONSOLE_RING_DOORBELL | (1 << CONSOLE_NUM_BYTES_SHIFT)) orr w2, w2, w3 str w2, [x1] - /* wait until spe is ready */ -2: ldr w2, [x1] - and w2, w2, #CONSOLE_IS_BUSY - cbnz w2, 2b +not_eol: + check_if_console_is_ready x1, x2, x3, putc_error /* spe is ready */ mov w2, w0 and w2, w2, #0xFF - mov w3, #(CONSOLE_WRITE | (1 << CONSOLE_NUM_BYTES_SHIFT)) + mov w3, #(CONSOLE_RING_DOORBELL | (1 << CONSOLE_NUM_BYTES_SHIFT)) orr w2, w2, w3 str w2, [x1] @@ -105,7 +122,7 @@ putc_error: endfunc console_spe_core_putc /* -------------------------------------------------------- - * int console_spe_putc(int c, console_spe_t *console) + * int console_spe_putc(int c, console_t *console) * Function to output a character over the console. It * returns the character printed on success or -1 on error. * In : w0 - character to be printed @@ -115,12 +132,12 @@ endfunc console_spe_core_putc * -------------------------------------------------------- */ func console_spe_putc - ldr x1, [x1, #CONSOLE_T_DRVDATA] + ldr x1, [x1, #CONSOLE_T_BASE] b console_spe_core_putc endfunc console_spe_putc /* --------------------------------------------- - * int console_spe_getc(console_spe_t *console) + * int console_spe_getc(console_t *console) * Function to get a character from the console. * It returns the character grabbed on success * or -1 if no character is available. @@ -135,37 +152,36 @@ func console_spe_getc endfunc console_spe_getc /* ------------------------------------------------- - * int console_spe_core_flush(uintptr_t base_addr) + * void console_spe_core_flush(uintptr_t base_addr) * Function to force a write of all buffered * data that hasn't been output. * In : x0 - console base address - * Out : return -1 on error else return 0. + * Out : void. * Clobber list : x0, x1 * ------------------------------------------------- */ func console_spe_core_flush - cbz x0, flush_error +#if ENABLE_ASSERTIONS + cmp x0, #0 + ASM_ASSERT(ne) +#endif /* ENABLE_ASSERTIONS */ /* flush console */ - mov w1, #CONSOLE_WRITE + mov w1, #(CONSOLE_RING_DOORBELL | CONSOLE_FLUSH_DATA_TO_PORT) str w1, [x0] - mov w0, #0 - ret -flush_error: - mov w0, #-1 ret endfunc console_spe_core_flush /* --------------------------------------------- - * int console_spe_flush(console_spe_t *console) + * void console_spe_flush(console_t *console) * Function to force a write of all buffered * data that hasn't been output. * In : x0 - pointer to console_t structure - * Out : return -1 on error else return 0. + * Out : void. * Clobber list : x0, x1 * --------------------------------------------- */ func console_spe_flush - ldr x0, [x0, #CONSOLE_T_DRVDATA] + ldr x0, [x0, #CONSOLE_T_BASE] b console_spe_core_flush endfunc console_spe_flush diff --git a/plat/nvidia/tegra/include/drivers/bpmp_ipc.h b/plat/nvidia/tegra/include/drivers/bpmp_ipc.h index a0d02c949..401a07a24 100644 --- a/plat/nvidia/tegra/include/drivers/bpmp_ipc.h +++ b/plat/nvidia/tegra/include/drivers/bpmp_ipc.h @@ -19,11 +19,6 @@ #define TEGRA_RESET_ID_GPCDMA U(70) /** - * Clock identifier for the SE device - */ -#define TEGRA_CLK_SE U(124) - -/** * Function to initialise the IPC with the bpmp */ int32_t tegra_bpmp_ipc_init(void); diff --git a/plat/nvidia/tegra/include/drivers/flowctrl.h b/plat/nvidia/tegra/include/drivers/flowctrl.h index 54336b044..e5ab600b4 100644 --- a/plat/nvidia/tegra/include/drivers/flowctrl.h +++ b/plat/nvidia/tegra/include/drivers/flowctrl.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -9,6 +10,8 @@ #include <lib/mmio.h> +#include <stdbool.h> + #include <tegra_def.h> #define FLOWCTRL_HALT_CPU0_EVENTS (0x0U) diff --git a/plat/nvidia/tegra/include/drivers/mce.h b/plat/nvidia/tegra/include/drivers/mce.h index 4470b6b8b..5f1bb4f28 100644 --- a/plat/nvidia/tegra/include/drivers/mce.h +++ b/plat/nvidia/tegra/include/drivers/mce.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -69,7 +69,6 @@ int mce_command_handler(uint64_t cmd, uint64_t arg0, uint64_t arg1, int mce_update_reset_vector(void); int mce_update_gsc_videomem(void); int mce_update_gsc_tzdram(void); -int mce_update_gsc_tzram(void); __dead2 void mce_enter_ccplex_state(uint32_t state_idx); void mce_update_cstate_info(const mce_cstate_info_t *cstate); void mce_verify_firmware_version(void); diff --git a/plat/nvidia/tegra/include/drivers/memctrl.h b/plat/nvidia/tegra/include/drivers/memctrl.h index d5ef60d0c..cc8509526 100644 --- a/plat/nvidia/tegra/include/drivers/memctrl.h +++ b/plat/nvidia/tegra/include/drivers/memctrl.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -10,7 +11,6 @@ void tegra_memctrl_setup(void); void tegra_memctrl_restore_settings(void); void tegra_memctrl_tzdram_setup(uint64_t phys_base, uint32_t size_in_bytes); -void tegra_memctrl_tzram_setup(uint64_t phys_base, uint32_t size_in_bytes); void tegra_memctrl_videomem_setup(uint64_t phys_base, uint32_t size_in_bytes); void tegra_memctrl_disable_ahb_redirection(void); void tegra_memctrl_clear_pending_interrupts(void); diff --git a/plat/nvidia/tegra/include/drivers/memctrl_v2.h b/plat/nvidia/tegra/include/drivers/memctrl_v2.h index a4085e247..9af3027ea 100644 --- a/plat/nvidia/tegra/include/drivers/memctrl_v2.h +++ b/plat/nvidia/tegra/include/drivers/memctrl_v2.h @@ -1,5 +1,6 @@ /* - * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -7,58 +8,9 @@ #ifndef MEMCTRL_V2_H #define MEMCTRL_V2_H -#include <tegra_def.h> - -#ifndef __ASSEMBLER__ - -#include <lib/mmio.h> -#include <stdint.h> - -/******************************************************************************* - * Structure to hold the transaction override settings to use to override - * client inputs - ******************************************************************************/ -typedef struct mc_txn_override_cfg { - uint32_t offset; - uint8_t cgid_tag; -} mc_txn_override_cfg_t; - -#define mc_make_txn_override_cfg(off, val) \ - { \ - .offset = MC_TXN_OVERRIDE_CONFIG_ ## off, \ - .cgid_tag = MC_TXN_OVERRIDE_ ## val \ - } - -/******************************************************************************* - * Structure to hold the Stream ID to use to override client inputs - ******************************************************************************/ -typedef struct mc_streamid_override_cfg { - uint32_t offset; - uint8_t stream_id; -} mc_streamid_override_cfg_t; +#include <arch.h> -/******************************************************************************* - * Structure to hold the Stream ID Security Configuration settings - ******************************************************************************/ -typedef struct mc_streamid_security_cfg { - char *name; - uint32_t offset; - int override_enable; - int override_client_inputs; - int override_client_ns_flag; -} mc_streamid_security_cfg_t; - -#define OVERRIDE_DISABLE 1U -#define OVERRIDE_ENABLE 0U -#define CLIENT_FLAG_SECURE 0U -#define CLIENT_FLAG_NON_SECURE 1U -#define CLIENT_INPUTS_OVERRIDE 1U -#define CLIENT_INPUTS_NO_OVERRIDE 0U -/******************************************************************************* - * StreamID to indicate no SMMU translations (requests to be steered on the - * SMMU bypass path) - ******************************************************************************/ -#define MC_STREAM_ID_MAX 0x7FU +#include <tegra_def.h> /******************************************************************************* * Memory Controller SMMU Bypass config register @@ -74,29 +26,38 @@ typedef struct mc_streamid_security_cfg { #define MC_SMMU_BYPASS_CONFIG_SETTINGS (MC_SMMU_BYPASS_CONFIG_WRITE_ACCESS_BIT | \ MC_SMMU_CTRL_TBU_BYPASS_SPL_STREAMID) -#define mc_make_sec_cfg(off, ns, ovrrd, access) \ +#ifndef __ASSEMBLER__ + +#include <assert.h> + +typedef struct mc_regs { + uint32_t reg; + uint32_t val; +} mc_regs_t; + +#define mc_smmu_bypass_cfg \ { \ - .name = # off, \ - .offset = MC_STREAMID_OVERRIDE_TO_SECURITY_CFG( \ - MC_STREAMID_OVERRIDE_CFG_ ## off), \ - .override_client_ns_flag = CLIENT_FLAG_ ## ns, \ - .override_client_inputs = CLIENT_INPUTS_ ## ovrrd, \ - .override_enable = OVERRIDE_ ## access \ + .reg = TEGRA_MC_BASE + MC_SMMU_BYPASS_CONFIG, \ + .val = 0x00000000U, \ } -/******************************************************************************* - * Structure to hold Memory Controller's Configuration settings - ******************************************************************************/ -typedef struct tegra_mc_settings { - const uint32_t *streamid_override_cfg; - uint32_t num_streamid_override_cfgs; - const mc_streamid_security_cfg_t *streamid_security_cfg; - uint32_t num_streamid_security_cfgs; - const mc_txn_override_cfg_t *txn_override_cfg; - uint32_t num_txn_override_cfgs; - void (*reconfig_mss_clients)(void); - void (*set_txn_overrides)(void); -} tegra_mc_settings_t; +#define _START_OF_TABLE_ \ + { \ + .reg = 0xCAFE05C7U, \ + .val = 0x00000000U, \ + } + +#define _END_OF_TABLE_ \ + { \ + .reg = 0xFFFFFFFFU, \ + .val = 0xFFFFFFFFU, \ + } + +#endif /* __ASSEMBLER__ */ + +#ifndef __ASSEMBLER__ + +#include <lib/mmio.h> static inline uint32_t tegra_mc_read_32(uint32_t off) { @@ -108,6 +69,7 @@ static inline void tegra_mc_write_32(uint32_t off, uint32_t val) mmio_write_32(TEGRA_MC_BASE + off, val); } +#if defined(TEGRA_MC_STREAMID_BASE) static inline uint32_t tegra_mc_streamid_read_32(uint32_t off) { return mmio_read_32(TEGRA_MC_STREAMID_BASE + off); @@ -116,54 +78,21 @@ static inline uint32_t tegra_mc_streamid_read_32(uint32_t off) static inline void tegra_mc_streamid_write_32(uint32_t off, uint32_t val) { mmio_write_32(TEGRA_MC_STREAMID_BASE + off, val); + assert(mmio_read_32(TEGRA_MC_STREAMID_BASE + off) == val); } +#endif -#define mc_set_pcfifo_unordered_boot_so_mss(id, client) \ - ((uint32_t)~MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_MASK | \ - MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_UNORDERED) - -#define mc_set_pcfifo_ordered_boot_so_mss(id, client) \ - MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_ORDERED +void plat_memctrl_setup(void); -#define mc_set_tsa_passthrough(client) \ - { \ - mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ - (TSA_CONFIG_STATIC0_CSW_##client##_RESET & \ - (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ - (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ - } - -#define mc_set_tsa_w_passthrough(client) \ - { \ - mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ - (TSA_CONFIG_STATIC0_CSW_RESET_W & \ - (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ - (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ - } - -#define mc_set_tsa_r_passthrough(client) \ - { \ - mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSR_##client, \ - (TSA_CONFIG_STATIC0_CSR_RESET_R & \ - (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ - (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ - } - -#define mc_set_txn_override(client, normal_axi_id, so_dev_axi_id, normal_override, so_dev_override) \ - { \ - tegra_mc_write_32(MC_TXN_OVERRIDE_CONFIG_##client, \ - MC_TXN_OVERRIDE_##normal_axi_id | \ - MC_TXN_OVERRIDE_CONFIG_COH_PATH_##so_dev_override##_SO_DEV | \ - MC_TXN_OVERRIDE_CONFIG_COH_PATH_##normal_override##_NORMAL | \ - MC_TXN_OVERRIDE_CONFIG_CGID_##so_dev_axi_id); \ - } +void plat_memctrl_restore(void); +mc_regs_t *plat_memctrl_get_sys_suspend_ctx(void); /******************************************************************************* - * Handler to read memory configuration settings + * Handler to save MC settings before "System Suspend" to TZDRAM * - * Implemented by SoCs under tegra/soc/txxx + * Implemented by Tegra common memctrl_v2 driver under common/drivers/memctrl ******************************************************************************/ -tegra_mc_settings_t *tegra_get_mc_settings(void); +void tegra_mc_save_context(uint64_t mc_ctx_addr); /******************************************************************************* * Handler to program the scratch registers with TZDRAM settings for the diff --git a/plat/nvidia/tegra/include/drivers/pmc.h b/plat/nvidia/tegra/include/drivers/pmc.h index 32252a28b..8752b84c6 100644 --- a/plat/nvidia/tegra/include/drivers/pmc.h +++ b/plat/nvidia/tegra/include/drivers/pmc.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -18,27 +19,37 @@ #define PMC_DPD_ENABLE_0 U(0x24) #define PMC_PWRGATE_STATUS U(0x38) #define PMC_PWRGATE_TOGGLE U(0x30) -#define PMC_SECURE_SCRATCH0 U(0xb0) -#define PMC_SECURE_SCRATCH5 U(0xc4) +#define PMC_SCRATCH1 U(0x54) #define PMC_CRYPTO_OP_0 U(0xf4) #define PMC_TOGGLE_START U(0x100) +#define PMC_SCRATCH31 U(0x118) +#define PMC_SCRATCH32 U(0x11C) +#define PMC_SCRATCH33 U(0x120) #define PMC_SCRATCH39 U(0x138) +#define PMC_SCRATCH40 U(0x13C) #define PMC_SCRATCH41 U(0x140) -#define PMC_SECURE_SCRATCH6 U(0x224) -#define PMC_SECURE_SCRATCH7 U(0x228) -#define PMC_SECURE_DISABLE2 U(0x2c4) +#define PMC_SCRATCH42 U(0x144) +#define PMC_SCRATCH43 U(0x22C) +#define PMC_SCRATCH44 U(0x230) +#define PMC_SCRATCH45 U(0x234) +#define PMC_SCRATCH46 U(0x238) +#define PMC_SCRATCH47 U(0x23C) +#define PMC_SCRATCH48 U(0x240) +#define PMC_SCRATCH50 U(0x248) +#define PMC_SCRATCH51 U(0x24C) +#define PMC_TSC_MULT_0 U(0x2B4) +#define PMC_STICKY_BIT U(0x2C0) +#define PMC_SECURE_DISABLE2 U(0x2C4) #define PMC_SECURE_DISABLE2_WRITE22_ON (U(1) << 28) -#define PMC_SECURE_SCRATCH8 U(0x300) -#define PMC_SECURE_SCRATCH79 U(0x41c) #define PMC_FUSE_CONTROL_0 U(0x450) -#define PMC_SECURE_SCRATCH22 U(0x338) -#define PMC_SECURE_DISABLE3 U(0x2d8) +#define PMC_SECURE_DISABLE3 U(0x2D8) #define PMC_SECURE_DISABLE3_WRITE34_ON (U(1) << 20) #define PMC_SECURE_DISABLE3_WRITE35_ON (U(1) << 22) +#define PMC_SECURE_SCRATCH22 U(0x338) #define PMC_SECURE_SCRATCH34 U(0x368) #define PMC_SECURE_SCRATCH35 U(0x36c) -#define PMC_SECURE_SCRATCH80 U(0xa98) -#define PMC_SECURE_SCRATCH119 U(0xb34) +#define PMC_SCRATCH56 U(0x600) +#define PMC_SCRATCH57 U(0x604) #define PMC_SCRATCH201 U(0x844) static inline uint32_t tegra_pmc_read_32(uint32_t off) diff --git a/plat/nvidia/tegra/include/drivers/security_engine.h b/plat/nvidia/tegra/include/drivers/security_engine.h index 8a249249b..5ae625793 100644 --- a/plat/nvidia/tegra/include/drivers/security_engine.h +++ b/plat/nvidia/tegra/include/drivers/security_engine.h @@ -1,6 +1,6 @@ /* * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved. - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -55,5 +55,6 @@ void tegra_se_init(void); int tegra_se_suspend(void); void tegra_se_resume(void); int tegra_se_save_tzram(void); +int32_t tegra_se_save_sha256_hash(uint64_t bl31_base, uint32_t src_len_inbyte); #endif /* SECURITY_ENGINE_H */ diff --git a/plat/nvidia/tegra/include/drivers/smmu.h b/plat/nvidia/tegra/include/drivers/smmu.h index 424a91aea..1de9af6e5 100644 --- a/plat/nvidia/tegra/include/drivers/smmu.h +++ b/plat/nvidia/tegra/include/drivers/smmu.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2016-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -12,566 +13,7 @@ #include <memctrl_v2.h> #include <tegra_def.h> -/******************************************************************************* - * SMMU Register constants - ******************************************************************************/ -#define SMMU_CBn_SCTLR (0x0U) -#define SMMU_CBn_SCTLR_STAGE2 (0x0U) #define SMMU_CBn_ACTLR (0x4U) -#define SMMU_CBn_RESUME (0x8U) -#define SMMU_CBn_TCR2 (0x10U) -#define SMMU_CBn_TTBR0_LO (0x20U) -#define SMMU_CBn_TTBR0_HI (0x24U) -#define SMMU_CBn_TTBR1_LO (0x28U) -#define SMMU_CBn_TTBR1_HI (0x2cU) -#define SMMU_CBn_TCR_LPAE (0x30U) -#define SMMU_CBn_TCR (0x30U) -#define SMMU_CBn_TCR_EAE_1 (0x30U) -#define SMMU_CBn_TCR (0x30U) -#define SMMU_CBn_CONTEXTIDR (0x34U) -#define SMMU_CBn_CONTEXTIDR_EAE_1 (0x34U) -#define SMMU_CBn_PRRR_MAIR0 (0x38U) -#define SMMU_CBn_NMRR_MAIR1 (0x3cU) -#define SMMU_CBn_SMMU_CBn_PAR (0x50U) -#define SMMU_CBn_SMMU_CBn_PAR0 (0x50U) -#define SMMU_CBn_SMMU_CBn_PAR1 (0x54U) -/* SMMU_CBn_SMMU_CBn_PAR0_Fault (0x50U) */ -/* SMMU_CBn_SMMU_CBn_PAR0_Fault (0x54U) */ -#define SMMU_CBn_FSR (0x58U) -#define SMMU_CBn_FSRRESTORE (0x5cU) -#define SMMU_CBn_FAR_LO (0x60U) -#define SMMU_CBn_FAR_HI (0x64U) -#define SMMU_CBn_FSYNR0 (0x68U) -#define SMMU_CBn_IPAFAR_LO (0x70U) -#define SMMU_CBn_IPAFAR_HI (0x74U) -#define SMMU_CBn_TLBIVA_LO (0x600U) -#define SMMU_CBn_TLBIVA_HI (0x604U) -#define SMMU_CBn_TLBIVA_AARCH_32 (0x600U) -#define SMMU_CBn_TLBIVAA_LO (0x608U) -#define SMMU_CBn_TLBIVAA_HI (0x60cU) -#define SMMU_CBn_TLBIVAA_AARCH_32 (0x608U) -#define SMMU_CBn_TLBIASID (0x610U) -#define SMMU_CBn_TLBIALL (0x618U) -#define SMMU_CBn_TLBIVAL_LO (0x620U) -#define SMMU_CBn_TLBIVAL_HI (0x624U) -#define SMMU_CBn_TLBIVAL_AARCH_32 (0x618U) -#define SMMU_CBn_TLBIVAAL_LO (0x628U) -#define SMMU_CBn_TLBIVAAL_HI (0x62cU) -#define SMMU_CBn_TLBIVAAL_AARCH_32 (0x628U) -#define SMMU_CBn_TLBIIPAS2_LO (0x630U) -#define SMMU_CBn_TLBIIPAS2_HI (0x634U) -#define SMMU_CBn_TLBIIPAS2L_LO (0x638U) -#define SMMU_CBn_TLBIIPAS2L_HI (0x63cU) -#define SMMU_CBn_TLBSYNC (0x7f0U) -#define SMMU_CBn_TLBSTATUS (0x7f4U) -#define SMMU_CBn_ATSR (0x800U) -#define SMMU_CBn_PMEVCNTR0 (0xe00U) -#define SMMU_CBn_PMEVCNTR1 (0xe04U) -#define SMMU_CBn_PMEVCNTR2 (0xe08U) -#define SMMU_CBn_PMEVCNTR3 (0xe0cU) -#define SMMU_CBn_PMEVTYPER0 (0xe80U) -#define SMMU_CBn_PMEVTYPER1 (0xe84U) -#define SMMU_CBn_PMEVTYPER2 (0xe88U) -#define SMMU_CBn_PMEVTYPER3 (0xe8cU) -#define SMMU_CBn_PMCFGR (0xf00U) -#define SMMU_CBn_PMCR (0xf04U) -#define SMMU_CBn_PMCEID (0xf20U) -#define SMMU_CBn_PMCNTENSE (0xf40U) -#define SMMU_CBn_PMCNTENCLR (0xf44U) -#define SMMU_CBn_PMCNTENSET (0xf48U) -#define SMMU_CBn_PMINTENCLR (0xf4cU) -#define SMMU_CBn_PMOVSCLR (0xf50U) -#define SMMU_CBn_PMOVSSET (0xf58U) -#define SMMU_CBn_PMAUTHSTATUS (0xfb8U) -#define SMMU_GNSR0_CR0 (0x0U) -#define SMMU_GNSR0_CR2 (0x8U) -#define SMMU_GNSR0_ACR (0x10U) -#define SMMU_GNSR0_IDR0 (0x20U) -#define SMMU_GNSR0_IDR1 (0x24U) -#define SMMU_GNSR0_IDR2 (0x28U) -#define SMMU_GNSR0_IDR7 (0x3cU) -#define SMMU_GNSR0_GFAR_LO (0x40U) -#define SMMU_GNSR0_GFAR_HI (0x44U) -#define SMMU_GNSR0_GFSR (0x48U) -#define SMMU_GNSR0_GFSRRESTORE (0x4cU) -#define SMMU_GNSR0_GFSYNR0 (0x50U) -#define SMMU_GNSR0_GFSYNR1 (0x54U) -#define SMMU_GNSR0_GFSYNR1_v2 (0x54U) -#define SMMU_GNSR0_TLBIVMID (0x64U) -#define SMMU_GNSR0_TLBIALLNSNH (0x68U) -#define SMMU_GNSR0_TLBIALLH (0x6cU) -#define SMMU_GNSR0_TLBGSYNC (0x70U) -#define SMMU_GNSR0_TLBGSTATUS (0x74U) -#define SMMU_GNSR0_TLBIVAH_LO (0x78U) -#define SMMU_GNSR0_TLBIVALH64_LO (0xb0U) -#define SMMU_GNSR0_TLBIVALH64_HI (0xb4U) -#define SMMU_GNSR0_TLBIVMIDS1 (0xb8U) -#define SMMU_GNSR0_TLBIVAH64_LO (0xc0U) -#define SMMU_GNSR0_TLBIVAH64_HI (0xc4U) -#define SMMU_GNSR0_SMR0 (0x800U) -#define SMMU_GNSR0_SMRn (0x800U) -#define SMMU_GNSR0_SMR1 (0x804U) -#define SMMU_GNSR0_SMR2 (0x808U) -#define SMMU_GNSR0_SMR3 (0x80cU) -#define SMMU_GNSR0_SMR4 (0x810U) -#define SMMU_GNSR0_SMR5 (0x814U) -#define SMMU_GNSR0_SMR6 (0x818U) -#define SMMU_GNSR0_SMR7 (0x81cU) -#define SMMU_GNSR0_SMR8 (0x820U) -#define SMMU_GNSR0_SMR9 (0x824U) -#define SMMU_GNSR0_SMR10 (0x828U) -#define SMMU_GNSR0_SMR11 (0x82cU) -#define SMMU_GNSR0_SMR12 (0x830U) -#define SMMU_GNSR0_SMR13 (0x834U) -#define SMMU_GNSR0_SMR14 (0x838U) -#define SMMU_GNSR0_SMR15 (0x83cU) -#define SMMU_GNSR0_SMR16 (0x840U) -#define SMMU_GNSR0_SMR17 (0x844U) -#define SMMU_GNSR0_SMR18 (0x848U) -#define SMMU_GNSR0_SMR19 (0x84cU) -#define SMMU_GNSR0_SMR20 (0x850U) -#define SMMU_GNSR0_SMR21 (0x854U) -#define SMMU_GNSR0_SMR22 (0x858U) -#define SMMU_GNSR0_SMR23 (0x85cU) -#define SMMU_GNSR0_SMR24 (0x860U) -#define SMMU_GNSR0_SMR25 (0x864U) -#define SMMU_GNSR0_SMR26 (0x868U) -#define SMMU_GNSR0_SMR27 (0x86cU) -#define SMMU_GNSR0_SMR28 (0x870U) -#define SMMU_GNSR0_SMR29 (0x874U) -#define SMMU_GNSR0_SMR30 (0x878U) -#define SMMU_GNSR0_SMR31 (0x87cU) -#define SMMU_GNSR0_SMR32 (0x880U) -#define SMMU_GNSR0_SMR33 (0x884U) -#define SMMU_GNSR0_SMR34 (0x888U) -#define SMMU_GNSR0_SMR35 (0x88cU) -#define SMMU_GNSR0_SMR36 (0x890U) -#define SMMU_GNSR0_SMR37 (0x894U) -#define SMMU_GNSR0_SMR38 (0x898U) -#define SMMU_GNSR0_SMR39 (0x89cU) -#define SMMU_GNSR0_SMR40 (0x8a0U) -#define SMMU_GNSR0_SMR41 (0x8a4U) -#define SMMU_GNSR0_SMR42 (0x8a8U) -#define SMMU_GNSR0_SMR43 (0x8acU) -#define SMMU_GNSR0_SMR44 (0x8b0U) -#define SMMU_GNSR0_SMR45 (0x8b4U) -#define SMMU_GNSR0_SMR46 (0x8b8U) -#define SMMU_GNSR0_SMR47 (0x8bcU) -#define SMMU_GNSR0_SMR48 (0x8c0U) -#define SMMU_GNSR0_SMR49 (0x8c4U) -#define SMMU_GNSR0_SMR50 (0x8c8U) -#define SMMU_GNSR0_SMR51 (0x8ccU) -#define SMMU_GNSR0_SMR52 (0x8d0U) -#define SMMU_GNSR0_SMR53 (0x8d4U) -#define SMMU_GNSR0_SMR54 (0x8d8U) -#define SMMU_GNSR0_SMR55 (0x8dcU) -#define SMMU_GNSR0_SMR56 (0x8e0U) -#define SMMU_GNSR0_SMR57 (0x8e4U) -#define SMMU_GNSR0_SMR58 (0x8e8U) -#define SMMU_GNSR0_SMR59 (0x8ecU) -#define SMMU_GNSR0_SMR60 (0x8f0U) -#define SMMU_GNSR0_SMR61 (0x8f4U) -#define SMMU_GNSR0_SMR62 (0x8f8U) -#define SMMU_GNSR0_SMR63 (0x8fcU) -#define SMMU_GNSR0_SMR64 (0x900U) -#define SMMU_GNSR0_SMR65 (0x904U) -#define SMMU_GNSR0_SMR66 (0x908U) -#define SMMU_GNSR0_SMR67 (0x90cU) -#define SMMU_GNSR0_SMR68 (0x910U) -#define SMMU_GNSR0_SMR69 (0x914U) -#define SMMU_GNSR0_SMR70 (0x918U) -#define SMMU_GNSR0_SMR71 (0x91cU) -#define SMMU_GNSR0_SMR72 (0x920U) -#define SMMU_GNSR0_SMR73 (0x924U) -#define SMMU_GNSR0_SMR74 (0x928U) -#define SMMU_GNSR0_SMR75 (0x92cU) -#define SMMU_GNSR0_SMR76 (0x930U) -#define SMMU_GNSR0_SMR77 (0x934U) -#define SMMU_GNSR0_SMR78 (0x938U) -#define SMMU_GNSR0_SMR79 (0x93cU) -#define SMMU_GNSR0_SMR80 (0x940U) -#define SMMU_GNSR0_SMR81 (0x944U) -#define SMMU_GNSR0_SMR82 (0x948U) -#define SMMU_GNSR0_SMR83 (0x94cU) -#define SMMU_GNSR0_SMR84 (0x950U) -#define SMMU_GNSR0_SMR85 (0x954U) -#define SMMU_GNSR0_SMR86 (0x958U) -#define SMMU_GNSR0_SMR87 (0x95cU) -#define SMMU_GNSR0_SMR88 (0x960U) -#define SMMU_GNSR0_SMR89 (0x964U) -#define SMMU_GNSR0_SMR90 (0x968U) -#define SMMU_GNSR0_SMR91 (0x96cU) -#define SMMU_GNSR0_SMR92 (0x970U) -#define SMMU_GNSR0_SMR93 (0x974U) -#define SMMU_GNSR0_SMR94 (0x978U) -#define SMMU_GNSR0_SMR95 (0x97cU) -#define SMMU_GNSR0_SMR96 (0x980U) -#define SMMU_GNSR0_SMR97 (0x984U) -#define SMMU_GNSR0_SMR98 (0x988U) -#define SMMU_GNSR0_SMR99 (0x98cU) -#define SMMU_GNSR0_SMR100 (0x990U) -#define SMMU_GNSR0_SMR101 (0x994U) -#define SMMU_GNSR0_SMR102 (0x998U) -#define SMMU_GNSR0_SMR103 (0x99cU) -#define SMMU_GNSR0_SMR104 (0x9a0U) -#define SMMU_GNSR0_SMR105 (0x9a4U) -#define SMMU_GNSR0_SMR106 (0x9a8U) -#define SMMU_GNSR0_SMR107 (0x9acU) -#define SMMU_GNSR0_SMR108 (0x9b0U) -#define SMMU_GNSR0_SMR109 (0x9b4U) -#define SMMU_GNSR0_SMR110 (0x9b8U) -#define SMMU_GNSR0_SMR111 (0x9bcU) -#define SMMU_GNSR0_SMR112 (0x9c0U) -#define SMMU_GNSR0_SMR113 (0x9c4U) -#define SMMU_GNSR0_SMR114 (0x9c8U) -#define SMMU_GNSR0_SMR115 (0x9ccU) -#define SMMU_GNSR0_SMR116 (0x9d0U) -#define SMMU_GNSR0_SMR117 (0x9d4U) -#define SMMU_GNSR0_SMR118 (0x9d8U) -#define SMMU_GNSR0_SMR119 (0x9dcU) -#define SMMU_GNSR0_SMR120 (0x9e0U) -#define SMMU_GNSR0_SMR121 (0x9e4U) -#define SMMU_GNSR0_SMR122 (0x9e8U) -#define SMMU_GNSR0_SMR123 (0x9ecU) -#define SMMU_GNSR0_SMR124 (0x9f0U) -#define SMMU_GNSR0_SMR125 (0x9f4U) -#define SMMU_GNSR0_SMR126 (0x9f8U) -#define SMMU_GNSR0_SMR127 (0x9fcU) -#define SMMU_GNSR0_S2CR0 (0xc00U) -#define SMMU_GNSR0_S2CRn (0xc00U) -#define SMMU_GNSR0_S2CRn (0xc00U) -#define SMMU_GNSR0_S2CR1 (0xc04U) -#define SMMU_GNSR0_S2CR2 (0xc08U) -#define SMMU_GNSR0_S2CR3 (0xc0cU) -#define SMMU_GNSR0_S2CR4 (0xc10U) -#define SMMU_GNSR0_S2CR5 (0xc14U) -#define SMMU_GNSR0_S2CR6 (0xc18U) -#define SMMU_GNSR0_S2CR7 (0xc1cU) -#define SMMU_GNSR0_S2CR8 (0xc20U) -#define SMMU_GNSR0_S2CR9 (0xc24U) -#define SMMU_GNSR0_S2CR10 (0xc28U) -#define SMMU_GNSR0_S2CR11 (0xc2cU) -#define SMMU_GNSR0_S2CR12 (0xc30U) -#define SMMU_GNSR0_S2CR13 (0xc34U) -#define SMMU_GNSR0_S2CR14 (0xc38U) -#define SMMU_GNSR0_S2CR15 (0xc3cU) -#define SMMU_GNSR0_S2CR16 (0xc40U) -#define SMMU_GNSR0_S2CR17 (0xc44U) -#define SMMU_GNSR0_S2CR18 (0xc48U) -#define SMMU_GNSR0_S2CR19 (0xc4cU) -#define SMMU_GNSR0_S2CR20 (0xc50U) -#define SMMU_GNSR0_S2CR21 (0xc54U) -#define SMMU_GNSR0_S2CR22 (0xc58U) -#define SMMU_GNSR0_S2CR23 (0xc5cU) -#define SMMU_GNSR0_S2CR24 (0xc60U) -#define SMMU_GNSR0_S2CR25 (0xc64U) -#define SMMU_GNSR0_S2CR26 (0xc68U) -#define SMMU_GNSR0_S2CR27 (0xc6cU) -#define SMMU_GNSR0_S2CR28 (0xc70U) -#define SMMU_GNSR0_S2CR29 (0xc74U) -#define SMMU_GNSR0_S2CR30 (0xc78U) -#define SMMU_GNSR0_S2CR31 (0xc7cU) -#define SMMU_GNSR0_S2CR32 (0xc80U) -#define SMMU_GNSR0_S2CR33 (0xc84U) -#define SMMU_GNSR0_S2CR34 (0xc88U) -#define SMMU_GNSR0_S2CR35 (0xc8cU) -#define SMMU_GNSR0_S2CR36 (0xc90U) -#define SMMU_GNSR0_S2CR37 (0xc94U) -#define SMMU_GNSR0_S2CR38 (0xc98U) -#define SMMU_GNSR0_S2CR39 (0xc9cU) -#define SMMU_GNSR0_S2CR40 (0xca0U) -#define SMMU_GNSR0_S2CR41 (0xca4U) -#define SMMU_GNSR0_S2CR42 (0xca8U) -#define SMMU_GNSR0_S2CR43 (0xcacU) -#define SMMU_GNSR0_S2CR44 (0xcb0U) -#define SMMU_GNSR0_S2CR45 (0xcb4U) -#define SMMU_GNSR0_S2CR46 (0xcb8U) -#define SMMU_GNSR0_S2CR47 (0xcbcU) -#define SMMU_GNSR0_S2CR48 (0xcc0U) -#define SMMU_GNSR0_S2CR49 (0xcc4U) -#define SMMU_GNSR0_S2CR50 (0xcc8U) -#define SMMU_GNSR0_S2CR51 (0xcccU) -#define SMMU_GNSR0_S2CR52 (0xcd0U) -#define SMMU_GNSR0_S2CR53 (0xcd4U) -#define SMMU_GNSR0_S2CR54 (0xcd8U) -#define SMMU_GNSR0_S2CR55 (0xcdcU) -#define SMMU_GNSR0_S2CR56 (0xce0U) -#define SMMU_GNSR0_S2CR57 (0xce4U) -#define SMMU_GNSR0_S2CR58 (0xce8U) -#define SMMU_GNSR0_S2CR59 (0xcecU) -#define SMMU_GNSR0_S2CR60 (0xcf0U) -#define SMMU_GNSR0_S2CR61 (0xcf4U) -#define SMMU_GNSR0_S2CR62 (0xcf8U) -#define SMMU_GNSR0_S2CR63 (0xcfcU) -#define SMMU_GNSR0_S2CR64 (0xd00U) -#define SMMU_GNSR0_S2CR65 (0xd04U) -#define SMMU_GNSR0_S2CR66 (0xd08U) -#define SMMU_GNSR0_S2CR67 (0xd0cU) -#define SMMU_GNSR0_S2CR68 (0xd10U) -#define SMMU_GNSR0_S2CR69 (0xd14U) -#define SMMU_GNSR0_S2CR70 (0xd18U) -#define SMMU_GNSR0_S2CR71 (0xd1cU) -#define SMMU_GNSR0_S2CR72 (0xd20U) -#define SMMU_GNSR0_S2CR73 (0xd24U) -#define SMMU_GNSR0_S2CR74 (0xd28U) -#define SMMU_GNSR0_S2CR75 (0xd2cU) -#define SMMU_GNSR0_S2CR76 (0xd30U) -#define SMMU_GNSR0_S2CR77 (0xd34U) -#define SMMU_GNSR0_S2CR78 (0xd38U) -#define SMMU_GNSR0_S2CR79 (0xd3cU) -#define SMMU_GNSR0_S2CR80 (0xd40U) -#define SMMU_GNSR0_S2CR81 (0xd44U) -#define SMMU_GNSR0_S2CR82 (0xd48U) -#define SMMU_GNSR0_S2CR83 (0xd4cU) -#define SMMU_GNSR0_S2CR84 (0xd50U) -#define SMMU_GNSR0_S2CR85 (0xd54U) -#define SMMU_GNSR0_S2CR86 (0xd58U) -#define SMMU_GNSR0_S2CR87 (0xd5cU) -#define SMMU_GNSR0_S2CR88 (0xd60U) -#define SMMU_GNSR0_S2CR89 (0xd64U) -#define SMMU_GNSR0_S2CR90 (0xd68U) -#define SMMU_GNSR0_S2CR91 (0xd6cU) -#define SMMU_GNSR0_S2CR92 (0xd70U) -#define SMMU_GNSR0_S2CR93 (0xd74U) -#define SMMU_GNSR0_S2CR94 (0xd78U) -#define SMMU_GNSR0_S2CR95 (0xd7cU) -#define SMMU_GNSR0_S2CR96 (0xd80U) -#define SMMU_GNSR0_S2CR97 (0xd84U) -#define SMMU_GNSR0_S2CR98 (0xd88U) -#define SMMU_GNSR0_S2CR99 (0xd8cU) -#define SMMU_GNSR0_S2CR100 (0xd90U) -#define SMMU_GNSR0_S2CR101 (0xd94U) -#define SMMU_GNSR0_S2CR102 (0xd98U) -#define SMMU_GNSR0_S2CR103 (0xd9cU) -#define SMMU_GNSR0_S2CR104 (0xda0U) -#define SMMU_GNSR0_S2CR105 (0xda4U) -#define SMMU_GNSR0_S2CR106 (0xda8U) -#define SMMU_GNSR0_S2CR107 (0xdacU) -#define SMMU_GNSR0_S2CR108 (0xdb0U) -#define SMMU_GNSR0_S2CR109 (0xdb4U) -#define SMMU_GNSR0_S2CR110 (0xdb8U) -#define SMMU_GNSR0_S2CR111 (0xdbcU) -#define SMMU_GNSR0_S2CR112 (0xdc0U) -#define SMMU_GNSR0_S2CR113 (0xdc4U) -#define SMMU_GNSR0_S2CR114 (0xdc8U) -#define SMMU_GNSR0_S2CR115 (0xdccU) -#define SMMU_GNSR0_S2CR116 (0xdd0U) -#define SMMU_GNSR0_S2CR117 (0xdd4U) -#define SMMU_GNSR0_S2CR118 (0xdd8U) -#define SMMU_GNSR0_S2CR119 (0xddcU) -#define SMMU_GNSR0_S2CR120 (0xde0U) -#define SMMU_GNSR0_S2CR121 (0xde4U) -#define SMMU_GNSR0_S2CR122 (0xde8U) -#define SMMU_GNSR0_S2CR123 (0xdecU) -#define SMMU_GNSR0_S2CR124 (0xdf0U) -#define SMMU_GNSR0_S2CR125 (0xdf4U) -#define SMMU_GNSR0_S2CR126 (0xdf8U) -#define SMMU_GNSR0_S2CR127 (0xdfcU) -#define SMMU_GNSR0_PIDR0 (0xfe0U) -#define SMMU_GNSR0_PIDR1 (0xfe4U) -#define SMMU_GNSR0_PIDR2 (0xfe8U) -#define SMMU_GNSR0_PIDR3 (0xfecU) -#define SMMU_GNSR0_PIDR4 (0xfd0U) -#define SMMU_GNSR0_PIDR5 (0xfd4U) -#define SMMU_GNSR0_PIDR6 (0xfd8U) -#define SMMU_GNSR0_PIDR7 (0xfdcU) -#define SMMU_GNSR0_CIDR0 (0xff0U) -#define SMMU_GNSR0_CIDR1 (0xff4U) -#define SMMU_GNSR0_CIDR2 (0xff8U) -#define SMMU_GNSR0_CIDR3 (0xffcU) -#define SMMU_GNSR1_CBAR0 (0x0U) -#define SMMU_GNSR1_CBARn (0x0U) -#define SMMU_GNSR1_CBFRSYNRA0 (0x400U) -#define SMMU_GNSR1_CBA2R0 (0x800U) -#define SMMU_GNSR1_CBAR1 (0x4U) -#define SMMU_GNSR1_CBFRSYNRA1 (0x404U) -#define SMMU_GNSR1_CBA2R1 (0x804U) -#define SMMU_GNSR1_CBAR2 (0x8U) -#define SMMU_GNSR1_CBFRSYNRA2 (0x408U) -#define SMMU_GNSR1_CBA2R2 (0x808U) -#define SMMU_GNSR1_CBAR3 (0xcU) -#define SMMU_GNSR1_CBFRSYNRA3 (0x40cU) -#define SMMU_GNSR1_CBA2R3 (0x80cU) -#define SMMU_GNSR1_CBAR4 (0x10U) -#define SMMU_GNSR1_CBFRSYNRA4 (0x410U) -#define SMMU_GNSR1_CBA2R4 (0x810U) -#define SMMU_GNSR1_CBAR5 (0x14U) -#define SMMU_GNSR1_CBFRSYNRA5 (0x414U) -#define SMMU_GNSR1_CBA2R5 (0x814U) -#define SMMU_GNSR1_CBAR6 (0x18U) -#define SMMU_GNSR1_CBFRSYNRA6 (0x418U) -#define SMMU_GNSR1_CBA2R6 (0x818U) -#define SMMU_GNSR1_CBAR7 (0x1cU) -#define SMMU_GNSR1_CBFRSYNRA7 (0x41cU) -#define SMMU_GNSR1_CBA2R7 (0x81cU) -#define SMMU_GNSR1_CBAR8 (0x20U) -#define SMMU_GNSR1_CBFRSYNRA8 (0x420U) -#define SMMU_GNSR1_CBA2R8 (0x820U) -#define SMMU_GNSR1_CBAR9 (0x24U) -#define SMMU_GNSR1_CBFRSYNRA9 (0x424U) -#define SMMU_GNSR1_CBA2R9 (0x824U) -#define SMMU_GNSR1_CBAR10 (0x28U) -#define SMMU_GNSR1_CBFRSYNRA10 (0x428U) -#define SMMU_GNSR1_CBA2R10 (0x828U) -#define SMMU_GNSR1_CBAR11 (0x2cU) -#define SMMU_GNSR1_CBFRSYNRA11 (0x42cU) -#define SMMU_GNSR1_CBA2R11 (0x82cU) -#define SMMU_GNSR1_CBAR12 (0x30U) -#define SMMU_GNSR1_CBFRSYNRA12 (0x430U) -#define SMMU_GNSR1_CBA2R12 (0x830U) -#define SMMU_GNSR1_CBAR13 (0x34U) -#define SMMU_GNSR1_CBFRSYNRA13 (0x434U) -#define SMMU_GNSR1_CBA2R13 (0x834U) -#define SMMU_GNSR1_CBAR14 (0x38U) -#define SMMU_GNSR1_CBFRSYNRA14 (0x438U) -#define SMMU_GNSR1_CBA2R14 (0x838U) -#define SMMU_GNSR1_CBAR15 (0x3cU) -#define SMMU_GNSR1_CBFRSYNRA15 (0x43cU) -#define SMMU_GNSR1_CBA2R15 (0x83cU) -#define SMMU_GNSR1_CBAR16 (0x40U) -#define SMMU_GNSR1_CBFRSYNRA16 (0x440U) -#define SMMU_GNSR1_CBA2R16 (0x840U) -#define SMMU_GNSR1_CBAR17 (0x44U) -#define SMMU_GNSR1_CBFRSYNRA17 (0x444U) -#define SMMU_GNSR1_CBA2R17 (0x844U) -#define SMMU_GNSR1_CBAR18 (0x48U) -#define SMMU_GNSR1_CBFRSYNRA18 (0x448U) -#define SMMU_GNSR1_CBA2R18 (0x848U) -#define SMMU_GNSR1_CBAR19 (0x4cU) -#define SMMU_GNSR1_CBFRSYNRA19 (0x44cU) -#define SMMU_GNSR1_CBA2R19 (0x84cU) -#define SMMU_GNSR1_CBAR20 (0x50U) -#define SMMU_GNSR1_CBFRSYNRA20 (0x450U) -#define SMMU_GNSR1_CBA2R20 (0x850U) -#define SMMU_GNSR1_CBAR21 (0x54U) -#define SMMU_GNSR1_CBFRSYNRA21 (0x454U) -#define SMMU_GNSR1_CBA2R21 (0x854U) -#define SMMU_GNSR1_CBAR22 (0x58U) -#define SMMU_GNSR1_CBFRSYNRA22 (0x458U) -#define SMMU_GNSR1_CBA2R22 (0x858U) -#define SMMU_GNSR1_CBAR23 (0x5cU) -#define SMMU_GNSR1_CBFRSYNRA23 (0x45cU) -#define SMMU_GNSR1_CBA2R23 (0x85cU) -#define SMMU_GNSR1_CBAR24 (0x60U) -#define SMMU_GNSR1_CBFRSYNRA24 (0x460U) -#define SMMU_GNSR1_CBA2R24 (0x860U) -#define SMMU_GNSR1_CBAR25 (0x64U) -#define SMMU_GNSR1_CBFRSYNRA25 (0x464U) -#define SMMU_GNSR1_CBA2R25 (0x864U) -#define SMMU_GNSR1_CBAR26 (0x68U) -#define SMMU_GNSR1_CBFRSYNRA26 (0x468U) -#define SMMU_GNSR1_CBA2R26 (0x868U) -#define SMMU_GNSR1_CBAR27 (0x6cU) -#define SMMU_GNSR1_CBFRSYNRA27 (0x46cU) -#define SMMU_GNSR1_CBA2R27 (0x86cU) -#define SMMU_GNSR1_CBAR28 (0x70U) -#define SMMU_GNSR1_CBFRSYNRA28 (0x470U) -#define SMMU_GNSR1_CBA2R28 (0x870U) -#define SMMU_GNSR1_CBAR29 (0x74U) -#define SMMU_GNSR1_CBFRSYNRA29 (0x474U) -#define SMMU_GNSR1_CBA2R29 (0x874U) -#define SMMU_GNSR1_CBAR30 (0x78U) -#define SMMU_GNSR1_CBFRSYNRA30 (0x478U) -#define SMMU_GNSR1_CBA2R30 (0x878U) -#define SMMU_GNSR1_CBAR31 (0x7cU) -#define SMMU_GNSR1_CBFRSYNRA31 (0x47cU) -#define SMMU_GNSR1_CBA2R31 (0x87cU) -#define SMMU_GNSR1_CBAR32 (0x80U) -#define SMMU_GNSR1_CBFRSYNRA32 (0x480U) -#define SMMU_GNSR1_CBA2R32 (0x880U) -#define SMMU_GNSR1_CBAR33 (0x84U) -#define SMMU_GNSR1_CBFRSYNRA33 (0x484U) -#define SMMU_GNSR1_CBA2R33 (0x884U) -#define SMMU_GNSR1_CBAR34 (0x88U) -#define SMMU_GNSR1_CBFRSYNRA34 (0x488U) -#define SMMU_GNSR1_CBA2R34 (0x888U) -#define SMMU_GNSR1_CBAR35 (0x8cU) -#define SMMU_GNSR1_CBFRSYNRA35 (0x48cU) -#define SMMU_GNSR1_CBA2R35 (0x88cU) -#define SMMU_GNSR1_CBAR36 (0x90U) -#define SMMU_GNSR1_CBFRSYNRA36 (0x490U) -#define SMMU_GNSR1_CBA2R36 (0x890U) -#define SMMU_GNSR1_CBAR37 (0x94U) -#define SMMU_GNSR1_CBFRSYNRA37 (0x494U) -#define SMMU_GNSR1_CBA2R37 (0x894U) -#define SMMU_GNSR1_CBAR38 (0x98U) -#define SMMU_GNSR1_CBFRSYNRA38 (0x498U) -#define SMMU_GNSR1_CBA2R38 (0x898U) -#define SMMU_GNSR1_CBAR39 (0x9cU) -#define SMMU_GNSR1_CBFRSYNRA39 (0x49cU) -#define SMMU_GNSR1_CBA2R39 (0x89cU) -#define SMMU_GNSR1_CBAR40 (0xa0U) -#define SMMU_GNSR1_CBFRSYNRA40 (0x4a0U) -#define SMMU_GNSR1_CBA2R40 (0x8a0U) -#define SMMU_GNSR1_CBAR41 (0xa4U) -#define SMMU_GNSR1_CBFRSYNRA41 (0x4a4U) -#define SMMU_GNSR1_CBA2R41 (0x8a4U) -#define SMMU_GNSR1_CBAR42 (0xa8U) -#define SMMU_GNSR1_CBFRSYNRA42 (0x4a8U) -#define SMMU_GNSR1_CBA2R42 (0x8a8U) -#define SMMU_GNSR1_CBAR43 (0xacU) -#define SMMU_GNSR1_CBFRSYNRA43 (0x4acU) -#define SMMU_GNSR1_CBA2R43 (0x8acU) -#define SMMU_GNSR1_CBAR44 (0xb0U) -#define SMMU_GNSR1_CBFRSYNRA44 (0x4b0U) -#define SMMU_GNSR1_CBA2R44 (0x8b0U) -#define SMMU_GNSR1_CBAR45 (0xb4U) -#define SMMU_GNSR1_CBFRSYNRA45 (0x4b4U) -#define SMMU_GNSR1_CBA2R45 (0x8b4U) -#define SMMU_GNSR1_CBAR46 (0xb8U) -#define SMMU_GNSR1_CBFRSYNRA46 (0x4b8U) -#define SMMU_GNSR1_CBA2R46 (0x8b8U) -#define SMMU_GNSR1_CBAR47 (0xbcU) -#define SMMU_GNSR1_CBFRSYNRA47 (0x4bcU) -#define SMMU_GNSR1_CBA2R47 (0x8bcU) -#define SMMU_GNSR1_CBAR48 (0xc0U) -#define SMMU_GNSR1_CBFRSYNRA48 (0x4c0U) -#define SMMU_GNSR1_CBA2R48 (0x8c0U) -#define SMMU_GNSR1_CBAR49 (0xc4U) -#define SMMU_GNSR1_CBFRSYNRA49 (0x4c4U) -#define SMMU_GNSR1_CBA2R49 (0x8c4U) -#define SMMU_GNSR1_CBAR50 (0xc8U) -#define SMMU_GNSR1_CBFRSYNRA50 (0x4c8U) -#define SMMU_GNSR1_CBA2R50 (0x8c8U) -#define SMMU_GNSR1_CBAR51 (0xccU) -#define SMMU_GNSR1_CBFRSYNRA51 (0x4ccU) -#define SMMU_GNSR1_CBA2R51 (0x8ccU) -#define SMMU_GNSR1_CBAR52 (0xd0U) -#define SMMU_GNSR1_CBFRSYNRA52 (0x4d0U) -#define SMMU_GNSR1_CBA2R52 (0x8d0U) -#define SMMU_GNSR1_CBAR53 (0xd4U) -#define SMMU_GNSR1_CBFRSYNRA53 (0x4d4U) -#define SMMU_GNSR1_CBA2R53 (0x8d4U) -#define SMMU_GNSR1_CBAR54 (0xd8U) -#define SMMU_GNSR1_CBFRSYNRA54 (0x4d8U) -#define SMMU_GNSR1_CBA2R54 (0x8d8U) -#define SMMU_GNSR1_CBAR55 (0xdcU) -#define SMMU_GNSR1_CBFRSYNRA55 (0x4dcU) -#define SMMU_GNSR1_CBA2R55 (0x8dcU) -#define SMMU_GNSR1_CBAR56 (0xe0U) -#define SMMU_GNSR1_CBFRSYNRA56 (0x4e0U) -#define SMMU_GNSR1_CBA2R56 (0x8e0U) -#define SMMU_GNSR1_CBAR57 (0xe4U) -#define SMMU_GNSR1_CBFRSYNRA57 (0x4e4U) -#define SMMU_GNSR1_CBA2R57 (0x8e4U) -#define SMMU_GNSR1_CBAR58 (0xe8U) -#define SMMU_GNSR1_CBFRSYNRA58 (0x4e8U) -#define SMMU_GNSR1_CBA2R58 (0x8e8U) -#define SMMU_GNSR1_CBAR59 (0xecU) -#define SMMU_GNSR1_CBFRSYNRA59 (0x4ecU) -#define SMMU_GNSR1_CBA2R59 (0x8ecU) -#define SMMU_GNSR1_CBAR60 (0xf0U) -#define SMMU_GNSR1_CBFRSYNRA60 (0x4f0U) -#define SMMU_GNSR1_CBA2R60 (0x8f0U) -#define SMMU_GNSR1_CBAR61 (0xf4U) -#define SMMU_GNSR1_CBFRSYNRA61 (0x4f4U) -#define SMMU_GNSR1_CBA2R61 (0x8f4U) -#define SMMU_GNSR1_CBAR62 (0xf8U) -#define SMMU_GNSR1_CBFRSYNRA62 (0x4f8U) -#define SMMU_GNSR1_CBA2R62 (0x8f8U) -#define SMMU_GNSR1_CBAR63 (0xfcU) -#define SMMU_GNSR1_CBFRSYNRA63 (0x4fcU) -#define SMMU_GNSR1_CBA2R63 (0x8fcU) /******************************************************************************* * SMMU Global Secure Aux. Configuration Register @@ -581,269 +23,70 @@ #define SMMU_GSR0_PGSIZE_SHIFT 16U #define SMMU_GSR0_PGSIZE_4K (0U << SMMU_GSR0_PGSIZE_SHIFT) #define SMMU_GSR0_PGSIZE_64K (1U << SMMU_GSR0_PGSIZE_SHIFT) -#define SMMU_ACR_CACHE_LOCK_ENABLE_BIT (1U << 26) +#define SMMU_ACR_CACHE_LOCK_ENABLE_BIT (1ULL << 26U) +#define SMMU_GSR0_PER (0x20200U) /******************************************************************************* * SMMU Global Aux. Control Register ******************************************************************************/ #define SMMU_CBn_ACTLR_CPRE_BIT (1ULL << 1U) -/******************************************************************************* - * SMMU configuration constants - ******************************************************************************/ -#define ID1_PAGESIZE (1U << 31U) -#define ID1_NUMPAGENDXB_SHIFT 28U -#define ID1_NUMPAGENDXB_MASK 7U -#define ID1_NUMS2CB_SHIFT 16U -#define ID1_NUMS2CB_MASK 0xffU -#define ID1_NUMCB_SHIFT 0U -#define ID1_NUMCB_MASK 0xffU -#define PGSHIFT 16U -#define CB_SIZE 0x800000U +/* SMMU IDs currently supported by the driver */ +enum { + TEGRA_SMMU0 = 0U, + TEGRA_SMMU1 = 1U, + TEGRA_SMMU2 = 2U +}; -typedef struct smmu_regs { - uint32_t reg; - uint32_t val; -} smmu_regs_t; +static inline uint32_t tegra_smmu_read_32(uint32_t smmu_id, uint32_t off) +{ + uint32_t ret = 0U; -#define mc_make_sid_override_cfg(name) \ - { \ - .reg = TEGRA_MC_STREAMID_BASE + MC_STREAMID_OVERRIDE_CFG_ ## name, \ - .val = 0x00000000U, \ +#if defined(TEGRA_SMMU0_BASE) + if (smmu_id == TEGRA_SMMU0) { + ret = mmio_read_32(TEGRA_SMMU0_BASE + (uint64_t)off); } +#endif -#define mc_make_sid_security_cfg(name) \ - { \ - .reg = TEGRA_MC_STREAMID_BASE + MC_STREAMID_OVERRIDE_TO_SECURITY_CFG(MC_STREAMID_OVERRIDE_CFG_ ## name), \ - .val = 0x00000000U, \ +#if defined(TEGRA_SMMU1_BASE) + if (smmu_id == TEGRA_SMMU1) { + ret = mmio_read_32(TEGRA_SMMU1_BASE + (uint64_t)off); } +#endif -#define smmu_make_gnsr0_sec_cfg(base_addr, name) \ - { \ - .reg = base_addr + SMMU_GNSR0_ ## name, \ - .val = 0x00000000U, \ +#if defined(TEGRA_SMMU2_BASE) + if (smmu_id == TEGRA_SMMU2) { + ret = mmio_read_32(TEGRA_SMMU2_BASE + (uint64_t)off); } +#endif -/* - * On ARM-SMMU, conditional offset to access secure aliases of non-secure registers - * is 0x400. So, add it to register address - */ -#define smmu_make_gnsr0_nsec_cfg(base_addr, name) \ - { \ - .reg = base_addr + 0x400U + SMMU_GNSR0_ ## name, \ - .val = 0x00000000U, \ - } - -#define smmu_make_gnsr0_smr_cfg(base_addr, n) \ - { \ - .reg = base_addr + SMMU_GNSR0_SMR ## n, \ - .val = 0x00000000U, \ - } - -#define smmu_make_gnsr0_s2cr_cfg(base_addr, n) \ - { \ - .reg = base_addr + SMMU_GNSR0_S2CR ## n, \ - .val = 0x00000000U, \ - } + return ret; +} -#define smmu_make_gnsr1_cbar_cfg(base_addr, n) \ - { \ - .reg = base_addr + (1U << PGSHIFT) + SMMU_GNSR1_CBAR ## n, \ - .val = 0x00000000U, \ +static inline void tegra_smmu_write_32(uint32_t smmu_id, + uint32_t off, uint32_t val) +{ +#if defined(TEGRA_SMMU0_BASE) + if (smmu_id == TEGRA_SMMU0) { + mmio_write_32(TEGRA_SMMU0_BASE + (uint64_t)off, val); } +#endif -#define smmu_make_gnsr1_cba2r_cfg(base_addr, n) \ - { \ - .reg = base_addr + (1U << PGSHIFT) + SMMU_GNSR1_CBA2R ## n, \ - .val = 0x00000000U, \ +#if defined(TEGRA_SMMU1_BASE) + if (smmu_id == TEGRA_SMMU1) { + mmio_write_32(TEGRA_SMMU1_BASE + (uint64_t)off, val); } +#endif -#define smmu_make_cb_cfg(base_addr, name, n) \ - { \ - .reg = base_addr + (CB_SIZE >> 1) + (n * (1 << PGSHIFT)) \ - + SMMU_CBn_ ## name, \ - .val = 0x00000000U, \ +#if defined(TEGRA_SMMU2_BASE) + if (smmu_id == TEGRA_SMMU2) { + mmio_write_32(TEGRA_SMMU2_BASE + (uint64_t)off, val); } - -#define smmu_make_smrg_group(base_addr, n) \ - smmu_make_gnsr0_smr_cfg(base_addr, n), \ - smmu_make_gnsr0_s2cr_cfg(base_addr, n), \ - smmu_make_gnsr1_cbar_cfg(base_addr, n), \ - smmu_make_gnsr1_cba2r_cfg(base_addr, n) /* don't put "," here. */ - -#define smmu_make_cb_group(base_addr, n) \ - smmu_make_cb_cfg(base_addr, SCTLR, n), \ - smmu_make_cb_cfg(base_addr, TCR2, n), \ - smmu_make_cb_cfg(base_addr, TTBR0_LO, n), \ - smmu_make_cb_cfg(base_addr, TTBR0_HI, n), \ - smmu_make_cb_cfg(base_addr, TCR, n), \ - smmu_make_cb_cfg(base_addr, PRRR_MAIR0, n),\ - smmu_make_cb_cfg(base_addr, FSR, n), \ - smmu_make_cb_cfg(base_addr, FAR_LO, n), \ - smmu_make_cb_cfg(base_addr, FAR_HI, n), \ - smmu_make_cb_cfg(base_addr, FSYNR0, n) /* don't put "," here. */ - -#define smmu_make_cfg(base_addr) \ - smmu_make_gnsr0_nsec_cfg(base_addr, CR0), \ - smmu_make_gnsr0_sec_cfg(base_addr, IDR0), \ - smmu_make_gnsr0_sec_cfg(base_addr, IDR1), \ - smmu_make_gnsr0_sec_cfg(base_addr, IDR2), \ - smmu_make_gnsr0_nsec_cfg(base_addr, GFSR), \ - smmu_make_gnsr0_nsec_cfg(base_addr, GFSYNR0), \ - smmu_make_gnsr0_nsec_cfg(base_addr, GFSYNR1), \ - smmu_make_gnsr0_nsec_cfg(base_addr, TLBGSTATUS),\ - smmu_make_gnsr0_nsec_cfg(base_addr, PIDR2), \ - smmu_make_smrg_group(base_addr, 0), \ - smmu_make_smrg_group(base_addr, 1), \ - smmu_make_smrg_group(base_addr, 2), \ - smmu_make_smrg_group(base_addr, 3), \ - smmu_make_smrg_group(base_addr, 4), \ - smmu_make_smrg_group(base_addr, 5), \ - smmu_make_smrg_group(base_addr, 6), \ - smmu_make_smrg_group(base_addr, 7), \ - smmu_make_smrg_group(base_addr, 8), \ - smmu_make_smrg_group(base_addr, 9), \ - smmu_make_smrg_group(base_addr, 10), \ - smmu_make_smrg_group(base_addr, 11), \ - smmu_make_smrg_group(base_addr, 12), \ - smmu_make_smrg_group(base_addr, 13), \ - smmu_make_smrg_group(base_addr, 14), \ - smmu_make_smrg_group(base_addr, 15), \ - smmu_make_smrg_group(base_addr, 16), \ - smmu_make_smrg_group(base_addr, 17), \ - smmu_make_smrg_group(base_addr, 18), \ - smmu_make_smrg_group(base_addr, 19), \ - smmu_make_smrg_group(base_addr, 20), \ - smmu_make_smrg_group(base_addr, 21), \ - smmu_make_smrg_group(base_addr, 22), \ - smmu_make_smrg_group(base_addr, 23), \ - smmu_make_smrg_group(base_addr, 24), \ - smmu_make_smrg_group(base_addr, 25), \ - smmu_make_smrg_group(base_addr, 26), \ - smmu_make_smrg_group(base_addr, 27), \ - smmu_make_smrg_group(base_addr, 28), \ - smmu_make_smrg_group(base_addr, 29), \ - smmu_make_smrg_group(base_addr, 30), \ - smmu_make_smrg_group(base_addr, 31), \ - smmu_make_smrg_group(base_addr, 32), \ - smmu_make_smrg_group(base_addr, 33), \ - smmu_make_smrg_group(base_addr, 34), \ - smmu_make_smrg_group(base_addr, 35), \ - smmu_make_smrg_group(base_addr, 36), \ - smmu_make_smrg_group(base_addr, 37), \ - smmu_make_smrg_group(base_addr, 38), \ - smmu_make_smrg_group(base_addr, 39), \ - smmu_make_smrg_group(base_addr, 40), \ - smmu_make_smrg_group(base_addr, 41), \ - smmu_make_smrg_group(base_addr, 42), \ - smmu_make_smrg_group(base_addr, 43), \ - smmu_make_smrg_group(base_addr, 44), \ - smmu_make_smrg_group(base_addr, 45), \ - smmu_make_smrg_group(base_addr, 46), \ - smmu_make_smrg_group(base_addr, 47), \ - smmu_make_smrg_group(base_addr, 48), \ - smmu_make_smrg_group(base_addr, 49), \ - smmu_make_smrg_group(base_addr, 50), \ - smmu_make_smrg_group(base_addr, 51), \ - smmu_make_smrg_group(base_addr, 52), \ - smmu_make_smrg_group(base_addr, 53), \ - smmu_make_smrg_group(base_addr, 54), \ - smmu_make_smrg_group(base_addr, 55), \ - smmu_make_smrg_group(base_addr, 56), \ - smmu_make_smrg_group(base_addr, 57), \ - smmu_make_smrg_group(base_addr, 58), \ - smmu_make_smrg_group(base_addr, 59), \ - smmu_make_smrg_group(base_addr, 60), \ - smmu_make_smrg_group(base_addr, 61), \ - smmu_make_smrg_group(base_addr, 62), \ - smmu_make_smrg_group(base_addr, 63), \ - smmu_make_cb_group(base_addr, 0), \ - smmu_make_cb_group(base_addr, 1), \ - smmu_make_cb_group(base_addr, 2), \ - smmu_make_cb_group(base_addr, 3), \ - smmu_make_cb_group(base_addr, 4), \ - smmu_make_cb_group(base_addr, 5), \ - smmu_make_cb_group(base_addr, 6), \ - smmu_make_cb_group(base_addr, 7), \ - smmu_make_cb_group(base_addr, 8), \ - smmu_make_cb_group(base_addr, 9), \ - smmu_make_cb_group(base_addr, 10), \ - smmu_make_cb_group(base_addr, 11), \ - smmu_make_cb_group(base_addr, 12), \ - smmu_make_cb_group(base_addr, 13), \ - smmu_make_cb_group(base_addr, 14), \ - smmu_make_cb_group(base_addr, 15), \ - smmu_make_cb_group(base_addr, 16), \ - smmu_make_cb_group(base_addr, 17), \ - smmu_make_cb_group(base_addr, 18), \ - smmu_make_cb_group(base_addr, 19), \ - smmu_make_cb_group(base_addr, 20), \ - smmu_make_cb_group(base_addr, 21), \ - smmu_make_cb_group(base_addr, 22), \ - smmu_make_cb_group(base_addr, 23), \ - smmu_make_cb_group(base_addr, 24), \ - smmu_make_cb_group(base_addr, 25), \ - smmu_make_cb_group(base_addr, 26), \ - smmu_make_cb_group(base_addr, 27), \ - smmu_make_cb_group(base_addr, 28), \ - smmu_make_cb_group(base_addr, 29), \ - smmu_make_cb_group(base_addr, 30), \ - smmu_make_cb_group(base_addr, 31), \ - smmu_make_cb_group(base_addr, 32), \ - smmu_make_cb_group(base_addr, 33), \ - smmu_make_cb_group(base_addr, 34), \ - smmu_make_cb_group(base_addr, 35), \ - smmu_make_cb_group(base_addr, 36), \ - smmu_make_cb_group(base_addr, 37), \ - smmu_make_cb_group(base_addr, 38), \ - smmu_make_cb_group(base_addr, 39), \ - smmu_make_cb_group(base_addr, 40), \ - smmu_make_cb_group(base_addr, 41), \ - smmu_make_cb_group(base_addr, 42), \ - smmu_make_cb_group(base_addr, 43), \ - smmu_make_cb_group(base_addr, 44), \ - smmu_make_cb_group(base_addr, 45), \ - smmu_make_cb_group(base_addr, 46), \ - smmu_make_cb_group(base_addr, 47), \ - smmu_make_cb_group(base_addr, 48), \ - smmu_make_cb_group(base_addr, 49), \ - smmu_make_cb_group(base_addr, 50), \ - smmu_make_cb_group(base_addr, 51), \ - smmu_make_cb_group(base_addr, 52), \ - smmu_make_cb_group(base_addr, 53), \ - smmu_make_cb_group(base_addr, 54), \ - smmu_make_cb_group(base_addr, 55), \ - smmu_make_cb_group(base_addr, 56), \ - smmu_make_cb_group(base_addr, 57), \ - smmu_make_cb_group(base_addr, 58), \ - smmu_make_cb_group(base_addr, 59), \ - smmu_make_cb_group(base_addr, 60), \ - smmu_make_cb_group(base_addr, 61), \ - smmu_make_cb_group(base_addr, 62), \ - smmu_make_cb_group(base_addr, 63) /* don't put "," here. */ - -#define smmu_bypass_cfg \ - { \ - .reg = TEGRA_MC_BASE + MC_SMMU_BYPASS_CONFIG, \ - .val = 0x00000000U, \ - } - -#define _START_OF_TABLE_ \ - { \ - .reg = 0xCAFE05C7U, \ - .val = 0x00000000U, \ - } - -#define _END_OF_TABLE_ \ - { \ - .reg = 0xFFFFFFFFU, \ - .val = 0xFFFFFFFFU, \ - } - +#endif +} void tegra_smmu_init(void); -void tegra_smmu_save_context(uint64_t smmu_ctx_addr); -smmu_regs_t *plat_get_smmu_ctx(void); +void tegra_smmu_verify(void); uint32_t plat_get_num_smmu_devices(void); #endif /* SMMU_H */ diff --git a/plat/nvidia/tegra/include/drivers/spe.h b/plat/nvidia/tegra/include/drivers/spe.h index 0d6d69d10..e0f871408 100644 --- a/plat/nvidia/tegra/include/drivers/spe.h +++ b/plat/nvidia/tegra/include/drivers/spe.h @@ -11,11 +11,6 @@ #include <drivers/console.h> -typedef struct { - console_t console; - uintptr_t base; -} console_spe_t; - /* * Initialize a new spe console instance and register it with the console * framework. The |console| pointer must point to storage that will be valid @@ -23,6 +18,6 @@ typedef struct { * Its contents will be reinitialized from scratch. */ int console_spe_register(uintptr_t baseaddr, uint32_t clock, uint32_t baud, - console_spe_t *console); + console_t *console); #endif /* SPE_H */ diff --git a/plat/nvidia/tegra/include/plat_macros.S b/plat/nvidia/tegra/include/plat_macros.S index 4f01e3306..2dc3b4152 100644 --- a/plat/nvidia/tegra/include/plat_macros.S +++ b/plat/nvidia/tegra/include/plat_macros.S @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -27,6 +28,7 @@ spacer: * --------------------------------------------- */ .macro plat_crash_print_regs +#ifdef TEGRA_GICC_BASE mov_imm x16, TEGRA_GICC_BASE /* gicc base address is now in x16 */ @@ -37,7 +39,7 @@ spacer: ldr w10, [x16, #GICC_CTLR] /* Store to the crash buf and print to cosole */ bl str_in_crash_buf_print - +#endif /* Print the GICD_ISPENDR regs */ mov_imm x16, TEGRA_GICD_BASE add x7, x16, #GICD_ISPENDR diff --git a/plat/nvidia/tegra/include/platform_def.h b/plat/nvidia/tegra/include/platform_def.h index eb55def4a..84b3297e0 100644 --- a/plat/nvidia/tegra/include/platform_def.h +++ b/plat/nvidia/tegra/include/platform_def.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -12,6 +13,19 @@ #include <tegra_def.h> +/******************************************************************************* + * Check and error if SEPARATE_CODE_AND_RODATA is not set to 1 + ******************************************************************************/ +#if !SEPARATE_CODE_AND_RODATA +#error "SEPARATE_CODE_AND_RODATA should be set to 1" +#endif + +/* + * Platform binary types for linking + */ +#define PLATFORM_LINKER_FORMAT "elf64-littleaarch64" +#define PLATFORM_LINKER_ARCH aarch64 + /* * Platform binary types for linking */ @@ -33,7 +47,7 @@ #define PLATFORM_CORE_COUNT (PLATFORM_CLUSTER_COUNT * \ PLATFORM_MAX_CPUS_PER_CLUSTER) #define PLAT_NUM_PWR_DOMAINS (PLATFORM_CORE_COUNT + \ - PLATFORM_CLUSTER_COUNT + 1) + PLATFORM_CLUSTER_COUNT + U(1)) /******************************************************************************* * Platform console related constants @@ -52,7 +66,6 @@ /******************************************************************************* * BL31 specific defines. ******************************************************************************/ -#define BL31_SIZE U(0x40000) #define BL31_BASE TZDRAM_BASE #define BL31_LIMIT (TZDRAM_BASE + BL31_SIZE - 1) #define BL32_BASE (TZDRAM_BASE + BL31_SIZE) @@ -72,4 +85,48 @@ #define MAX_IO_DEVICES U(0) #define MAX_IO_HANDLES U(0) +/******************************************************************************* + * Platforms macros to support SDEI + ******************************************************************************/ +#define TEGRA_SDEI_SGI_PRIVATE U(8) + +/******************************************************************************* + * Platform macros to support exception handling framework + ******************************************************************************/ +#define PLAT_PRI_BITS U(3) +#define PLAT_RAS_PRI U(0x10) +#define PLAT_SDEI_CRITICAL_PRI U(0x20) +#define PLAT_SDEI_NORMAL_PRI U(0x30) +#define PLAT_TEGRA_WDT_PRIO U(0x40) + +#define PLAT_EHF_DESC EHF_PRI_DESC(PLAT_PRI_BITS,\ + PLAT_TEGRA_WDT_PRIO) + +/******************************************************************************* + * SDEI events + ******************************************************************************/ +/* SDEI dynamic private event numbers */ +#define TEGRA_SDEI_DP_EVENT_0 U(100) +#define TEGRA_SDEI_DP_EVENT_1 U(101) +#define TEGRA_SDEI_DP_EVENT_2 U(102) + +/* SDEI dynamic shared event numbers */ +#define TEGRA_SDEI_DS_EVENT_0 U(200) +#define TEGRA_SDEI_DS_EVENT_1 U(201) +#define TEGRA_SDEI_DS_EVENT_2 U(202) + +/* SDEI explicit events */ +#define TEGRA_SDEI_EP_EVENT_0 U(300) +#define TEGRA_SDEI_EP_EVENT_1 U(301) +#define TEGRA_SDEI_EP_EVENT_2 U(302) +#define TEGRA_SDEI_EP_EVENT_3 U(303) +#define TEGRA_SDEI_EP_EVENT_4 U(304) +#define TEGRA_SDEI_EP_EVENT_5 U(305) +#define TEGRA_SDEI_EP_EVENT_6 U(306) +#define TEGRA_SDEI_EP_EVENT_7 U(307) +#define TEGRA_SDEI_EP_EVENT_8 U(308) +#define TEGRA_SDEI_EP_EVENT_9 U(309) +#define TEGRA_SDEI_EP_EVENT_10 U(310) +#define TEGRA_SDEI_EP_EVENT_11 U(311) + #endif /* PLATFORM_DEF_H */ diff --git a/plat/nvidia/tegra/include/t132/tegra_def.h b/plat/nvidia/tegra/include/t132/tegra_def.h index dfed2aa60..6b87655e3 100644 --- a/plat/nvidia/tegra/include/t132/tegra_def.h +++ b/plat/nvidia/tegra/include/t132/tegra_def.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -10,6 +11,11 @@ #include <lib/utils_def.h> /******************************************************************************* + * Platform BL31 specific defines. + ******************************************************************************/ +#define BL31_SIZE U(0x40000) + +/******************************************************************************* * This value is used by the PSCI implementation during the `SYSTEM_SUSPEND` * call as the `state-id` field in the 'power state' parameter. ******************************************************************************/ @@ -103,6 +109,8 @@ #define MC_VIDEO_PROTECT_BASE_HI U(0x978) #define MC_VIDEO_PROTECT_BASE_LO U(0x648) #define MC_VIDEO_PROTECT_SIZE_MB U(0x64c) +#define MC_VIDEO_PROTECT_REG_CTRL U(0x650) +#define MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED U(3) /******************************************************************************* * Tegra TZRAM constants @@ -110,4 +118,10 @@ #define TEGRA_TZRAM_BASE U(0x7C010000) #define TEGRA_TZRAM_SIZE U(0x10000) +/******************************************************************************* + * Tegra DRAM memory base address + ******************************************************************************/ +#define TEGRA_DRAM_BASE ULL(0x80000000) +#define TEGRA_DRAM_END ULL(0x27FFFFFFF) + #endif /* TEGRA_DEF_H */ diff --git a/plat/nvidia/tegra/include/t186/tegra186_private.h b/plat/nvidia/tegra/include/t186/tegra186_private.h index 9e2c02b4b..4514e1477 100644 --- a/plat/nvidia/tegra/include/t186/tegra186_private.h +++ b/plat/nvidia/tegra/include/t186/tegra186_private.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -7,10 +7,6 @@ #ifndef TEGRA186_PRIVATE_H #define TEGRA186_PRIVATE_H -void tegra186_cpu_reset_handler(void); -uint64_t tegra186_get_cpu_reset_handler_base(void); -uint64_t tegra186_get_cpu_reset_handler_size(void); -uint64_t tegra186_get_smmu_ctx_offset(void); -void tegra186_set_system_suspend_entry(void); +uint64_t tegra186_get_mc_ctx_size(void); #endif /* TEGRA186_PRIVATE_H */ diff --git a/plat/nvidia/tegra/include/t186/tegra_def.h b/plat/nvidia/tegra/include/t186/tegra_def.h index da050a895..a971cec93 100644 --- a/plat/nvidia/tegra/include/t186/tegra_def.h +++ b/plat/nvidia/tegra/include/t186/tegra_def.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -10,6 +11,11 @@ #include <lib/utils_def.h> /******************************************************************************* + * Platform BL31 specific defines. + ******************************************************************************/ +#define BL31_SIZE U(0x40000) + +/******************************************************************************* * MCE apertures used by the ARI interface * * Aperture 0 - Cpu0 (ARM Cortex A-57) @@ -72,6 +78,12 @@ #define TEGRA186_SEC_IRQ_TARGET_MASK U(0xF3) /* 4 A57 - 2 Denver */ /******************************************************************************* + * Clock identifier for the SE device + ******************************************************************************/ +#define TEGRA186_CLK_SE U(103) +#define TEGRA_CLK_SE TEGRA186_CLK_SE + +/******************************************************************************* * Tegra Miscellanous register constants ******************************************************************************/ #define TEGRA_MISC_BASE U(0x00100000) @@ -156,6 +168,8 @@ #define MC_VIDEO_PROTECT_BASE_HI U(0x978) #define MC_VIDEO_PROTECT_BASE_LO U(0x648) #define MC_VIDEO_PROTECT_SIZE_MB U(0x64C) +#define MC_VIDEO_PROTECT_REG_CTRL U(0x650) +#define MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED U(3) /* * Carveout (MC_SECURITY_CARVEOUT24) registers used to clear the @@ -212,6 +226,14 @@ #define RNG_MUTEX_WATCHDOG_NS_LIMIT U(0xFE0) /******************************************************************************* + * Tegra HSP doorbell #0 constants + ******************************************************************************/ +#define TEGRA_HSP_DBELL_BASE U(0x03C90000) +#define HSP_DBELL_1_ENABLE U(0x104) +#define HSP_DBELL_3_TRIGGER U(0x300) +#define HSP_DBELL_3_ENABLE U(0x304) + +/******************************************************************************* * Tegra Clock and Reset Controller constants ******************************************************************************/ #define TEGRA_CAR_RESET_BASE U(0x05000000) @@ -237,6 +259,7 @@ * Tegra scratch registers constants ******************************************************************************/ #define TEGRA_SCRATCH_BASE U(0x0C390000) +#define SECURE_SCRATCH_RSV0_HI U(0x654) #define SECURE_SCRATCH_RSV1_LO U(0x658) #define SECURE_SCRATCH_RSV1_HI U(0x65C) #define SECURE_SCRATCH_RSV6 U(0x680) @@ -246,12 +269,21 @@ #define SECURE_SCRATCH_RSV53_HI U(0x7FC) #define SECURE_SCRATCH_RSV55_LO U(0x808) #define SECURE_SCRATCH_RSV55_HI U(0x80C) +#define SECURE_SCRATCH_RSV63_LO U(0x848) +#define SECURE_SCRATCH_RSV63_HI U(0x84C) +#define SECURE_SCRATCH_RSV64_LO U(0x850) +#define SECURE_SCRATCH_RSV64_HI U(0x854) +#define SECURE_SCRATCH_RSV65_LO U(0x858) +#define SECURE_SCRATCH_RSV65_HI U(0x85c) +#define SECURE_SCRATCH_RSV66_LO U(0x860) +#define SECURE_SCRATCH_RSV66_HI U(0x864) +#define SECURE_SCRATCH_RSV68_LO U(0x870) #define SCRATCH_RESET_VECTOR_LO SECURE_SCRATCH_RSV1_LO #define SCRATCH_RESET_VECTOR_HI SECURE_SCRATCH_RSV1_HI #define SCRATCH_SECURE_BOOTP_FCFG SECURE_SCRATCH_RSV6 -#define SCRATCH_SMMU_TABLE_ADDR_LO SECURE_SCRATCH_RSV11_LO -#define SCRATCH_SMMU_TABLE_ADDR_HI SECURE_SCRATCH_RSV11_HI +#define SCRATCH_MC_TABLE_ADDR_LO SECURE_SCRATCH_RSV11_LO +#define SCRATCH_MC_TABLE_ADDR_HI SECURE_SCRATCH_RSV11_HI #define SCRATCH_BL31_PARAMS_ADDR SECURE_SCRATCH_RSV53_LO #define SCRATCH_BL31_PLAT_PARAMS_ADDR SECURE_SCRATCH_RSV53_HI #define SCRATCH_TZDRAM_ADDR_LO SECURE_SCRATCH_RSV55_LO @@ -279,4 +311,17 @@ #define TEGRA_TZRAM_BASE U(0x30000000) #define TEGRA_TZRAM_SIZE U(0x40000) +/******************************************************************************* + * Tegra CCPLEX-BPMP IPC constants + ******************************************************************************/ +#define TEGRA_BPMP_IPC_TX_PHYS_BASE U(0x3004C000) +#define TEGRA_BPMP_IPC_RX_PHYS_BASE U(0x3004D000) +#define TEGRA_BPMP_IPC_CH_MAP_SIZE U(0x1000) /* 4KB */ + +/******************************************************************************* + * Tegra DRAM memory base address + ******************************************************************************/ +#define TEGRA_DRAM_BASE ULL(0x80000000) +#define TEGRA_DRAM_END ULL(0x27FFFFFFF) + #endif /* TEGRA_DEF_H */ diff --git a/plat/nvidia/tegra/include/t186/tegra_mc_def.h b/plat/nvidia/tegra/include/t186/tegra_mc_def.h index d051a150a..fa447725b 100644 --- a/plat/nvidia/tegra/include/t186/tegra_mc_def.h +++ b/plat/nvidia/tegra/include/t186/tegra_mc_def.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -282,4 +282,117 @@ #define MC_CLIENT_HOTRESET_CTRL1_SCE_FLUSH_ENB (1U << 24) #define MC_CLIENT_HOTRESET_STATUS1 0x974U +#ifndef __ASSEMBLER__ + +/******************************************************************************* + * Structure to hold the transaction override settings to use to override + * client inputs + ******************************************************************************/ +typedef struct mc_txn_override_cfg { + uint32_t offset; + uint8_t cgid_tag; +} mc_txn_override_cfg_t; + +#define mc_make_txn_override_cfg(off, val) \ + { \ + .offset = MC_TXN_OVERRIDE_CONFIG_ ## off, \ + .cgid_tag = MC_TXN_OVERRIDE_ ## val \ + } + +/******************************************************************************* + * Structure to hold the Stream ID to use to override client inputs + ******************************************************************************/ +typedef struct mc_streamid_override_cfg { + uint32_t offset; + uint8_t stream_id; +} mc_streamid_override_cfg_t; + +/******************************************************************************* + * Structure to hold the Stream ID Security Configuration settings + ******************************************************************************/ +typedef struct mc_streamid_security_cfg { + char *name; + uint32_t offset; + uint32_t override_enable; + uint32_t override_client_inputs; + uint32_t override_client_ns_flag; +} mc_streamid_security_cfg_t; + +#define OVERRIDE_DISABLE 1U +#define OVERRIDE_ENABLE 0U +#define CLIENT_FLAG_SECURE 0U +#define CLIENT_FLAG_NON_SECURE 1U +#define CLIENT_INPUTS_OVERRIDE 1U +#define CLIENT_INPUTS_NO_OVERRIDE 0U + +/******************************************************************************* + * StreamID to indicate no SMMU translations (requests to be steered on the + * SMMU bypass path) + ******************************************************************************/ +#define MC_STREAM_ID_MAX 0x7FU + +#define mc_make_sec_cfg(off, ns, ovrrd, access) \ + { \ + .name = # off, \ + .offset = MC_STREAMID_OVERRIDE_TO_SECURITY_CFG( \ + MC_STREAMID_OVERRIDE_CFG_ ## off), \ + .override_client_ns_flag = CLIENT_FLAG_ ## ns, \ + .override_client_inputs = CLIENT_INPUTS_ ## ovrrd, \ + .override_enable = OVERRIDE_ ## access \ + } + +#define mc_make_sid_override_cfg(name) \ + { \ + .reg = TEGRA_MC_STREAMID_BASE + MC_STREAMID_OVERRIDE_CFG_ ## name, \ + .val = 0x00000000U, \ + } + +#define mc_make_sid_security_cfg(name) \ + { \ + .reg = TEGRA_MC_STREAMID_BASE + MC_STREAMID_OVERRIDE_TO_SECURITY_CFG(MC_STREAMID_OVERRIDE_CFG_ ## name), \ + .val = 0x00000000U, \ + } + +#define mc_set_pcfifo_unordered_boot_so_mss(id, client) \ + ((uint32_t)~MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_MASK | \ + MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_UNORDERED) + +#define mc_set_pcfifo_ordered_boot_so_mss(id, client) \ + MC_PCFIFO_CLIENT_CONFIG##id##_PCFIFO_##client##_ORDERED + +#define mc_set_tsa_passthrough(client) \ + do { \ + mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ + (TSA_CONFIG_STATIC0_CSW_##client##_RESET & \ + (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ + (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ + } while (0) + +#define mc_set_tsa_w_passthrough(client) \ + do { \ + mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ + (TSA_CONFIG_STATIC0_CSW_RESET_W & \ + (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ + (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ + } while (0) + +#define mc_set_tsa_r_passthrough(client) \ + { \ + mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSR_##client, \ + (TSA_CONFIG_STATIC0_CSR_RESET_R & \ + (uint32_t)~TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK) | \ + (uint32_t)TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU); \ + } while (0) + +#define mc_set_txn_override(client, normal_axi_id, so_dev_axi_id, normal_override, so_dev_override) \ + do { \ + tegra_mc_write_32(MC_TXN_OVERRIDE_CONFIG_##client, \ + MC_TXN_OVERRIDE_##normal_axi_id | \ + MC_TXN_OVERRIDE_CONFIG_COH_PATH_##so_dev_override##_SO_DEV | \ + MC_TXN_OVERRIDE_CONFIG_COH_PATH_##normal_override##_NORMAL | \ + MC_TXN_OVERRIDE_CONFIG_CGID_##so_dev_axi_id); \ + } while (0) + +#endif /* __ASSEMBLER__ */ + #endif /* TEGRA_MC_DEF_H */ diff --git a/plat/nvidia/tegra/include/t194/tegra194_private.h b/plat/nvidia/tegra/include/t194/tegra194_private.h index 8f1deb2a3..c5a51e951 100644 --- a/plat/nvidia/tegra/include/t194/tegra194_private.h +++ b/plat/nvidia/tegra/include/t194/tegra194_private.h @@ -10,7 +10,7 @@ void tegra194_cpu_reset_handler(void); uint64_t tegra194_get_cpu_reset_handler_base(void); uint64_t tegra194_get_cpu_reset_handler_size(void); -uint64_t tegra194_get_smmu_ctx_offset(void); +uint64_t tegra194_get_mc_ctx_offset(void); void tegra194_set_system_suspend_entry(void); #endif /* TEGRA194_PRIVATE_H */ diff --git a/plat/nvidia/tegra/include/t194/tegra194_ras_private.h b/plat/nvidia/tegra/include/t194/tegra194_ras_private.h new file mode 100644 index 000000000..336461af3 --- /dev/null +++ b/plat/nvidia/tegra/include/t194/tegra194_ras_private.h @@ -0,0 +1,263 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef TEGRA194_RAS_PRIVATE +#define TEGRA194_RAS_PRIVATE + +#include <stdint.h> + +/* Implementation defined RAS error and corresponding error message */ +struct ras_error { + const char *error_msg; + /* IERR(bits[15:8]) from ERR<n>STATUS */ + uint8_t error_code; +}; + +/* RAS error node-specific auxiliary data */ +struct ras_aux_data { + /* name for current RAS node. */ + const char *name; + /* point to null-terminated ras_error array to convert error code to msg. */ + const struct ras_error *error_records; + /* + * function to return an value which needs to be programmed into ERXCTLR_EL1 + * to enable all specified RAS errors for current node. + */ + uint64_t (*err_ctrl)(void); +}; + +/* IFU Uncorrectable RAS ERROR */ +#define IFU_UNCORR_RAS_ERROR_LIST(X) + +/* JSR_RET Uncorrectable RAS ERROR */ +#define JSR_RET_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(JSR_RET, 35, 0x13, "Floating Point Register File Parity Error") \ + X(JSR_RET, 34, 0x12, "Integer Register File Parity Error") \ + X(JSR_RET, 33, 0x11, "Garbage Bundle") \ + X(JSR_RET, 32, 0x10, "Bundle Completion Timeout") + +/* JSR_MTS Uncorrectable RAS ERROR */ +#define JSR_MTS_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(JSR_MTS, 40, 0x28, "CoreSight Access Error") \ + X(JSR_MTS, 39, 0x27, "Dual Execution Uncorrectable Error") \ + X(JSR_MTS, 37, 0x25, "CTU MMIO Region") \ + X(JSR_MTS, 36, 0x24, "MTS MMCRAB Region Access") \ + X(JSR_MTS, 35, 0x23, "MTS_CARVEOUT Access from ARM SW") \ + X(JSR_MTS, 34, 0x22, "NAFLL PLL Failure to Lock") \ + X(JSR_MTS, 32, 0x20, "Internal Uncorrectable MTS Error") + +/* LSD_STQ Uncorrectable RAS ERROR */ +#define LSD_STQ_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(LSD_STQ, 41, 0x39, "Coherent Cache Data Store Multi-Line ECC Error") \ + X(LSD_STQ, 40, 0x38, "Coherent Cache Data Store Uncorrectable ECC Error") \ + X(LSD_STQ, 38, 0x36, "Coherent Cache Data Load Uncorrectable ECC Error") \ + X(LSD_STQ, 33, 0x31, "Coherent Cache Tag Store Parity Error") \ + X(LSD_STQ, 32, 0x30, "Coherent Cache Tag Load Parity Error") + +/* LSD_DCC Uncorrectable RAS ERROR */ +#define LSD_DCC_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(LSD_DCC, 41, 0x49, "BTU Copy Mini-Cache PPN Multi-Hit Error") \ + X(LSD_DCC, 39, 0x47, "Coherent Cache Data Uncorrectable ECC Error") \ + X(LSD_DCC, 37, 0x45, "Version Cache Byte-Enable Parity Error") \ + X(LSD_DCC, 36, 0x44, "Version Cache Data Uncorrectable ECC Error") \ + X(LSD_DCC, 33, 0x41, "BTU Copy Coherent Cache PPN Parity Error") \ + X(LSD_DCC, 32, 0x40, "BTU Copy Coherent Cache VPN Parity Error") + +/* LSD_L1HPF Uncorrectable RAS ERROR */ +#define LSD_L1HPF_UNCORR_RAS_ERROR_LIST(X) + +/* L2 Uncorrectable RAS ERROR */ +#define L2_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(L2, 56, 0x68, "URT Timeout") \ + X(L2, 55, 0x67, "L2 Protocol Violation") \ + X(L2, 54, 0x66, "SCF to L2 Slave Error Read") \ + X(L2, 53, 0x65, "SCF to L2 Slave Error Write") \ + X(L2, 52, 0x64, "SCF to L2 Decode Error Read") \ + X(L2, 51, 0x63, "SCF to L2 Decode Error Write") \ + X(L2, 50, 0x62, "SCF to L2 Request Response Interface Parity Errors") \ + X(L2, 49, 0x61, "SCF to L2 Advance notice interface parity errors") \ + X(L2, 48, 0x60, "SCF to L2 Filldata Parity Errors") \ + X(L2, 47, 0x5F, "SCF to L2 UnCorrectable ECC Data Error on interface") \ + X(L2, 45, 0x5D, "Core 1 to L2 Parity Error") \ + X(L2, 44, 0x5C, "Core 0 to L2 Parity Error") \ + X(L2, 43, 0x5B, "L2 Multi-Hit") \ + X(L2, 42, 0x5A, "L2 URT Tag Parity Error") \ + X(L2, 41, 0x59, "L2 NTT Tag Parity Error") \ + X(L2, 40, 0x58, "L2 MLT Tag Parity Error") \ + X(L2, 39, 0x57, "L2 URD Data") \ + X(L2, 38, 0x56, "L2 NTP Data") \ + X(L2, 36, 0x54, "L2 MLC Uncorrectable Clean") \ + X(L2, 35, 0x53, "L2 URD Uncorrectable Dirty") \ + X(L2, 34, 0x52, "L2 MLC Uncorrectable Dirty") + +/* CLUSTER_CLOCKS Uncorrectable RAS ERROR */ +#define CLUSTER_CLOCKS_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(CLUSTER_CLOCKS, 32, 0xE4, "Frequency Monitor Error") + +/* MMU Uncorrectable RAS ERROR */ +#define MMU_UNCORR_RAS_ERROR_LIST(X) + +/* L3 Uncorrectable RAS ERROR */ +#define L3_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(L3, 43, 0x7B, "SNOC Interface Parity Error") \ + X(L3, 42, 0x7A, "MCF Interface Parity Error") \ + X(L3, 41, 0x79, "L3 Tag Parity Error") \ + X(L3, 40, 0x78, "L3 Dir Parity Error") \ + X(L3, 39, 0x77, "L3 Uncorrectable ECC Error") \ + X(L3, 37, 0x75, "Multi-Hit CAM Error") \ + X(L3, 36, 0x74, "Multi-Hit Tag Error") \ + X(L3, 35, 0x73, "Unrecognized Command Error") \ + X(L3, 34, 0x72, "L3 Protocol Error") + +/* CCPMU Uncorrectable RAS ERROR */ +#define CCPMU_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(CCPMU, 40, 0x87, "CoreSight Access Error") \ + X(CCPMU, 36, 0x84, "MCE Ucode Error") \ + X(CCPMU, 35, 0x83, "MCE IL1 Parity Error") \ + X(CCPMU, 34, 0x82, "MCE Timeout Error") \ + X(CCPMU, 33, 0x81, "CRAB Access Error") \ + X(CCPMU, 32, 0x80, "MCE Memory Access Error") + +/* SCF_IOB Uncorrectable RAS ERROR */ +#define SCF_IOB_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(SCF_IOB, 41, 0x99, "Request parity error") \ + X(SCF_IOB, 40, 0x98, "Putdata parity error") \ + X(SCF_IOB, 39, 0x97, "Uncorrectable ECC on Putdata") \ + X(SCF_IOB, 38, 0x96, "CBB Interface Error") \ + X(SCF_IOB, 37, 0x95, "MMCRAB Error") \ + X(SCF_IOB, 36, 0x94, "IHI Interface Error") \ + X(SCF_IOB, 35, 0x93, "CRI Error") \ + X(SCF_IOB, 34, 0x92, "TBX Interface Error") \ + X(SCF_IOB, 33, 0x91, "EVP Interface Error") + +/* SCF_SNOC Uncorrectable RAS ERROR */ +#define SCF_SNOC_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(SCF_SNOC, 42, 0xAA, "Misc Client Parity Error") \ + X(SCF_SNOC, 41, 0xA9, "Misc Filldata Parity Error") \ + X(SCF_SNOC, 40, 0xA8, "Uncorrectable ECC Misc Client") \ + X(SCF_SNOC, 39, 0xA7, "DVMU Interface Parity Error") \ + X(SCF_SNOC, 38, 0xA6, "DVMU Interface Timeout Error") \ + X(SCF_SNOC, 37, 0xA5, "CPE Request Error") \ + X(SCF_SNOC, 36, 0xA4, "CPE Response Error") \ + X(SCF_SNOC, 35, 0xA3, "CPE Timeout Error") \ + X(SCF_SNOC, 34, 0xA2, "Uncorrectable Carveout Error") + +/* SCF_CTU Uncorrectable RAS ERROR */ +#define SCF_CTU_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(SCF_CTU, 39, 0xB7, "Timeout error for TRC_DMA request") \ + X(SCF_CTU, 38, 0xB6, "Timeout error for CTU Snp") \ + X(SCF_CTU, 37, 0xB5, "Parity error in CTU TAG RAM") \ + X(SCF_CTU, 36, 0xB3, "Parity error in CTU DATA RAM") \ + X(SCF_CTU, 35, 0xB4, "Parity error for Cluster Rsp") \ + X(SCF_CTU, 34, 0xB2, "Parity error for TRL requests from 9 agents") \ + X(SCF_CTU, 33, 0xB1, "Parity error for MCF request") \ + X(SCF_CTU, 32, 0xB0, "TRC DMA fillsnoop parity error") + +/* CMU_CLOCKS Uncorrectable RAS ERROR */ +#define CMU_CLOCKS_UNCORR_RAS_ERROR_LIST(X) \ + /* Name, ERR_CTRL, IERR, ISA Desc */ \ + X(CMU_CLOCKS, 39, 0xC7, "Cluster 3 frequency monitor error") \ + X(CMU_CLOCKS, 38, 0xC6, "Cluster 2 frequency monitor error") \ + X(CMU_CLOCKS, 37, 0xC5, "Cluster 1 frequency monitor error") \ + X(CMU_CLOCKS, 36, 0xC3, "Cluster 0 frequency monitor error") \ + X(CMU_CLOCKS, 35, 0xC4, "Voltage error on ADC1 Monitored Logic") \ + X(CMU_CLOCKS, 34, 0xC2, "Voltage error on ADC0 Monitored Logic") \ + X(CMU_CLOCKS, 33, 0xC1, "Lookup Table 1 Parity Error") \ + X(CMU_CLOCKS, 32, 0xC0, "Lookup Table 0 Parity Error") + +/* + * Define one ras_error entry. + * + * This macro wille be used to to generate ras_error records for each node + * defined by <NODE_NAME>_UNCORR_RAS_ERROR_LIST macro. + */ +#define DEFINE_ONE_RAS_ERROR_MSG(unit, ras_bit, ierr, msg) \ + { \ + .error_msg = (msg), \ + .error_code = (ierr) \ + }, + +/* + * Set one implementation defined bit in ERR<n>CTLR + * + * This macro will be used to collect all defined ERR_CTRL bits for each node + * defined by <NODE_NAME>_UNCORR_RAS_ERROR_LIST macro. + */ +#define DEFINE_ENABLE_RAS_BIT(unit, ras_bit, ierr, msg) \ + do { \ + val |= (1ULL << ras_bit##U); \ + } while (0); + +/* Represent one RAS node with 0 or more error bits (ERR_CTLR) enabled */ +#define DEFINE_ONE_RAS_NODE(node) \ +static const struct ras_error node##_uncorr_ras_errors[] = { \ + node##_UNCORR_RAS_ERROR_LIST(DEFINE_ONE_RAS_ERROR_MSG) \ + { \ + NULL, \ + 0U \ + }, \ +}; \ +static inline uint64_t node##_err_ctrl(void) \ +{ \ + uint64_t val = 0ULL; \ + node##_UNCORR_RAS_ERROR_LIST(DEFINE_ENABLE_RAS_BIT) \ + return val; \ +} + +#define DEFINE_ONE_RAS_AUX_DATA(node) \ + { \ + .name = #node, \ + .error_records = node##_uncorr_ras_errors, \ + .err_ctrl = &node##_err_ctrl \ + }, + +#define PER_CORE_RAS_NODE_LIST(X) \ + X(IFU) \ + X(JSR_RET) \ + X(JSR_MTS) \ + X(LSD_STQ) \ + X(LSD_DCC) \ + X(LSD_L1HPF) + +#define PER_CORE_RAS_GROUP_NODES PER_CORE_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) + +#define PER_CLUSTER_RAS_NODE_LIST(X) \ + X(L2) \ + X(CLUSTER_CLOCKS) \ + X(MMU) + +#define PER_CLUSTER_RAS_GROUP_NODES PER_CLUSTER_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) + +#define SCF_L3_BANK_RAS_NODE_LIST(X) X(L3) + +/* we have 4 SCF_L3 nodes:3*256 + L3_Bank_ID(0-3) */ +#define SCF_L3_BANK_RAS_GROUP_NODES \ + SCF_L3_BANK_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) \ + SCF_L3_BANK_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) \ + SCF_L3_BANK_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) \ + SCF_L3_BANK_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) + +#define CCPLEX_RAS_NODE_LIST(X) \ + X(CCPMU) \ + X(SCF_IOB) \ + X(SCF_SNOC) \ + X(SCF_CTU) \ + X(CMU_CLOCKS) + +#define CCPLEX_RAS_GROUP_NODES CCPLEX_RAS_NODE_LIST(DEFINE_ONE_RAS_AUX_DATA) + +#endif /* TEGRA194_RAS_PRIVATE */ diff --git a/plat/nvidia/tegra/include/t194/tegra_def.h b/plat/nvidia/tegra/include/t194/tegra_def.h index df1d65630..abe193fcd 100644 --- a/plat/nvidia/tegra/include/t194/tegra_def.h +++ b/plat/nvidia/tegra/include/t194/tegra_def.h @@ -10,6 +10,17 @@ #include <lib/utils_def.h> /******************************************************************************* + * Platform BL31 specific defines. + ******************************************************************************/ +#define BL31_SIZE U(0x40000) + +/******************************************************************************* + * Chip specific cluster and cpu numbers + ******************************************************************************/ +#define PLATFORM_CLUSTER_COUNT U(4) +#define PLATFORM_MAX_CPUS_PER_CLUSTER U(2) + +/******************************************************************************* * Chip specific page table and MMU setup constants ******************************************************************************/ #define PLAT_PHY_ADDR_SPACE_SIZE (ULL(1) << 40) @@ -43,6 +54,12 @@ #define TEGRA194_SEC_IRQ_TARGET_MASK U(0xFF) /* 8 Carmel */ /******************************************************************************* + * Clock identifier for the SE device + ******************************************************************************/ +#define TEGRA194_CLK_SE U(124) +#define TEGRA_CLK_SE TEGRA194_CLK_SE + +/******************************************************************************* * Tegra Miscellanous register constants ******************************************************************************/ #define TEGRA_MISC_BASE U(0x00100000) @@ -93,6 +110,8 @@ #define MC_VIDEO_PROTECT_BASE_HI U(0x978) #define MC_VIDEO_PROTECT_BASE_LO U(0x648) #define MC_VIDEO_PROTECT_SIZE_MB U(0x64c) +#define MC_VIDEO_PROTECT_REG_CTRL U(0x650) +#define MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED U(3) /* * Carveout (MC_SECURITY_CARVEOUT24) registers used to clear the @@ -197,6 +216,16 @@ * Tegra scratch registers constants ******************************************************************************/ #define TEGRA_SCRATCH_BASE U(0x0C390000) +#define SECURE_SCRATCH_RSV68_LO U(0x284) +#define SECURE_SCRATCH_RSV68_HI U(0x288) +#define SECURE_SCRATCH_RSV69_LO U(0x28C) +#define SECURE_SCRATCH_RSV69_HI U(0x290) +#define SECURE_SCRATCH_RSV70_LO U(0x294) +#define SECURE_SCRATCH_RSV70_HI U(0x298) +#define SECURE_SCRATCH_RSV71_LO U(0x29C) +#define SECURE_SCRATCH_RSV71_HI U(0x2A0) +#define SECURE_SCRATCH_RSV72_LO U(0x2A4) +#define SECURE_SCRATCH_RSV72_HI U(0x2A8) #define SECURE_SCRATCH_RSV75 U(0x2BC) #define SECURE_SCRATCH_RSV81_LO U(0x2EC) #define SECURE_SCRATCH_RSV81_HI U(0x2F0) @@ -215,8 +244,8 @@ #define SCRATCH_BL31_PLAT_PARAMS_HI_ADDR_SHIFT U(16) #define SCRATCH_BL31_PLAT_PARAMS_LO_ADDR SECURE_SCRATCH_RSV81_HI #define SCRATCH_SECURE_BOOTP_FCFG SECURE_SCRATCH_RSV97 -#define SCRATCH_SMMU_TABLE_ADDR_LO SECURE_SCRATCH_RSV99_LO -#define SCRATCH_SMMU_TABLE_ADDR_HI SECURE_SCRATCH_RSV99_HI +#define SCRATCH_MC_TABLE_ADDR_LO SECURE_SCRATCH_RSV99_LO +#define SCRATCH_MC_TABLE_ADDR_HI SECURE_SCRATCH_RSV99_HI #define SCRATCH_RESET_VECTOR_LO SECURE_SCRATCH_RSV109_LO #define SCRATCH_RESET_VECTOR_HI SECURE_SCRATCH_RSV109_HI @@ -257,6 +286,12 @@ #define TEGRA_GPCDMA_RST_CLR_REG_OFFSET U(0x6A0008) /******************************************************************************* + * Tegra DRAM memory base address + ******************************************************************************/ +#define TEGRA_DRAM_BASE ULL(0x80000000) +#define TEGRA_DRAM_END ULL(0xFFFFFFFFF) + +/******************************************************************************* * XUSB STREAMIDs ******************************************************************************/ #define TEGRA_SID_XUSB_HOST U(0x1b) @@ -266,4 +301,26 @@ #define TEGRA_SID_XUSB_VF2 U(0x5f) #define TEGRA_SID_XUSB_VF3 U(0x60) +/******************************************************************************* + * SCR addresses and expected settings + ******************************************************************************/ +#define SCRATCH_RSV68_SCR U(0x0C398110) +#define SCRATCH_RSV68_SCR_VAL U(0x38000101) +#define SCRATCH_RSV71_SCR U(0x0C39811C) +#define SCRATCH_RSV71_SCR_VAL U(0x38000101) +#define SCRATCH_RSV72_SCR U(0x0C398120) +#define SCRATCH_RSV72_SCR_VAL U(0x38000101) +#define SCRATCH_RSV75_SCR U(0x0C39812C) +#define SCRATCH_RSV75_SCR_VAL U(0x3A000005) +#define SCRATCH_RSV81_SCR U(0x0C398144) +#define SCRATCH_RSV81_SCR_VAL U(0x3A000105) +#define SCRATCH_RSV97_SCR U(0x0C398184) +#define SCRATCH_RSV97_SCR_VAL U(0x38000101) +#define SCRATCH_RSV99_SCR U(0x0C39818C) +#define SCRATCH_RSV99_SCR_VAL U(0x38000101) +#define SCRATCH_RSV109_SCR U(0x0C3981B4) +#define SCRATCH_RSV109_SCR_VAL U(0x38000101) +#define MISCREG_SCR_SCRTZWELCK U(0x00109000) +#define MISCREG_SCR_SCRTZWELCK_VAL U(0x30000100) + #endif /* TEGRA_DEF_H */ diff --git a/plat/nvidia/tegra/include/t194/tegra_mc_def.h b/plat/nvidia/tegra/include/t194/tegra_mc_def.h deleted file mode 100644 index 34bdd7557..000000000 --- a/plat/nvidia/tegra/include/t194/tegra_mc_def.h +++ /dev/null @@ -1,685 +0,0 @@ -/* - * Copyright (c) 2019-2020, NVIDIA Corporation. All rights reserved. - * - * SPDX-License-Identifier: BSD-3-Clause - */ - -#ifndef TEGRA_MC_DEF_H -#define TEGRA_MC_DEF_H - -/******************************************************************************* - * Memory Controller Order_id registers - ******************************************************************************/ -#define MC_CLIENT_ORDER_ID_9 U(0x2a24) -#define MC_CLIENT_ORDER_ID_9_RESET_VAL 0x00000000U -#define MC_CLIENT_ORDER_ID_9_XUSB_HOSTW_MASK (0x3U << 12) -#define MC_CLIENT_ORDER_ID_9_XUSB_HOSTW_ORDER_ID (3U << 12) - -#define MC_CLIENT_ORDER_ID_27 U(0x2a6c) -#define MC_CLIENT_ORDER_ID_27_RESET_VAL 0x00000000U -#define MC_CLIENT_ORDER_ID_27_PCIE0W_MASK (0x3U << 4) -#define MC_CLIENT_ORDER_ID_27_PCIE0W_ORDER_ID (2U << 4) - -#define MC_CLIENT_ORDER_ID_28 U(0x2a70) -#define MC_CLIENT_ORDER_ID_28_RESET_VAL 0x00000000U -#define MC_CLIENT_ORDER_ID_28_PCIE4W_MASK (0x3U << 4) -#define MC_CLIENT_ORDER_ID_28_PCIE4W_ORDER_ID (3U << 4) -#define MC_CLIENT_ORDER_ID_28_PCIE5W_MASK (0x3U << 12) -#define MC_CLIENT_ORDER_ID_28_PCIE5W_ORDER_ID (1U << 12) - -#define mc_client_order_id(val, id, client) \ - ((val & ~MC_CLIENT_ORDER_ID_##id##_##client##_MASK) | \ - MC_CLIENT_ORDER_ID_##id##_##client##_ORDER_ID) - -/******************************************************************************* - * Memory Controller's VC ID configuration registers - ******************************************************************************/ -#define VC_NISO 0U -#define VC_SISO 1U -#define VC_ISO 2U - -#define MC_HUB_PC_VC_ID_0 U(0x2a78) -#define MC_HUB_PC_VC_ID_0_RESET_VAL 0x00020100U -#define MC_HUB_PC_VC_ID_0_APB_VC_ID_MASK (0x3U << 8) -#define MC_HUB_PC_VC_ID_0_APB_VC_ID (VC_NISO << 8) - -#define MC_HUB_PC_VC_ID_2 U(0x2a80) -#define MC_HUB_PC_VC_ID_2_RESET_VAL 0x10001000U -#define MC_HUB_PC_VC_ID_2_SD_VC_ID_MASK (0x3U << 28) -#define MC_HUB_PC_VC_ID_2_SD_VC_ID (VC_NISO << 28) - -#define MC_HUB_PC_VC_ID_4 U(0x2a88) -#define MC_HUB_PC_VC_ID_4_RESET_VAL 0x10020011U -#define MC_HUB_PC_VC_ID_4_NIC_VC_ID_MASK (0x3U << 28) -#define MC_HUB_PC_VC_ID_4_NIC_VC_ID (VC_NISO << 28) - -#define MC_HUB_PC_VC_ID_12 U(0x2aa8) -#define MC_HUB_PC_VC_ID_12_RESET_VAL 0x11001011U -#define MC_HUB_PC_VC_ID_12_UFSHCPC2_VC_ID_MASK (0x3U << 12) -#define MC_HUB_PC_VC_ID_12_UFSHCPC2_VC_ID (VC_NISO << 12) - -#define mc_hub_vc_id(val, id, client) \ - ((val & ~MC_HUB_PC_VC_ID_##id##_##client##_VC_ID_MASK) | \ - MC_HUB_PC_VC_ID_##id##_##client##_VC_ID) - -/******************************************************************************* - * Memory Controller's PCFIFO client configuration registers - ******************************************************************************/ -#define MC_PCFIFO_CLIENT_CONFIG0 0xdd0U - -#define MC_PCFIFO_CLIENT_CONFIG1 0xdd4U -#define MC_PCFIFO_CLIENT_CONFIG1_RESET_VAL 0x20200000U -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_AFIW_UNORDERED (0U << 17) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_AFIW_MASK (1U << 17) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_HDAW_UNORDERED (0U << 21) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_HDAW_MASK (1U << 21) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_SATAW_UNORDERED (0U << 29) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_SATAW_ORDERED (1U << 29) -#define MC_PCFIFO_CLIENT_CONFIG1_PCFIFO_SATAW_MASK (1U << 29) - -#define MC_PCFIFO_CLIENT_CONFIG2 0xdd8U -#define MC_PCFIFO_CLIENT_CONFIG2_RESET_VAL 0x00002800U -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_XUSB_HOSTW_UNORDERED (0U << 11) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_XUSB_HOSTW_MASK (1U << 11) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_XUSB_DEVW_UNORDERED (0U << 13) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_XUSB_DEVW_ORDERED (1U << 13) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_XUSB_DEVW_MASK (1U << 13) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_TSECSWR_UNORDERED (0U << 21) -#define MC_PCFIFO_CLIENT_CONFIG2_PCFIFO_TSECSWR_MASK (1U << 21) - -#define MC_PCFIFO_CLIENT_CONFIG3 0xddcU -#define MC_PCFIFO_CLIENT_CONFIG3_RESET_VAL 0x08000080U -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCWA_UNORDERED (0U << 4) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCWA_MASK (1U << 4) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCW_UNORDERED (0U << 6) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCW_MASK (1U << 6) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCWAB_UNORDERED (0U << 7) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_SDMMCWAB_MASK (1U << 7) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_VICSWR_UNORDERED (0U << 13) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_VICSWR_MASK (1U << 13) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_APEW_UNORDERED (0U << 27) -#define MC_PCFIFO_CLIENT_CONFIG3_PCFIFO_APEW_MASK (1U << 27) - -#define MC_PCFIFO_CLIENT_CONFIG4 0xde0U -#define MC_PCFIFO_CLIENT_CONFIG4_RESET_VAL 0x5552a022U -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SESWR_UNORDERED (0U << 1) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SESWR_MASK (1U << 1) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_ETRW_UNORDERED (0U << 5) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_ETRW_MASK (1U << 5) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_TSECSWRB_UNORDERED (0U << 7) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_TSECSWRB_MASK (1U << 7) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AXISW_UNORDERED (0U << 13) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AXISW_MASK (1U << 13) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_EQOSW_UNORDERED (0U << 15) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_EQOSW_MASK (1U << 15) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_UFSHCW_UNORDERED (0U << 17) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_UFSHCW_MASK (1U << 17) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_BPMPW_UNORDERED (0U << 20) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_BPMPW_MASK (1U << 20) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_BPMPDMAW_UNORDERED (0U << 22) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_BPMPDMAW_MASK (1U << 22) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AONW_UNORDERED (0U << 24) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AONW_MASK (1U << 24) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AONDMAW_UNORDERED (0U << 26) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_AONDMAW_MASK (1U << 26) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SCEW_UNORDERED (0U << 28) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SCEW_MASK (1U << 28) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SCEDMAW_UNORDERED (0U << 30) -#define MC_PCFIFO_CLIENT_CONFIG4_PCFIFO_SCEDMAW_MASK (1U << 30) - -#define MC_PCFIFO_CLIENT_CONFIG5 0xbf4U -#define MC_PCFIFO_CLIENT_CONFIG5_RESET_VAL 0x20000001U -#define MC_PCFIFO_CLIENT_CONFIG5_PCFIFO_APEDMAW_UNORDERED (0U << 0) -#define MC_PCFIFO_CLIENT_CONFIG5_PCFIFO_APEDMAW_MASK (1U << 0) -#define MC_PCFIFO_CLIENT_CONFIG5_PCFIFO_VIFALW_UNORDERED (0U << 30) -#define MC_PCFIFO_CLIENT_CONFIG5_PCFIFO_VIFALW_MASK (1U << 30) - -#define MC_PCFIFO_CLIENT_CONFIG6 0xb90U -#define MC_PCFIFO_CLIENT_CONFIG6_RESET_VAL 0xaa280000U -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_RCEW_UNORDERED (0U << 19) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_RCEW_MASK (1U << 19) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_RCEDMAW_UNORDERED (0U << 21) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_RCEDMAW_MASK (1U << 21) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE0W_UNORDERED (0U << 25) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE0W_MASK (1U << 25) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE1W_ORDERED (1U << 27) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE1W_MASK (1U << 27) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE2W_ORDERED (1U << 29) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE2W_MASK (1U << 29) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE3W_ORDERED (1U << 31) -#define MC_PCFIFO_CLIENT_CONFIG6_PCFIFO_PCIE3W_MASK (1U << 31) - -#define MC_PCFIFO_CLIENT_CONFIG7 0xaccU -#define MC_PCFIFO_CLIENT_CONFIG7_RESET_VAL 0x0000000aU -#define MC_PCFIFO_CLIENT_CONFIG7_PCFIFO_PCIE4W_UNORDERED (0U << 1) -#define MC_PCFIFO_CLIENT_CONFIG7_PCFIFO_PCIE4W_MASK (1U << 1) -#define MC_PCFIFO_CLIENT_CONFIG7_PCFIFO_PCIE5W_UNORDERED (0U << 3) -#define MC_PCFIFO_CLIENT_CONFIG7_PCFIFO_PCIE5W_MASK (1U << 3) - -/******************************************************************************* - * StreamID to indicate no SMMU translations (requests to be steered on the - * SMMU bypass path) - ******************************************************************************/ -#define MC_STREAM_ID_MAX 0x7FU - -/******************************************************************************* - * Stream ID Override Config registers - ******************************************************************************/ -#define MC_STREAMID_OVERRIDE_CFG_PVA1RDA 0x660U -#define MC_STREAMID_OVERRIDE_CFG_NVENCSRD 0xe0U -#define MC_STREAMID_OVERRIDE_CFG_NVJPGSWR 0x3f8U -#define MC_STREAMID_OVERRIDE_CFG_PVA0RDA1 0x758U -#define MC_STREAMID_OVERRIDE_CFG_PVA0RDC 0x640U -#define MC_STREAMID_OVERRIDE_CFG_DLA0RDA 0x5f0U -#define MC_STREAMID_OVERRIDE_CFG_BPMPR 0x498U -#define MC_STREAMID_OVERRIDE_CFG_APEDMAR 0x4f8U -#define MC_STREAMID_OVERRIDE_CFG_AXISR 0x460U -#define MC_STREAMID_OVERRIDE_CFG_TSECSRD 0x2a0U -#define MC_STREAMID_OVERRIDE_CFG_DLA0FALRDB 0x5f8U -#define MC_STREAMID_OVERRIDE_CFG_NVENC1SRD1 0x788U -#define MC_STREAMID_OVERRIDE_CFG_MPCOREW 0x1c8U -#define MC_STREAMID_OVERRIDE_CFG_NVENCSRD1 0x780U -#define MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTR 0x250U -#define MC_STREAMID_OVERRIDE_CFG_MIU1R 0x540U -#define MC_STREAMID_OVERRIDE_CFG_MIU0R 0x530U -#define MC_STREAMID_OVERRIDE_CFG_PCIE1W 0x6d8U -#define MC_STREAMID_OVERRIDE_CFG_PVA1WRA 0x678U -#define MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTW 0x258U -#define MC_STREAMID_OVERRIDE_CFG_AXIAPW 0x418U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCWAB 0x338U -#define MC_STREAMID_OVERRIDE_CFG_SATAW 0x1e8U -#define MC_STREAMID_OVERRIDE_CFG_DLA0WRA 0x600U -#define MC_STREAMID_OVERRIDE_CFG_PCIE3R 0x6f0U -#define MC_STREAMID_OVERRIDE_CFG_MIU3W 0x588U -#define MC_STREAMID_OVERRIDE_CFG_SCEDMAR 0x4e8U -#define MC_STREAMID_OVERRIDE_CFG_HOST1XDMAR 0xb0U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCWA 0x320U -#define MC_STREAMID_OVERRIDE_CFG_MIU2R 0x570U -#define MC_STREAMID_OVERRIDE_CFG_APEDMAW 0x500U -#define MC_STREAMID_OVERRIDE_CFG_PCIE2AW 0x6e8U -#define MC_STREAMID_OVERRIDE_CFG_SESWR 0x408U -#define MC_STREAMID_OVERRIDE_CFG_PVA1RDB1 0x770U -#define MC_STREAMID_OVERRIDE_CFG_AXISW 0x468U -#define MC_STREAMID_OVERRIDE_CFG_DLA1FALRDB 0x618U -#define MC_STREAMID_OVERRIDE_CFG_AONDMAW 0x4d0U -#define MC_STREAMID_OVERRIDE_CFG_TSECSWRB 0x438U -#define MC_STREAMID_OVERRIDE_CFG_ISPWB 0x238U -#define MC_STREAMID_OVERRIDE_CFG_HDAR 0xa8U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCRA 0x300U -#define MC_STREAMID_OVERRIDE_CFG_ETRW 0x428U -#define MC_STREAMID_OVERRIDE_CFG_RCEDMAW 0x6a8U -#define MC_STREAMID_OVERRIDE_CFG_TSECSWR 0x2a8U -#define MC_STREAMID_OVERRIDE_CFG_ETRR 0x420U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCR 0x310U -#define MC_STREAMID_OVERRIDE_CFG_NVJPGSRD 0x3f0U -#define MC_STREAMID_OVERRIDE_CFG_AONDMAR 0x4c8U -#define MC_STREAMID_OVERRIDE_CFG_SCER 0x4d8U -#define MC_STREAMID_OVERRIDE_CFG_MIU5W 0x7e8U -#define MC_STREAMID_OVERRIDE_CFG_NVENC1SRD 0x6b0U -#define MC_STREAMID_OVERRIDE_CFG_PCIE4R 0x700U -#define MC_STREAMID_OVERRIDE_CFG_ISPWA 0x230U -#define MC_STREAMID_OVERRIDE_CFG_PCIE0W 0x6c8U -#define MC_STREAMID_OVERRIDE_CFG_PCIE5R1 0x778U -#define MC_STREAMID_OVERRIDE_CFG_DLA1RDA 0x610U -#define MC_STREAMID_OVERRIDE_CFG_VICSWR 0x368U -#define MC_STREAMID_OVERRIDE_CFG_SESRD 0x400U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCW 0x330U -#define MC_STREAMID_OVERRIDE_CFG_SDMMCRAB 0x318U -#define MC_STREAMID_OVERRIDE_CFG_ISPFALW 0x720U -#define MC_STREAMID_OVERRIDE_CFG_EQOSW 0x478U -#define MC_STREAMID_OVERRIDE_CFG_RCEDMAR 0x6a0U -#define MC_STREAMID_OVERRIDE_CFG_RCER 0x690U -#define MC_STREAMID_OVERRIDE_CFG_NVDECSWR 0x3c8U -#define MC_STREAMID_OVERRIDE_CFG_UFSHCR 0x480U -#define MC_STREAMID_OVERRIDE_CFG_PCIE4W 0x708U -#define MC_STREAMID_OVERRIDE_CFG_VICSRD 0x360U -#define MC_STREAMID_OVERRIDE_CFG_APER 0x3d0U -#define MC_STREAMID_OVERRIDE_CFG_MIU7R 0x8U -#define MC_STREAMID_OVERRIDE_CFG_NVDEC1SRD 0x7c8U -#define MC_STREAMID_OVERRIDE_CFG_MIU7W 0x10U -#define MC_STREAMID_OVERRIDE_CFG_PVA1RDA1 0x768U -#define MC_STREAMID_OVERRIDE_CFG_PVA1WRC 0x688U -#define MC_STREAMID_OVERRIDE_CFG_AONW 0x4c0U -#define MC_STREAMID_OVERRIDE_CFG_MIU4W 0x598U -#define MC_STREAMID_OVERRIDE_CFG_HDAW 0x1a8U -#define MC_STREAMID_OVERRIDE_CFG_BPMPW 0x4a0U -#define MC_STREAMID_OVERRIDE_CFG_DLA1WRA 0x620U -#define MC_STREAMID_OVERRIDE_CFG_DLA0RDA1 0x748U -#define MC_STREAMID_OVERRIDE_CFG_MIU1W 0x548U -#define MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR1 0x508U -#define MC_STREAMID_OVERRIDE_CFG_VICSRD1 0x510U -#define MC_STREAMID_OVERRIDE_CFG_BPMPDMAW 0x4b0U -#define MC_STREAMID_OVERRIDE_CFG_NVDEC1SWR 0x7d8U -#define MC_STREAMID_OVERRIDE_CFG_PVA0WRC 0x658U -#define MC_STREAMID_OVERRIDE_CFG_PCIE5R 0x710U -#define MC_STREAMID_OVERRIDE_CFG_XUSB_DEVR 0x260U -#define MC_STREAMID_OVERRIDE_CFG_UFSHCW 0x488U -#define MC_STREAMID_OVERRIDE_CFG_PVA1WRB 0x680U -#define MC_STREAMID_OVERRIDE_CFG_PVA0WRB 0x650U -#define MC_STREAMID_OVERRIDE_CFG_DLA1FALWRB 0x628U -#define MC_STREAMID_OVERRIDE_CFG_NVENC1SWR 0x6b8U -#define MC_STREAMID_OVERRIDE_CFG_PCIE0R 0x6c0U -#define MC_STREAMID_OVERRIDE_CFG_PCIE3W 0x6f8U -#define MC_STREAMID_OVERRIDE_CFG_PVA0RDA 0x630U -#define MC_STREAMID_OVERRIDE_CFG_MIU6W 0x7f8U -#define MC_STREAMID_OVERRIDE_CFG_PCIE1R 0x6d0U -#define MC_STREAMID_OVERRIDE_CFG_NVDEC1SRD1 0x7d0U -#define MC_STREAMID_OVERRIDE_CFG_DLA0FALWRB 0x608U -#define MC_STREAMID_OVERRIDE_CFG_PVA1RDC 0x670U -#define MC_STREAMID_OVERRIDE_CFG_MIU0W 0x538U -#define MC_STREAMID_OVERRIDE_CFG_MIU2W 0x578U -#define MC_STREAMID_OVERRIDE_CFG_MPCORER 0x138U -#define MC_STREAMID_OVERRIDE_CFG_AXIAPR 0x410U -#define MC_STREAMID_OVERRIDE_CFG_AONR 0x4b8U -#define MC_STREAMID_OVERRIDE_CFG_BPMPDMAR 0x4a8U -#define MC_STREAMID_OVERRIDE_CFG_PVA0RDB 0x638U -#define MC_STREAMID_OVERRIDE_CFG_VIFALW 0x5e8U -#define MC_STREAMID_OVERRIDE_CFG_MIU6R 0x7f0U -#define MC_STREAMID_OVERRIDE_CFG_EQOSR 0x470U -#define MC_STREAMID_OVERRIDE_CFG_NVDECSRD 0x3c0U -#define MC_STREAMID_OVERRIDE_CFG_TSECSRDB 0x430U -#define MC_STREAMID_OVERRIDE_CFG_NVDECSRD1 0x518U -#define MC_STREAMID_OVERRIDE_CFG_PVA0RDB1 0x760U -#define MC_STREAMID_OVERRIDE_CFG_PCIE0R1 0x798U -#define MC_STREAMID_OVERRIDE_CFG_SCEDMAW 0x4f0U -#define MC_STREAMID_OVERRIDE_CFG_APEW 0x3d8U -#define MC_STREAMID_OVERRIDE_CFG_MIU5R 0x7e0U -#define MC_STREAMID_OVERRIDE_CFG_DLA1RDA1 0x750U -#define MC_STREAMID_OVERRIDE_CFG_PVA0WRA 0x648U -#define MC_STREAMID_OVERRIDE_CFG_ISPFALR 0x228U -#define MC_STREAMID_OVERRIDE_CFG_PTCR 0x0U -#define MC_STREAMID_OVERRIDE_CFG_MIU4R 0x590U -#define MC_STREAMID_OVERRIDE_CFG_ISPRA 0x220U -#define MC_STREAMID_OVERRIDE_CFG_VIFALR 0x5e0U -#define MC_STREAMID_OVERRIDE_CFG_PCIE2AR 0x6e0U -#define MC_STREAMID_OVERRIDE_CFG_RCEW 0x698U -#define MC_STREAMID_OVERRIDE_CFG_ISPRA1 0x790U -#define MC_STREAMID_OVERRIDE_CFG_SCEW 0x4e0U -#define MC_STREAMID_OVERRIDE_CFG_MIU3R 0x580U -#define MC_STREAMID_OVERRIDE_CFG_XUSB_DEVW 0x268U -#define MC_STREAMID_OVERRIDE_CFG_SATAR 0xf8U -#define MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR 0x490U -#define MC_STREAMID_OVERRIDE_CFG_PVA1RDB 0x668U -#define MC_STREAMID_OVERRIDE_CFG_VIW 0x390U -#define MC_STREAMID_OVERRIDE_CFG_NVENCSWR 0x158U -#define MC_STREAMID_OVERRIDE_CFG_PCIE5W 0x718U - -/******************************************************************************* - * Macro to calculate Security cfg register addr from StreamID Override register - ******************************************************************************/ -#define MC_STREAMID_OVERRIDE_TO_SECURITY_CFG(addr) ((addr) + (uint32_t)sizeof(uint32_t)) - -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_NO_OVERRIDE_SO_DEV (0U << 4) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_NON_COHERENT_SO_DEV (1U << 4) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_COHERENT_SO_DEV (2U << 4) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_COHERENT_SNOOP_SO_DEV (3U << 4) - -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_NO_OVERRIDE_NORMAL (0U << 8) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_NON_COHERENT_NORMAL (1U << 8) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_COHERENT_NORMAL (2U << 8) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_FORCE_COHERENT_SNOOP_NORMAL (3U << 8) - -#define MC_TXN_OVERRIDE_CONFIG_CGID_SO_DEV_ZERO (0U << 12) -#define MC_TXN_OVERRIDE_CONFIG_CGID_SO_DEV_CLIENT_AXI_ID (1U << 12) - -/******************************************************************************* - * Memory Controller transaction override config registers - ******************************************************************************/ -#define MC_TXN_OVERRIDE_CONFIG_HDAR 0x10a8U -#define MC_TXN_OVERRIDE_CONFIG_DLA1WRA 0x1624U -#define MC_TXN_OVERRIDE_CONFIG_PCIE1W 0x16dcU -#define MC_TXN_OVERRIDE_CONFIG_PVA0RDC 0x1644U -#define MC_TXN_OVERRIDE_CONFIG_PTCR 0x1000U -#define MC_TXN_OVERRIDE_CONFIG_EQOSW 0x1478U -#define MC_TXN_OVERRIDE_CONFIG_MPCOREW 0x11c8U -#define MC_TXN_OVERRIDE_CONFIG_DLA1FALWRB 0x162cU -#define MC_TXN_OVERRIDE_CONFIG_AXISR 0x1460U -#define MC_TXN_OVERRIDE_CONFIG_PVA0WRB 0x1654U -#define MC_TXN_OVERRIDE_CONFIG_MIU6R 0x17f4U -#define MC_TXN_OVERRIDE_CONFIG_MIU5R 0x17e4U -#define MC_TXN_OVERRIDE_CONFIG_NVENCSRD1 0x1784U -#define MC_TXN_OVERRIDE_CONFIG_PCIE0R 0x16c4U -#define MC_TXN_OVERRIDE_CONFIG_EQOSR 0x1470U -#define MC_TXN_OVERRIDE_CONFIG_NVENCSRD 0x10e0U -#define MC_TXN_OVERRIDE_CONFIG_NVENC1SRD1 0x178cU -#define MC_TXN_OVERRIDE_CONFIG_PVA1RDB1 0x1774U -#define MC_TXN_OVERRIDE_CONFIG_NVENC1SWR 0x16bcU -#define MC_TXN_OVERRIDE_CONFIG_VICSRD1 0x1510U -#define MC_TXN_OVERRIDE_CONFIG_BPMPDMAR 0x14a8U -#define MC_TXN_OVERRIDE_CONFIG_VIW 0x1390U -#define MC_TXN_OVERRIDE_CONFIG_PCIE5R 0x1714U -#define MC_TXN_OVERRIDE_CONFIG_AXISW 0x1468U -#define MC_TXN_OVERRIDE_CONFIG_MIU6W 0x17fcU -#define MC_TXN_OVERRIDE_CONFIG_UFSHCR 0x1480U -#define MC_TXN_OVERRIDE_CONFIG_PCIE0R1 0x179cU -#define MC_TXN_OVERRIDE_CONFIG_PVA0RDB1 0x1764U -#define MC_TXN_OVERRIDE_CONFIG_TSECSWR 0x12a8U -#define MC_TXN_OVERRIDE_CONFIG_MIU7R 0x1008U -#define MC_TXN_OVERRIDE_CONFIG_SATAR 0x10f8U -#define MC_TXN_OVERRIDE_CONFIG_XUSB_HOSTW 0x1258U -#define MC_TXN_OVERRIDE_CONFIG_DLA0RDA 0x15f4U -#define MC_TXN_OVERRIDE_CONFIG_TSECSWRB 0x1438U -#define MC_TXN_OVERRIDE_CONFIG_NVDEC1SWR 0x17dcU -#define MC_TXN_OVERRIDE_CONFIG_PVA1RDA1 0x176cU -#define MC_TXN_OVERRIDE_CONFIG_PVA1RDB 0x166cU -#define MC_TXN_OVERRIDE_CONFIG_AONDMAW 0x14d0U -#define MC_TXN_OVERRIDE_CONFIG_AONW 0x14c0U -#define MC_TXN_OVERRIDE_CONFIG_ETRR 0x1420U -#define MC_TXN_OVERRIDE_CONFIG_PCIE2AW 0x16ecU -#define MC_TXN_OVERRIDE_CONFIG_PCIE1R 0x16d4U -#define MC_TXN_OVERRIDE_CONFIG_PVA1RDC 0x1674U -#define MC_TXN_OVERRIDE_CONFIG_PVA0WRA 0x164cU -#define MC_TXN_OVERRIDE_CONFIG_TSECSRDB 0x1430U -#define MC_TXN_OVERRIDE_CONFIG_MIU1W 0x1548U -#define MC_TXN_OVERRIDE_CONFIG_PCIE0W 0x16ccU -#define MC_TXN_OVERRIDE_CONFIG_NVDEC1SRD 0x17ccU -#define MC_TXN_OVERRIDE_CONFIG_MIU7W 0x1010U -#define MC_TXN_OVERRIDE_CONFIG_NVDECSRD1 0x1518U -#define MC_TXN_OVERRIDE_CONFIG_MIU3R 0x1580U -#define MC_TXN_OVERRIDE_CONFIG_MIU3W 0x158cU -#define MC_TXN_OVERRIDE_CONFIG_XUSB_HOSTR 0x1250U -#define MC_TXN_OVERRIDE_CONFIG_SESRD 0x1400U -#define MC_TXN_OVERRIDE_CONFIG_SCER 0x14d8U -#define MC_TXN_OVERRIDE_CONFIG_MPCORER 0x1138U -#define MC_TXN_OVERRIDE_CONFIG_SDMMCWA 0x1320U -#define MC_TXN_OVERRIDE_CONFIG_HDAW 0x11a8U -#define MC_TXN_OVERRIDE_CONFIG_NVDECSWR 0x13c8U -#define MC_TXN_OVERRIDE_CONFIG_PVA0RDA 0x1634U -#define MC_TXN_OVERRIDE_CONFIG_AONDMAR 0x14c8U -#define MC_TXN_OVERRIDE_CONFIG_SDMMCWAB 0x1338U -#define MC_TXN_OVERRIDE_CONFIG_ISPFALR 0x1228U -#define MC_TXN_OVERRIDE_CONFIG_PVA0RDA1 0x175cU -#define MC_TXN_OVERRIDE_CONFIG_NVENC1SRD 0x16b4U -#define MC_TXN_OVERRIDE_CONFIG_NVDISPLAYR1 0x1508U -#define MC_TXN_OVERRIDE_CONFIG_PVA1RDA 0x1664U -#define MC_TXN_OVERRIDE_CONFIG_DLA0RDA1 0x174cU -#define MC_TXN_OVERRIDE_CONFIG_ISPWB 0x1238U -#define MC_TXN_OVERRIDE_CONFIG_APEW 0x13d8U -#define MC_TXN_OVERRIDE_CONFIG_AXIAPR 0x1410U -#define MC_TXN_OVERRIDE_CONFIG_PCIE2AR 0x16e4U -#define MC_TXN_OVERRIDE_CONFIG_ISPFALW 0x1724U -#define MC_TXN_OVERRIDE_CONFIG_SDMMCR 0x1310U -#define MC_TXN_OVERRIDE_CONFIG_MIU2W 0x1578U -#define MC_TXN_OVERRIDE_CONFIG_RCER 0x1694U -#define MC_TXN_OVERRIDE_CONFIG_PCIE4W 0x170cU -#define MC_TXN_OVERRIDE_CONFIG_BPMPW 0x14a0U -#define MC_TXN_OVERRIDE_CONFIG_NVDISPLAYR 0x1490U -#define MC_TXN_OVERRIDE_CONFIG_ISPRA 0x1220U -#define MC_TXN_OVERRIDE_CONFIG_NVJPGSWR 0x13f8U -#define MC_TXN_OVERRIDE_CONFIG_VICSRD 0x1360U -#define MC_TXN_OVERRIDE_CONFIG_NVDEC1SRD1 0x17d4U -#define MC_TXN_OVERRIDE_CONFIG_DLA1RDA 0x1614U -#define MC_TXN_OVERRIDE_CONFIG_SCEDMAW 0x14f0U -#define MC_TXN_OVERRIDE_CONFIG_SDMMCW 0x1330U -#define MC_TXN_OVERRIDE_CONFIG_DLA1FALRDB 0x161cU -#define MC_TXN_OVERRIDE_CONFIG_APEDMAR 0x14f8U -#define MC_TXN_OVERRIDE_CONFIG_RCEW 0x169cU -#define MC_TXN_OVERRIDE_CONFIG_SDMMCRAB 0x1318U -#define MC_TXN_OVERRIDE_CONFIG_DLA0WRA 0x1604U -#define MC_TXN_OVERRIDE_CONFIG_VIFALR 0x15e4U -#define MC_TXN_OVERRIDE_CONFIG_PCIE3R 0x16f4U -#define MC_TXN_OVERRIDE_CONFIG_MIU1R 0x1540U -#define MC_TXN_OVERRIDE_CONFIG_PCIE5W 0x171cU -#define MC_TXN_OVERRIDE_CONFIG_XUSB_DEVR 0x1260U -#define MC_TXN_OVERRIDE_CONFIG_MIU0W 0x1538U -#define MC_TXN_OVERRIDE_CONFIG_DLA0FALWRB 0x160cU -#define MC_TXN_OVERRIDE_CONFIG_VIFALW 0x15ecU -#define MC_TXN_OVERRIDE_CONFIG_DLA0FALRDB 0x15fcU -#define MC_TXN_OVERRIDE_CONFIG_PCIE3W 0x16fcU -#define MC_TXN_OVERRIDE_CONFIG_MIU0R 0x1530U -#define MC_TXN_OVERRIDE_CONFIG_PVA0WRC 0x165cU -#define MC_TXN_OVERRIDE_CONFIG_SCEDMAR 0x14e8U -#define MC_TXN_OVERRIDE_CONFIG_APEDMAW 0x1500U -#define MC_TXN_OVERRIDE_CONFIG_HOST1XDMAR 0x10b0U -#define MC_TXN_OVERRIDE_CONFIG_SESWR 0x1408U -#define MC_TXN_OVERRIDE_CONFIG_AXIAPW 0x1418U -#define MC_TXN_OVERRIDE_CONFIG_MIU4R 0x1594U -#define MC_TXN_OVERRIDE_CONFIG_MIU4W 0x159cU -#define MC_TXN_OVERRIDE_CONFIG_NVJPGSRD 0x13f0U -#define MC_TXN_OVERRIDE_CONFIG_NVDECSRD 0x13c0U -#define MC_TXN_OVERRIDE_CONFIG_BPMPDMAW 0x14b0U -#define MC_TXN_OVERRIDE_CONFIG_APER 0x13d0U -#define MC_TXN_OVERRIDE_CONFIG_DLA1RDA1 0x1754U -#define MC_TXN_OVERRIDE_CONFIG_PVA1WRB 0x1684U -#define MC_TXN_OVERRIDE_CONFIG_ISPWA 0x1230U -#define MC_TXN_OVERRIDE_CONFIG_PVA1WRC 0x168cU -#define MC_TXN_OVERRIDE_CONFIG_RCEDMAR 0x16a4U -#define MC_TXN_OVERRIDE_CONFIG_ISPRA1 0x1794U -#define MC_TXN_OVERRIDE_CONFIG_AONR 0x14b8U -#define MC_TXN_OVERRIDE_CONFIG_RCEDMAW 0x16acU -#define MC_TXN_OVERRIDE_CONFIG_UFSHCW 0x1488U -#define MC_TXN_OVERRIDE_CONFIG_ETRW 0x1428U -#define MC_TXN_OVERRIDE_CONFIG_SATAW 0x11e8U -#define MC_TXN_OVERRIDE_CONFIG_VICSWR 0x1368U -#define MC_TXN_OVERRIDE_CONFIG_NVENCSWR 0x1158U -#define MC_TXN_OVERRIDE_CONFIG_PCIE5R1 0x177cU -#define MC_TXN_OVERRIDE_CONFIG_PVA0RDB 0x163cU -#define MC_TXN_OVERRIDE_CONFIG_SDMMCRA 0x1300U -#define MC_TXN_OVERRIDE_CONFIG_PVA1WRA 0x167cU -#define MC_TXN_OVERRIDE_CONFIG_MIU5W 0x17ecU -#define MC_TXN_OVERRIDE_CONFIG_BPMPR 0x1498U -#define MC_TXN_OVERRIDE_CONFIG_MIU2R 0x1570U -#define MC_TXN_OVERRIDE_CONFIG_XUSB_DEVW 0x1268U -#define MC_TXN_OVERRIDE_CONFIG_TSECSRD 0x12a0U -#define MC_TXN_OVERRIDE_CONFIG_PCIE4R 0x1704U -#define MC_TXN_OVERRIDE_CONFIG_SCEW 0x14e0U - -#define MC_TXN_OVERRIDE_CONFIG_AXID_OVERRIDE_CGID (1U << 0) -#define MC_TXN_OVERRIDE_CONFIG_COH_PATH_OVERRIDE_SO_DEV (2U << 4) -#define MC_TXN_OVERRIDE_CONFIG_AXID_OVERRIDE_SO_DEV_CGID_SO_DEV_CLIENT (1U << 12) - -/******************************************************************************* - * Non-SO_DEV transactions override values for CGID_TAG bitfield for the - * MC_TXN_OVERRIDE_CONFIG_{module} registers - ******************************************************************************/ -#define MC_TXN_OVERRIDE_CGID_TAG_DEFAULT 0U -#define MC_TXN_OVERRIDE_CGID_TAG_CLIENT_AXI_ID 1U -#define MC_TXN_OVERRIDE_CGID_TAG_ZERO 2U -#define MC_TXN_OVERRIDE_CGID_TAG_ADR 3U -#define MC_TXN_OVERRIDE_CGID_TAG_MASK 3ULL - -/******************************************************************************* - * Memory Controller Reset Control registers - ******************************************************************************/ -#define MC_CLIENT_HOTRESET_CTRL0 0x200U -#define MC_CLIENT_HOTRESET_CTRL0_RESET_VAL 0U -#define MC_CLIENT_HOTRESET_CTRL0_AFI_FLUSH_ENB (1U << 0) -#define MC_CLIENT_HOTRESET_CTRL0_HC_FLUSH_ENB (1U << 6) -#define MC_CLIENT_HOTRESET_CTRL0_HDA_FLUSH_ENB (1U << 7) -#define MC_CLIENT_HOTRESET_CTRL0_ISP2_FLUSH_ENB (1U << 8) -#define MC_CLIENT_HOTRESET_CTRL0_MPCORE_FLUSH_ENB (1U << 9) -#define MC_CLIENT_HOTRESET_CTRL0_NVENC_FLUSH_ENB (1U << 11) -#define MC_CLIENT_HOTRESET_CTRL0_SATA_FLUSH_ENB (1U << 15) -#define MC_CLIENT_HOTRESET_CTRL0_VI_FLUSH_ENB (1U << 17) -#define MC_CLIENT_HOTRESET_CTRL0_VIC_FLUSH_ENB (1U << 18) -#define MC_CLIENT_HOTRESET_CTRL0_XUSB_HOST_FLUSH_ENB (1U << 19) -#define MC_CLIENT_HOTRESET_CTRL0_XUSB_DEV_FLUSH_ENB (1U << 20) -#define MC_CLIENT_HOTRESET_CTRL0_TSEC_FLUSH_ENB (1U << 22) -#define MC_CLIENT_HOTRESET_CTRL0_SDMMC1A_FLUSH_ENB (1U << 29) -#define MC_CLIENT_HOTRESET_CTRL0_SDMMC2A_FLUSH_ENB (1U << 30) -#define MC_CLIENT_HOTRESET_CTRL0_SDMMC3A_FLUSH_ENB (1U << 31) -#define MC_CLIENT_HOTRESET_STATUS0 0x204U -#define MC_CLIENT_HOTRESET_CTRL1 0x970U -#define MC_CLIENT_HOTRESET_CTRL1_RESET_VAL 0U -#define MC_CLIENT_HOTRESET_CTRL1_SDMMC4A_FLUSH_ENB (1U << 0) -#define MC_CLIENT_HOTRESET_CTRL1_GPU_FLUSH_ENB (1U << 2) -#define MC_CLIENT_HOTRESET_CTRL1_NVDEC_FLUSH_ENB (1U << 5) -#define MC_CLIENT_HOTRESET_CTRL1_APE_FLUSH_ENB (1U << 6) -#define MC_CLIENT_HOTRESET_CTRL1_SE_FLUSH_ENB (1U << 7) -#define MC_CLIENT_HOTRESET_CTRL1_NVJPG_FLUSH_ENB (1U << 8) -#define MC_CLIENT_HOTRESET_CTRL1_ETR_FLUSH_ENB (1U << 12) -#define MC_CLIENT_HOTRESET_CTRL1_TSECB_FLUSH_ENB (1U << 13) -#define MC_CLIENT_HOTRESET_CTRL1_AXIS_FLUSH_ENB (1U << 17) -#define MC_CLIENT_HOTRESET_CTRL1_EQOS_FLUSH_ENB (1U << 18) -#define MC_CLIENT_HOTRESET_CTRL1_UFSHC_FLUSH_ENB (1U << 19) -#define MC_CLIENT_HOTRESET_CTRL1_NVDISPLAY_FLUSH_ENB (1U << 20) -#define MC_CLIENT_HOTRESET_CTRL1_BPMP_FLUSH_ENB (1U << 21) -#define MC_CLIENT_HOTRESET_CTRL1_AON_FLUSH_ENB (1U << 22) -#define MC_CLIENT_HOTRESET_CTRL1_SCE_FLUSH_ENB (1U << 23) -#define MC_CLIENT_HOTRESET_CTRL1_VIFAL_FLUSH_ENB (1U << 26) -#define MC_CLIENT_HOTRESET_CTRL1_RCE_FLUSH_ENB (1U << 31) -#define MC_CLIENT_HOTRESET_STATUS1 0x974U -#define MC_CLIENT_HOTRESET_CTRL2 0x97cU -#define MC_CLIENT_HOTRESET_CTRL2_RESET_VAL 0U -#define MC_CLIENT_HOTRESET_CTRL2_RCEDMA_FLUSH_ENB (1U << 0) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE_FLUSH_ENB (1U << 2) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE5A_FLUSH_ENB (1U << 4) -#define MC_CLIENT_HOTRESET_CTRL2_AONDMA_FLUSH_ENB (1U << 9) -#define MC_CLIENT_HOTRESET_CTRL2_BPMPDMA_FLUSH_ENB (1U << 10) -#define MC_CLIENT_HOTRESET_CTRL2_SCEDMA_FLUSH_ENB (1U << 11) -#define MC_CLIENT_HOTRESET_CTRL2_APEDMA_FLUSH_ENB (1U << 14) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE3A_FLUSH_ENB (1U << 16) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE3_FLUSH_ENB (1U << 17) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE0A_FLUSH_ENB (1U << 22) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE0A2_FLUSH_ENB (1U << 23) -#define MC_CLIENT_HOTRESET_CTRL2_PCIE4A_FLUSH_ENB (1U << 25) -#define MC_CLIENT_HOTRESET_STATUS2 0x1898U - -#define MC_COALESCE_CTRL 0x2930U -#define MC_COALESCE_CTRL_COALESCER_ENABLE (1U << 31) -#define MC_COALESCE_CONFIG_6_0 0x294cU -#define MC_COALESCE_CONFIG_6_0_PVA0RDC_COALESCER_ENABLED (1U << 8) -#define MC_COALESCE_CONFIG_6_0_PVA1RDC_COALESCER_ENABLED (1U << 14) - -/******************************************************************************* - * Tegra TSA Controller constants - ******************************************************************************/ -#define TEGRA_TSA_BASE U(0x02000000) - -#define TSA_CONFIG_STATIC0_CSR_RESET_R 0x20000000U -#define TSA_CONFIG_STATIC0_CSW_RESET_W 0x20001000U -#define TSA_CONFIG_STATIC0_CSW_RESET_SO_DEV 0x20001000U - -#define TSA_CONFIG_STATIC0_CSW_PCIE1W 0x1004U -#define TSA_CONFIG_STATIC0_CSW_PCIE2AW 0x1008U -#define TSA_CONFIG_STATIC0_CSW_PCIE3W 0x100cU -#define TSA_CONFIG_STATIC0_CSW_PCIE4W 0x1028U -#define TSA_CONFIG_STATIC0_CSW_XUSB_DEVW 0x2004U -#define TSA_CONFIG_STATIC0_CSR_SATAR 0x2010U -#define TSA_CONFIG_STATIC0_CSW_SATAW 0x2014U -#define TSA_CONFIG_STATIC0_CSW_PCIE0W 0x2020U -#define TSA_CONFIG_STATIC0_CSW_XUSB_HOSTW 0x202cU -#define TSA_CONFIG_STATIC0_CSW_NVENC1SWR 0x3004U -#define TSA_CONFIG_STATIC0_CSW_NVENCSWR 0x3010U -#define TSA_CONFIG_STATIC0_CSW_NVDEC1SWR 0x4004U -#define TSA_CONFIG_STATIC0_CSR_ISPFALR 0x4010U -#define TSA_CONFIG_STATIC0_CSW_ISPWA 0x4014U -#define TSA_CONFIG_STATIC0_CSW_ISPWB 0x4018U -#define TSA_CONFIG_STATIC0_CSW_ISPFALW 0x401cU -#define TSA_CONFIG_STATIC0_CSW_NVDECSWR 0x5004U -#define TSA_CONFIG_STATIC0_CSR_EQOSR 0x5010U -#define TSA_CONFIG_STATIC0_CSW_EQOSW 0x5014U -#define TSA_CONFIG_STATIC0_CSR_SDMMCRAB 0x5020U -#define TSA_CONFIG_STATIC0_CSW_SDMMCWAB 0x5024U -#define TSA_CONFIG_STATIC0_CSW_UFSHCW 0x6004U -#define TSA_CONFIG_STATIC0_CSR_SDMMCR 0x6010U -#define TSA_CONFIG_STATIC0_CSR_SDMMCRA 0x6014U -#define TSA_CONFIG_STATIC0_CSW_SDMMCW 0x6018U -#define TSA_CONFIG_STATIC0_CSW_SDMMCWA 0x601cU -#define TSA_CONFIG_STATIC0_CSR_RCER 0x6030U -#define TSA_CONFIG_STATIC0_CSR_RCEDMAR 0x6034U -#define TSA_CONFIG_STATIC0_CSW_RCEW 0x6038U -#define TSA_CONFIG_STATIC0_CSW_RCEDMAW 0x603cU -#define TSA_CONFIG_STATIC0_CSR_SCER 0x6050U -#define TSA_CONFIG_STATIC0_CSR_SCEDMAR 0x6054U -#define TSA_CONFIG_STATIC0_CSW_SCEW 0x6058U -#define TSA_CONFIG_STATIC0_CSW_SCEDMAW 0x605cU -#define TSA_CONFIG_STATIC0_CSR_AXIAPR 0x7004U -#define TSA_CONFIG_STATIC0_CSR_ETRR 0x7008U -#define TSA_CONFIG_STATIC0_CSR_HOST1XDMAR 0x700cU -#define TSA_CONFIG_STATIC0_CSW_AXIAPW 0x7010U -#define TSA_CONFIG_STATIC0_CSW_ETRW 0x7014U -#define TSA_CONFIG_STATIC0_CSR_NVJPGSRD 0x8004U -#define TSA_CONFIG_STATIC0_CSW_NVJPGSWR 0x8008U -#define TSA_CONFIG_STATIC0_CSR_AXISR 0x8014U -#define TSA_CONFIG_STATIC0_CSW_AXISW 0x8018U -#define TSA_CONFIG_STATIC0_CSR_BPMPR 0x9004U -#define TSA_CONFIG_STATIC0_CSR_BPMPDMAR 0x9008U -#define TSA_CONFIG_STATIC0_CSW_BPMPW 0x900cU -#define TSA_CONFIG_STATIC0_CSW_BPMPDMAW 0x9010U -#define TSA_CONFIG_STATIC0_CSR_SESRD 0x9024U -#define TSA_CONFIG_STATIC0_CSR_TSECSRD 0x9028U -#define TSA_CONFIG_STATIC0_CSR_TSECSRDB 0x902cU -#define TSA_CONFIG_STATIC0_CSW_SESWR 0x9030U -#define TSA_CONFIG_STATIC0_CSW_TSECSWR 0x9034U -#define TSA_CONFIG_STATIC0_CSW_TSECSWRB 0x9038U -#define TSA_CONFIG_STATIC0_CSW_PCIE5W 0xb004U -#define TSA_CONFIG_STATIC0_CSW_VICSWR 0xc004U -#define TSA_CONFIG_STATIC0_CSR_APER 0xd004U -#define TSA_CONFIG_STATIC0_CSR_APEDMAR 0xd008U -#define TSA_CONFIG_STATIC0_CSW_APEW 0xd00cU -#define TSA_CONFIG_STATIC0_CSW_APEDMAW 0xd010U -#define TSA_CONFIG_STATIC0_CSR_HDAR 0xf004U -#define TSA_CONFIG_STATIC0_CSW_HDAW 0xf008U -#define TSA_CONFIG_STATIC0_CSR_NVDISPLAYR 0xf014U -#define TSA_CONFIG_STATIC0_CSR_VIFALR 0x10004U -#define TSA_CONFIG_STATIC0_CSW_VIW 0x10008U -#define TSA_CONFIG_STATIC0_CSW_VIFALW 0x1000cU -#define TSA_CONFIG_STATIC0_CSR_AONR 0x12004U -#define TSA_CONFIG_STATIC0_CSR_AONDMAR 0x12008U -#define TSA_CONFIG_STATIC0_CSW_AONW 0x1200cU -#define TSA_CONFIG_STATIC0_CSW_AONDMAW 0x12010U -#define TSA_CONFIG_STATIC0_CSR_PCIE1R 0x14004U -#define TSA_CONFIG_STATIC0_CSR_PCIE2AR 0x14008U -#define TSA_CONFIG_STATIC0_CSR_PCIE3R 0x1400cU -#define TSA_CONFIG_STATIC0_CSR_PCIE4R 0x14028U -#define TSA_CONFIG_STATIC0_CSR_XUSB_DEVR 0x15004U -#define TSA_CONFIG_STATIC0_CSR_XUSB_HOSTR 0x15010U -#define TSA_CONFIG_STATIC0_CSR_UFSHCR 0x16004U -#define TSA_CONFIG_STATIC0_CSW_DLA1WRA 0x18004U -#define TSA_CONFIG_STATIC0_CSR_DLA1FALRDB 0x18010U -#define TSA_CONFIG_STATIC0_CSW_DLA1FALWRB 0x18014U -#define TSA_CONFIG_STATIC0_CSW_DLA0WRA 0x19004U -#define TSA_CONFIG_STATIC0_CSR_DLA0FALRDB 0x19010U -#define TSA_CONFIG_STATIC0_CSW_DLA0FALWRB 0x19014U -#define TSA_CONFIG_STATIC0_CSR_PVA1RDC 0x1a004U -#define TSA_CONFIG_STATIC0_CSW_PVA1WRC 0x1a008U -#define TSA_CONFIG_STATIC0_CSW_PVA1WRA 0x1a014U -#define TSA_CONFIG_STATIC0_CSW_PVA1WRB 0x1a020U -#define TSA_CONFIG_STATIC0_CSW_PVA0WRB 0x1b004U -#define TSA_CONFIG_STATIC0_CSR_PVA0RDC 0x1b010U -#define TSA_CONFIG_STATIC0_CSW_PVA0WRC 0x1b014U -#define TSA_CONFIG_STATIC0_CSW_PVA0WRA 0x1b020U -#define TSA_CONFIG_STATIC0_CSR_NVENC1SRD 0x1d004U -#define TSA_CONFIG_STATIC0_CSR_NVENCSRD 0x1d010U -#define TSA_CONFIG_STATIC0_CSR_NVDEC1SRD 0x1e004U -#define TSA_CONFIG_STATIC0_CSR_ISPRA 0x1e010U -#define TSA_CONFIG_STATIC0_CSR_NVDECSRD 0x1f004U -#define TSA_CONFIG_STATIC0_CSR_PCIE0R 0x21004U -#define TSA_CONFIG_STATIC0_CSR_PCIE5R 0x23004U -#define TSA_CONFIG_STATIC0_CSR_VICSRD 0x24004U -#define TSA_CONFIG_STATIC0_CSR_DLA1RDA 0x26004U -#define TSA_CONFIG_STATIC0_CSR_DLA0RDA 0x27004U -#define TSA_CONFIG_STATIC0_CSR_PVA1RDA 0x28004U -#define TSA_CONFIG_STATIC0_CSR_PVA1RDB 0x28010U -#define TSA_CONFIG_STATIC0_CSR_PVA0RDB 0x29004U -#define TSA_CONFIG_STATIC0_CSR_PVA0RDA 0x29010U - -#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_MASK (ULL(0x3) << 11) -#define TSA_CONFIG_CSW_MEMTYPE_OVERRIDE_PASTHRU (ULL(0) << 11) -#define TSA_CONFIG_CSW_SO_DEV_HUBID_MASK (ULL(0x3) << 15) -#define TSA_CONFIG_CSW_SO_DEV_HUB2 (ULL(2) << 15) - -#define REORDER_DEPTH_LIMIT 16 -#define TSA_CONFIG_CSW_REORDER_DEPTH_LIMIT_MASK (ULL(0x7FF) << 21) -#define reorder_depth_limit(limit) (ULL(limit) << 21) - -#define tsa_read_32(client) \ - mmio_read_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client) - -#define mc_set_tsa_hub2(val, client) \ - { \ - mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ - ((val & ~TSA_CONFIG_CSW_SO_DEV_HUBID_MASK) | \ - TSA_CONFIG_CSW_SO_DEV_HUB2)); \ - } - -#define mc_set_tsa_depth_limit(limit, client) \ - { \ - uint32_t val = mmio_read_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client); \ - mmio_write_32(TEGRA_TSA_BASE + TSA_CONFIG_STATIC0_CSW_##client, \ - ((val & ~TSA_CONFIG_CSW_REORDER_DEPTH_LIMIT_MASK) | \ - reorder_depth_limit(limit))); \ - } - -#endif /* TEGRA_MC_DEF_H */ diff --git a/plat/nvidia/tegra/include/t210/tegra_def.h b/plat/nvidia/tegra/include/t210/tegra_def.h index bbcfdc5c1..81b25e036 100644 --- a/plat/nvidia/tegra/include/t210/tegra_def.h +++ b/plat/nvidia/tegra/include/t210/tegra_def.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -10,6 +11,11 @@ #include <lib/utils_def.h> /******************************************************************************* + * Platform BL31 specific defines. + ******************************************************************************/ +#define BL31_SIZE U(0x40000) + +/******************************************************************************* * Power down state IDs ******************************************************************************/ #define PSTATE_ID_CORE_POWERDN U(7) @@ -43,6 +49,11 @@ #define SC7ENTRY_FW_HEADER_SIZE_BYTES U(0x400) /******************************************************************************* + * Counter-timer physical secure timer PPI + ******************************************************************************/ +#define TEGRA210_TIMER1_IRQ 32 + +/******************************************************************************* * iRAM memory constants ******************************************************************************/ #define TEGRA_IRAM_BASE U(0x40000000) @@ -143,6 +154,9 @@ #define SE_CLK_ENB_BIT (U(1) << 31) #define TEGRA_CLK_OUT_ENB_W U(0x364) #define ENTROPY_RESET_BIT (U(1) << 21) +#define TEGRA_CLK_RST_CTL_CLK_SRC_SE U(0x42C) +#define SE_CLK_SRC_MASK (U(7) << 29) +#define SE_CLK_SRC_CLK_M (U(6) << 29) #define TEGRA_RST_DEV_SET_V U(0x430) #define SE_RESET_BIT (U(1) << 31) #define HDA_RESET_BIT (U(1) << 29) @@ -231,6 +245,8 @@ #define MC_VIDEO_PROTECT_BASE_HI U(0x978) #define MC_VIDEO_PROTECT_BASE_LO U(0x648) #define MC_VIDEO_PROTECT_SIZE_MB U(0x64c) +#define MC_VIDEO_PROTECT_REG_CTRL U(0x650) +#define MC_VIDEO_PROTECT_WRITE_ACCESS_ENABLED U(3) /* SMMU configuration registers*/ #define MC_SMMU_PPCS_ASID_0 0x270U @@ -268,4 +284,10 @@ #define TEGRA_TZRAM_CARVEOUT_BASE U(0x7C04C000) #define TEGRA_TZRAM_CARVEOUT_SIZE U(0x4000) +/******************************************************************************* + * Tegra DRAM memory base address + ******************************************************************************/ +#define TEGRA_DRAM_BASE ULL(0x80000000) +#define TEGRA_DRAM_END ULL(0x27FFFFFFF) + #endif /* TEGRA_DEF_H */ diff --git a/plat/nvidia/tegra/include/tegra_platform.h b/plat/nvidia/tegra/include/tegra_platform.h index d83ce48b8..b8297fd93 100644 --- a/plat/nvidia/tegra/include/tegra_platform.h +++ b/plat/nvidia/tegra/include/tegra_platform.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -29,6 +30,13 @@ #define TEGRA_CHIPID_TEGRA13 U(0x13) #define TEGRA_CHIPID_TEGRA21 U(0x21) #define TEGRA_CHIPID_TEGRA18 U(0x18) +#define TEGRA_CHIPID_TEGRA19 U(0x19) + +/******************************************************************************* + * JEDEC Standard Manufacturer's Identification Code and Bank ID + ******************************************************************************/ +#define JEDEC_NVIDIA_MFID U(0x6B) +#define JEDEC_NVIDIA_BKID U(3) #ifndef __ASSEMBLER__ @@ -45,6 +53,7 @@ bool tegra_chipid_is_t132(void); bool tegra_chipid_is_t186(void); bool tegra_chipid_is_t210(void); bool tegra_chipid_is_t210_b01(void); +bool tegra_chipid_is_t194(void); /* * Tegra platform identifiers diff --git a/plat/nvidia/tegra/include/tegra_private.h b/plat/nvidia/tegra/include/tegra_private.h index 761acdea5..cc2ad869c 100644 --- a/plat/nvidia/tegra/include/tegra_private.h +++ b/plat/nvidia/tegra/include/tegra_private.h @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -8,6 +9,7 @@ #define TEGRA_PRIVATE_H #include <platform_def.h> +#include <stdbool.h> #include <arch.h> #include <arch_helpers.h> @@ -18,12 +20,6 @@ #include <tegra_gic.h> /******************************************************************************* - * Tegra DRAM memory base address - ******************************************************************************/ -#define TEGRA_DRAM_BASE ULL(0x80000000) -#define TEGRA_DRAM_END ULL(0x27FFFFFFF) - -/******************************************************************************* * Implementation defined ACTLR_EL1 bit definitions ******************************************************************************/ #define ACTLR_EL1_PMSTATE_MASK (ULL(0xF) << 0) @@ -51,6 +47,8 @@ typedef struct plat_params_from_bl2 { uint64_t sc7entry_fw_size; /* System Suspend Entry Firmware base address */ uint64_t sc7entry_fw_base; + /* Enable dual execution */ + uint8_t enable_ccplex_lock_step; } plat_params_from_bl2_t; /******************************************************************************* @@ -70,6 +68,11 @@ struct tegra_bl31_params { image_info_t *bl33_image_info; }; +/******************************************************************************* +* To suppress Coverity MISRA C-2012 Rule 2.2 violations +*******************************************************************************/ +#define UNUSED_FUNC_NOP() asm("nop") + /* Declarations for plat_psci_handlers.c */ int32_t tegra_soc_validate_power_state(uint32_t power_state, psci_power_state_t *req_state); @@ -82,6 +85,9 @@ struct tegra_bl31_params *plat_get_bl31_params(void); plat_params_from_bl2_t *plat_get_bl31_plat_params(void); void plat_early_platform_setup(void); void plat_late_platform_setup(void); +void plat_relocate_bl32_image(const image_info_t *bl32_img_info); +bool plat_supports_system_suspend(void); +void plat_runtime_setup(void); /* Declarations for plat_secondary.c */ void plat_secondary_setup(void); @@ -89,7 +95,7 @@ int32_t plat_lock_cpu_vectors(void); /* Declarations for tegra_fiq_glue.c */ void tegra_fiq_handler_setup(void); -int tegra_fiq_get_intr_context(void); +int32_t tegra_fiq_get_intr_context(void); void tegra_fiq_set_ns_entrypoint(uint64_t entrypoint); /* Declarations for tegra_security.c */ @@ -106,24 +112,12 @@ int32_t tegra_soc_pwr_domain_on(u_register_t mpidr); int32_t tegra_soc_pwr_domain_off(const psci_power_state_t *target_state); int32_t tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state); int32_t tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state); +int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state); int32_t tegra_soc_prepare_system_reset(void); __dead2 void tegra_soc_prepare_system_off(void); plat_local_state_t tegra_soc_get_target_pwr_state(uint32_t lvl, const plat_local_state_t *states, uint32_t ncpu); -void tegra_get_sys_suspend_power_state(psci_power_state_t *req_state); -void tegra_cpu_standby(plat_local_state_t cpu_state); -int32_t tegra_pwr_domain_on(u_register_t mpidr); -void tegra_pwr_domain_off(const psci_power_state_t *target_state); -void tegra_pwr_domain_suspend(const psci_power_state_t *target_state); -void __dead2 tegra_pwr_domain_power_down_wfi(const psci_power_state_t *target_state); -void tegra_pwr_domain_on_finish(const psci_power_state_t *target_state); -void tegra_pwr_domain_suspend_finish(const psci_power_state_t *target_state); -__dead2 void tegra_system_off(void); -__dead2 void tegra_system_reset(void); -int32_t tegra_validate_power_state(uint32_t power_state, - psci_power_state_t *req_state); -int32_t tegra_validate_ns_entrypoint(uintptr_t entrypoint); /* Declarations for tegraXXX_pm.c */ int tegra_prepare_cpu_suspend(unsigned int id, unsigned int afflvl); @@ -156,4 +150,9 @@ int plat_sip_handler(uint32_t smc_fid, void *handle, uint64_t flags); +#if RAS_EXTENSION +void tegra194_ras_enable(void); +void tegra194_ras_corrected_err_clear(uint64_t *cookie); +#endif + #endif /* TEGRA_PRIVATE_H */ diff --git a/plat/nvidia/tegra/common/lib/debug/profiler.c b/plat/nvidia/tegra/lib/debug/profiler.c index dd76a4e96..dd76a4e96 100644 --- a/plat/nvidia/tegra/common/lib/debug/profiler.c +++ b/plat/nvidia/tegra/lib/debug/profiler.c diff --git a/plat/nvidia/tegra/platform.mk b/plat/nvidia/tegra/platform.mk index 0917d8701..6ed1cdf0b 100644 --- a/plat/nvidia/tegra/platform.mk +++ b/plat/nvidia/tegra/platform.mk @@ -1,5 +1,6 @@ # # Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2020, NVIDIA Corporation. All rights reserved. # # SPDX-License-Identifier: BSD-3-Clause # @@ -12,13 +13,17 @@ $(eval $(call add_define,CRASH_REPORTING)) # enable assert() for release/debug builds ENABLE_ASSERTIONS := 1 -PLAT_LOG_LEVEL_ASSERT := 40 +PLAT_LOG_LEVEL_ASSERT := 50 $(eval $(call add_define,PLAT_LOG_LEVEL_ASSERT)) # enable dynamic memory mapping PLAT_XLAT_TABLES_DYNAMIC := 1 $(eval $(call add_define,PLAT_XLAT_TABLES_DYNAMIC)) +# Enable exception handling at EL3 +EL3_EXCEPTION_HANDLING := 1 +GICV2_G0_FOR_EL3 := 1 + # Enable PSCI v1.0 extended state ID format PSCI_EXTENDED_STATE_ID := 1 @@ -28,32 +33,49 @@ SEPARATE_CODE_AND_RODATA := 1 # do not use coherent memory USE_COHERENT_MEM := 0 -# do not enable SVE -ENABLE_SVE_FOR_NS := 0 - # enable D-cache early during CPU warmboot WARMBOOT_ENABLE_DCACHE_EARLY := 1 # remove the standard libc OVERRIDE_LIBC := 1 -include plat/nvidia/tegra/common/tegra_common.mk -include ${SOC_DIR}/platform_${TARGET_SOC}.mk +# Flag to enable WDT FIQ interrupt handling for Tegra SoCs +# prior to Tegra186 +ENABLE_TEGRA_WDT_LEGACY_FIQ_HANDLING ?= 0 + +# Flag to allow relocation of BL32 image to TZDRAM during boot +RELOCATE_BL32_IMAGE ?= 0 + +# Enable stack protection +ENABLE_STACK_PROTECTOR := strong + +# Enable SDEI +SDEI_SUPPORT := 1 # modify BUILD_PLAT to point to SoC specific build directory BUILD_PLAT := ${BUILD_BASE}/${PLAT}/${TARGET_SOC}/${BUILD_TYPE} +include plat/nvidia/tegra/common/tegra_common.mk +include ${SOC_DIR}/platform_${TARGET_SOC}.mk + +$(eval $(call add_define,ENABLE_TEGRA_WDT_LEGACY_FIQ_HANDLING)) +$(eval $(call add_define,RELOCATE_BL32_IMAGE)) + # platform cflags (enable signed comparisons, disable stdlib) -TF_CFLAGS += -Wsign-compare -nostdlib +TF_CFLAGS += -nostdlib # override with necessary libc files for the Tegra platform override LIBC_SRCS := $(addprefix lib/libc/, \ + aarch64/setjmp.S \ assert.c \ + memchr.c \ + memcmp.c \ memcpy.c \ memmove.c \ memset.c \ printf.c \ putchar.c \ + strrchr.c \ strlen.c \ snprintf.c) diff --git a/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c index bd3f46fcc..0e2edf096 100644 --- a/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c +++ b/plat/nvidia/tegra/soc/t132/plat_psci_handlers.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -35,6 +36,30 @@ static int cpu_powergate_mask[PLATFORM_MAX_CPUS_PER_CLUSTER]; +plat_local_state_t tegra_soc_get_target_pwr_state(uint32_t lvl, + const plat_local_state_t *states, + uint32_t ncpu) +{ + plat_local_state_t target = PLAT_MAX_OFF_STATE, temp; + uint32_t num_cpu = ncpu; + const plat_local_state_t *local_state = states; + + (void)lvl; + + assert(ncpu != 0U); + + do { + temp = *local_state; + if ((temp < target)) { + target = temp; + } + --num_cpu; + local_state++; + } while (num_cpu != 0U); + + return target; +} + int32_t tegra_soc_validate_power_state(unsigned int power_state, psci_power_state_t *req_state) { @@ -112,6 +137,12 @@ int tegra_soc_pwr_domain_off(const psci_power_state_t *target_state) return PSCI_E_SUCCESS; } +int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state) +{ + (void)cpu_state; + return PSCI_E_SUCCESS; +} + int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) { uint64_t val; @@ -139,6 +170,16 @@ int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) return PSCI_E_SUCCESS; } +int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state) +{ + return PSCI_E_NOT_SUPPORTED; +} + +int tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state) +{ + return PSCI_E_SUCCESS; +} + int tegra_soc_prepare_system_reset(void) { /* @@ -152,5 +193,16 @@ int tegra_soc_prepare_system_reset(void) /* Wait 1 ms to make sure clock source/device logic is stabilized. */ mdelay(1); + /* + * Program the PMC in order to restart the system. + */ + tegra_pmc_system_reset(); + return PSCI_E_SUCCESS; } + +__dead2 void tegra_soc_prepare_system_off(void) +{ + ERROR("Tegra System Off: operation not handled.\n"); + panic(); +} diff --git a/plat/nvidia/tegra/soc/t132/plat_setup.c b/plat/nvidia/tegra/soc/t132/plat_setup.c index df6267897..49e8b5d88 100644 --- a/plat/nvidia/tegra/soc/t132/plat_setup.c +++ b/plat/nvidia/tegra/soc/t132/plat_setup.c @@ -1,13 +1,16 @@ /* * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ #include <arch_helpers.h> +#include <assert.h> #include <common/bl_common.h> #include <drivers/console.h> #include <lib/xlat_tables/xlat_tables_v2.h> +#include <memctrl.h> #include <plat/common/platform.h> #include <tegra_def.h> #include <tegra_platform.h> @@ -91,7 +94,7 @@ static uint32_t tegra132_uart_addresses[TEGRA132_MAX_UART_PORTS + 1] = { ******************************************************************************/ void plat_enable_console(int32_t id) { - static console_16550_t uart_console; + static console_t uart_console; uint32_t console_clock; if ((id > 0) && (id < TEGRA132_MAX_UART_PORTS)) { @@ -108,7 +111,7 @@ void plat_enable_console(int32_t id) console_clock, TEGRA_CONSOLE_BAUDRATE, &uart_console); - console_set_scope(&uart_console.console, CONSOLE_FLAG_BOOT | + console_set_scope(&uart_console, CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH); } } @@ -121,3 +124,78 @@ void plat_gic_setup(void) tegra_gic_setup(NULL, 0); tegra_gic_init(); } + +/******************************************************************************* + * Return pointer to the BL31 params from previous bootloader + ******************************************************************************/ +struct tegra_bl31_params *plat_get_bl31_params(void) +{ + return NULL; +} + +/******************************************************************************* + * Return pointer to the BL31 platform params from previous bootloader + ******************************************************************************/ +plat_params_from_bl2_t *plat_get_bl31_plat_params(void) +{ + return NULL; +} + +/******************************************************************************* + * Handler for early platform setup + ******************************************************************************/ +void plat_early_platform_setup(void) +{ + plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); + + /* Verify chip id is t132 */ + assert(tegra_chipid_is_t132()); + + /* + * Do initial security configuration to allow DRAM/device access. + */ + tegra_memctrl_tzdram_setup(plat_params->tzdram_base, + (uint32_t)plat_params->tzdram_size); +} + +/******************************************************************************* + * Handler for late platform setup + ******************************************************************************/ +void plat_late_platform_setup(void) +{ + ; /* do nothing */ +} + +/******************************************************************************* + * Handler to indicate support for System Suspend + ******************************************************************************/ +bool plat_supports_system_suspend(void) +{ + return true; +} + +/******************************************************************************* + * Platform specific runtime setup. + ******************************************************************************/ +void plat_runtime_setup(void) +{ + /* + * During cold boot, it is observed that the arbitration + * bit is set in the Memory controller leading to false + * error interrupts in the non-secure world. To avoid + * this, clean the interrupt status register before + * booting into the non-secure world + */ + tegra_memctrl_clear_pending_interrupts(); + + /* + * During boot, USB3 and flash media (SDMMC/SATA) devices need + * access to IRAM. Because these clients connect to the MC and + * do not have a direct path to the IRAM, the MC implements AHB + * redirection during boot to allow path to IRAM. In this mode + * accesses to a programmed memory address aperture are directed + * to the AHB bus, allowing access to the IRAM. This mode must be + * disabled before we jump to the non-secure world. + */ + tegra_memctrl_disable_ahb_redirection(); +} diff --git a/plat/nvidia/tegra/soc/t132/platform_t132.mk b/plat/nvidia/tegra/soc/t132/platform_t132.mk index bb7b7ee66..9534c07b9 100644 --- a/plat/nvidia/tegra/soc/t132/platform_t132.mk +++ b/plat/nvidia/tegra/soc/t132/platform_t132.mk @@ -1,5 +1,6 @@ # # Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2020, NVIDIA Corporation. All rights reserved. # # SPDX-License-Identifier: BSD-3-Clause # @@ -19,10 +20,15 @@ $(eval $(call add_define,MAX_XLAT_TABLES)) MAX_MMAP_REGIONS := 8 $(eval $(call add_define,MAX_MMAP_REGIONS)) -BL31_SOURCES += drivers/ti/uart/aarch64/16550_console.S \ +# platform files +PLAT_INCLUDES += -Iplat/nvidia/tegra/include/t132 + +BL31_SOURCES += ${TEGRA_GICv2_SOURCES} \ + drivers/ti/uart/aarch64/16550_console.S \ lib/cpus/aarch64/denver.S \ - ${COMMON_DIR}/drivers/flowctrl/flowctrl.c \ - ${COMMON_DIR}/drivers/memctrl/memctrl_v1.c \ + ${TEGRA_DRIVERS}/flowctrl/flowctrl.c \ + ${TEGRA_DRIVERS}/memctrl/memctrl_v1.c \ + ${TEGRA_DRIVERS}/pmc/pmc.c \ ${SOC_DIR}/plat_psci_handlers.c \ ${SOC_DIR}/plat_sip_calls.c \ ${SOC_DIR}/plat_setup.c \ diff --git a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c index 9e42b2bcb..54d3b2ccd 100644 --- a/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c +++ b/plat/nvidia/tegra/soc/t186/drivers/mce/mce.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -386,14 +387,6 @@ int32_t mce_update_gsc_tzdram(void) } /******************************************************************************* - * Handler to update carveout values for TZ SysRAM aperture - ******************************************************************************/ -int32_t mce_update_gsc_tzram(void) -{ - return mce_update_ccplex_gsc(TEGRA_ARI_GSC_TZRAM); -} - -/******************************************************************************* * Handler to shutdown/reset the entire system ******************************************************************************/ __dead2 void mce_enter_ccplex_state(uint32_t state_idx) diff --git a/plat/nvidia/tegra/soc/t186/drivers/se/se.c b/plat/nvidia/tegra/soc/t186/drivers/se/se.c new file mode 100644 index 000000000..25f8cd028 --- /dev/null +++ b/plat/nvidia/tegra/soc/t186/drivers/se/se.c @@ -0,0 +1,277 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <assert.h> +#include <drivers/delay_timer.h> +#include <errno.h> +#include <string.h> + +#include <bpmp_ipc.h> +#include <pmc.h> +#include <security_engine.h> +#include <tegra_private.h> + +#include "se_private.h" + +/******************************************************************************* + * Constants and Macros + ******************************************************************************/ +#define SE0_MAX_BUSY_TIMEOUT_MS U(100) /* 100ms */ +#define BYTES_IN_WORD U(4) +#define SHA256_MAX_HASH_RESULT U(7) +#define SHA256_DST_SIZE U(32) +#define SHA_FIRST_OP U(1) +#define MAX_SHA_ENGINE_CHUNK_SIZE U(0xFFFFFF) +#define SHA256_MSG_LENGTH_ONETIME U(0xffff) + +/* + * Check that SE operation has completed after kickoff + * This function is invoked after an SE operation has been started, + * and it checks the following conditions: + * 1. SE0_INT_STATUS = SE0_OP_DONE + * 2. SE0_STATUS = IDLE + * 3. SE0_ERR_STATUS is clean. + */ +static int32_t tegra_se_operation_complete(void) +{ + uint32_t val = 0U; + + /* Read SE0 interrupt register to ensure H/W operation complete */ + val = tegra_se_read_32(SE0_INT_STATUS_REG_OFFSET); + if (SE0_INT_OP_DONE(val) == SE0_INT_OP_DONE_CLEAR) { + ERROR("%s: Engine busy state too many times! val = 0x%x\n", + __func__, val); + return -ETIMEDOUT; + } + + /* Read SE0 status idle to ensure H/W operation complete */ + val = tegra_se_read_32(SE0_SHA_STATUS_0); + if (val != SE0_SHA_STATUS_IDLE) { + ERROR("%s: Idle state timeout! val = 0x%x\n", __func__, + val); + return -ETIMEDOUT; + } + + /* Ensure that no errors are thrown during operation */ + val = tegra_se_read_32(SE0_ERR_STATUS_REG_OFFSET); + if (val != SE0_ERR_STATUS_CLEAR) { + ERROR("%s: Error during SE operation! val = 0x%x", + __func__, val); + return -ENOTSUP; + } + + return 0; +} + +/* + * Security engine primitive normal operations + */ +static int32_t tegra_se_start_normal_operation(uint64_t src_addr, + uint32_t nbytes, uint32_t last_buf, uint32_t src_len_inbytes) +{ + int32_t ret = 0; + uint32_t val = 0U; + uint32_t src_in_lo; + uint32_t src_in_msb; + uint32_t src_in_hi; + + if ((src_addr == 0UL) || (nbytes == 0U)) + return -EINVAL; + + src_in_lo = (uint32_t)src_addr; + src_in_msb = ((uint32_t)(src_addr >> 32U) & 0xffU); + src_in_hi = ((src_in_msb << SE0_IN_HI_ADDR_HI_0_MSB_SHIFT) | + (nbytes & 0xffffffU)); + + /* set SRC_IN_ADDR_LO and SRC_IN_ADDR_HI*/ + tegra_se_write_32(SE0_IN_ADDR, src_in_lo); + tegra_se_write_32(SE0_IN_HI_ADDR_HI, src_in_hi); + + val = tegra_se_read_32(SE0_INT_STATUS_REG_OFFSET); + if (val > 0U) { + tegra_se_write_32(SE0_INT_STATUS_REG_OFFSET, 0x00000U); + } + + /* Enable SHA interrupt for SE0 Operation */ + tegra_se_write_32(SE0_SHA_INT_ENABLE, 0x1aU); + + /* flush to DRAM for SE to use the updated contents */ + flush_dcache_range(src_addr, src_len_inbytes); + + /* Start SHA256 operation */ + if (last_buf == 1U) { + tegra_se_write_32(SE0_OPERATION_REG_OFFSET, SE0_OP_START | + SE0_UNIT_OPERATION_PKT_LASTBUF_FIELD); + } else { + tegra_se_write_32(SE0_OPERATION_REG_OFFSET, SE0_OP_START); + } + + /* Wait for SE-operation to finish */ + udelay(SE0_MAX_BUSY_TIMEOUT_MS * 100U); + + /* Check SE0 operation status */ + ret = tegra_se_operation_complete(); + if (ret != 0) { + ERROR("SE operation complete Failed! 0x%x", ret); + return ret; + } + + return 0; +} + +static int32_t tegra_se_calculate_sha256_hash(uint64_t src_addr, + uint32_t src_len_inbyte) +{ + uint32_t val, last_buf, i; + int32_t ret = 0; + uint32_t operations; + uint64_t src_len_inbits; + uint32_t len_bits_msb; + uint32_t len_bits_lsb; + uint32_t number_of_operations, max_bytes, bytes_left, remaining_bytes; + + if (src_len_inbyte > MAX_SHA_ENGINE_CHUNK_SIZE) { + ERROR("SHA input chunk size too big: 0x%x\n", src_len_inbyte); + return -EINVAL; + } + + if (src_addr == 0UL) { + return -EINVAL; + } + + /* number of bytes per operation */ + max_bytes = SHA256_HASH_SIZE_BYTES * SHA256_MSG_LENGTH_ONETIME; + + src_len_inbits = src_len_inbyte * 8U; + len_bits_msb = (uint32_t)(src_len_inbits >> 32U); + len_bits_lsb = (uint32_t)(src_len_inbits & 0xFFFFFFFF); + + /* program SE0_CONFIG for SHA256 operation */ + val = SE0_CONFIG_ENC_ALG_SHA | SE0_CONFIG_ENC_MODE_SHA256 | + SE0_CONFIG_DEC_ALG_NOP | SE0_CONFIG_DST_HASHREG; + tegra_se_write_32(SE0_SHA_CONFIG, val); + + /* set SE0_SHA_MSG_LENGTH registers */ + tegra_se_write_32(SE0_SHA_MSG_LENGTH_0, len_bits_lsb); + tegra_se_write_32(SE0_SHA_MSG_LEFT_0, len_bits_lsb); + tegra_se_write_32(SE0_SHA_MSG_LENGTH_1, len_bits_msb); + + /* zero out unused SE0_SHA_MSG_LENGTH and SE0_SHA_MSG_LEFT */ + tegra_se_write_32(SE0_SHA_MSG_LENGTH_2, 0U); + tegra_se_write_32(SE0_SHA_MSG_LENGTH_3, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_1, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_2, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_3, 0U); + + number_of_operations = src_len_inbyte / max_bytes; + remaining_bytes = src_len_inbyte % max_bytes; + if (remaining_bytes > 0U) { + number_of_operations += 1U; + } + + /* + * 1. Operations == 1: program SE0_SHA_TASK register to initiate SHA256 + * hash generation by setting + * 1(SE0_SHA_CONFIG_HW_INIT_HASH) to SE0_SHA_TASK + * and start SHA256-normal operation. + * 2. 1 < Operations < number_of_operations: program SE0_SHA_TASK to + * 0(SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE) to load + * intermediate SHA256 digest result from + * HASH_RESULT register to continue SHA256 + * generation and start SHA256-normal operation. + * 3. Operations == number_of_operations: continue with step 2 and set + * max_bytes to bytes_left to process final + * hash-result generation and + * start SHA256-normal operation. + */ + bytes_left = src_len_inbyte; + for (operations = 1U; operations <= number_of_operations; + operations++) { + if (operations == SHA_FIRST_OP) { + val = SE0_SHA_CONFIG_HW_INIT_HASH; + } else { + /* Load intermediate SHA digest result to + * SHA:HASH_RESULT(0..7) to continue the SHA + * calculation and tell the SHA engine to use it. + */ + for (i = 0U; (i / BYTES_IN_WORD) <= + SHA256_MAX_HASH_RESULT; i += BYTES_IN_WORD) { + val = tegra_se_read_32(SE0_SHA_HASH_RESULT_0 + + i); + tegra_se_write_32(SE0_SHA_HASH_RESULT_0 + i, + val); + } + val = SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE; + if (len_bits_lsb <= (max_bytes * 8U)) { + len_bits_lsb = (remaining_bytes * 8U); + } else { + len_bits_lsb -= (max_bytes * 8U); + } + tegra_se_write_32(SE0_SHA_MSG_LEFT_0, len_bits_lsb); + } + tegra_se_write_32(SE0_SHA_TASK_CONFIG, val); + + max_bytes = (SHA256_HASH_SIZE_BYTES * + SHA256_MSG_LENGTH_ONETIME); + if (bytes_left < max_bytes) { + max_bytes = bytes_left; + last_buf = 1U; + } else { + bytes_left = bytes_left - max_bytes; + last_buf = 0U; + } + /* start operation */ + ret = tegra_se_start_normal_operation(src_addr, max_bytes, + last_buf, src_len_inbyte); + if (ret != 0) { + ERROR("Error during SE operation! 0x%x", ret); + return -EINVAL; + } + } + + return ret; +} + +/* + * Handler to generate SHA256 and save SHA256 hash to PMC-Scratch register. + */ +int32_t tegra_se_save_sha256_hash(uint64_t bl31_base, uint32_t src_len_inbyte) +{ + int32_t ret = 0; + uint32_t val = 0U, hash_offset = 0U, scratch_offset = 0U, security; + + /* + * Set SE_SOFT_SETTINGS=SE_SECURE to prevent NS process to change SE + * registers. + */ + security = tegra_se_read_32(SE0_SECURITY); + tegra_se_write_32(SE0_SECURITY, security | SE0_SECURITY_SE_SOFT_SETTING); + + ret = tegra_se_calculate_sha256_hash(bl31_base, src_len_inbyte); + if (ret != 0L) { + ERROR("%s: SHA256 generation failed\n", __func__); + return ret; + } + + /* + * Reset SE_SECURE to previous value. + */ + tegra_se_write_32(SE0_SECURITY, security); + + /* read SHA256_HASH_RESULT and save to PMC Scratch registers */ + scratch_offset = SECURE_SCRATCH_TZDRAM_SHA256_HASH_START; + while (scratch_offset <= SECURE_SCRATCH_TZDRAM_SHA256_HASH_END) { + + val = tegra_se_read_32(SE0_SHA_HASH_RESULT_0 + hash_offset); + mmio_write_32(TEGRA_SCRATCH_BASE + scratch_offset, val); + + hash_offset += BYTES_IN_WORD; + scratch_offset += BYTES_IN_WORD; + } + + return ret; +} + diff --git a/plat/nvidia/tegra/soc/t186/drivers/se/se_private.h b/plat/nvidia/tegra/soc/t186/drivers/se/se_private.h new file mode 100644 index 000000000..7aa0dd691 --- /dev/null +++ b/plat/nvidia/tegra/soc/t186/drivers/se/se_private.h @@ -0,0 +1,100 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#ifndef SE_PRIVATE_H +#define SE_PRIVATE_H + +#include <lib/utils_def.h> + +/* SE0 security register */ +#define SE0_SECURITY U(0x18) +#define SE0_SECURITY_SE_SOFT_SETTING (((uint32_t)1) << 16U) + +/* SE0 config register */ +#define SE0_SHA_CONFIG U(0x104) +#define SE0_SHA_TASK_CONFIG U(0x108) +#define SE0_SHA_CONFIG_HW_INIT_HASH ((1U) << 0U) +#define SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE U(0) + +#define SE0_CONFIG_ENC_ALG_SHIFT U(12) +#define SE0_CONFIG_ENC_ALG_SHA \ + (((uint32_t)3) << SE0_CONFIG_ENC_ALG_SHIFT) +#define SE0_CONFIG_DEC_ALG_SHIFT U(8) +#define SE0_CONFIG_DEC_ALG_NOP \ + (((uint32_t)0) << SE0_CONFIG_DEC_ALG_SHIFT) +#define SE0_CONFIG_DST_SHIFT U(2) +#define SE0_CONFIG_DST_HASHREG \ + (((uint32_t)1) << SE0_CONFIG_DST_SHIFT) +#define SHA256_HASH_SIZE_BYTES U(256) + +#define SE0_CONFIG_ENC_MODE_SHIFT U(24) +#define SE0_CONFIG_ENC_MODE_SHA256 \ + (((uint32_t)5) << SE0_CONFIG_ENC_MODE_SHIFT) + +/* SHA input message length */ +#define SE0_SHA_MSG_LENGTH_0 U(0x11c) +#define SE0_SHA_MSG_LENGTH_1 U(0x120) +#define SE0_SHA_MSG_LENGTH_2 U(0x124) +#define SE0_SHA_MSG_LENGTH_3 U(0x128) + +/* SHA input message left */ +#define SE0_SHA_MSG_LEFT_0 U(0x12c) +#define SE0_SHA_MSG_LEFT_1 U(0x130) +#define SE0_SHA_MSG_LEFT_2 U(0x134) +#define SE0_SHA_MSG_LEFT_3 U(0x138) + +/* SE Hash Result */ +#define SE0_SHA_HASH_RESULT_0 U(0x13c) + +/* SE OPERATION */ +#define SE0_OPERATION_REG_OFFSET U(0x17c) +#define SE0_UNIT_OPERATION_PKT_LASTBUF_SHIFT U(16) +#define SE0_UNIT_OPERATION_PKT_LASTBUF_FIELD \ + (((uint32_t)0x1) << SE0_UNIT_OPERATION_PKT_LASTBUF_SHIFT) +#define SE0_OPERATION_SHIFT U(0) +#define SE0_OP_START \ + (((uint32_t)0x1) << SE0_OPERATION_SHIFT) + +/* SE Interrupt */ +#define SE0_SHA_INT_ENABLE U(0x180) + +#define SE0_INT_STATUS_REG_OFFSET U(0x184) +#define SE0_INT_OP_DONE_SHIFT U(4) +#define SE0_INT_OP_DONE_CLEAR \ + (((uint32_t)0) << SE0_INT_OP_DONE_SHIFT) +#define SE0_INT_OP_DONE(x) \ + ((x) & (((uint32_t)0x1) << SE0_INT_OP_DONE_SHIFT)) + +/* SE SHA status */ +#define SE0_SHA_STATUS_0 U(0x188) +#define SE0_SHA_STATUS_IDLE U(0) + +/* SE error status */ +#define SE0_ERR_STATUS_REG_OFFSET U(0x18c) +#define SE0_ERR_STATUS_CLEAR U(0) +#define SE0_IN_ADDR U(0x10c) +#define SE0_IN_HI_ADDR_HI U(0x110) +#define SE0_IN_HI_ADDR_HI_0_MSB_SHIFT U(24) + +/* SE error status */ +#define SECURE_SCRATCH_TZDRAM_SHA256_HASH_START SECURE_SCRATCH_RSV63_LO +#define SECURE_SCRATCH_TZDRAM_SHA256_HASH_END SECURE_SCRATCH_RSV66_HI + +/******************************************************************************* + * Inline functions definition + ******************************************************************************/ + +static inline uint32_t tegra_se_read_32(uint32_t offset) +{ + return mmio_read_32((uint32_t)(TEGRA_SE0_BASE + offset)); +} + +static inline void tegra_se_write_32(uint32_t offset, uint32_t val) +{ + mmio_write_32(((uint32_t)(TEGRA_SE0_BASE + offset)), val); +} + +#endif /* SE_PRIVATE_H */ diff --git a/plat/nvidia/tegra/soc/t186/plat_memctrl.c b/plat/nvidia/tegra/soc/t186/plat_memctrl.c index df943969e..81de674bc 100644 --- a/plat/nvidia/tegra/soc/t186/plat_memctrl.c +++ b/plat/nvidia/tegra/soc/t186/plat_memctrl.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2017-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -9,36 +10,17 @@ #include <mce.h> #include <memctrl_v2.h> +#include <tegra186_private.h> #include <tegra_mc_def.h> #include <tegra_platform.h> +#include <tegra_private.h> + +extern uint64_t tegra_bl31_phys_base; /******************************************************************************* * Array to hold stream_id override config register offsets ******************************************************************************/ const static uint32_t tegra186_streamid_override_regs[] = { - MC_STREAMID_OVERRIDE_CFG_PTCR, - MC_STREAMID_OVERRIDE_CFG_AFIR, - MC_STREAMID_OVERRIDE_CFG_HDAR, - MC_STREAMID_OVERRIDE_CFG_HOST1XDMAR, - MC_STREAMID_OVERRIDE_CFG_NVENCSRD, - MC_STREAMID_OVERRIDE_CFG_SATAR, - MC_STREAMID_OVERRIDE_CFG_MPCORER, - MC_STREAMID_OVERRIDE_CFG_NVENCSWR, - MC_STREAMID_OVERRIDE_CFG_AFIW, - MC_STREAMID_OVERRIDE_CFG_HDAW, - MC_STREAMID_OVERRIDE_CFG_MPCOREW, - MC_STREAMID_OVERRIDE_CFG_SATAW, - MC_STREAMID_OVERRIDE_CFG_ISPRA, - MC_STREAMID_OVERRIDE_CFG_ISPWA, - MC_STREAMID_OVERRIDE_CFG_ISPWB, - MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTR, - MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTW, - MC_STREAMID_OVERRIDE_CFG_XUSB_DEVR, - MC_STREAMID_OVERRIDE_CFG_XUSB_DEVW, - MC_STREAMID_OVERRIDE_CFG_TSECSRD, - MC_STREAMID_OVERRIDE_CFG_TSECSWR, - MC_STREAMID_OVERRIDE_CFG_GPUSRD, - MC_STREAMID_OVERRIDE_CFG_GPUSWR, MC_STREAMID_OVERRIDE_CFG_SDMMCRA, MC_STREAMID_OVERRIDE_CFG_SDMMCRAA, MC_STREAMID_OVERRIDE_CFG_SDMMCR, @@ -47,47 +29,6 @@ const static uint32_t tegra186_streamid_override_regs[] = { MC_STREAMID_OVERRIDE_CFG_SDMMCWAA, MC_STREAMID_OVERRIDE_CFG_SDMMCW, MC_STREAMID_OVERRIDE_CFG_SDMMCWAB, - MC_STREAMID_OVERRIDE_CFG_VICSRD, - MC_STREAMID_OVERRIDE_CFG_VICSWR, - MC_STREAMID_OVERRIDE_CFG_VIW, - MC_STREAMID_OVERRIDE_CFG_NVDECSRD, - MC_STREAMID_OVERRIDE_CFG_NVDECSWR, - MC_STREAMID_OVERRIDE_CFG_APER, - MC_STREAMID_OVERRIDE_CFG_APEW, - MC_STREAMID_OVERRIDE_CFG_NVJPGSRD, - MC_STREAMID_OVERRIDE_CFG_NVJPGSWR, - MC_STREAMID_OVERRIDE_CFG_SESRD, - MC_STREAMID_OVERRIDE_CFG_SESWR, - MC_STREAMID_OVERRIDE_CFG_ETRR, - MC_STREAMID_OVERRIDE_CFG_ETRW, - MC_STREAMID_OVERRIDE_CFG_TSECSRDB, - MC_STREAMID_OVERRIDE_CFG_TSECSWRB, - MC_STREAMID_OVERRIDE_CFG_GPUSRD2, - MC_STREAMID_OVERRIDE_CFG_GPUSWR2, - MC_STREAMID_OVERRIDE_CFG_AXISR, - MC_STREAMID_OVERRIDE_CFG_AXISW, - MC_STREAMID_OVERRIDE_CFG_EQOSR, - MC_STREAMID_OVERRIDE_CFG_EQOSW, - MC_STREAMID_OVERRIDE_CFG_UFSHCR, - MC_STREAMID_OVERRIDE_CFG_UFSHCW, - MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR, - MC_STREAMID_OVERRIDE_CFG_BPMPR, - MC_STREAMID_OVERRIDE_CFG_BPMPW, - MC_STREAMID_OVERRIDE_CFG_BPMPDMAR, - MC_STREAMID_OVERRIDE_CFG_BPMPDMAW, - MC_STREAMID_OVERRIDE_CFG_AONR, - MC_STREAMID_OVERRIDE_CFG_AONW, - MC_STREAMID_OVERRIDE_CFG_AONDMAR, - MC_STREAMID_OVERRIDE_CFG_AONDMAW, - MC_STREAMID_OVERRIDE_CFG_SCER, - MC_STREAMID_OVERRIDE_CFG_SCEW, - MC_STREAMID_OVERRIDE_CFG_SCEDMAR, - MC_STREAMID_OVERRIDE_CFG_SCEDMAW, - MC_STREAMID_OVERRIDE_CFG_APEDMAR, - MC_STREAMID_OVERRIDE_CFG_APEDMAW, - MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR1, - MC_STREAMID_OVERRIDE_CFG_VICSRD1, - MC_STREAMID_OVERRIDE_CFG_NVDECSRD1 }; /******************************************************************************* @@ -95,71 +36,71 @@ const static uint32_t tegra186_streamid_override_regs[] = { ******************************************************************************/ const static mc_streamid_security_cfg_t tegra186_streamid_sec_cfgs[] = { mc_make_sec_cfg(SCEW, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(AFIR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(AFIW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDISPLAYR1, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(AFIR, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(AFIW, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(NVDISPLAYR1, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(XUSB_DEVR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(VICSRD1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENCSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSRDB, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(VICSRD1, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(NVENCSWR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(TSECSRDB, NON_SECURE, NO_OVERRIDE, DISABLE), 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, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(SDMMCWAB, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(AONDMAW, NON_SECURE, NO_OVERRIDE, DISABLE), 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), - mc_make_sec_cfg(SDMMCR, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(SATAW, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(UFSHCW, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCR, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(SCEDMAW, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(UFSHCR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCWAA, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SESWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(MPCORER, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PTCR, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(UFSHCR, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCWAA, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(SESWR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(MPCORER, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(PTCR, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(BPMPW, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(ETRW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(ETRW, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(GPUSRD, SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(VICSWR, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(VICSWR, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(SCEDMAR, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(HDAW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(HDAW, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(ISPWA, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(EQOSW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(EQOSW, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(XUSB_HOSTW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCRAA, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(TSECSWR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCRAA, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(VIW, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(AXISR, SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(SDMMCW, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(SDMMCW, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(BPMPDMAW, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(ISPRA, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDECSWR, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(NVDECSWR, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(XUSB_DEVW, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(NVDECSRD, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(MPCOREW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDISPLAYR, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(MPCOREW, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(NVDISPLAYR, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(BPMPDMAR, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(NVJPGSWR, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(NVJPGSWR, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(NVDECSRD1, NON_SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(TSECSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVJPGSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCWA, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(TSECSRD, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(NVJPGSRD, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCWA, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(SCER, NON_SECURE, NO_OVERRIDE, DISABLE), 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, 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), - mc_make_sec_cfg(SATAR, NON_SECURE, OVERRIDE, ENABLE), + mc_make_sec_cfg(VICSRD, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(AONDMAR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(AONW, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCRA, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(HOST1XDMAR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(EQOSR, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(SATAR, NON_SECURE, OVERRIDE, DISABLE), mc_make_sec_cfg(BPMPR, NON_SECURE, NO_OVERRIDE, DISABLE), - 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, 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(HDAR, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(SDMMCRAB, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(ETRR, NON_SECURE, OVERRIDE, DISABLE), + mc_make_sec_cfg(AONR, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(SESRD, NON_SECURE, NO_OVERRIDE, DISABLE), + mc_make_sec_cfg(NVENCSRD, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(GPUSWR, SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(TSECSWRB, NON_SECURE, NO_OVERRIDE, ENABLE), + mc_make_sec_cfg(TSECSWRB, NON_SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(ISPWB, NON_SECURE, OVERRIDE, ENABLE), mc_make_sec_cfg(GPUSRD2, SECURE, NO_OVERRIDE, DISABLE), mc_make_sec_cfg(APEDMAW, NON_SECURE, NO_OVERRIDE, DISABLE), @@ -461,16 +402,8 @@ static void tegra186_memctrl_reconfig_mss_clients(void) static void tegra186_memctrl_set_overrides(void) { - const tegra_mc_settings_t *plat_mc_settings = tegra_get_mc_settings(); - const mc_txn_override_cfg_t *mc_txn_override_cfgs; - uint32_t num_txn_override_cfgs; uint32_t i, val; - /* Get the settings from the platform */ - assert(plat_mc_settings != NULL); - mc_txn_override_cfgs = plat_mc_settings->txn_override_cfg; - num_txn_override_cfgs = plat_mc_settings->num_txn_override_cfgs; - /* * Set the MC_TXN_OVERRIDE registers for write clients. */ @@ -502,35 +435,226 @@ static void tegra186_memctrl_set_overrides(void) /* * Settings for Tegra186 silicon rev. A02 and onwards. */ - for (i = 0; i < num_txn_override_cfgs; i++) { - val = tegra_mc_read_32(mc_txn_override_cfgs[i].offset); + for (i = 0; i < ARRAY_SIZE(tegra186_txn_override_cfgs); i++) { + val = tegra_mc_read_32(tegra186_txn_override_cfgs[i].offset); val &= (uint32_t)~MC_TXN_OVERRIDE_CGID_TAG_MASK; - tegra_mc_write_32(mc_txn_override_cfgs[i].offset, - val | mc_txn_override_cfgs[i].cgid_tag); + tegra_mc_write_32(tegra186_txn_override_cfgs[i].offset, + val | tegra186_txn_override_cfgs[i].cgid_tag); } } } + /******************************************************************************* - * Struct to hold the memory controller settings + * Array to hold MC context for Tegra186 ******************************************************************************/ -static tegra_mc_settings_t tegra186_mc_settings = { - .streamid_override_cfg = tegra186_streamid_override_regs, - .num_streamid_override_cfgs = (uint32_t)ARRAY_SIZE(tegra186_streamid_override_regs), - .streamid_security_cfg = tegra186_streamid_sec_cfgs, - .num_streamid_security_cfgs = (uint32_t)ARRAY_SIZE(tegra186_streamid_sec_cfgs), - .txn_override_cfg = tegra186_txn_override_cfgs, - .num_txn_override_cfgs = (uint32_t)ARRAY_SIZE(tegra186_txn_override_cfgs), - .reconfig_mss_clients = tegra186_memctrl_reconfig_mss_clients, - .set_txn_overrides = tegra186_memctrl_set_overrides, +static __attribute__((aligned(16))) mc_regs_t tegra186_mc_context[] = { + _START_OF_TABLE_, + mc_make_sid_security_cfg(SCEW), + mc_make_sid_security_cfg(AFIR), + mc_make_sid_security_cfg(NVDISPLAYR1), + mc_make_sid_security_cfg(XUSB_DEVR), + mc_make_sid_security_cfg(VICSRD1), + mc_make_sid_security_cfg(NVENCSWR), + mc_make_sid_security_cfg(TSECSRDB), + mc_make_sid_security_cfg(AXISW), + mc_make_sid_security_cfg(SDMMCWAB), + mc_make_sid_security_cfg(AONDMAW), + mc_make_sid_security_cfg(GPUSWR2), + mc_make_sid_security_cfg(SATAW), + mc_make_sid_security_cfg(UFSHCW), + mc_make_sid_security_cfg(AFIW), + mc_make_sid_security_cfg(SDMMCR), + mc_make_sid_security_cfg(SCEDMAW), + mc_make_sid_security_cfg(UFSHCR), + mc_make_sid_security_cfg(SDMMCWAA), + mc_make_sid_security_cfg(APEDMAW), + mc_make_sid_security_cfg(SESWR), + mc_make_sid_security_cfg(MPCORER), + mc_make_sid_security_cfg(PTCR), + mc_make_sid_security_cfg(BPMPW), + mc_make_sid_security_cfg(ETRW), + mc_make_sid_security_cfg(GPUSRD), + mc_make_sid_security_cfg(VICSWR), + mc_make_sid_security_cfg(SCEDMAR), + mc_make_sid_security_cfg(HDAW), + mc_make_sid_security_cfg(ISPWA), + mc_make_sid_security_cfg(EQOSW), + mc_make_sid_security_cfg(XUSB_HOSTW), + mc_make_sid_security_cfg(TSECSWR), + mc_make_sid_security_cfg(SDMMCRAA), + mc_make_sid_security_cfg(APER), + mc_make_sid_security_cfg(VIW), + mc_make_sid_security_cfg(APEW), + mc_make_sid_security_cfg(AXISR), + mc_make_sid_security_cfg(SDMMCW), + mc_make_sid_security_cfg(BPMPDMAW), + mc_make_sid_security_cfg(ISPRA), + mc_make_sid_security_cfg(NVDECSWR), + mc_make_sid_security_cfg(XUSB_DEVW), + mc_make_sid_security_cfg(NVDECSRD), + mc_make_sid_security_cfg(MPCOREW), + mc_make_sid_security_cfg(NVDISPLAYR), + mc_make_sid_security_cfg(BPMPDMAR), + mc_make_sid_security_cfg(NVJPGSWR), + mc_make_sid_security_cfg(NVDECSRD1), + mc_make_sid_security_cfg(TSECSRD), + mc_make_sid_security_cfg(NVJPGSRD), + mc_make_sid_security_cfg(SDMMCWA), + mc_make_sid_security_cfg(SCER), + mc_make_sid_security_cfg(XUSB_HOSTR), + mc_make_sid_security_cfg(VICSRD), + mc_make_sid_security_cfg(AONDMAR), + mc_make_sid_security_cfg(AONW), + mc_make_sid_security_cfg(SDMMCRA), + mc_make_sid_security_cfg(HOST1XDMAR), + mc_make_sid_security_cfg(EQOSR), + mc_make_sid_security_cfg(SATAR), + mc_make_sid_security_cfg(BPMPR), + mc_make_sid_security_cfg(HDAR), + mc_make_sid_security_cfg(SDMMCRAB), + mc_make_sid_security_cfg(ETRR), + mc_make_sid_security_cfg(AONR), + mc_make_sid_security_cfg(APEDMAR), + mc_make_sid_security_cfg(SESRD), + mc_make_sid_security_cfg(NVENCSRD), + mc_make_sid_security_cfg(GPUSWR), + mc_make_sid_security_cfg(TSECSWRB), + mc_make_sid_security_cfg(ISPWB), + mc_make_sid_security_cfg(GPUSRD2), + mc_make_sid_override_cfg(APER), + mc_make_sid_override_cfg(VICSRD), + mc_make_sid_override_cfg(NVENCSRD), + mc_make_sid_override_cfg(NVJPGSWR), + mc_make_sid_override_cfg(AONW), + mc_make_sid_override_cfg(BPMPR), + mc_make_sid_override_cfg(BPMPW), + mc_make_sid_override_cfg(HDAW), + mc_make_sid_override_cfg(NVDISPLAYR1), + mc_make_sid_override_cfg(APEDMAR), + mc_make_sid_override_cfg(AFIR), + mc_make_sid_override_cfg(AXISR), + mc_make_sid_override_cfg(VICSRD1), + mc_make_sid_override_cfg(TSECSRD), + mc_make_sid_override_cfg(BPMPDMAW), + mc_make_sid_override_cfg(MPCOREW), + mc_make_sid_override_cfg(XUSB_HOSTR), + mc_make_sid_override_cfg(GPUSWR), + mc_make_sid_override_cfg(XUSB_DEVR), + mc_make_sid_override_cfg(UFSHCW), + mc_make_sid_override_cfg(XUSB_HOSTW), + mc_make_sid_override_cfg(SDMMCWAB), + mc_make_sid_override_cfg(SATAW), + mc_make_sid_override_cfg(SCEDMAR), + mc_make_sid_override_cfg(HOST1XDMAR), + mc_make_sid_override_cfg(SDMMCWA), + mc_make_sid_override_cfg(APEDMAW), + mc_make_sid_override_cfg(SESWR), + mc_make_sid_override_cfg(AXISW), + mc_make_sid_override_cfg(AONDMAW), + mc_make_sid_override_cfg(TSECSWRB), + mc_make_sid_override_cfg(MPCORER), + mc_make_sid_override_cfg(ISPWB), + mc_make_sid_override_cfg(AONR), + mc_make_sid_override_cfg(BPMPDMAR), + mc_make_sid_override_cfg(HDAR), + mc_make_sid_override_cfg(SDMMCRA), + mc_make_sid_override_cfg(ETRW), + mc_make_sid_override_cfg(GPUSWR2), + mc_make_sid_override_cfg(EQOSR), + mc_make_sid_override_cfg(TSECSWR), + mc_make_sid_override_cfg(ETRR), + mc_make_sid_override_cfg(NVDECSRD), + mc_make_sid_override_cfg(TSECSRDB), + mc_make_sid_override_cfg(SDMMCRAA), + mc_make_sid_override_cfg(NVDECSRD1), + mc_make_sid_override_cfg(SDMMCR), + mc_make_sid_override_cfg(NVJPGSRD), + mc_make_sid_override_cfg(SCEDMAW), + mc_make_sid_override_cfg(SDMMCWAA), + mc_make_sid_override_cfg(APEW), + mc_make_sid_override_cfg(AONDMAR), + mc_make_sid_override_cfg(PTCR), + mc_make_sid_override_cfg(SCER), + mc_make_sid_override_cfg(ISPRA), + mc_make_sid_override_cfg(ISPWA), + mc_make_sid_override_cfg(VICSWR), + mc_make_sid_override_cfg(SESRD), + mc_make_sid_override_cfg(SDMMCW), + mc_make_sid_override_cfg(SDMMCRAB), + mc_make_sid_override_cfg(EQOSW), + mc_make_sid_override_cfg(GPUSRD2), + mc_make_sid_override_cfg(SCEW), + mc_make_sid_override_cfg(GPUSRD), + mc_make_sid_override_cfg(NVDECSWR), + mc_make_sid_override_cfg(XUSB_DEVW), + mc_make_sid_override_cfg(SATAR), + mc_make_sid_override_cfg(NVDISPLAYR), + mc_make_sid_override_cfg(VIW), + mc_make_sid_override_cfg(UFSHCR), + mc_make_sid_override_cfg(NVENCSWR), + mc_make_sid_override_cfg(AFIW), + mc_smmu_bypass_cfg, /* TBU settings */ + _END_OF_TABLE_, }; /******************************************************************************* - * Handler to return the pointer to the memory controller's settings struct + * Handler to return the pointer to the MC's context struct + ******************************************************************************/ +mc_regs_t *plat_memctrl_get_sys_suspend_ctx(void) +{ + /* index of _END_OF_TABLE_ */ + tegra186_mc_context[0].val = (uint32_t)(ARRAY_SIZE(tegra186_mc_context)) - 1U; + + return tegra186_mc_context; +} + +void plat_memctrl_setup(void) +{ + uint32_t val; + unsigned int i; + + /* Program all the Stream ID overrides */ + for (i = 0U; i < ARRAY_SIZE(tegra186_streamid_override_regs); i++) { + tegra_mc_streamid_write_32(tegra186_streamid_override_regs[i], + MC_STREAM_ID_MAX); + } + + /* Program the security config settings for all Stream IDs */ + for (i = 0U; i < ARRAY_SIZE(tegra186_streamid_sec_cfgs); i++) { + val = (tegra186_streamid_sec_cfgs[i].override_enable << 16) | + (tegra186_streamid_sec_cfgs[i].override_client_inputs << 8) | + (tegra186_streamid_sec_cfgs[i].override_client_ns_flag << 0); + tegra_mc_streamid_write_32(tegra186_streamid_sec_cfgs[i].offset, val); + } + + /* + * Re-configure MSS to allow ROC to deal with ordering of the + * Memory Controller traffic. This is needed as the Memory Controller + * boots with MSS having all control, but ROC provides a performance + * boost as compared to MSS. + */ + tegra186_memctrl_reconfig_mss_clients(); + + /* Program overrides for MC transactions */ + tegra186_memctrl_set_overrides(); +} + +/******************************************************************************* + * Handler to restore platform specific settings to the memory controller ******************************************************************************/ -tegra_mc_settings_t *tegra_get_mc_settings(void) +void plat_memctrl_restore(void) { - return &tegra186_mc_settings; + /* + * Re-configure MSS to allow ROC to deal with ordering of the + * Memory Controller traffic. This is needed as the Memory Controller + * boots with MSS having all control, but ROC provides a performance + * boost as compared to MSS. + */ + tegra186_memctrl_reconfig_mss_clients(); + + /* Program overrides for MC transactions */ + tegra186_memctrl_set_overrides(); } /******************************************************************************* diff --git a/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c index 11394c0ce..af4182e24 100644 --- a/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c +++ b/plat/nvidia/tegra/soc/t186/plat_psci_handlers.c @@ -1,10 +1,12 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ #include <assert.h> +#include <stdbool.h> #include <string.h> #include <arch.h> @@ -18,9 +20,11 @@ #include <lib/psci/psci.h> #include <plat/common/platform.h> +#include <bpmp_ipc.h> #include <mce.h> +#include <memctrl_v2.h> +#include <security_engine.h> #include <smmu.h> -#include <stdbool.h> #include <t18x_ari.h> #include <tegra186_private.h> #include <tegra_private.h> @@ -68,6 +72,11 @@ int32_t tegra_soc_validate_power_state(uint32_t power_state, case PSTATE_ID_CORE_IDLE: case PSTATE_ID_CORE_POWERDN: + if (psci_get_pstate_type(power_state) != PSTATE_TYPE_POWERDOWN) { + ret = PSCI_E_INVALID_PARAMS; + break; + } + /* Core powerdown request */ req_state->pwr_domain_state[MPIDR_AFFLVL0] = state_id; req_state->pwr_domain_state[MPIDR_AFFLVL1] = state_id; @@ -83,6 +92,12 @@ int32_t tegra_soc_validate_power_state(uint32_t power_state, return ret; } +int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state) +{ + (void)cpu_state; + return PSCI_E_SUCCESS; +} + int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) { const plat_local_state_t *pwr_domain_state; @@ -90,7 +105,7 @@ int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) uint32_t cpu = plat_my_core_pos(); const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); mce_cstate_info_t cstate_info = { 0 }; - uint64_t smmu_ctx_base; + uint64_t mc_ctx_base; uint32_t val; /* get the state ID */ @@ -123,10 +138,9 @@ int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) val = mmio_read_32(TEGRA_MISC_BASE + MISCREG_PFCFG); mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_SECURE_BOOTP_FCFG, val); - /* save SMMU context to TZDRAM */ - smmu_ctx_base = params_from_bl2->tzdram_base + - tegra186_get_smmu_ctx_offset(); - tegra_smmu_save_context((uintptr_t)smmu_ctx_base); + /* save MC context to TZDRAM */ + mc_ctx_base = params_from_bl2->tzdram_base; + tegra_mc_save_context((uintptr_t)mc_ctx_base); /* Prepare for system suspend */ cstate_info.cluster = (uint32_t)TEGRA_ARI_CLUSTER_CC7; @@ -148,9 +162,6 @@ int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) (void)mce_command_handler((uint64_t)MCE_CMD_ENTER_CSTATE, (uint64_t)TEGRA_ARI_CORE_C7, MCE_CORE_SLEEP_TIME_INFINITE, 0U); - /* set system suspend state for house-keeping */ - tegra186_set_system_suspend_entry(); - } else { ; /* do nothing */ } @@ -273,22 +284,67 @@ int32_t tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_sta uint8_t stateid_afflvl2 = pwr_domain_state[PLAT_MAX_PWR_LVL] & TEGRA186_STATE_ID_MASK; uint64_t val; + uint64_t src_len_in_bytes = (uint64_t)(((uintptr_t)(&__BL31_END__) - + (uintptr_t)BL31_BASE)); + int32_t ret; if (stateid_afflvl2 == PSTATE_ID_SOC_POWERDN) { + val = params_from_bl2->tzdram_base + + tegra186_get_mc_ctx_size(); + + /* Initialise communication channel with BPMP */ + assert(tegra_bpmp_ipc_init() == 0); + + /* Enable SE clock */ + ret = tegra_bpmp_ipc_enable_clock(TEGRA186_CLK_SE); + if (ret != 0) { + ERROR("Failed to enable clock\n"); + return ret; + } + + /* + * Generate/save SHA256 of ATF during SC7 entry + */ + if (tegra_se_save_sha256_hash(BL31_BASE, + (uint32_t)src_len_in_bytes) != 0) { + ERROR("Hash calculation failed. Reboot\n"); + (void)tegra_soc_prepare_system_reset(); + } + /* * The TZRAM loses power when we enter system suspend. To * allow graceful exit from system suspend, we need to copy * BL3-1 over to TZDRAM. */ val = params_from_bl2->tzdram_base + - tegra186_get_cpu_reset_handler_size(); + tegra186_get_mc_ctx_size(); memcpy16((void *)(uintptr_t)val, (void *)(uintptr_t)BL31_BASE, (uintptr_t)BL31_END - (uintptr_t)BL31_BASE); + + /* + * Save code base and size; this would be used by SC7-RF to + * verify binary + */ + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV68_LO, + (uint32_t)val); + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV0_HI, + (uint32_t)src_len_in_bytes); + + ret = tegra_bpmp_ipc_disable_clock(TEGRA186_CLK_SE); + if (ret != 0) { + ERROR("Failed to disable clock\n"); + return ret; + } } return PSCI_E_SUCCESS; } +int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state) +{ + return PSCI_E_NOT_SUPPORTED; +} + int32_t tegra_soc_pwr_domain_on(u_register_t mpidr) { int32_t ret = PSCI_E_SUCCESS; diff --git a/plat/nvidia/tegra/soc/t186/plat_secondary.c b/plat/nvidia/tegra/soc/t186/plat_secondary.c index 16508093e..fbb550af9 100644 --- a/plat/nvidia/tegra/soc/t186/plat_secondary.c +++ b/plat/nvidia/tegra/soc/t186/plat_secondary.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -11,56 +12,30 @@ #include <lib/mmio.h> #include <mce.h> -#include <tegra186_private.h> #include <tegra_def.h> #include <tegra_private.h> -#define MISCREG_AA64_RST_LOW 0x2004U -#define MISCREG_AA64_RST_HIGH 0x2008U - #define SCRATCH_SECURE_RSV1_SCRATCH_0 0x658U #define SCRATCH_SECURE_RSV1_SCRATCH_1 0x65CU #define CPU_RESET_MODE_AA64 1U -extern void memcpy16(void *dest, const void *src, unsigned int length); - /******************************************************************************* * Setup secondary CPU vectors ******************************************************************************/ void plat_secondary_setup(void) { uint32_t addr_low, addr_high; - const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); - uint64_t cpu_reset_handler_base, cpu_reset_handler_size; INFO("Setting up secondary CPU boot\n"); - /* - * The BL31 code resides in the TZSRAM which loses state - * when we enter System Suspend. Copy the wakeup trampoline - * code to TZDRAM to help us exit from System Suspend. - */ - cpu_reset_handler_base = tegra186_get_cpu_reset_handler_base(); - cpu_reset_handler_size = tegra186_get_cpu_reset_handler_size(); - (void)memcpy16((void *)(uintptr_t)params_from_bl2->tzdram_base, - (const void *)(uintptr_t)cpu_reset_handler_base, - cpu_reset_handler_size); - /* TZDRAM base will be used as the "resume" address */ - addr_low = (uint32_t)params_from_bl2->tzdram_base | CPU_RESET_MODE_AA64; - addr_high = (uint32_t)((params_from_bl2->tzdram_base >> 32U) & 0x7ffU); - - /* write lower 32 bits first, then the upper 11 bits */ - mmio_write_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_LOW, addr_low); - mmio_write_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_HIGH, addr_high); + addr_low = (uintptr_t)&tegra_secure_entrypoint | CPU_RESET_MODE_AA64; + addr_high = (uintptr_t)(((uintptr_t)&tegra_secure_entrypoint >> 32U) & 0x7ffU); /* save reset vector to be used during SYSTEM_SUSPEND exit */ mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_LO, addr_low); mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_HI, addr_high); - - /* update reset vector address to the CCPLEX */ - (void)mce_update_reset_vector(); } diff --git a/plat/nvidia/tegra/soc/t186/plat_setup.c b/plat/nvidia/tegra/soc/t186/plat_setup.c index 1018caa94..d6d090aba 100644 --- a/plat/nvidia/tegra/soc/t186/plat_setup.c +++ b/plat/nvidia/tegra/soc/t186/plat_setup.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -11,6 +12,7 @@ #include <bl31/interrupt_mgmt.h> #include <common/bl_common.h> #include <common/debug.h> +#include <common/ep_info.h> #include <common/interrupt_props.h> #include <context.h> #include <cortex_a57.h> @@ -19,14 +21,19 @@ #include <drivers/arm/gicv2.h> #include <drivers/console.h> #include <lib/el3_runtime/context_mgmt.h> +#include <lib/utils.h> #include <lib/xlat_tables/xlat_tables_v2.h> #include <plat/common/platform.h> #include <mce.h> +#include <memctrl.h> +#include <smmu.h> #include <tegra_def.h> #include <tegra_platform.h> #include <tegra_private.h> +extern void memcpy16(void *dest, const void *src, unsigned int length); + /******************************************************************************* * Tegra186 CPU numbers in cluster #0 ******************************************************************************* @@ -101,6 +108,12 @@ static const mmap_region_t tegra_mmap[] = { MT_DEVICE | MT_RW | MT_SECURE), MAP_REGION_FLAT(TEGRA_SMMU0_BASE, 0x1000000U, /* 64KB */ MT_DEVICE | MT_RW | MT_SECURE), + MAP_REGION_FLAT(TEGRA_HSP_DBELL_BASE, 0x10000U, /* 64KB */ + MT_DEVICE | MT_RW | MT_SECURE), + MAP_REGION_FLAT(TEGRA_BPMP_IPC_TX_PHYS_BASE, TEGRA_BPMP_IPC_CH_MAP_SIZE, /* 4KB */ + MT_DEVICE | MT_RW | MT_SECURE), + MAP_REGION_FLAT(TEGRA_BPMP_IPC_RX_PHYS_BASE, TEGRA_BPMP_IPC_CH_MAP_SIZE, /* 4KB */ + MT_DEVICE | MT_RW | MT_SECURE), {0} }; @@ -145,7 +158,7 @@ static uint32_t tegra186_uart_addresses[TEGRA186_MAX_UART_PORTS + 1] = { ******************************************************************************/ void plat_enable_console(int32_t id) { - static console_16550_t uart_console; + static console_t uart_console; uint32_t console_clock; if ((id > 0) && (id < TEGRA186_MAX_UART_PORTS)) { @@ -162,7 +175,7 @@ void plat_enable_console(int32_t id) console_clock, TEGRA_CONSOLE_BAUDRATE, &uart_console); - console_set_scope(&uart_console.console, CONSOLE_FLAG_BOOT | + console_set_scope(&uart_console, CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH); } } @@ -174,10 +187,20 @@ void plat_early_platform_setup(void) { uint64_t impl, val; const plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); + const struct tegra_bl31_params *arg_from_bl2 = plat_get_bl31_params(); + + /* Verify chip id is t186 */ + assert(tegra_chipid_is_t186()); /* sanity check MCE firmware compatibility */ mce_verify_firmware_version(); + /* + * Do initial security configuration to allow DRAM/device access. + */ + tegra_memctrl_tzdram_setup(plat_params->tzdram_base, + (uint32_t)plat_params->tzdram_size); + impl = (read_midr() >> MIDR_IMPL_SHIFT) & (uint64_t)MIDR_IMPL_MASK; /* @@ -191,13 +214,30 @@ void plat_early_platform_setup(void) val |= CORTEX_A57_L2_ECC_PARITY_PROTECTION_BIT; write_l2ctlr_el1(val); } + + /* + * The previous bootloader might not have placed the BL32 image + * inside the TZDRAM. Platform handler to allow relocation of BL32 + * image to TZDRAM memory. This behavior might change per platform. + */ + plat_relocate_bl32_image(arg_from_bl2->bl32_image_info); +} + +/******************************************************************************* + * Handler for late platform setup + ******************************************************************************/ +void plat_late_platform_setup(void) +{ + ; /* do nothing */ } /* Secure IRQs for Tegra186 */ static const interrupt_prop_t tegra186_interrupt_props[] = { - INTR_PROP_DESC(TEGRA186_TOP_WDT_IRQ, GIC_HIGHEST_SEC_PRIORITY, + INTR_PROP_DESC(TEGRA_SDEI_SGI_PRIVATE, PLAT_SDEI_CRITICAL_PRI, + GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), + INTR_PROP_DESC(TEGRA186_TOP_WDT_IRQ, PLAT_TEGRA_WDT_PRIO, GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), - INTR_PROP_DESC(TEGRA186_AON_WDT_IRQ, GIC_HIGHEST_SEC_PRIORITY, + INTR_PROP_DESC(TEGRA186_AON_WDT_IRQ, PLAT_TEGRA_WDT_PRIO, GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE) }; @@ -277,3 +317,81 @@ int32_t plat_core_pos_by_mpidr(u_register_t mpidr) return ret; } + +/******************************************************************************* + * Handler to relocate BL32 image to TZDRAM + ******************************************************************************/ +void plat_relocate_bl32_image(const image_info_t *bl32_img_info) +{ + const plat_params_from_bl2_t *plat_bl31_params = plat_get_bl31_plat_params(); + const entry_point_info_t *bl32_ep_info = bl31_plat_get_next_image_ep_info(SECURE); + uint64_t tzdram_start, tzdram_end, bl32_start, bl32_end; + + if ((bl32_img_info != NULL) && (bl32_ep_info != NULL)) { + + /* Relocate BL32 if it resides outside of the TZDRAM */ + tzdram_start = plat_bl31_params->tzdram_base; + tzdram_end = plat_bl31_params->tzdram_base + + plat_bl31_params->tzdram_size; + bl32_start = bl32_img_info->image_base; + bl32_end = bl32_img_info->image_base + bl32_img_info->image_size; + + assert(tzdram_end > tzdram_start); + assert(bl32_end > bl32_start); + assert(bl32_ep_info->pc > tzdram_start); + assert(bl32_ep_info->pc < tzdram_end); + + /* relocate BL32 */ + if ((bl32_start >= tzdram_end) || (bl32_end <= tzdram_start)) { + + INFO("Relocate BL32 to TZDRAM\n"); + + (void)memcpy16((void *)(uintptr_t)bl32_ep_info->pc, + (void *)(uintptr_t)bl32_start, + bl32_img_info->image_size); + + /* clean up non-secure intermediate buffer */ + zeromem((void *)(uintptr_t)bl32_start, + bl32_img_info->image_size); + } + } +} + +/******************************************************************************* + * Handler to indicate support for System Suspend + ******************************************************************************/ +bool plat_supports_system_suspend(void) +{ + return true; +} +/******************************************************************************* + * Platform specific runtime setup. + ******************************************************************************/ +void plat_runtime_setup(void) +{ + /* + * During cold boot, it is observed that the arbitration + * bit is set in the Memory controller leading to false + * error interrupts in the non-secure world. To avoid + * this, clean the interrupt status register before + * booting into the non-secure world + */ + tegra_memctrl_clear_pending_interrupts(); + + /* + * During boot, USB3 and flash media (SDMMC/SATA) devices need + * access to IRAM. Because these clients connect to the MC and + * do not have a direct path to the IRAM, the MC implements AHB + * redirection during boot to allow path to IRAM. In this mode + * accesses to a programmed memory address aperture are directed + * to the AHB bus, allowing access to the IRAM. This mode must be + * disabled before we jump to the non-secure world. + */ + tegra_memctrl_disable_ahb_redirection(); + + /* + * Verify the integrity of the previously configured SMMU(s) + * settings + */ + tegra_smmu_verify(); +} diff --git a/plat/nvidia/tegra/soc/t186/plat_smmu.c b/plat/nvidia/tegra/soc/t186/plat_smmu.c index b4a7fe596..f1bc235e8 100644 --- a/plat/nvidia/tegra/soc/t186/plat_smmu.c +++ b/plat/nvidia/tegra/soc/t186/plat_smmu.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2017, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -13,171 +14,6 @@ #define MAX_NUM_SMMU_DEVICES U(1) /******************************************************************************* - * Array to hold SMMU context for Tegra186 - ******************************************************************************/ -static __attribute__((aligned(16))) smmu_regs_t tegra186_smmu_context[] = { - _START_OF_TABLE_, - mc_make_sid_security_cfg(SCEW), - mc_make_sid_security_cfg(AFIR), - mc_make_sid_security_cfg(NVDISPLAYR1), - mc_make_sid_security_cfg(XUSB_DEVR), - mc_make_sid_security_cfg(VICSRD1), - mc_make_sid_security_cfg(NVENCSWR), - mc_make_sid_security_cfg(TSECSRDB), - mc_make_sid_security_cfg(AXISW), - mc_make_sid_security_cfg(SDMMCWAB), - mc_make_sid_security_cfg(AONDMAW), - mc_make_sid_security_cfg(GPUSWR2), - mc_make_sid_security_cfg(SATAW), - mc_make_sid_security_cfg(UFSHCW), - mc_make_sid_security_cfg(AFIW), - mc_make_sid_security_cfg(SDMMCR), - mc_make_sid_security_cfg(SCEDMAW), - mc_make_sid_security_cfg(UFSHCR), - mc_make_sid_security_cfg(SDMMCWAA), - mc_make_sid_security_cfg(APEDMAW), - mc_make_sid_security_cfg(SESWR), - mc_make_sid_security_cfg(MPCORER), - mc_make_sid_security_cfg(PTCR), - mc_make_sid_security_cfg(BPMPW), - mc_make_sid_security_cfg(ETRW), - mc_make_sid_security_cfg(GPUSRD), - mc_make_sid_security_cfg(VICSWR), - mc_make_sid_security_cfg(SCEDMAR), - mc_make_sid_security_cfg(HDAW), - mc_make_sid_security_cfg(ISPWA), - mc_make_sid_security_cfg(EQOSW), - mc_make_sid_security_cfg(XUSB_HOSTW), - mc_make_sid_security_cfg(TSECSWR), - mc_make_sid_security_cfg(SDMMCRAA), - mc_make_sid_security_cfg(APER), - mc_make_sid_security_cfg(VIW), - mc_make_sid_security_cfg(APEW), - mc_make_sid_security_cfg(AXISR), - mc_make_sid_security_cfg(SDMMCW), - mc_make_sid_security_cfg(BPMPDMAW), - mc_make_sid_security_cfg(ISPRA), - mc_make_sid_security_cfg(NVDECSWR), - mc_make_sid_security_cfg(XUSB_DEVW), - mc_make_sid_security_cfg(NVDECSRD), - mc_make_sid_security_cfg(MPCOREW), - mc_make_sid_security_cfg(NVDISPLAYR), - mc_make_sid_security_cfg(BPMPDMAR), - mc_make_sid_security_cfg(NVJPGSWR), - mc_make_sid_security_cfg(NVDECSRD1), - mc_make_sid_security_cfg(TSECSRD), - mc_make_sid_security_cfg(NVJPGSRD), - mc_make_sid_security_cfg(SDMMCWA), - mc_make_sid_security_cfg(SCER), - mc_make_sid_security_cfg(XUSB_HOSTR), - mc_make_sid_security_cfg(VICSRD), - mc_make_sid_security_cfg(AONDMAR), - mc_make_sid_security_cfg(AONW), - mc_make_sid_security_cfg(SDMMCRA), - mc_make_sid_security_cfg(HOST1XDMAR), - mc_make_sid_security_cfg(EQOSR), - mc_make_sid_security_cfg(SATAR), - mc_make_sid_security_cfg(BPMPR), - mc_make_sid_security_cfg(HDAR), - mc_make_sid_security_cfg(SDMMCRAB), - mc_make_sid_security_cfg(ETRR), - mc_make_sid_security_cfg(AONR), - mc_make_sid_security_cfg(APEDMAR), - mc_make_sid_security_cfg(SESRD), - mc_make_sid_security_cfg(NVENCSRD), - mc_make_sid_security_cfg(GPUSWR), - mc_make_sid_security_cfg(TSECSWRB), - mc_make_sid_security_cfg(ISPWB), - mc_make_sid_security_cfg(GPUSRD2), - mc_make_sid_override_cfg(APER), - mc_make_sid_override_cfg(VICSRD), - mc_make_sid_override_cfg(NVENCSRD), - mc_make_sid_override_cfg(NVJPGSWR), - mc_make_sid_override_cfg(AONW), - mc_make_sid_override_cfg(BPMPR), - mc_make_sid_override_cfg(BPMPW), - mc_make_sid_override_cfg(HDAW), - mc_make_sid_override_cfg(NVDISPLAYR1), - mc_make_sid_override_cfg(APEDMAR), - mc_make_sid_override_cfg(AFIR), - mc_make_sid_override_cfg(AXISR), - mc_make_sid_override_cfg(VICSRD1), - mc_make_sid_override_cfg(TSECSRD), - mc_make_sid_override_cfg(BPMPDMAW), - mc_make_sid_override_cfg(MPCOREW), - mc_make_sid_override_cfg(XUSB_HOSTR), - mc_make_sid_override_cfg(GPUSWR), - mc_make_sid_override_cfg(XUSB_DEVR), - mc_make_sid_override_cfg(UFSHCW), - mc_make_sid_override_cfg(XUSB_HOSTW), - mc_make_sid_override_cfg(SDMMCWAB), - mc_make_sid_override_cfg(SATAW), - mc_make_sid_override_cfg(SCEDMAR), - mc_make_sid_override_cfg(HOST1XDMAR), - mc_make_sid_override_cfg(SDMMCWA), - mc_make_sid_override_cfg(APEDMAW), - mc_make_sid_override_cfg(SESWR), - mc_make_sid_override_cfg(AXISW), - mc_make_sid_override_cfg(AONDMAW), - mc_make_sid_override_cfg(TSECSWRB), - mc_make_sid_override_cfg(MPCORER), - mc_make_sid_override_cfg(ISPWB), - mc_make_sid_override_cfg(AONR), - mc_make_sid_override_cfg(BPMPDMAR), - mc_make_sid_override_cfg(HDAR), - mc_make_sid_override_cfg(SDMMCRA), - mc_make_sid_override_cfg(ETRW), - mc_make_sid_override_cfg(GPUSWR2), - mc_make_sid_override_cfg(EQOSR), - mc_make_sid_override_cfg(TSECSWR), - mc_make_sid_override_cfg(ETRR), - mc_make_sid_override_cfg(NVDECSRD), - mc_make_sid_override_cfg(TSECSRDB), - mc_make_sid_override_cfg(SDMMCRAA), - mc_make_sid_override_cfg(NVDECSRD1), - mc_make_sid_override_cfg(SDMMCR), - mc_make_sid_override_cfg(NVJPGSRD), - mc_make_sid_override_cfg(SCEDMAW), - mc_make_sid_override_cfg(SDMMCWAA), - mc_make_sid_override_cfg(APEW), - mc_make_sid_override_cfg(AONDMAR), - mc_make_sid_override_cfg(PTCR), - mc_make_sid_override_cfg(SCER), - mc_make_sid_override_cfg(ISPRA), - mc_make_sid_override_cfg(ISPWA), - mc_make_sid_override_cfg(VICSWR), - mc_make_sid_override_cfg(SESRD), - mc_make_sid_override_cfg(SDMMCW), - mc_make_sid_override_cfg(SDMMCRAB), - mc_make_sid_override_cfg(EQOSW), - mc_make_sid_override_cfg(GPUSRD2), - mc_make_sid_override_cfg(SCEW), - mc_make_sid_override_cfg(GPUSRD), - mc_make_sid_override_cfg(NVDECSWR), - mc_make_sid_override_cfg(XUSB_DEVW), - mc_make_sid_override_cfg(SATAR), - mc_make_sid_override_cfg(NVDISPLAYR), - mc_make_sid_override_cfg(VIW), - mc_make_sid_override_cfg(UFSHCR), - mc_make_sid_override_cfg(NVENCSWR), - mc_make_sid_override_cfg(AFIW), - smmu_make_cfg(TEGRA_SMMU0_BASE), - smmu_bypass_cfg, /* TBU settings */ - _END_OF_TABLE_, -}; - -/******************************************************************************* - * Handler to return the pointer to the SMMU's context struct - ******************************************************************************/ -smmu_regs_t *plat_get_smmu_ctx(void) -{ - /* index of _END_OF_TABLE_ */ - tegra186_smmu_context[0].val = (uint32_t)(ARRAY_SIZE(tegra186_smmu_context)) - 1U; - - return tegra186_smmu_context; -} - -/******************************************************************************* * Handler to return the support SMMU devices number ******************************************************************************/ uint32_t plat_get_num_smmu_devices(void) diff --git a/plat/nvidia/tegra/soc/t186/plat_trampoline.S b/plat/nvidia/tegra/soc/t186/plat_trampoline.S index db692349e..2fc2046d0 100644 --- a/plat/nvidia/tegra/soc/t186/plat_trampoline.S +++ b/plat/nvidia/tegra/soc/t186/plat_trampoline.S @@ -1,5 +1,6 @@ /* * Copyright (c) 2016-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -11,135 +12,30 @@ #include <plat/common/common_def.h> #include <tegra_def.h> -#define TEGRA186_STATE_SYSTEM_SUSPEND 0x5C7 -#define TEGRA186_STATE_SYSTEM_RESUME 0x600D -#define TEGRA186_SMMU_CTX_SIZE 0x420 +#define TEGRA186_MC_CTX_SIZE 0x93 - .globl tegra186_cpu_reset_handler - -/* CPU reset handler routine */ -func tegra186_cpu_reset_handler _align=4 - /* check if we are exiting system suspend state */ - adr x0, __tegra186_system_suspend_state - ldr x1, [x0] - mov x2, #TEGRA186_STATE_SYSTEM_SUSPEND - lsl x2, x2, #16 - add x2, x2, #TEGRA186_STATE_SYSTEM_SUSPEND - cmp x1, x2 - bne boot_cpu - - /* set system resume state */ - mov x1, #TEGRA186_STATE_SYSTEM_RESUME - lsl x1, x1, #16 - mov x2, #TEGRA186_STATE_SYSTEM_RESUME - add x1, x1, x2 - str x1, [x0] - dsb sy - - /* prepare to relocate to TZSRAM */ - mov x0, #BL31_BASE - adr x1, __tegra186_cpu_reset_handler_end - adr x2, __tegra186_cpu_reset_handler_data - ldr x2, [x2, #8] - - /* memcpy16 */ -m_loop16: - cmp x2, #16 - b.lt m_loop1 - ldp x3, x4, [x1], #16 - stp x3, x4, [x0], #16 - sub x2, x2, #16 - b m_loop16 - /* copy byte per byte */ -m_loop1: - cbz x2, boot_cpu - ldrb w3, [x1], #1 - strb w3, [x0], #1 - subs x2, x2, #1 - b.ne m_loop1 - -boot_cpu: - adr x0, __tegra186_cpu_reset_handler_data - ldr x0, [x0] - br x0 -endfunc tegra186_cpu_reset_handler + .globl tegra186_get_mc_ctx_size /* - * Tegra186 reset data (offset 0x0 - 0x430) + * Tegra186 reset data (offset 0x0 - 0x420) * - * 0x000: secure world's entrypoint - * 0x008: BL31 size (RO + RW) - * 0x00C: SMMU context start - * 0x42C: SMMU context end + * 0x000: MC context start + * 0x420: MC context end */ .align 4 - .type __tegra186_cpu_reset_handler_data, %object - .globl __tegra186_cpu_reset_handler_data -__tegra186_cpu_reset_handler_data: - .quad tegra_secure_entrypoint - .quad __BL31_END__ - BL31_BASE - - .globl __tegra186_system_suspend_state -__tegra186_system_suspend_state: - .quad 0 - - .align 4 - .globl __tegra186_smmu_context -__tegra186_smmu_context: - .rept TEGRA186_SMMU_CTX_SIZE +__tegra186_mc_context: + .rept TEGRA186_MC_CTX_SIZE .quad 0 .endr - .size __tegra186_cpu_reset_handler_data, \ - . - __tegra186_cpu_reset_handler_data .align 4 - .globl __tegra186_cpu_reset_handler_end -__tegra186_cpu_reset_handler_end: +__tegra186_mc_context_end: - .globl tegra186_get_cpu_reset_handler_size - .globl tegra186_get_cpu_reset_handler_base - .globl tegra186_get_smmu_ctx_offset - .globl tegra186_set_system_suspend_entry - -/* return size of the CPU reset handler */ -func tegra186_get_cpu_reset_handler_size - adr x0, __tegra186_cpu_reset_handler_end - adr x1, tegra186_cpu_reset_handler - sub x0, x0, x1 - ret -endfunc tegra186_get_cpu_reset_handler_size - -/* return the start address of the CPU reset handler */ -func tegra186_get_cpu_reset_handler_base - adr x0, tegra186_cpu_reset_handler - ret -endfunc tegra186_get_cpu_reset_handler_base - -/* return the size of the SMMU context */ -func tegra186_get_smmu_ctx_offset - adr x0, __tegra186_smmu_context - adr x1, tegra186_cpu_reset_handler +/* return the size of the MC context */ +func tegra186_get_mc_ctx_size + adr x0, __tegra186_mc_context_end + adr x1, __tegra186_mc_context sub x0, x0, x1 ret -endfunc tegra186_get_smmu_ctx_offset - -/* set system suspend state before SC7 entry */ -func tegra186_set_system_suspend_entry - mov x0, #TEGRA_MC_BASE - mov x3, #MC_SECURITY_CFG3_0 - ldr w1, [x0, x3] - lsl x1, x1, #32 - mov x3, #MC_SECURITY_CFG0_0 - ldr w2, [x0, x3] - orr x3, x1, x2 /* TZDRAM base */ - adr x0, __tegra186_system_suspend_state - adr x1, tegra186_cpu_reset_handler - sub x2, x0, x1 /* offset in TZDRAM */ - mov x0, #TEGRA186_STATE_SYSTEM_SUSPEND - lsl x0, x0, #16 - add x0, x0, #TEGRA186_STATE_SYSTEM_SUSPEND - str x0, [x3, x2] /* set value in TZDRAM */ - dsb sy - ret -endfunc tegra186_set_system_suspend_entry +endfunc tegra186_get_mc_ctx_size diff --git a/plat/nvidia/tegra/soc/t186/platform_t186.mk b/plat/nvidia/tegra/soc/t186/platform_t186.mk index fe158536c..5275b8e65 100644 --- a/plat/nvidia/tegra/soc/t186/platform_t186.mk +++ b/plat/nvidia/tegra/soc/t186/platform_t186.mk @@ -1,5 +1,6 @@ # # Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2020, NVIDIA Corporation. All rights reserved. # # SPDX-License-Identifier: BSD-3-Clause # @@ -13,10 +14,12 @@ $(eval $(call add_define,ENABLE_CHIP_VERIFICATION_HARNESS)) RESET_TO_BL31 := 1 -PROGRAMMABLE_RESET_ADDRESS := 1 +PROGRAMMABLE_RESET_ADDRESS := 0 COLD_BOOT_SINGLE_CPU := 1 +RELOCATE_BL32_IMAGE := 1 + # platform settings TZDRAM_BASE := 0x30000000 $(eval $(call add_define,TZDRAM_BASE)) @@ -27,25 +30,30 @@ $(eval $(call add_define,PLATFORM_CLUSTER_COUNT)) PLATFORM_MAX_CPUS_PER_CLUSTER := 4 $(eval $(call add_define,PLATFORM_MAX_CPUS_PER_CLUSTER)) -MAX_XLAT_TABLES := 24 +MAX_XLAT_TABLES := 25 $(eval $(call add_define,MAX_XLAT_TABLES)) -MAX_MMAP_REGIONS := 25 +MAX_MMAP_REGIONS := 30 $(eval $(call add_define,MAX_MMAP_REGIONS)) # platform files -PLAT_INCLUDES += -I${SOC_DIR}/drivers/include +PLAT_INCLUDES += -Iplat/nvidia/tegra/include/t186 \ + -I${SOC_DIR}/drivers/include -BL31_SOURCES += drivers/ti/uart/aarch64/16550_console.S \ +BL31_SOURCES += ${TEGRA_GICv2_SOURCES} \ + drivers/ti/uart/aarch64/16550_console.S \ lib/cpus/aarch64/denver.S \ lib/cpus/aarch64/cortex_a57.S \ - ${COMMON_DIR}/drivers/gpcdma/gpcdma.c \ - ${COMMON_DIR}/drivers/memctrl/memctrl_v2.c \ - ${COMMON_DIR}/drivers/smmu/smmu.c \ + ${TEGRA_DRIVERS}/bpmp_ipc/intf.c \ + ${TEGRA_DRIVERS}/bpmp_ipc/ivc.c \ + ${TEGRA_DRIVERS}/gpcdma/gpcdma.c \ + ${TEGRA_DRIVERS}/memctrl/memctrl_v2.c \ + ${TEGRA_DRIVERS}/smmu/smmu.c \ ${SOC_DIR}/drivers/mce/mce.c \ ${SOC_DIR}/drivers/mce/ari.c \ ${SOC_DIR}/drivers/mce/nvg.c \ ${SOC_DIR}/drivers/mce/aarch64/nvg_helpers.S \ + $(SOC_DIR)/drivers/se/se.c \ ${SOC_DIR}/plat_memctrl.c \ ${SOC_DIR}/plat_psci_handlers.c \ ${SOC_DIR}/plat_setup.c \ @@ -64,3 +72,6 @@ ERRATA_A57_826977 := 1 ERRATA_A57_828024 := 1 ERRATA_A57_829520 := 1 ERRATA_A57_833471 := 1 + +# Enable higher performance Non-cacheable load forwarding +A57_ENABLE_NONCACHEABLE_LOAD_FWD := 1 diff --git a/plat/nvidia/tegra/soc/t194/drivers/include/mce_private.h b/plat/nvidia/tegra/soc/t194/drivers/include/mce_private.h index 1fe3aad39..ef169808e 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/include/mce_private.h +++ b/plat/nvidia/tegra/soc/t194/drivers/include/mce_private.h @@ -56,8 +56,10 @@ int32_t nvg_update_ccplex_gsc(uint32_t gsc_idx); int32_t nvg_enter_cstate(uint32_t state, uint32_t wake_time); int32_t nvg_roc_clean_cache_trbits(void); void nvg_enable_strict_checking_mode(void); +void nvg_verify_strict_checking_mode(void); void nvg_system_shutdown(void); void nvg_system_reboot(void); +void nvg_clear_hsm_corr_status(void); /* declarations for assembly functions */ void nvg_set_request_data(uint64_t req, uint64_t data); @@ -69,7 +71,9 @@ uint64_t nvg_cache_inval_all(void); /* MCE helper functions */ void mce_enable_strict_checking(void); +void mce_verify_strict_checking(void); void mce_system_shutdown(void); void mce_system_reboot(void); +void mce_clear_hsm_corr_status(void); #endif /* MCE_PRIVATE_H */ diff --git a/plat/nvidia/tegra/soc/t194/drivers/include/se.h b/plat/nvidia/tegra/soc/t194/drivers/include/se.h index e7cf88d05..7de55a74d 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/include/se.h +++ b/plat/nvidia/tegra/soc/t194/drivers/include/se.h @@ -7,6 +7,8 @@ #ifndef SE_H #define SE_H +int32_t tegra_se_calculate_save_sha256(uint64_t src_addr, + uint32_t src_len_inbyte); int32_t tegra_se_suspend(void); void tegra_se_resume(void); diff --git a/plat/nvidia/tegra/soc/t194/drivers/include/t194_nvg.h b/plat/nvidia/tegra/soc/t194/drivers/include/t194_nvg.h index ccc46655a..7a68a4303 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/include/t194_nvg.h +++ b/plat/nvidia/tegra/soc/t194/drivers/include/t194_nvg.h @@ -7,6 +7,8 @@ #ifndef T194_NVG_H #define T194_NVG_H +#include <lib/utils_def.h> + /** * t194_nvg.h - Header for the NVIDIA Generic interface (NVG). * Official documentation for this interface is included as part @@ -19,123 +21,127 @@ * occur when there is only new functionality. */ enum { - TEGRA_NVG_VERSION_MAJOR = 6, - TEGRA_NVG_VERSION_MINOR = 6 + TEGRA_NVG_VERSION_MAJOR = U(6), + TEGRA_NVG_VERSION_MINOR = U(7) }; typedef enum { - TEGRA_NVG_CHANNEL_VERSION = 0, - TEGRA_NVG_CHANNEL_POWER_PERF = 1, - TEGRA_NVG_CHANNEL_POWER_MODES = 2, - TEGRA_NVG_CHANNEL_WAKE_TIME = 3, - TEGRA_NVG_CHANNEL_CSTATE_INFO = 4, - TEGRA_NVG_CHANNEL_CROSSOVER_C6_LOWER_BOUND = 5, - TEGRA_NVG_CHANNEL_CROSSOVER_CC6_LOWER_BOUND = 6, - TEGRA_NVG_CHANNEL_CROSSOVER_CG7_LOWER_BOUND = 8, - TEGRA_NVG_CHANNEL_CSTATE_STAT_QUERY_REQUEST = 10, - TEGRA_NVG_CHANNEL_CSTATE_STAT_QUERY_VALUE = 11, - TEGRA_NVG_CHANNEL_NUM_CORES = 20, - TEGRA_NVG_CHANNEL_UNIQUE_LOGICAL_ID = 21, - TEGRA_NVG_CHANNEL_LOGICAL_TO_PHYSICAL_MAPPING = 22, - TEGRA_NVG_CHANNEL_LOGICAL_TO_MPIDR = 23, - TEGRA_NVG_CHANNEL_SHUTDOWN = 42, - TEGRA_NVG_CHANNEL_IS_SC7_ALLOWED = 43, - TEGRA_NVG_CHANNEL_ONLINE_CORE = 44, - TEGRA_NVG_CHANNEL_CC3_CTRL = 45, - TEGRA_NVG_CHANNEL_CCPLEX_CACHE_CONTROL = 49, - TEGRA_NVG_CHANNEL_UPDATE_CCPLEX_GSC = 50, - TEGRA_NVG_CHANNEL_HSM_ERROR_CTRL = 53, - TEGRA_NVG_CHANNEL_SECURITY_CONFIG = 54, - TEGRA_NVG_CHANNEL_DEBUG_CONFIG = 55, - TEGRA_NVG_CHANNEL_DDA_SNOC_MCF = 56, - TEGRA_NVG_CHANNEL_DDA_MCF_ORD1 = 57, - TEGRA_NVG_CHANNEL_DDA_MCF_ORD2 = 58, - TEGRA_NVG_CHANNEL_DDA_MCF_ORD3 = 59, - TEGRA_NVG_CHANNEL_DDA_MCF_ISO = 60, - TEGRA_NVG_CHANNEL_DDA_MCF_SISO = 61, - TEGRA_NVG_CHANNEL_DDA_MCF_NISO = 62, - TEGRA_NVG_CHANNEL_DDA_MCF_NISO_REMOTE = 63, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_ISO = 64, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_SISO = 65, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_NISO = 66, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_NISO_REMOTE = 67, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3FILL = 68, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3WR = 69, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_RSP_L3RD_DMA = 70, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_RSP_MCFRD_DMA = 71, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_GLOBAL = 72, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_LL = 73, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3D = 74, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_FCM_RD = 75, - TEGRA_NVG_CHANNEL_DDA_L3CTRL_FCM_WR = 76, - TEGRA_NVG_CHANNEL_DDA_SNOC_GLOBAL_CTRL = 77, - TEGRA_NVG_CHANNEL_DDA_SNOC_CLIENT_REQ_CTRL = 78, - TEGRA_NVG_CHANNEL_DDA_SNOC_CLIENT_REPLENTISH_CTRL = 79, + TEGRA_NVG_CHANNEL_VERSION = U(0), + TEGRA_NVG_CHANNEL_POWER_PERF = U(1), + TEGRA_NVG_CHANNEL_POWER_MODES = U(2), + TEGRA_NVG_CHANNEL_WAKE_TIME = U(3), + TEGRA_NVG_CHANNEL_CSTATE_INFO = U(4), + TEGRA_NVG_CHANNEL_CROSSOVER_C6_LOWER_BOUND = U(5), + TEGRA_NVG_CHANNEL_CROSSOVER_CC6_LOWER_BOUND = U(6), + TEGRA_NVG_CHANNEL_CROSSOVER_CG7_LOWER_BOUND = U(8), + TEGRA_NVG_CHANNEL_CSTATE_STAT_QUERY_REQUEST = U(10), + TEGRA_NVG_CHANNEL_CSTATE_STAT_QUERY_VALUE = U(11), + TEGRA_NVG_CHANNEL_NUM_CORES = U(20), + TEGRA_NVG_CHANNEL_UNIQUE_LOGICAL_ID = U(21), + TEGRA_NVG_CHANNEL_LOGICAL_TO_PHYSICAL_MAPPING = U(22), + TEGRA_NVG_CHANNEL_LOGICAL_TO_MPIDR = U(23), + TEGRA_NVG_CHANNEL_SHUTDOWN = U(42), + TEGRA_NVG_CHANNEL_IS_SC7_ALLOWED = U(43), + TEGRA_NVG_CHANNEL_ONLINE_CORE = U(44), + TEGRA_NVG_CHANNEL_CC3_CTRL = U(45), + TEGRA_NVG_CHANNEL_CCPLEX_CACHE_CONTROL = U(49), + TEGRA_NVG_CHANNEL_UPDATE_CCPLEX_GSC = U(50), + TEGRA_NVG_CHANNEL_HSM_ERROR_CTRL = U(53), + TEGRA_NVG_CHANNEL_SECURITY_CONFIG = U(54), + TEGRA_NVG_CHANNEL_DEBUG_CONFIG = U(55), + TEGRA_NVG_CHANNEL_DDA_SNOC_MCF = U(56), + TEGRA_NVG_CHANNEL_DDA_MCF_ORD1 = U(57), + TEGRA_NVG_CHANNEL_DDA_MCF_ORD2 = U(58), + TEGRA_NVG_CHANNEL_DDA_MCF_ORD3 = U(59), + TEGRA_NVG_CHANNEL_DDA_MCF_ISO = U(60), + TEGRA_NVG_CHANNEL_DDA_MCF_SISO = U(61), + TEGRA_NVG_CHANNEL_DDA_MCF_NISO = U(62), + TEGRA_NVG_CHANNEL_DDA_MCF_NISO_REMOTE = U(63), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_ISO = U(64), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_SISO = U(65), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_NISO = U(66), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_NISO_REMOTE = U(67), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3FILL = U(68), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3WR = U(69), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_RSP_L3RD_DMA = U(70), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_RSP_MCFRD_DMA = U(71), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_GLOBAL = U(72), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_LL = U(73), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_L3D = U(74), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_FCM_RD = U(75), + TEGRA_NVG_CHANNEL_DDA_L3CTRL_FCM_WR = U(76), + TEGRA_NVG_CHANNEL_DDA_SNOC_GLOBAL_CTRL = U(77), + TEGRA_NVG_CHANNEL_DDA_SNOC_CLIENT_REQ_CTRL = U(78), + TEGRA_NVG_CHANNEL_DDA_SNOC_CLIENT_REPLENTISH_CTRL = U(79), + TEGRA_NVG_CHANNEL_RT_SAFE_MASK = U(80), + TEGRA_NVG_CHANNEL_RT_WINDOW_US = U(81), + TEGRA_NVG_CHANNEL_RT_FWD_PROGRESS_US = U(82), TEGRA_NVG_CHANNEL_LAST_INDEX } tegra_nvg_channel_id_t; typedef enum { - NVG_STAT_QUERY_SC7_ENTRIES = 1, - NVG_STAT_QUERY_CC6_ENTRIES = 6, - NVG_STAT_QUERY_CG7_ENTRIES = 7, - NVG_STAT_QUERY_C6_ENTRIES = 10, - NVG_STAT_QUERY_C7_ENTRIES = 14, - NVG_STAT_QUERY_SC7_RESIDENCY_SUM = 32, - NVG_STAT_QUERY_CC6_RESIDENCY_SUM = 41, - NVG_STAT_QUERY_CG7_RESIDENCY_SUM = 46, - NVG_STAT_QUERY_C6_RESIDENCY_SUM = 51, - NVG_STAT_QUERY_C7_RESIDENCY_SUM = 56, - NVG_STAT_QUERY_SC7_ENTRY_TIME_SUM = 60, - NVG_STAT_QUERY_CC6_ENTRY_TIME_SUM = 61, - NVG_STAT_QUERY_CG7_ENTRY_TIME_SUM = 62, - NVG_STAT_QUERY_C6_ENTRY_TIME_SUM = 63, - NVG_STAT_QUERY_C7_ENTRY_TIME_SUM = 64, - NVG_STAT_QUERY_SC7_EXIT_TIME_SUM = 70, - NVG_STAT_QUERY_CC6_EXIT_TIME_SUM = 71, - NVG_STAT_QUERY_CG7_EXIT_TIME_SUM = 72, - NVG_STAT_QUERY_C6_EXIT_TIME_SUM = 73, - NVG_STAT_QUERY_C7_EXIT_TIME_SUM = 74, - NVG_STAT_QUERY_SC7_ENTRY_LAST = 80, - NVG_STAT_QUERY_CC6_ENTRY_LAST = 81, - NVG_STAT_QUERY_CG7_ENTRY_LAST = 82, - NVG_STAT_QUERY_C6_ENTRY_LAST = 83, - NVG_STAT_QUERY_C7_ENTRY_LAST = 84, - NVG_STAT_QUERY_SC7_EXIT_LAST = 90, - NVG_STAT_QUERY_CC6_EXIT_LAST = 91, - NVG_STAT_QUERY_CG7_EXIT_LAST = 92, - NVG_STAT_QUERY_C6_EXIT_LAST = 93, - NVG_STAT_QUERY_C7_EXIT_LAST = 94 + NVG_STAT_QUERY_SC7_ENTRIES = U(1), + NVG_STAT_QUERY_CC6_ENTRIES = U(6), + NVG_STAT_QUERY_CG7_ENTRIES = U(7), + NVG_STAT_QUERY_C6_ENTRIES = U(10), + NVG_STAT_QUERY_C7_ENTRIES = U(14), + NVG_STAT_QUERY_SC7_RESIDENCY_SUM = U(32), + NVG_STAT_QUERY_CC6_RESIDENCY_SUM = U(41), + NVG_STAT_QUERY_CG7_RESIDENCY_SUM = U(46), + NVG_STAT_QUERY_C6_RESIDENCY_SUM = U(51), + NVG_STAT_QUERY_C7_RESIDENCY_SUM = U(56), + NVG_STAT_QUERY_SC7_ENTRY_TIME_SUM = U(60), + NVG_STAT_QUERY_CC6_ENTRY_TIME_SUM = U(61), + NVG_STAT_QUERY_CG7_ENTRY_TIME_SUM = U(62), + NVG_STAT_QUERY_C6_ENTRY_TIME_SUM = U(63), + NVG_STAT_QUERY_C7_ENTRY_TIME_SUM = U(64), + NVG_STAT_QUERY_SC7_EXIT_TIME_SUM = U(70), + NVG_STAT_QUERY_CC6_EXIT_TIME_SUM = U(71), + NVG_STAT_QUERY_CG7_EXIT_TIME_SUM = U(72), + NVG_STAT_QUERY_C6_EXIT_TIME_SUM = U(73), + NVG_STAT_QUERY_C7_EXIT_TIME_SUM = U(74), + NVG_STAT_QUERY_SC7_ENTRY_LAST = U(80), + NVG_STAT_QUERY_CC6_ENTRY_LAST = U(81), + NVG_STAT_QUERY_CG7_ENTRY_LAST = U(82), + NVG_STAT_QUERY_C6_ENTRY_LAST = U(83), + NVG_STAT_QUERY_C7_ENTRY_LAST = U(84), + NVG_STAT_QUERY_SC7_EXIT_LAST = U(90), + NVG_STAT_QUERY_CC6_EXIT_LAST = U(91), + NVG_STAT_QUERY_CG7_EXIT_LAST = U(92), + NVG_STAT_QUERY_C6_EXIT_LAST = U(93), + NVG_STAT_QUERY_C7_EXIT_LAST = U(94) + } tegra_nvg_stat_query_t; typedef enum { - TEGRA_NVG_CORE_C0 = 0, - TEGRA_NVG_CORE_C1 = 1, - TEGRA_NVG_CORE_C6 = 6, - TEGRA_NVG_CORE_C7 = 7, - TEGRA_NVG_CORE_WARMRSTREQ = 8 + TEGRA_NVG_CORE_C0 = U(0), + TEGRA_NVG_CORE_C1 = U(1), + TEGRA_NVG_CORE_C6 = U(6), + TEGRA_NVG_CORE_C7 = U(7), + TEGRA_NVG_CORE_WARMRSTREQ = U(8) } tegra_nvg_core_sleep_state_t; typedef enum { - TEGRA_NVG_SHUTDOWN = 0U, - TEGRA_NVG_REBOOT = 1U + TEGRA_NVG_SHUTDOWN = U(0), + TEGRA_NVG_REBOOT = U(1) } tegra_nvg_shutdown_reboot_state_t; typedef enum { - TEGRA_NVG_CLUSTER_CC0 = 0, - TEGRA_NVG_CLUSTER_AUTO_CC1 = 1, - TEGRA_NVG_CLUSTER_CC6 = 6 + TEGRA_NVG_CLUSTER_CC0 = U(0), + TEGRA_NVG_CLUSTER_AUTO_CC1 = U(1), + TEGRA_NVG_CLUSTER_CC6 = U(6) } tegra_nvg_cluster_sleep_state_t; typedef enum { - TEGRA_NVG_CG_CG0 = 0, - TEGRA_NVG_CG_CG7 = 7 + TEGRA_NVG_CG_CG0 = U(0), + TEGRA_NVG_CG_CG7 = U(7) } tegra_nvg_cluster_group_sleep_state_t; typedef enum { - TEGRA_NVG_SYSTEM_SC0 = 0, - TEGRA_NVG_SYSTEM_SC7 = 7, - TEGRA_NVG_SYSTEM_SC8 = 8 + TEGRA_NVG_SYSTEM_SC0 = U(0), + TEGRA_NVG_SYSTEM_SC7 = U(7), + TEGRA_NVG_SYSTEM_SC8 = U(8) } tegra_nvg_system_sleep_state_t; // --------------------------------------------------------------------------- @@ -145,95 +151,95 @@ typedef enum { typedef union { uint64_t flat; struct nvg_version_channel_t { - uint32_t minor_version : 32; - uint32_t major_version : 32; + uint32_t minor_version : U(32); + uint32_t major_version : U(32); } bits; } nvg_version_data_t; typedef union { uint64_t flat; - struct nvg_power_perf_channel_t { - uint32_t perf_per_watt : 1; - uint32_t reserved_31_1 : 31; - uint32_t reserved_63_32 : 32; + struct { + uint32_t perf_per_watt : U(1); + uint32_t reserved_31_1 : U(31); + uint32_t reserved_63_32 : U(32); } bits; } nvg_power_perf_channel_t; typedef union { uint64_t flat; - struct nvg_power_modes_channel_t { - uint32_t low_battery : 1; - uint32_t reserved_1_1 : 1; - uint32_t battery_save : 1; - uint32_t reserved_31_3 : 29; - uint32_t reserved_63_32 : 32; + struct { + uint32_t low_battery : U(1); + uint32_t reserved_1_1 : U(1); + uint32_t battery_save : U(1); + uint32_t reserved_31_3 : U(29); + uint32_t reserved_63_32 : U(32); } bits; } nvg_power_modes_channel_t; typedef union nvg_channel_1_data_u { uint64_t flat; struct nvg_channel_1_data_s { - uint32_t perf_per_watt_mode : 1; - uint32_t reserved_31_1 : 31; - uint32_t reserved_63_32 : 32; + uint32_t perf_per_watt_mode : U(1); + uint32_t reserved_31_1 : U(31); + uint32_t reserved_63_32 : U(32); } bits; } nvg_channel_1_data_t; typedef union { uint64_t flat; - struct nvg_ccplex_cache_control_channel_t { - uint32_t gpu_ways : 5; - uint32_t reserved_7_5 : 3; - uint32_t gpu_only_ways : 5; - uint32_t reserved_31_13 : 19; - uint32_t reserved_63_32 : 32; + struct { + uint32_t gpu_ways : U(5); + uint32_t reserved_7_5 : U(3); + uint32_t gpu_only_ways : U(5); + uint32_t reserved_31_13 : U(19); + uint32_t reserved_63_32 : U(32); } bits; } nvg_ccplex_cache_control_channel_t; typedef union nvg_channel_2_data_u { uint64_t flat; struct nvg_channel_2_data_s { - uint32_t reserved_1_0 : 2; - uint32_t battery_saver_mode : 1; - uint32_t reserved_31_3 : 29; - uint32_t reserved_63_32 : 32; + uint32_t reserved_1_0 : U(2); + uint32_t battery_saver_mode : U(1); + uint32_t reserved_31_3 : U(29); + uint32_t reserved_63_32 : U(32); } bits; } nvg_channel_2_data_t; typedef union { uint64_t flat; - struct nvg_wake_time_channel_t { - uint32_t wake_time : 32; - uint32_t reserved_63_32 : 32; + struct { + uint32_t wake_time : U(32); + uint32_t reserved_63_32 : U(32); } bits; } nvg_wake_time_channel_t; typedef union { uint64_t flat; - struct nvg_cstate_info_channel_t { - uint32_t cluster_state : 3; - uint32_t reserved_6_3 : 4; - uint32_t update_cluster : 1; - uint32_t cg_cstate : 3; - uint32_t reserved_14_11 : 4; - uint32_t update_cg : 1; - uint32_t system_cstate : 4; - uint32_t reserved_22_20 : 3; - uint32_t update_system : 1; - uint32_t reserved_30_24 : 7; - uint32_t update_wake_mask : 1; + struct { + uint32_t cluster_state : U(3); + uint32_t reserved_6_3 : U(4); + uint32_t update_cluster : U(1); + uint32_t cg_cstate : U(3); + uint32_t reserved_14_11 : U(4); + uint32_t update_cg : U(1); + uint32_t system_cstate : U(4); + uint32_t reserved_22_20 : U(3); + uint32_t update_system : U(1); + uint32_t reserved_30_24 : U(7); + uint32_t update_wake_mask : U(1); union { - uint32_t flat : 32; + uint32_t flat : U(32); struct { - uint32_t vfiq : 1; - uint32_t virq : 1; - uint32_t fiq : 1; - uint32_t irq : 1; - uint32_t serror : 1; - uint32_t reserved_10_5 : 6; - uint32_t fiqout : 1; - uint32_t irqout : 1; - uint32_t reserved_31_13 : 19; + uint32_t vfiq : U(1); + uint32_t virq : U(1); + uint32_t fiq : U(1); + uint32_t irq : U(1); + uint32_t serror : U(1); + uint32_t reserved_10_5 : U(6); + uint32_t fiqout : U(1); + uint32_t irqout : U(1); + uint32_t reserved_31_13 : U(19); } carmel; } wake_mask; } bits; @@ -241,184 +247,183 @@ typedef union { typedef union { uint64_t flat; - struct nvg_lower_bound_channel_t { - uint32_t crossover_value : 32; - uint32_t reserved_63_32 : 32; + struct { + uint32_t crossover_value : U(32); + uint32_t reserved_63_32 : U(32); } bits; } nvg_lower_bound_channel_t; typedef union { uint64_t flat; - struct nvg_cstate_stat_query_channel_t { - uint32_t unit_id : 4; - uint32_t reserved_15_4 : 12; - uint32_t stat_id : 16; - uint32_t reserved_63_32 : 32; + struct { + uint32_t unit_id : U(4); + uint32_t reserved_15_4 : U(12); + uint32_t stat_id : U(16); + uint32_t reserved_63_32 : U(32); } bits; } nvg_cstate_stat_query_channel_t; typedef union { uint64_t flat; - struct nvg_num_cores_channel_t { - uint32_t num_cores : 4; - uint32_t reserved_31_4 : 28; - uint32_t reserved_63_32 : 32; + struct { + uint32_t num_cores : U(4); + uint32_t reserved_31_4 : U(28); + uint32_t reserved_63_32 : U(32); } bits; } nvg_num_cores_channel_t; typedef union { uint64_t flat; - struct nvg_unique_logical_id_channel_t { - uint32_t unique_core_id : 3; - uint32_t reserved_31_3 : 29; - uint32_t reserved_63_32 : 32; + struct { + uint32_t unique_core_id : U(3); + uint32_t reserved_31_3 : U(29); + uint32_t reserved_63_32 : U(32); } bits; } nvg_unique_logical_id_channel_t; typedef union { uint64_t flat; - struct nvg_logical_to_physical_mappings_channel_t { - uint32_t lcore0_pcore_id : 4; - uint32_t lcore1_pcore_id : 4; - uint32_t lcore2_pcore_id : 4; - uint32_t lcore3_pcore_id : 4; - uint32_t lcore4_pcore_id : 4; - uint32_t lcore5_pcore_id : 4; - uint32_t lcore6_pcore_id : 4; - uint32_t lcore7_pcore_id : 4; - uint32_t reserved_63_32 : 32; + struct { + uint32_t lcore0_pcore_id : U(4); + uint32_t lcore1_pcore_id : U(4); + uint32_t lcore2_pcore_id : U(4); + uint32_t lcore3_pcore_id : U(4); + uint32_t lcore4_pcore_id : U(4); + uint32_t lcore5_pcore_id : U(4); + uint32_t lcore6_pcore_id : U(4); + uint32_t lcore7_pcore_id : U(4); + uint32_t reserved_63_32 : U(32); } bits; } nvg_logical_to_physical_mappings_channel_t; typedef union { uint64_t flat; struct nvg_logical_to_mpidr_channel_write_t { - uint32_t lcore_id : 3; - uint32_t reserved_31_3 : 29; - uint32_t reserved_63_32 : 32; + uint32_t lcore_id : U(3); + uint32_t reserved_31_3 : U(29); + uint32_t reserved_63_32 : U(32); } write; struct nvg_logical_to_mpidr_channel_read_t { - uint32_t mpidr : 32; - uint32_t reserved_63_32 : 32; + uint32_t mpidr : U(32); + uint32_t reserved_63_32 : U(32); } read; } nvg_logical_to_mpidr_channel_t; typedef union { uint64_t flat; - struct nvg_is_sc7_allowed_channel_t { - uint32_t is_sc7_allowed : 1; - uint32_t reserved_31_1 : 31; - uint32_t reserved_63_32 : 32; + struct { + uint32_t is_sc7_allowed : U(1); + uint32_t reserved_31_1 : U(31); + uint32_t reserved_63_32 : U(32); } bits; } nvg_is_sc7_allowed_channel_t; typedef union { uint64_t flat; - struct nvg_core_online_channel_t { - uint32_t core_id : 4; - uint32_t reserved_31_4 : 28; - uint32_t reserved_63_32 : 32; + struct { + uint32_t core_id : U(4); + uint32_t reserved_31_4 : U(28); + uint32_t reserved_63_32 : U(32); } bits; } nvg_core_online_channel_t; typedef union { uint64_t flat; - struct nvg_cc3_control_channel_t { - uint32_t freq_req : 9; - uint32_t reserved_30_9 : 22; - uint32_t enable : 1; - uint32_t reserved_63_32 : 32; + struct { + uint32_t freq_req : U(9); + uint32_t reserved_30_9 : U(22); + uint32_t enable : U(1); + uint32_t reserved_63_32 : U(32); } bits; } nvg_cc3_control_channel_t; typedef enum { - TEGRA_NVG_CHANNEL_UPDATE_GSC_ALL = 0, - TEGRA_NVG_CHANNEL_UPDATE_GSC_NVDEC = 1, - TEGRA_NVG_CHANNEL_UPDATE_GSC_WPR1 = 2, - TEGRA_NVG_CHANNEL_UPDATE_GSC_WPR2 = 3, - TEGRA_NVG_CHANNEL_UPDATE_GSC_TSECA = 4, - TEGRA_NVG_CHANNEL_UPDATE_GSC_TSECB = 5, - TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP = 6, - TEGRA_NVG_CHANNEL_UPDATE_GSC_APE = 7, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SPE = 8, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SCE = 9, - TEGRA_NVG_CHANNEL_UPDATE_GSC_APR = 10, - TEGRA_NVG_CHANNEL_UPDATE_GSC_TZRAM = 11, - TEGRA_NVG_CHANNEL_UPDATE_GSC_IPC_SE_TSEC = 12, - TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_RCE = 13, - TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_MCE = 14, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SE_SC7 = 15, - TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_SPE = 16, - TEGRA_NVG_CHANNEL_UPDATE_GSC_RCE = 17, - TEGRA_NVG_CHANNEL_UPDATE_GSC_CPU_TZ_TO_BPMP = 18, - TEGRA_NVG_CHANNEL_UPDATE_GSC_VM_ENCR1 = 19, - TEGRA_NVG_CHANNEL_UPDATE_GSC_CPU_NS_TO_BPMP = 20, - TEGRA_NVG_CHANNEL_UPDATE_GSC_OEM_SC7 = 21, - TEGRA_NVG_CHANNEL_UPDATE_GSC_IPC_SE_SPE_SCE_BPMP = 22, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SC7_RESUME_FW = 23, - TEGRA_NVG_CHANNEL_UPDATE_GSC_CAMERA_TASKLIST = 24, - TEGRA_NVG_CHANNEL_UPDATE_GSC_XUSB = 25, - TEGRA_NVG_CHANNEL_UPDATE_GSC_CV = 26, - TEGRA_NVG_CHANNEL_UPDATE_GSC_VM_ENCR2 = 27, - TEGRA_NVG_CHANNEL_UPDATE_GSC_HYPERVISOR_SW = 28, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SMMU_PAGETABLES = 29, - TEGRA_NVG_CHANNEL_UPDATE_GSC_30 = 30, - TEGRA_NVG_CHANNEL_UPDATE_GSC_31 = 31, - TEGRA_NVG_CHANNEL_UPDATE_GSC_TZ_DRAM = 32, - TEGRA_NVG_CHANNEL_UPDATE_GSC_NVLINK = 33, - TEGRA_NVG_CHANNEL_UPDATE_GSC_SBS = 34, - TEGRA_NVG_CHANNEL_UPDATE_GSC_VPR = 35, + TEGRA_NVG_CHANNEL_UPDATE_GSC_ALL = U(0), + TEGRA_NVG_CHANNEL_UPDATE_GSC_NVDEC = U(1), + TEGRA_NVG_CHANNEL_UPDATE_GSC_WPR1 = U(2), + TEGRA_NVG_CHANNEL_UPDATE_GSC_WPR2 = U(3), + TEGRA_NVG_CHANNEL_UPDATE_GSC_TSECA = U(4), + TEGRA_NVG_CHANNEL_UPDATE_GSC_TSECB = U(5), + TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP = U(6), + TEGRA_NVG_CHANNEL_UPDATE_GSC_APE = U(7), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SPE = U(8), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SCE = U(9), + TEGRA_NVG_CHANNEL_UPDATE_GSC_APR = U(10), + TEGRA_NVG_CHANNEL_UPDATE_GSC_TZRAM = U(11), + TEGRA_NVG_CHANNEL_UPDATE_GSC_IPC_SE_TSEC = U(12), + TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_RCE = U(13), + TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_MCE = U(14), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SE_SC7 = U(15), + TEGRA_NVG_CHANNEL_UPDATE_GSC_BPMP_TO_SPE = U(16), + TEGRA_NVG_CHANNEL_UPDATE_GSC_RCE = U(17), + TEGRA_NVG_CHANNEL_UPDATE_GSC_CPU_TZ_TO_BPMP = U(18), + TEGRA_NVG_CHANNEL_UPDATE_GSC_VM_ENCR1 = U(19), + TEGRA_NVG_CHANNEL_UPDATE_GSC_CPU_NS_TO_BPMP = U(20), + TEGRA_NVG_CHANNEL_UPDATE_GSC_OEM_SC7 = U(21), + TEGRA_NVG_CHANNEL_UPDATE_GSC_IPC_SE_SPE_SCE_BPMP = U(22), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SC7_RESUME_FW = U(23), + TEGRA_NVG_CHANNEL_UPDATE_GSC_CAMERA_TASKLIST = U(24), + TEGRA_NVG_CHANNEL_UPDATE_GSC_XUSB = U(25), + TEGRA_NVG_CHANNEL_UPDATE_GSC_CV = U(26), + TEGRA_NVG_CHANNEL_UPDATE_GSC_VM_ENCR2 = U(27), + TEGRA_NVG_CHANNEL_UPDATE_GSC_HYPERVISOR_SW = U(28), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SMMU_PAGETABLES = U(29), + TEGRA_NVG_CHANNEL_UPDATE_GSC_30 = U(30), + TEGRA_NVG_CHANNEL_UPDATE_GSC_31 = U(31), + TEGRA_NVG_CHANNEL_UPDATE_GSC_TZ_DRAM = U(32), + TEGRA_NVG_CHANNEL_UPDATE_GSC_NVLINK = U(33), + TEGRA_NVG_CHANNEL_UPDATE_GSC_SBS = U(34), + TEGRA_NVG_CHANNEL_UPDATE_GSC_VPR = U(35), TEGRA_NVG_CHANNEL_UPDATE_GSC_LAST_INDEX } tegra_nvg_channel_update_gsc_gsc_enum_t; typedef union { uint64_t flat; - struct nvg_update_ccplex_gsc_channel_t { - uint32_t gsc_enum : 16; - uint32_t reserved_31_16 : 16; - uint32_t reserved_63_32 : 32; + struct { + uint32_t gsc_enum : U(16); + uint32_t reserved_31_16 : U(16); + uint32_t reserved_63_32 : U(32); } bits; } nvg_update_ccplex_gsc_channel_t; typedef union { uint64_t flat; struct nvg_security_config_channel_t { - uint32_t strict_checking_enabled : 1; - uint32_t strict_checking_locked : 1; - uint32_t reserved_31_2 : 30; - uint32_t reserved_63_32 : 32; + uint32_t strict_checking_enabled : U(1); + uint32_t strict_checking_locked : U(1); + uint32_t reserved_31_2 : U(30); + uint32_t reserved_63_32 : U(32); } bits; } nvg_security_config_t; typedef union { uint64_t flat; struct nvg_shutdown_channel_t { - uint32_t reboot : 1; - uint32_t reserved_31_1 : 31; - uint32_t reserved_63_32 : 32; + uint32_t reboot : U(1); + uint32_t reserved_31_1 : U(31); + uint32_t reserved_63_32 : U(32); } bits; } nvg_shutdown_t; typedef union { uint64_t flat; struct nvg_debug_config_channel_t { - uint32_t enter_debug_state_on_mca : 1; - uint32_t reserved_31_1 : 31; - uint32_t reserved_63_32 : 32; + uint32_t enter_debug_state_on_mca : U(1); + uint32_t reserved_31_1 : U(31); + uint32_t reserved_63_32 : U(32); } bits; } nvg_debug_config_t; typedef union { uint64_t flat; - struct nvg_hsm_error_ctrl_channel_t { - uint32_t uncorr : 1; - uint32_t corr : 1; - uint32_t reserved_31_2 : 30; - uint32_t reserved_63_32 : 32; + struct { + uint32_t uncorr : U(1); + uint32_t corr : U(1); + uint32_t reserved_31_2 : U(30); + uint32_t reserved_63_32 : U(32); } bits; } nvg_hsm_error_ctrl_channel_t; extern nvg_debug_config_t nvg_debug_config; -#endif - +#endif /* T194_NVG_H */ diff --git a/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c b/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c index 00c671bcc..e3d5bd513 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c +++ b/plat/nvidia/tegra/soc/t194/drivers/mce/mce.c @@ -116,25 +116,6 @@ int32_t mce_update_gsc_tzdram(void) } /******************************************************************************* - * Handler to update carveout values for TZ SysRAM aperture - ******************************************************************************/ -int32_t mce_update_gsc_tzram(void) -{ - int32_t ret; - - /* - * MCE firmware is not running on simulation platforms. - */ - if (mce_firmware_not_supported()) { - ret = -EINVAL; - } else { - ret = nvg_update_ccplex_gsc((uint32_t)TEGRA_NVG_CHANNEL_UPDATE_GSC_TZRAM); - } - - return ret; -} - -/******************************************************************************* * Handler to issue the UPDATE_CSTATE_INFO request ******************************************************************************/ void mce_update_cstate_info(const mce_cstate_info_t *cstate) @@ -236,6 +217,15 @@ void mce_enable_strict_checking(void) nvg_enable_strict_checking_mode(); } } +void mce_verify_strict_checking(void) +{ + bool is_silicon = tegra_platform_is_silicon(); + bool is_fpga = tegra_platform_is_fpga(); + + if (is_silicon || is_fpga) { + nvg_verify_strict_checking_mode(); + } +} #endif /******************************************************************************* @@ -253,3 +243,11 @@ void mce_system_reboot(void) { nvg_system_reboot(); } + +/******************************************************************************* + * Handler to clear CCPLEX->HSM correctable RAS error signal. + ******************************************************************************/ +void mce_clear_hsm_corr_status(void) +{ + nvg_clear_hsm_corr_status(); +} diff --git a/plat/nvidia/tegra/soc/t194/drivers/mce/nvg.c b/plat/nvidia/tegra/soc/t194/drivers/mce/nvg.c index 1012cdf11..f76ab14a6 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/mce/nvg.c +++ b/plat/nvidia/tegra/soc/t194/drivers/mce/nvg.c @@ -4,19 +4,22 @@ * SPDX-License-Identifier: BSD-3-Clause */ +#include <assert.h> +#include <errno.h> + #include <arch.h> #include <arch_helpers.h> #include <common/debug.h> #include <denver.h> -#include <errno.h> #include <lib/mmio.h> + #include <mce_private.h> #include <platform_def.h> #include <t194_nvg.h> #include <tegra_private.h> -#define ID_AFR0_EL1_CACHE_OPS_SHIFT 12 -#define ID_AFR0_EL1_CACHE_OPS_MASK 0xFU +#define ID_AFR0_EL1_CACHE_OPS_SHIFT U(12) +#define ID_AFR0_EL1_CACHE_OPS_MASK U(0xF) /* * Reports the major and minor version of this interface. * @@ -209,7 +212,16 @@ void nvg_enable_strict_checking_mode(void) uint64_t params = (uint64_t)(STRICT_CHECKING_ENABLED_SET | STRICT_CHECKING_LOCKED_SET); - nvg_set_request_data(TEGRA_NVG_CHANNEL_SECURITY_CONFIG, params); + nvg_set_request_data((uint64_t)TEGRA_NVG_CHANNEL_SECURITY_CONFIG, params); +} + +void nvg_verify_strict_checking_mode(void) +{ + uint64_t params = (uint64_t)(STRICT_CHECKING_ENABLED_SET | + STRICT_CHECKING_LOCKED_SET); + + nvg_set_request((uint64_t)TEGRA_NVG_CHANNEL_SECURITY_CONFIG); + assert(params == (uint64_t)nvg_get_result()); } #endif @@ -221,7 +233,8 @@ void nvg_enable_strict_checking_mode(void) void nvg_system_reboot(void) { /* issue command for reboot */ - nvg_set_request_data(TEGRA_NVG_CHANNEL_SHUTDOWN, TEGRA_NVG_REBOOT); + nvg_set_request_data((uint64_t)TEGRA_NVG_CHANNEL_SHUTDOWN, + (uint64_t)TEGRA_NVG_REBOOT); } /* @@ -232,5 +245,18 @@ void nvg_system_reboot(void) void nvg_system_shutdown(void) { /* issue command for shutdown */ - nvg_set_request_data(TEGRA_NVG_CHANNEL_SHUTDOWN, TEGRA_NVG_SHUTDOWN); + nvg_set_request_data((uint64_t)TEGRA_NVG_CHANNEL_SHUTDOWN, + (uint64_t)TEGRA_NVG_SHUTDOWN); +} + +/* + * Request to clear CCPLEX->HSM correctable error signal. + * NVGDATA[1]: A write of 1 clears the CCPLEX->HSM correctable error signal, + * A write of 0 has no effect. + */ +void nvg_clear_hsm_corr_status(void) +{ + nvg_hsm_error_ctrl_channel_t status = { .bits = { .corr = 1U, }, }; + + nvg_set_request_data((uint64_t)TEGRA_NVG_CHANNEL_HSM_ERROR_CTRL, status.flat); } diff --git a/plat/nvidia/tegra/soc/t194/drivers/se/se.c b/plat/nvidia/tegra/soc/t194/drivers/se/se.c index 3a2e959d0..31b0e2678 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/se/se.c +++ b/plat/nvidia/tegra/soc/t194/drivers/se/se.c @@ -15,6 +15,7 @@ #include <drivers/delay_timer.h> #include <lib/mmio.h> #include <lib/psci/psci.h> +#include <se.h> #include <tegra_platform.h> #include "se_private.h" @@ -22,10 +23,17 @@ /******************************************************************************* * Constants and Macros ******************************************************************************/ -#define ERR_STATUS_SW_CLEAR U(0xFFFFFFFF) -#define INT_STATUS_SW_CLEAR U(0xFFFFFFFF) -#define MAX_TIMEOUT_MS U(100) /* Timeout in 100ms */ -#define NUM_SE_REGS_TO_SAVE U(4) +#define ERR_STATUS_SW_CLEAR U(0xFFFFFFFF) +#define INT_STATUS_SW_CLEAR U(0xFFFFFFFF) +#define MAX_TIMEOUT_MS U(1000) /* Max. timeout of 1s */ +#define NUM_SE_REGS_TO_SAVE U(4) + +#define BYTES_IN_WORD U(4) +#define SHA256_MAX_HASH_RESULT U(7) +#define SHA256_DST_SIZE U(32) +#define SHA_FIRST_OP U(1) +#define MAX_SHA_ENGINE_CHUNK_SIZE U(0xFFFFFF) +#define SHA256_MSG_LENGTH_ONETIME U(0xFFFF) /******************************************************************************* * Data structure and global variables @@ -54,7 +62,7 @@ static bool tegra_se_is_operation_complete(void) */ do { val = tegra_se_read_32(CTX_SAVE_AUTO_STATUS); - se_is_busy = !!(val & CTX_SAVE_AUTO_SE_BUSY); + se_is_busy = ((val & CTX_SAVE_AUTO_SE_BUSY) != 0U); /* sleep until SE finishes */ if (se_is_busy) { @@ -175,6 +183,270 @@ static int32_t tegra_se_save_context(void) } /* + * Check that SE operation has completed after kickoff + * This function is invoked after an SE operation has been started, + * and it checks the following conditions: + * 1. SE0_INT_STATUS = SE0_OP_DONE + * 2. SE0_STATUS = IDLE + * 3. SE0_ERR_STATUS is clean. + */ +static int32_t tegra_se_sha256_hash_operation_complete(void) +{ + uint32_t val = 0U; + + /* Poll the SE interrupt register to ensure H/W operation complete */ + val = tegra_se_read_32(SE0_INT_STATUS_REG_OFFSET); + while (SE0_INT_OP_DONE(val) == SE0_INT_OP_DONE_CLEAR) { + val = tegra_se_read_32(SE0_INT_STATUS_REG_OFFSET); + if (SE0_INT_OP_DONE(val) != SE0_INT_OP_DONE_CLEAR) { + break; + } + } + + /* Poll the SE status idle to ensure H/W operation complete */ + val = tegra_se_read_32(SE0_SHA_STATUS_0); + while (val != SE0_SHA_STATUS_IDLE) { + val = tegra_se_read_32(SE0_SHA_STATUS_0); + if (val == SE0_SHA_STATUS_IDLE) { + break; + } + } + + /* Ensure that no errors are thrown during operation */ + val = tegra_se_read_32(SE0_ERR_STATUS_REG_OFFSET); + if (val != 0U) { + ERROR("%s: error during SE operation! 0x%x", __func__, + val); + return -ENOTSUP; + } + + return 0; +} + +/* + * Security engine primitive normal operations + */ +static int32_t tegra_se_start_normal_operation(uint64_t src_addr, + uint32_t nbytes, uint32_t last_buf, uint32_t src_len_inbytes) +{ + uint32_t val = 0U; + uint32_t src_in_lo; + uint32_t src_in_msb; + uint32_t src_in_hi; + int32_t ret = 0; + + if ((src_addr == 0ULL) || (nbytes == 0U)) + return -EINVAL; + + src_in_lo = (uint32_t)src_addr; + src_in_msb = (uint32_t)((src_addr >> 32U) & 0xFFU); + src_in_hi = ((src_in_msb << SE0_IN_HI_ADDR_HI_0_MSB_SHIFT) | + (nbytes & MAX_SHA_ENGINE_CHUNK_SIZE)); + + /* set SRC_IN_ADDR_LO and SRC_IN_ADDR_HI*/ + tegra_se_write_32(SE0_IN_ADDR, src_in_lo); + tegra_se_write_32(SE0_IN_HI_ADDR_HI, src_in_hi); + + val = tegra_se_read_32(SE0_INT_STATUS_REG_OFFSET); + if (val > 0U) { + tegra_se_write_32(SE0_INT_STATUS_REG_OFFSET, 0x0U); + } + + /* Enable SHA interrupt for SE0 Operation */ + tegra_se_write_32(SE0_SHA_INT_ENABLE, 0x1aU); + + /* flush to DRAM for SE to use the updated contents */ + flush_dcache_range(src_addr, src_len_inbytes); + + /* Start SHA256 operation */ + if (last_buf == 1U) { + tegra_se_write_32(SE0_OPERATION_REG_OFFSET, SE0_OP_START | + SE0_UNIT_OPERATION_PKT_LASTBUF_FIELD); + } else { + tegra_se_write_32(SE0_OPERATION_REG_OFFSET, SE0_OP_START); + } + + return ret; +} + +static int32_t tegra_se_calculate_sha256_hash(uint64_t src_addr, + uint32_t src_len_inbyte) +{ + uint32_t val, last_buf, i; + int32_t ret = 0; + uint32_t operations; + uint64_t src_len_inbits; + uint32_t len_bits_msb; + uint32_t len_bits_lsb; + uint32_t number_of_operations, max_bytes, bytes_left, remaining_bytes; + + if (src_len_inbyte > MAX_SHA_ENGINE_CHUNK_SIZE) { + ERROR("SHA input chunk size too big: 0x%x\n", src_len_inbyte); + return -EINVAL; + } + + if (src_addr == 0ULL) { + return -EINVAL; + } + + /* number of bytes per operation */ + max_bytes = (SHA256_HASH_SIZE_BYTES * SHA256_MSG_LENGTH_ONETIME); + + src_len_inbits = (uint32_t)(src_len_inbyte * 8U); + len_bits_msb = (uint32_t)(src_len_inbits >> 32U); + len_bits_lsb = (uint32_t)src_len_inbits; + + /* program SE0_CONFIG for SHA256 operation */ + val = (uint32_t)(SE0_CONFIG_ENC_ALG_SHA | SE0_CONFIG_ENC_MODE_SHA256 | + SE0_CONFIG_DEC_ALG_NOP | SE0_CONFIG_DST_HASHREG); + tegra_se_write_32(SE0_SHA_CONFIG, val); + + /* set SE0_SHA_MSG_LENGTH registers */ + tegra_se_write_32(SE0_SHA_MSG_LENGTH_0, len_bits_lsb); + tegra_se_write_32(SE0_SHA_MSG_LEFT_0, len_bits_lsb); + tegra_se_write_32(SE0_SHA_MSG_LENGTH_1, len_bits_msb); + + /* zero out unused SE0_SHA_MSG_LENGTH and SE0_SHA_MSG_LEFT */ + tegra_se_write_32(SE0_SHA_MSG_LENGTH_2, 0U); + tegra_se_write_32(SE0_SHA_MSG_LENGTH_3, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_1, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_2, 0U); + tegra_se_write_32(SE0_SHA_MSG_LEFT_3, 0U); + + number_of_operations = (src_len_inbyte / max_bytes); + remaining_bytes = (src_len_inbyte % max_bytes); + if (remaining_bytes > 0U) { + number_of_operations += 1U; + } + + /* + * 1. Operations == 1: program SE0_SHA_TASK register to initiate SHA256 + * hash generation by setting + * 1(SE0_SHA_CONFIG_HW_INIT_HASH) to SE0_SHA_TASK + * and start SHA256-normal operation. + * 2. 1 < Operations < number_of_operations: program SE0_SHA_TASK to + * 0(SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE) to load + * intermediate SHA256 digest result from + * HASH_RESULT register to continue SHA256 + * generation and start SHA256-normal operation. + * 3. Operations == number_of_operations: continue with step 2 and set + * max_bytes to bytes_left to process final + * hash-result generation and start SHA256-normal + * operation. + */ + bytes_left = src_len_inbyte; + for (operations = 1U; operations <= number_of_operations; + operations++) { + if (operations == SHA_FIRST_OP) { + val = SE0_SHA_CONFIG_HW_INIT_HASH; + } else { + /* Load intermediate SHA digest result to + * SHA:HASH_RESULT(0..7) to continue the SHA + * calculation and tell the SHA engine to use it. + */ + for (i = 0U; (i / BYTES_IN_WORD) <= + SHA256_MAX_HASH_RESULT; i += BYTES_IN_WORD) { + val = tegra_se_read_32(SE0_SHA_HASH_RESULT_0 + + i); + tegra_se_write_32(SE0_SHA_HASH_RESULT_0 + i, + val); + } + val = SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE; + if (len_bits_lsb <= (max_bytes * 8U)) { + len_bits_lsb = (remaining_bytes * 8U); + } else { + len_bits_lsb -= (max_bytes * 8U); + } + tegra_se_write_32(SE0_SHA_MSG_LEFT_0, len_bits_lsb); + } + tegra_se_write_32(SE0_SHA_TASK_CONFIG, val); + + max_bytes = (SHA256_HASH_SIZE_BYTES * + SHA256_MSG_LENGTH_ONETIME); + if (bytes_left < max_bytes) { + max_bytes = bytes_left; + last_buf = 1U; + } else { + bytes_left = bytes_left - max_bytes; + last_buf = 0U; + } + /* start operation */ + ret = tegra_se_start_normal_operation(src_addr, max_bytes, + last_buf, src_len_inbyte); + if (ret != 0) { + ERROR("Error during SE operation! 0x%x", ret); + return -EINVAL; + } + } + + return ret; +} + +static int32_t tegra_se_save_sha256_pmc_scratch(void) +{ + uint32_t val = 0U, hash_offset = 0U, scratch_offset = 0U; + int32_t ret; + + /* Check SE0 operation status */ + ret = tegra_se_sha256_hash_operation_complete(); + if (ret != 0) { + ERROR("SE operation complete Failed! 0x%x", ret); + return ret; + } + + for (scratch_offset = SECURE_SCRATCH_TZDRAM_SHA256_HASH_START; + scratch_offset <= SECURE_SCRATCH_TZDRAM_SHA256_HASH_END; + scratch_offset += BYTES_IN_WORD) { + val = tegra_se_read_32(SE0_SHA_HASH_RESULT_0 + hash_offset); + mmio_write_32((uint32_t)(TEGRA_SCRATCH_BASE + scratch_offset), + val); + hash_offset += BYTES_IN_WORD; + } + return 0; +} + +/* + * Handler to generate SHA256 and save HASH-result to pmc-scratch register + */ +int32_t tegra_se_calculate_save_sha256(uint64_t src_addr, + uint32_t src_len_inbyte) +{ + uint32_t security; + int32_t val = 0; + + /* Set SE_SOFT_SETTINGS=SE_SECURE to prevent NS process to change SE + * registers. + */ + security = tegra_se_read_32(SE0_SECURITY); + tegra_se_write_32(SE0_SECURITY, security | SE0_SECURITY_SE_SOFT_SETTING); + + /* Bootrom enable IN_ID bit in SE0_SHA_GSCID_0 register during SC7-exit, causing + * SE0 ignores SE0 operation, and therefore failure of 2nd iteration of SC7 cycle. + */ + tegra_se_write_32(SE0_SHA_GSCID_0, 0x0U); + + /* Calculate SHA256 of BL31 */ + val = tegra_se_calculate_sha256_hash(src_addr, src_len_inbyte); + if (val != 0) { + ERROR("%s: SHA256 generation failed\n", __func__); + return val; + } + + /* + * Reset SE_SECURE to previous value. + */ + tegra_se_write_32(SE0_SECURITY, security); + + /* copy sha256_dst to PMC Scratch register */ + val = tegra_se_save_sha256_pmc_scratch(); + if (val != 0) { + ERROR("%s: SE0 status Error.\n", __func__); + } + + return val; +} + +/* * Handler to power down the SE hardware blocks - SE, RNG1 and PKA1. This * needs to be called only during System Suspend. */ @@ -186,7 +458,8 @@ int32_t tegra_se_suspend(void) assert(tegra_bpmp_ipc_init() == 0); /* Enable SE clock before SE context save */ - tegra_bpmp_ipc_enable_clock(TEGRA_CLK_SE); + ret = tegra_bpmp_ipc_enable_clock(TEGRA194_CLK_SE); + assert(ret == 0); /* save SE registers */ se_regs[0] = mmio_read_32(TEGRA_SE0_BASE + SE0_MUTEX_WATCHDOG_NS_LIMIT); @@ -201,7 +474,8 @@ int32_t tegra_se_suspend(void) } /* Disable SE clock after SE context save */ - tegra_bpmp_ipc_disable_clock(TEGRA_CLK_SE); + ret = tegra_bpmp_ipc_disable_clock(TEGRA194_CLK_SE); + assert(ret == 0); return ret; } @@ -211,11 +485,14 @@ int32_t tegra_se_suspend(void) */ void tegra_se_resume(void) { + int32_t ret = 0; + /* initialise communication channel with BPMP */ assert(tegra_bpmp_ipc_init() == 0); /* Enable SE clock before SE context restore */ - tegra_bpmp_ipc_enable_clock(TEGRA_CLK_SE); + ret = tegra_bpmp_ipc_enable_clock(TEGRA194_CLK_SE); + assert(ret == 0); /* * When TZ takes over after System Resume, TZ should first reconfigure @@ -229,5 +506,6 @@ void tegra_se_resume(void) mmio_write_32(TEGRA_PKA1_BASE + PKA1_MUTEX_WATCHDOG_NS_LIMIT, se_regs[3]); /* Disable SE clock after SE context restore */ - tegra_bpmp_ipc_disable_clock(TEGRA_CLK_SE); + ret = tegra_bpmp_ipc_disable_clock(TEGRA194_CLK_SE); + assert(ret == 0); } diff --git a/plat/nvidia/tegra/soc/t194/drivers/se/se_private.h b/plat/nvidia/tegra/soc/t194/drivers/se/se_private.h index a2c5d1c38..fc118aaa1 100644 --- a/plat/nvidia/tegra/soc/t194/drivers/se/se_private.h +++ b/plat/nvidia/tegra/soc/t194/drivers/se/se_private.h @@ -9,6 +9,86 @@ #define SE_PRIVATE_H #include <lib/utils_def.h> +#include <tegra_def.h> + +/* SE0 security register */ +#define SE0_SECURITY U(0x18) +#define SE0_SECURITY_SE_SOFT_SETTING (((uint32_t)1) << 16U) + +/* SE0 SHA GSCID register */ +#define SE0_SHA_GSCID_0 U(0x100) + +/* SE0 config register */ +#define SE0_SHA_CONFIG U(0x104) +#define SE0_SHA_TASK_CONFIG U(0x108) +#define SE0_SHA_CONFIG_HW_INIT_HASH (((uint32_t)1) << 0U) +#define SE0_SHA_CONFIG_HW_INIT_HASH_DISABLE U(0) + +#define SE0_CONFIG_ENC_ALG_SHIFT U(12) +#define SE0_CONFIG_ENC_ALG_SHA \ + (((uint32_t)3) << SE0_CONFIG_ENC_ALG_SHIFT) +#define SE0_CONFIG_DEC_ALG_SHIFT U(8) +#define SE0_CONFIG_DEC_ALG_NOP \ + (((uint32_t)0) << SE0_CONFIG_DEC_ALG_SHIFT) +#define SE0_CONFIG_DST_SHIFT U(2) +#define SE0_CONFIG_DST_HASHREG \ + (((uint32_t)1) << SE0_CONFIG_DST_SHIFT) +#define SHA256_HASH_SIZE_BYTES U(256) + +#define SE0_CONFIG_ENC_MODE_SHIFT U(24) +#define SE0_CONFIG_ENC_MODE_SHA256 \ + (((uint32_t)5) << SE0_CONFIG_ENC_MODE_SHIFT) + +/* SHA input message length */ +#define SE0_IN_ADDR U(0x10c) +#define SE0_IN_HI_ADDR_HI U(0x110) +#define SE0_IN_HI_ADDR_HI_0_MSB_SHIFT U(24) + +/* SHA input message length */ +#define SE0_SHA_MSG_LENGTH_0 U(0x11c) +#define SE0_SHA_MSG_LENGTH_1 U(0x120) +#define SE0_SHA_MSG_LENGTH_2 U(0x124) +#define SE0_SHA_MSG_LENGTH_3 U(0x128) + +/* SHA input message left */ +#define SE0_SHA_MSG_LEFT_0 U(0x12c) +#define SE0_SHA_MSG_LEFT_1 U(0x130) +#define SE0_SHA_MSG_LEFT_2 U(0x134) +#define SE0_SHA_MSG_LEFT_3 U(0x138) + +/* SE HASH-RESULT */ +#define SE0_SHA_HASH_RESULT_0 U(0x13c) + +/* SE OPERATION */ +#define SE0_OPERATION_REG_OFFSET U(0x17c) +#define SE0_UNIT_OPERATION_PKT_LASTBUF_SHIFT U(16) +#define SE0_UNIT_OPERATION_PKT_LASTBUF_FIELD \ + ((uint32_t)0x1 << SE0_UNIT_OPERATION_PKT_LASTBUF_SHIFT) +#define SE0_OPERATION_SHIFT U(0) +#define SE0_OP_START \ + (((uint32_t)0x1) << SE0_OPERATION_SHIFT) + +/* SE Interrupt */ +#define SE0_SHA_INT_ENABLE U(0x180) + +#define SE0_INT_STATUS_REG_OFFSET U(0x184) +#define SE0_INT_OP_DONE_SHIFT U(4) +#define SE0_INT_OP_DONE_CLEAR \ + (((uint32_t)0U) << SE0_INT_OP_DONE_SHIFT) +#define SE0_INT_OP_DONE(x) \ + ((x) & (((uint32_t)0x1U) << SE0_INT_OP_DONE_SHIFT)) + +/* SE SHA Status */ +#define SE0_SHA_STATUS_0 U(0x188) +#define SE0_SHA_STATUS_IDLE U(0) + +/* SE error status */ +#define SE0_ERR_STATUS_REG_OFFSET U(0x18c) +#define SE0_ERR_STATUS_CLEAR U(0) + +/* SE error status */ +#define SECURE_SCRATCH_TZDRAM_SHA256_HASH_START SECURE_SCRATCH_RSV68_LO +#define SECURE_SCRATCH_TZDRAM_SHA256_HASH_END SECURE_SCRATCH_RSV71_HI /* SE0_INT_ENABLE_0 */ #define SE0_INT_ENABLE U(0x88) @@ -20,7 +100,7 @@ /* SE0_SHA_INT_STATUS_0 */ #define SHA_INT_STATUS U(0x184) -#define SHA_SE_OP_DONE (U(1) << 4) +#define SHA_SE_OP_DONE (U(1) << 4) /* SE0_SHA_ERR_STATUS_0 */ #define SHA_ERR_STATUS U(0x18C) @@ -74,12 +154,12 @@ static inline uint32_t tegra_se_read_32(uint32_t offset) { - return mmio_read_32(TEGRA_SE0_BASE + offset); + return mmio_read_32((uint32_t)(TEGRA_SE0_BASE + offset)); } static inline void tegra_se_write_32(uint32_t offset, uint32_t val) { - mmio_write_32(TEGRA_SE0_BASE + offset, val); + mmio_write_32((uint32_t)(TEGRA_SE0_BASE + offset), val); } #endif /* SE_PRIVATE_H */ diff --git a/plat/nvidia/tegra/soc/t194/plat_memctrl.c b/plat/nvidia/tegra/soc/t194/plat_memctrl.c index bb1dd6706..9ddcacf31 100644 --- a/plat/nvidia/tegra/soc/t194/plat_memctrl.c +++ b/plat/nvidia/tegra/soc/t194/plat_memctrl.c @@ -8,693 +8,43 @@ #include <common/bl_common.h> #include <mce.h> #include <memctrl_v2.h> -#include <tegra_mc_def.h> #include <tegra_platform.h> +#include <tegra_private.h> /******************************************************************************* - * Array to hold stream_id override config register offsets + * Array to hold MC context for Tegra194 ******************************************************************************/ -const static uint32_t tegra194_streamid_override_regs[] = { - MC_STREAMID_OVERRIDE_CFG_HDAR, - MC_STREAMID_OVERRIDE_CFG_HOST1XDMAR, - MC_STREAMID_OVERRIDE_CFG_NVENCSRD, - MC_STREAMID_OVERRIDE_CFG_SATAR, - MC_STREAMID_OVERRIDE_CFG_NVENCSWR, - MC_STREAMID_OVERRIDE_CFG_HDAW, - MC_STREAMID_OVERRIDE_CFG_SATAW, - MC_STREAMID_OVERRIDE_CFG_ISPRA, - MC_STREAMID_OVERRIDE_CFG_ISPFALR, - MC_STREAMID_OVERRIDE_CFG_ISPWA, - MC_STREAMID_OVERRIDE_CFG_ISPWB, - MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTR, - MC_STREAMID_OVERRIDE_CFG_XUSB_HOSTW, - MC_STREAMID_OVERRIDE_CFG_XUSB_DEVR, - MC_STREAMID_OVERRIDE_CFG_XUSB_DEVW, - MC_STREAMID_OVERRIDE_CFG_TSECSRD, - MC_STREAMID_OVERRIDE_CFG_TSECSWR, - MC_STREAMID_OVERRIDE_CFG_SDMMCRA, - MC_STREAMID_OVERRIDE_CFG_SDMMCR, - MC_STREAMID_OVERRIDE_CFG_SDMMCRAB, - MC_STREAMID_OVERRIDE_CFG_SDMMCWA, - MC_STREAMID_OVERRIDE_CFG_SDMMCW, - MC_STREAMID_OVERRIDE_CFG_SDMMCWAB, - MC_STREAMID_OVERRIDE_CFG_VICSRD, - MC_STREAMID_OVERRIDE_CFG_VICSWR, - MC_STREAMID_OVERRIDE_CFG_VIW, - MC_STREAMID_OVERRIDE_CFG_NVDECSRD, - MC_STREAMID_OVERRIDE_CFG_NVDECSWR, - MC_STREAMID_OVERRIDE_CFG_APER, - MC_STREAMID_OVERRIDE_CFG_APEW, - MC_STREAMID_OVERRIDE_CFG_NVJPGSRD, - MC_STREAMID_OVERRIDE_CFG_NVJPGSWR, - MC_STREAMID_OVERRIDE_CFG_SESRD, - MC_STREAMID_OVERRIDE_CFG_SESWR, - MC_STREAMID_OVERRIDE_CFG_AXIAPR, - MC_STREAMID_OVERRIDE_CFG_AXIAPW, - MC_STREAMID_OVERRIDE_CFG_ETRR, - MC_STREAMID_OVERRIDE_CFG_ETRW, - MC_STREAMID_OVERRIDE_CFG_TSECSRDB, - MC_STREAMID_OVERRIDE_CFG_TSECSWRB, - MC_STREAMID_OVERRIDE_CFG_AXISR, - MC_STREAMID_OVERRIDE_CFG_AXISW, - MC_STREAMID_OVERRIDE_CFG_EQOSR, - MC_STREAMID_OVERRIDE_CFG_EQOSW, - MC_STREAMID_OVERRIDE_CFG_UFSHCR, - MC_STREAMID_OVERRIDE_CFG_UFSHCW, - MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR, - MC_STREAMID_OVERRIDE_CFG_BPMPR, - MC_STREAMID_OVERRIDE_CFG_BPMPW, - MC_STREAMID_OVERRIDE_CFG_BPMPDMAR, - MC_STREAMID_OVERRIDE_CFG_BPMPDMAW, - MC_STREAMID_OVERRIDE_CFG_AONR, - MC_STREAMID_OVERRIDE_CFG_AONW, - MC_STREAMID_OVERRIDE_CFG_AONDMAR, - MC_STREAMID_OVERRIDE_CFG_AONDMAW, - MC_STREAMID_OVERRIDE_CFG_SCER, - MC_STREAMID_OVERRIDE_CFG_SCEW, - MC_STREAMID_OVERRIDE_CFG_SCEDMAR, - MC_STREAMID_OVERRIDE_CFG_SCEDMAW, - MC_STREAMID_OVERRIDE_CFG_APEDMAR, - MC_STREAMID_OVERRIDE_CFG_APEDMAW, - MC_STREAMID_OVERRIDE_CFG_NVDISPLAYR1, - MC_STREAMID_OVERRIDE_CFG_VICSRD1, - MC_STREAMID_OVERRIDE_CFG_NVDECSRD1, - MC_STREAMID_OVERRIDE_CFG_VIFALR, - MC_STREAMID_OVERRIDE_CFG_VIFALW, - MC_STREAMID_OVERRIDE_CFG_DLA0RDA, - MC_STREAMID_OVERRIDE_CFG_DLA0FALRDB, - MC_STREAMID_OVERRIDE_CFG_DLA0WRA, - MC_STREAMID_OVERRIDE_CFG_DLA0FALWRB, - MC_STREAMID_OVERRIDE_CFG_DLA1RDA, - MC_STREAMID_OVERRIDE_CFG_DLA1FALRDB, - MC_STREAMID_OVERRIDE_CFG_DLA1WRA, - MC_STREAMID_OVERRIDE_CFG_DLA1FALWRB, - MC_STREAMID_OVERRIDE_CFG_PVA0RDA, - MC_STREAMID_OVERRIDE_CFG_PVA0RDB, - MC_STREAMID_OVERRIDE_CFG_PVA0RDC, - MC_STREAMID_OVERRIDE_CFG_PVA0WRA, - MC_STREAMID_OVERRIDE_CFG_PVA0WRB, - MC_STREAMID_OVERRIDE_CFG_PVA0WRC, - MC_STREAMID_OVERRIDE_CFG_PVA1RDA, - MC_STREAMID_OVERRIDE_CFG_PVA1RDB, - MC_STREAMID_OVERRIDE_CFG_PVA1RDC, - MC_STREAMID_OVERRIDE_CFG_PVA1WRA, - MC_STREAMID_OVERRIDE_CFG_PVA1WRB, - MC_STREAMID_OVERRIDE_CFG_PVA1WRC, - MC_STREAMID_OVERRIDE_CFG_RCER, - MC_STREAMID_OVERRIDE_CFG_RCEW, - MC_STREAMID_OVERRIDE_CFG_RCEDMAR, - MC_STREAMID_OVERRIDE_CFG_RCEDMAW, - MC_STREAMID_OVERRIDE_CFG_NVENC1SRD, - MC_STREAMID_OVERRIDE_CFG_NVENC1SWR, - MC_STREAMID_OVERRIDE_CFG_PCIE0R, - MC_STREAMID_OVERRIDE_CFG_PCIE0W, - MC_STREAMID_OVERRIDE_CFG_PCIE1R, - MC_STREAMID_OVERRIDE_CFG_PCIE1W, - MC_STREAMID_OVERRIDE_CFG_PCIE2AR, - MC_STREAMID_OVERRIDE_CFG_PCIE2AW, - MC_STREAMID_OVERRIDE_CFG_PCIE3R, - MC_STREAMID_OVERRIDE_CFG_PCIE3W, - MC_STREAMID_OVERRIDE_CFG_PCIE4R, - MC_STREAMID_OVERRIDE_CFG_PCIE4W, - MC_STREAMID_OVERRIDE_CFG_PCIE5R, - MC_STREAMID_OVERRIDE_CFG_PCIE5W, - MC_STREAMID_OVERRIDE_CFG_ISPFALW, - MC_STREAMID_OVERRIDE_CFG_DLA0RDA1, - MC_STREAMID_OVERRIDE_CFG_DLA1RDA1, - MC_STREAMID_OVERRIDE_CFG_PVA0RDA1, - MC_STREAMID_OVERRIDE_CFG_PVA0RDB1, - MC_STREAMID_OVERRIDE_CFG_PVA1RDA1, - MC_STREAMID_OVERRIDE_CFG_PVA1RDB1, - MC_STREAMID_OVERRIDE_CFG_PCIE5R1, - MC_STREAMID_OVERRIDE_CFG_NVENCSRD1, - MC_STREAMID_OVERRIDE_CFG_NVENC1SRD1, - MC_STREAMID_OVERRIDE_CFG_ISPRA1, - MC_STREAMID_OVERRIDE_CFG_PCIE0R1, - MC_STREAMID_OVERRIDE_CFG_MIU0R, - MC_STREAMID_OVERRIDE_CFG_MIU0W, - MC_STREAMID_OVERRIDE_CFG_MIU1R, - MC_STREAMID_OVERRIDE_CFG_MIU1W, - MC_STREAMID_OVERRIDE_CFG_MIU2R, - MC_STREAMID_OVERRIDE_CFG_MIU2W, - MC_STREAMID_OVERRIDE_CFG_MIU3R, - MC_STREAMID_OVERRIDE_CFG_MIU3W +static __attribute__((aligned(16))) mc_regs_t tegra194_mc_context[] = { + _START_OF_TABLE_, + mc_smmu_bypass_cfg, /* TBU settings */ + _END_OF_TABLE_, }; /******************************************************************************* - * Array to hold the security configs for stream IDs + * Handler to return the pointer to the MC's context struct ******************************************************************************/ -const static mc_streamid_security_cfg_t tegra194_streamid_sec_cfgs[] = { - mc_make_sec_cfg(HDAR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(HOST1XDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENCSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SATAR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENCSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(HDAW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SATAW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPRA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPFALR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPWA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPWB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(XUSB_HOSTR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(XUSB_HOSTW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(XUSB_DEVR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(XUSB_DEVW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCRA, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCRAB, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCWA, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(SDMMCWAB, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(VICSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(VICSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(VIW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDECSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDECSWR, 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(NVJPGSRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVJPGSWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SESRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SESWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AXIAPR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(AXIAPW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(ETRR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(ETRW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSRDB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(TSECSWRB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AXISR, SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(AXISW, SECURE, NO_OVERRIDE, DISABLE), - mc_make_sec_cfg(EQOSR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(EQOSW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(UFSHCR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(UFSHCW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDISPLAYR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(BPMPR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(BPMPW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(BPMPDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(BPMPDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AONR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AONW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AONDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(AONDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SCER, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SCEW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SCEDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(SCEDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(APEDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(APEDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDISPLAYR1, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(VICSRD1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVDECSRD1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(VIFALR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(VIFALW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA0RDA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA0FALRDB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA0WRA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA0FALWRB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA1RDA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA1FALRDB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA1WRA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA1FALWRB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0RDA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0RDB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0RDC, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0WRA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0WRB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0WRC, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1RDA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1RDB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1RDC, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1WRA, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1WRB, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1WRC, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(RCER, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(RCEW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(RCEDMAR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(RCEDMAW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENC1SRD, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENC1SWR, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE0R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE0W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE1R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE1W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE2AR, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE2AW, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE3R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE3W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE4R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE4W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE5R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE5W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPFALW, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA0RDA1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(DLA1RDA1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0RDA1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA0RDB1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1RDA1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PVA1RDB1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE5R1, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENCSRD1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(NVENC1SRD1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(ISPRA1, NON_SECURE, NO_OVERRIDE, ENABLE), - mc_make_sec_cfg(PCIE0R1, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU0R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU0W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU1R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU1W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU2R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU2W, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU3R, NON_SECURE, OVERRIDE, ENABLE), - mc_make_sec_cfg(MIU3W, NON_SECURE, OVERRIDE, ENABLE), -}; - -/* To be called by common memctrl_v2.c */ -static void tegra194_memctrl_reconfig_mss_clients(void) +mc_regs_t *plat_memctrl_get_sys_suspend_ctx(void) { - uint32_t reg_val, wdata_0, wdata_1, wdata_2; - - wdata_0 = MC_CLIENT_HOTRESET_CTRL0_HC_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_SATA_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_VIC_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_XUSB_HOST_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_XUSB_DEV_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_TSEC_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL0_SDMMC3A_FLUSH_ENB; - if (tegra_platform_is_silicon()) { - wdata_0 |= MC_CLIENT_HOTRESET_CTRL0_SDMMC1A_FLUSH_ENB; - } - - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL0, wdata_0); - - /* Wait for HOTRESET STATUS to indicate FLUSH_DONE */ - do { - reg_val = tegra_mc_read_32(MC_CLIENT_HOTRESET_STATUS0); - } while ((reg_val & wdata_0) != wdata_0); - - wdata_1 = MC_CLIENT_HOTRESET_CTRL1_SDMMC4A_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_SE_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_ETR_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_TSECB_FLUSH_ENB| - MC_CLIENT_HOTRESET_CTRL1_AXIS_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_UFSHC_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_NVDISPLAY_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_BPMP_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_AON_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_SCE_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_VIFAL_FLUSH_ENB; - if (tegra_platform_is_silicon()) { - wdata_1 |= MC_CLIENT_HOTRESET_CTRL1_APE_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_EQOS_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL1_RCE_FLUSH_ENB; - } - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL1, wdata_1); - /* Wait for HOTRESET STATUS to indicate FLUSH_DONE */ - do { - reg_val = tegra_mc_read_32(MC_CLIENT_HOTRESET_STATUS1); - } while ((reg_val & wdata_1) != wdata_1); - - wdata_2 = MC_CLIENT_HOTRESET_CTRL2_PCIE_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_AONDMA_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_BPMPDMA_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_SCEDMA_FLUSH_ENB; - if (tegra_platform_is_silicon()) { - wdata_2 |= MC_CLIENT_HOTRESET_CTRL2_RCEDMA_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE5A_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE3A_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE3_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE0A_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE0A2_FLUSH_ENB | - MC_CLIENT_HOTRESET_CTRL2_PCIE4A_FLUSH_ENB; - } - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL2, wdata_2); - /* Wait for HOTRESET STATUS to indicate FLUSH_DONE */ - do { - reg_val = tegra_mc_read_32(MC_CLIENT_HOTRESET_STATUS2); - } while ((reg_val & wdata_2) != wdata_2); - - /* - * Change MEMTYPE_OVERRIDE from SO_DEV -> PASSTHRU for boot and - * strongly ordered MSS clients. - * - * MC clients with default SO_DEV override still enabled at TSA: - * EQOSW, SATAW, XUSB_DEVW, XUSB_HOSTW, PCIe0w, PCIe1w, PCIe2w, - * PCIe3w, PCIe4w and PCIe5w. - */ - mc_set_tsa_w_passthrough(AONDMAW); - mc_set_tsa_w_passthrough(AONW); - mc_set_tsa_w_passthrough(APEDMAW); - mc_set_tsa_w_passthrough(APEW); - mc_set_tsa_w_passthrough(AXISW); - mc_set_tsa_w_passthrough(BPMPDMAW); - mc_set_tsa_w_passthrough(BPMPW); - mc_set_tsa_w_passthrough(EQOSW); - mc_set_tsa_w_passthrough(ETRW); - mc_set_tsa_w_passthrough(RCEDMAW); - mc_set_tsa_w_passthrough(RCEW); - mc_set_tsa_w_passthrough(SCEDMAW); - mc_set_tsa_w_passthrough(SCEW); - mc_set_tsa_w_passthrough(SDMMCW); - mc_set_tsa_w_passthrough(SDMMCWA); - mc_set_tsa_w_passthrough(SDMMCWAB); - mc_set_tsa_w_passthrough(SESWR); - mc_set_tsa_w_passthrough(TSECSWR); - mc_set_tsa_w_passthrough(TSECSWRB); - mc_set_tsa_w_passthrough(UFSHCW); - mc_set_tsa_w_passthrough(VICSWR); - mc_set_tsa_w_passthrough(VIFALW); - /* - * set HUB2 as SO_DEV_HUBID - */ - reg_val = tsa_read_32(PCIE0W); - mc_set_tsa_hub2(reg_val, PCIE0W); - reg_val = tsa_read_32(PCIE1W); - mc_set_tsa_hub2(reg_val, PCIE1W); - reg_val = tsa_read_32(PCIE2AW); - mc_set_tsa_hub2(reg_val, PCIE2AW); - reg_val = tsa_read_32(PCIE3W); - mc_set_tsa_hub2(reg_val, PCIE3W); - reg_val = tsa_read_32(PCIE4W); - mc_set_tsa_hub2(reg_val, PCIE4W); - reg_val = tsa_read_32(SATAW); - mc_set_tsa_hub2(reg_val, SATAW); - reg_val = tsa_read_32(XUSB_DEVW); - mc_set_tsa_hub2(reg_val, XUSB_DEVW); - reg_val = tsa_read_32(XUSB_HOSTW); - mc_set_tsa_hub2(reg_val, XUSB_HOSTW); - - /* - * Hw Bug: 200385660, 200394107 - * PCIE datapath hangs when there are more than 28 outstanding - * requests on data backbone for x1 controller. This is seen - * on third party PCIE IP, C1 - PCIE1W, C2 - PCIE2AW and C3 - PCIE3W. - * - * Setting Reorder depth limit, 16 which is < 28. - */ - mc_set_tsa_depth_limit(REORDER_DEPTH_LIMIT, PCIE1W); - mc_set_tsa_depth_limit(REORDER_DEPTH_LIMIT, PCIE2AW); - mc_set_tsa_depth_limit(REORDER_DEPTH_LIMIT, PCIE3W); - - /* Ordered MC Clients on Xavier are EQOS, SATA, XUSB, PCIe1 and PCIe3 - * ISO clients(DISP, VI, EQOS) should never snoop caches and - * don't need ROC/PCFIFO ordering. - * ISO clients(EQOS) that need ordering should use PCFIFO ordering - * and bypass ROC ordering by using FORCE_NON_COHERENT path. - * FORCE_NON_COHERENT/FORCE_COHERENT config take precedence - * over SMMU attributes. - * Force all Normal memory transactions from ISO and non-ISO to be - * non-coherent(bypass ROC, avoid cache snoop to avoid perf hit). - * Force the SO_DEV transactions from ordered ISO clients(EQOS) to - * non-coherent path and enable MC PCFIFO interlock for ordering. - * Force the SO_DEV transactions from ordered non-ISO clients (PCIe, - * XUSB, SATA) to coherent so that the transactions are - * ordered by ROC. - * PCFIFO ensure write ordering. - * Read after Write ordering is maintained/enforced by MC clients. - * Clients that need PCIe type write ordering must - * go through ROC ordering. - * Ordering enable for Read clients is not necessary. - * R5's and A9 would get necessary ordering from AXI and - * don't need ROC ordering enable: - * - MMIO ordering is through dev mapping and MMIO - * accesses bypass SMMU. - * - Normal memory is accessed through SMMU and ordering is - * ensured by client and AXI. - * - Ack point for Normal memory is WCAM in MC. - * - MMIO's can be early acked and AXI ensures dev memory ordering, - * Client ensures read/write direction change ordering. - * - See Bug 200312466 for more details. - */ - mc_set_txn_override(AONDMAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(AONDMAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(AONR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(AONW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(APEDMAR, CGID_TAG_ADR, SO_DEV_CLIENT_AXI_ID, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(APEDMAW, CGID_TAG_ADR, SO_DEV_CLIENT_AXI_ID, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(APER, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(APEW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(AXISR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(AXISW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(BPMPDMAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(BPMPDMAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(BPMPR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(BPMPW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(EQOSR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(EQOSW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(ETRR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ETRW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(HOST1XDMAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(MPCORER, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MPCOREW, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(NVDISPLAYR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(NVDISPLAYR1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(PCIE0R, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE0R1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE0W, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE1R, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE1W, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - if (tegra_platform_is_silicon()) { - mc_set_txn_override(PCIE2AR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE2AW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE3R, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE3W, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE4R, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE4W, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE5R, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE5W, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(PCIE5R1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - } - mc_set_txn_override(PTCR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(RCEDMAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(RCEDMAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(RCER, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(RCEW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SATAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(SATAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(SCEDMAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SCEDMAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SCER, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SCEW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCRAB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCWA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(SDMMCWAB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - /* - * TO DO: make SESRD/WR FORCE_COHERENT once SE+TZ with SMMU is enabled. - */ - mc_set_txn_override(SESRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(SESWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(TSECSRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(TSECSRDB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(TSECSWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(TSECSWRB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(UFSHCR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(UFSHCW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(VICSRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(VICSRD1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(VICSWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(VIFALR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(VIFALW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(XUSB_DEVR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(XUSB_DEVW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(XUSB_HOSTR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(XUSB_HOSTW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT_SNOOP, FORCE_COHERENT_SNOOP); - mc_set_txn_override(AXIAPR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(AXIAPW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA0FALRDB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA0FALWRB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA0RDA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA0RDA1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA0WRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA1FALRDB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA1FALWRB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA1RDA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA1RDA1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(DLA1WRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(HDAR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(HDAW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - mc_set_txn_override(ISPFALR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ISPFALW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ISPRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ISPRA1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ISPWA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(ISPWB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDEC1SRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDEC1SRD1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDEC1SWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDECSRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDECSRD1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVDECSWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENC1SRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENC1SRD1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENC1SWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENCSRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENCSRD1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVENCSWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVJPGSRD, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(NVJPGSWR, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0RDA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0RDA1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0RDB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0RDB1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0RDC, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0WRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0WRB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA0WRC, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1RDA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1RDA1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1RDB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1RDB1, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1RDC, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1WRA, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1WRB, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(PVA1WRC, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_COHERENT, FORCE_COHERENT); - mc_set_txn_override(VIW, CGID_TAG_ADR, SO_DEV_ZERO, FORCE_NON_COHERENT, FORCE_NON_COHERENT); - - if (tegra_platform_is_silicon()) { - mc_set_txn_override(MIU0R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU0W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU1R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU1W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU2R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU2W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU3R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU3W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU4R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU4W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU5R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU5W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU6R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU6W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU7R, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - mc_set_txn_override(MIU7W, CGID_TAG_ADR, SO_DEV_ZERO, NO_OVERRIDE, NO_OVERRIDE); - } - - /* - * At this point, ordering can occur at SCF. So, remove PCFIFO's - * control over ordering requests. - * - * Change PCFIFO_*_ORDERED_CLIENT from ORDERED -> UNORDERED for - * boot and strongly ordered MSS clients - */ - reg_val = MC_PCFIFO_CLIENT_CONFIG2_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(2, XUSB_HOSTW) & - mc_set_pcfifo_unordered_boot_so_mss(2, TSECSWR); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG2, reg_val); - - reg_val = MC_PCFIFO_CLIENT_CONFIG3_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(3, SDMMCWA) & - mc_set_pcfifo_unordered_boot_so_mss(3, SDMMCW) & - mc_set_pcfifo_unordered_boot_so_mss(3, SDMMCWAB) & - mc_set_pcfifo_unordered_boot_so_mss(3, VICSWR) & - mc_set_pcfifo_unordered_boot_so_mss(3, APEW); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG3, reg_val); - - reg_val = MC_PCFIFO_CLIENT_CONFIG4_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(4, SESWR) & - mc_set_pcfifo_unordered_boot_so_mss(4, ETRW) & - mc_set_pcfifo_unordered_boot_so_mss(4, TSECSWRB) & - mc_set_pcfifo_unordered_boot_so_mss(4, AXISW) & - mc_set_pcfifo_unordered_boot_so_mss(4, UFSHCW) & - mc_set_pcfifo_unordered_boot_so_mss(4, BPMPW) & - mc_set_pcfifo_unordered_boot_so_mss(4, BPMPDMAW) & - mc_set_pcfifo_unordered_boot_so_mss(4, AONW) & - mc_set_pcfifo_unordered_boot_so_mss(4, AONDMAW) & - mc_set_pcfifo_unordered_boot_so_mss(4, SCEW) & - mc_set_pcfifo_unordered_boot_so_mss(4, SCEDMAW); - /* EQOSW has PCFIFO order enabled. */ - reg_val |= mc_set_pcfifo_unordered_boot_so_mss(4, EQOSW); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG4, reg_val); - - reg_val = MC_PCFIFO_CLIENT_CONFIG5_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(5, APEDMAW) & - mc_set_pcfifo_unordered_boot_so_mss(5, VIFALW); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG5, reg_val); - - reg_val = MC_PCFIFO_CLIENT_CONFIG6_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(6, RCEW) & - mc_set_pcfifo_unordered_boot_so_mss(6, RCEDMAW) & - mc_set_pcfifo_unordered_boot_so_mss(6, PCIE0W); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG6, reg_val); - - reg_val = MC_PCFIFO_CLIENT_CONFIG7_RESET_VAL & - mc_set_pcfifo_unordered_boot_so_mss(7, PCIE4W) & - mc_set_pcfifo_unordered_boot_so_mss(7, PCIE5W); - tegra_mc_write_32(MC_PCFIFO_CLIENT_CONFIG7, reg_val); - - /* Set Order Id only for the clients having non zero order id */ - reg_val = mc_client_order_id(MC_CLIENT_ORDER_ID_9_RESET_VAL, 9, XUSB_HOSTW); - tegra_mc_write_32(MC_CLIENT_ORDER_ID_9, reg_val); - - reg_val = mc_client_order_id(MC_CLIENT_ORDER_ID_27_RESET_VAL, 27, PCIE0W); - tegra_mc_write_32(MC_CLIENT_ORDER_ID_27, reg_val); - - reg_val = mc_client_order_id(MC_CLIENT_ORDER_ID_28_RESET_VAL, 28, PCIE4W); - reg_val = mc_client_order_id(reg_val, 28, PCIE5W); - tegra_mc_write_32(MC_CLIENT_ORDER_ID_28, reg_val); - - /* - * Set VC Id only for the clients having different reset values like - * SDMMCRAB, SDMMCWAB, SESRD, SESWR, TSECSRD,TSECSRDB, TSECSWR and - * TSECSWRB clients - */ - reg_val = mc_hub_vc_id(MC_HUB_PC_VC_ID_0_RESET_VAL, 0, APB); - tegra_mc_write_32(MC_HUB_PC_VC_ID_0, reg_val); + /* index of _END_OF_TABLE_ */ + tegra194_mc_context[0].val = (uint32_t)ARRAY_SIZE(tegra194_mc_context) - 1U; - /* SDMMCRAB and SDMMCWAB clients */ - reg_val = mc_hub_vc_id(MC_HUB_PC_VC_ID_2_RESET_VAL, 2, SD); - tegra_mc_write_32(MC_HUB_PC_VC_ID_2, reg_val); - - reg_val = mc_hub_vc_id(MC_HUB_PC_VC_ID_4_RESET_VAL, 4, NIC); - tegra_mc_write_32(MC_HUB_PC_VC_ID_4, reg_val); - - reg_val = mc_hub_vc_id(MC_HUB_PC_VC_ID_12_RESET_VAL, 12, UFSHCPC2); - tegra_mc_write_32(MC_HUB_PC_VC_ID_12, reg_val); - - wdata_0 = MC_CLIENT_HOTRESET_CTRL0_RESET_VAL; - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL0, wdata_0); - - wdata_1 = MC_CLIENT_HOTRESET_CTRL1_RESET_VAL; - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL1, wdata_1); - - wdata_2 = MC_CLIENT_HOTRESET_CTRL2_RESET_VAL; - tegra_mc_write_32(MC_CLIENT_HOTRESET_CTRL2, wdata_2); - - reg_val = MC_COALESCE_CTRL_COALESCER_ENABLE; - tegra_mc_write_32(MC_COALESCE_CTRL, reg_val); - - /* - * WAR to hardware bug 1953865: Coalescer must be disabled - * for PVA0RDC and PVA1RDC interfaces. - */ - reg_val = tegra_mc_read_32(MC_COALESCE_CONFIG_6_0); - reg_val &= ~(MC_COALESCE_CONFIG_6_0_PVA0RDC_COALESCER_ENABLED | - MC_COALESCE_CONFIG_6_0_PVA1RDC_COALESCER_ENABLED); - tegra_mc_write_32(MC_COALESCE_CONFIG_6_0, reg_val); + return tegra194_mc_context; } /******************************************************************************* - * Struct to hold the memory controller settings + * Handler to restore platform specific settings to the memory controller ******************************************************************************/ -static tegra_mc_settings_t tegra194_mc_settings = { - .streamid_override_cfg = tegra194_streamid_override_regs, - .num_streamid_override_cfgs = (uint32_t)ARRAY_SIZE(tegra194_streamid_override_regs), - .streamid_security_cfg = tegra194_streamid_sec_cfgs, - .num_streamid_security_cfgs = (uint32_t)ARRAY_SIZE(tegra194_streamid_sec_cfgs), - .reconfig_mss_clients = tegra194_memctrl_reconfig_mss_clients -}; +void plat_memctrl_restore(void) +{ + UNUSED_FUNC_NOP(); /* do nothing */ +} /******************************************************************************* - * Handler to return the pointer to the memory controller's settings struct + * Handler to program platform specific settings to the memory controller ******************************************************************************/ -tegra_mc_settings_t *tegra_get_mc_settings(void) +void plat_memctrl_setup(void) { - return &tegra194_mc_settings; + UNUSED_FUNC_NOP(); /* do nothing */ } /******************************************************************************* @@ -704,6 +54,8 @@ tegra_mc_settings_t *tegra_get_mc_settings(void) void plat_memctrl_tzdram_setup(uint64_t phys_base, uint64_t size_in_bytes) { uint32_t sec_reg_ctrl = tegra_mc_read_32(MC_SECURITY_CFG_REG_CTRL_0); + uint32_t phys_base_lo = (uint32_t)phys_base & 0xFFF00000; + uint32_t phys_base_hi = (uint32_t)(phys_base >> 32); /* * Check TZDRAM carveout register access status. Setup TZDRAM fence @@ -718,8 +70,8 @@ void plat_memctrl_tzdram_setup(uint64_t phys_base, uint64_t size_in_bytes) */ INFO("Configuring TrustZone DRAM Memory Carveout\n"); - tegra_mc_write_32(MC_SECURITY_CFG0_0, (uint32_t)phys_base); - tegra_mc_write_32(MC_SECURITY_CFG3_0, (uint32_t)(phys_base >> 32)); + tegra_mc_write_32(MC_SECURITY_CFG0_0, phys_base_lo); + tegra_mc_write_32(MC_SECURITY_CFG3_0, phys_base_hi); tegra_mc_write_32(MC_SECURITY_CFG1_0, (uint32_t)(size_in_bytes >> 20)); /* diff --git a/plat/nvidia/tegra/soc/t194/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t194/plat_psci_handlers.c index cc8be128a..41a85ee7c 100644 --- a/plat/nvidia/tegra/soc/t194/plat_psci_handlers.c +++ b/plat/nvidia/tegra/soc/t194/plat_psci_handlers.c @@ -10,14 +10,17 @@ #include <string.h> #include <arch_helpers.h> +#include <bpmp_ipc.h> #include <common/bl_common.h> #include <common/debug.h> #include <context.h> +#include <drivers/delay_timer.h> #include <denver.h> #include <lib/el3_runtime/context_mgmt.h> #include <lib/psci/psci.h> #include <mce.h> #include <mce_private.h> +#include <memctrl_v2.h> #include <plat/common/platform.h> #include <se.h> #include <smmu.h> @@ -44,14 +47,6 @@ static struct t19x_psci_percpu_data { uint32_t wake_time; } __aligned(CACHE_WRITEBACK_GRANULE) t19x_percpu_data[PLATFORM_CORE_COUNT]; -/* - * tegra_fake_system_suspend acts as a boolean var controlling whether - * we are going to take fake system suspend code or normal system suspend code - * path. This variable is set inside the sip call handlers, when the kernel - * requests an SIP call to set the suspend debug flags. - */ -bool tegra_fake_system_suspend; - int32_t tegra_soc_validate_power_state(uint32_t power_state, psci_power_state_t *req_state) { @@ -78,19 +73,16 @@ int32_t tegra_soc_validate_power_state(uint32_t power_state, switch (state_id) { case PSTATE_ID_CORE_IDLE: + if (psci_get_pstate_type(power_state) != PSTATE_TYPE_STANDBY) { + ret = PSCI_E_INVALID_PARAMS; + break; + } + /* Core idle request */ req_state->pwr_domain_state[MPIDR_AFFLVL0] = PLAT_MAX_RET_STATE; req_state->pwr_domain_state[MPIDR_AFFLVL1] = PSCI_LOCAL_STATE_RUN; break; - case PSTATE_ID_CORE_POWERDN: - - /* Core powerdown request */ - req_state->pwr_domain_state[MPIDR_AFFLVL0] = state_id; - req_state->pwr_domain_state[MPIDR_AFFLVL1] = state_id; - - break; - default: ERROR("%s: unsupported state id (%d)\n", __func__, state_id); ret = PSCI_E_INVALID_PARAMS; @@ -122,9 +114,9 @@ int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state) int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) { const plat_local_state_t *pwr_domain_state; - uint8_t stateid_afflvl0, stateid_afflvl2; + uint8_t stateid_afflvl2; plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); - uint64_t smmu_ctx_base; + uint64_t mc_ctx_base; uint32_t val; mce_cstate_info_t sc7_cstate_info = { .cluster = (uint32_t)TEGRA_NVG_CLUSTER_CC6, @@ -133,34 +125,23 @@ int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) .system_state_force = 1U, .update_wake_mask = 1U, }; - uint32_t cpu = plat_my_core_pos(); int32_t ret = 0; /* get the state ID */ pwr_domain_state = target_state->pwr_domain_state; - stateid_afflvl0 = pwr_domain_state[MPIDR_AFFLVL0] & - TEGRA194_STATE_ID_MASK; stateid_afflvl2 = pwr_domain_state[PLAT_MAX_PWR_LVL] & TEGRA194_STATE_ID_MASK; - if ((stateid_afflvl0 == PSTATE_ID_CORE_POWERDN)) { - - /* Enter CPU powerdown */ - (void)mce_command_handler((uint64_t)MCE_CMD_ENTER_CSTATE, - (uint64_t)TEGRA_NVG_CORE_C7, - t19x_percpu_data[cpu].wake_time, - 0U); - - } else if (stateid_afflvl2 == PSTATE_ID_SOC_POWERDN) { + if (stateid_afflvl2 == PSTATE_ID_SOC_POWERDN) { /* save 'Secure Boot' Processor Feature Config Register */ val = mmio_read_32(TEGRA_MISC_BASE + MISCREG_PFCFG); mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_SECURE_BOOTP_FCFG, val); - /* save SMMU context */ - smmu_ctx_base = params_from_bl2->tzdram_base + - tegra194_get_smmu_ctx_offset(); - tegra_smmu_save_context((uintptr_t)smmu_ctx_base); + /* save MC context */ + mc_ctx_base = params_from_bl2->tzdram_base + + tegra194_get_mc_ctx_offset(); + tegra_mc_save_context((uintptr_t)mc_ctx_base); /* * Suspend SE, RNG1 and PKA1 only on silcon and fpga, @@ -171,32 +152,27 @@ int32_t tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) assert(ret == 0); } - if (!tegra_fake_system_suspend) { - - /* Prepare for system suspend */ - mce_update_cstate_info(&sc7_cstate_info); + /* Prepare for system suspend */ + mce_update_cstate_info(&sc7_cstate_info); - do { - val = (uint32_t)mce_command_handler( - (uint32_t)MCE_CMD_IS_SC7_ALLOWED, - (uint32_t)TEGRA_NVG_CORE_C7, - MCE_CORE_SLEEP_TIME_INFINITE, - 0U); - } while (val == 0U); - - /* Instruct the MCE to enter system suspend state */ - ret = mce_command_handler( - (uint64_t)MCE_CMD_ENTER_CSTATE, - (uint64_t)TEGRA_NVG_CORE_C7, + do { + val = (uint32_t)mce_command_handler( + (uint32_t)MCE_CMD_IS_SC7_ALLOWED, + (uint32_t)TEGRA_NVG_CORE_C7, MCE_CORE_SLEEP_TIME_INFINITE, 0U); - assert(ret == 0); - - /* set system suspend state for house-keeping */ - tegra194_set_system_suspend_entry(); - } - } else { - ; /* do nothing */ + } while (val == 0U); + + /* Instruct the MCE to enter system suspend state */ + ret = mce_command_handler( + (uint64_t)MCE_CMD_ENTER_CSTATE, + (uint64_t)TEGRA_NVG_CORE_C7, + MCE_CORE_SLEEP_TIME_INFINITE, + 0U); + assert(ret == 0); + + /* set system suspend state for house-keeping */ + tegra194_set_system_suspend_entry(); } return PSCI_E_SUCCESS; @@ -234,15 +210,6 @@ static plat_local_state_t tegra_get_afflvl1_pwr_state(const plat_local_state_t * plat_local_state_t target = states[core_pos]; mce_cstate_info_t cstate_info = { 0 }; - /* CPU suspend */ - if (target == PSTATE_ID_CORE_POWERDN) { - - /* Program default wake mask */ - cstate_info.wake_mask = TEGRA194_CORE_WAKE_MASK; - cstate_info.update_wake_mask = 1; - mce_update_cstate_info(&cstate_info); - } - /* CPU off */ if (target == PLAT_MAX_OFF_STATE) { @@ -300,10 +267,34 @@ int32_t tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_sta plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); uint8_t stateid_afflvl2 = pwr_domain_state[PLAT_MAX_PWR_LVL] & TEGRA194_STATE_ID_MASK; + uint64_t src_len_in_bytes = (uintptr_t)&__BL31_END__ - (uintptr_t)BL31_BASE; uint64_t val; - u_register_t ns_sctlr_el1; + int32_t ret = PSCI_E_SUCCESS; if (stateid_afflvl2 == PSTATE_ID_SOC_POWERDN) { + val = params_from_bl2->tzdram_base + + tegra194_get_cpu_reset_handler_size(); + + /* initialise communication channel with BPMP */ + ret = tegra_bpmp_ipc_init(); + assert(ret == 0); + + /* Enable SE clock before SE context save */ + ret = tegra_bpmp_ipc_enable_clock(TEGRA194_CLK_SE); + assert(ret == 0); + + /* + * It is very unlikely that the BL31 image would be + * bigger than 2^32 bytes + */ + assert(src_len_in_bytes < UINT32_MAX); + + if (tegra_se_calculate_save_sha256(BL31_BASE, + (uint32_t)src_len_in_bytes) != 0) { + ERROR("Hash calculation failed. Reboot\n"); + (void)tegra_soc_prepare_system_reset(); + } + /* * The TZRAM loses power when we enter system suspend. To * allow graceful exit from system suspend, we need to copy @@ -312,34 +303,19 @@ int32_t tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_sta val = params_from_bl2->tzdram_base + tegra194_get_cpu_reset_handler_size(); memcpy((void *)(uintptr_t)val, (void *)(uintptr_t)BL31_BASE, - (uintptr_t)&__BL31_END__ - (uintptr_t)BL31_BASE); + src_len_in_bytes); - /* - * In fake suspend mode, ensure that the loopback procedure - * towards system suspend exit is started, instead of calling - * WFI. This is done by disabling both MMU's of EL1 & El3 - * and calling tegra_secure_entrypoint(). - */ - if (tegra_fake_system_suspend) { - - /* - * Disable EL1's MMU. - */ - ns_sctlr_el1 = read_sctlr_el1(); - ns_sctlr_el1 &= (~((u_register_t)SCTLR_M_BIT)); - write_sctlr_el1(ns_sctlr_el1); - - /* - * Disable MMU to power up the CPU in a "clean" - * state - */ - disable_mmu_el3(); - tegra_secure_entrypoint(); - panic(); - } + /* Disable SE clock after SE context save */ + ret = tegra_bpmp_ipc_disable_clock(TEGRA194_CLK_SE); + assert(ret == 0); } - return PSCI_E_SUCCESS; + return ret; +} + +int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state) +{ + return PSCI_E_NOT_SUPPORTED; } int32_t tegra_soc_pwr_domain_on(u_register_t mpidr) @@ -367,7 +343,11 @@ int32_t tegra_soc_pwr_domain_on(u_register_t mpidr) int32_t tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) { + const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); + uint8_t enable_ccplex_lock_step = params_from_bl2->enable_ccplex_lock_step; uint8_t stateid_afflvl2 = target_state->pwr_domain_state[PLAT_MAX_PWR_LVL]; + cpu_context_t *ctx = cm_get_context(NON_SECURE); + uint64_t actlr_elx; /* * Reset power state info for CPUs when onlining, we set @@ -376,6 +356,10 @@ int32_t tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) * will re-init this info from non-secure software when the * core come online. */ + actlr_elx = read_ctx_reg((get_el1_sysregs_ctx(ctx)), (CTX_ACTLR_EL1)); + actlr_elx &= ~DENVER_CPU_PMSTATE_MASK; + actlr_elx |= DENVER_CPU_PMSTATE_C1; + write_ctx_reg((get_el1_sysregs_ctx(ctx)), (CTX_ACTLR_EL1), (actlr_elx)); /* * Check if we are exiting from deep sleep and restore SE @@ -434,24 +418,46 @@ int32_t tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_PF_0, TEGRA_SID_XUSB_HOST); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_PF_0) == TEGRA_SID_XUSB_HOST); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_0, TEGRA_SID_XUSB_VF0); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_0) == TEGRA_SID_XUSB_VF0); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_1, TEGRA_SID_XUSB_VF1); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_1) == TEGRA_SID_XUSB_VF1); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_2, TEGRA_SID_XUSB_VF2); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_2) == TEGRA_SID_XUSB_VF2); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_3, TEGRA_SID_XUSB_VF3); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_3) == TEGRA_SID_XUSB_VF3); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_DEV_AXI_STREAMID_PF_0, TEGRA_SID_XUSB_DEV); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_DEV_AXI_STREAMID_PF_0) == TEGRA_SID_XUSB_DEV); } + } - /* - * Reset power state info for the last core doing SC7 - * entry and exit, we set deepest power state as CC7 - * and SC7 for SC7 entry which may not be requested by - * non-secure SW which controls idle states. - */ + /* + * Enable dual execution optimized translations for all ELx. + */ + if (enable_ccplex_lock_step != 0U) { + actlr_elx = read_actlr_el3(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL3; + write_actlr_el3(actlr_elx); + + actlr_elx = read_actlr_el2(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL2; + write_actlr_el2(actlr_elx); + + actlr_elx = read_actlr_el1(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL1; + write_actlr_el1(actlr_elx); } return PSCI_E_SUCCESS; diff --git a/plat/nvidia/tegra/soc/t194/plat_ras.c b/plat/nvidia/tegra/soc/t194/plat_ras.c new file mode 100644 index 000000000..0c4c6fad6 --- /dev/null +++ b/plat/nvidia/tegra/soc/t194/plat_ras.c @@ -0,0 +1,501 @@ +/* + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. + * + * SPDX-License-Identifier: BSD-3-Clause + */ + +#include <stdbool.h> +#include <stdint.h> + +#include <common/debug.h> +#include <lib/bakery_lock.h> +#include <lib/cassert.h> +#include <lib/extensions/ras.h> +#include <lib/utils_def.h> +#include <services/sdei.h> + +#include <plat/common/platform.h> +#include <platform_def.h> +#include <tegra194_ras_private.h> +#include <tegra_def.h> +#include <tegra_platform.h> +#include <tegra_private.h> + +/* + * ERR<n>FR bits[63:32], it indicates supported RAS errors which can be enabled + * by setting corresponding bits in ERR<n>CTLR + */ +#define ERR_FR_EN_BITS_MASK 0xFFFFFFFF00000000ULL + +/* + * Number of RAS errors will be cleared per 'tegra194_ras_corrected_err_clear' + * function call. + */ +#define RAS_ERRORS_PER_CALL 8 + +/* + * the max possible RAS node index value. + */ +#define RAS_NODE_INDEX_MAX 0x1FFFFFFFU + +/* bakery lock for platform RAS handler. */ +static DEFINE_BAKERY_LOCK(ras_handler_lock); +#define ras_lock() bakery_lock_get(&ras_handler_lock) +#define ras_unlock() bakery_lock_release(&ras_handler_lock) + +/* + * Function to handle an External Abort received at EL3. + * This function is invoked by RAS framework. + */ +static void tegra194_ea_handler(unsigned int ea_reason, uint64_t syndrome, + void *cookie, void *handle, uint64_t flags) +{ + int32_t ret; + + ras_lock(); + + ERROR("MPIDR 0x%lx: exception reason=%u syndrome=0x%llx\n", + read_mpidr(), ea_reason, syndrome); + + /* Call RAS EA handler */ + ret = ras_ea_handler(ea_reason, syndrome, cookie, handle, flags); + if (ret != 0) { + ERROR("RAS error handled!\n"); + ret = sdei_dispatch_event(TEGRA_SDEI_EP_EVENT_0 + + plat_my_core_pos()); + if (ret != 0) + ERROR("sdei_dispatch_event returned %d\n", ret); + } else { + ERROR("Not a RAS error!\n"); + } + + ras_unlock(); +} + +/* + * Function to enable all supported RAS error report. + * + * Uncorrected errors are set to report as External abort (SError) + * Corrected errors are set to report as interrupt. + */ +void tegra194_ras_enable(void) +{ + VERBOSE("%s\n", __func__); + + /* skip RAS enablement if not a silicon platform. */ + if (!tegra_platform_is_silicon()) { + return; + } + + /* + * Iterate for each group(num_idx ERRSELRs starting from idx_start) + * use normal for loop instead of for_each_err_record_info to get rid + * of MISRA noise.. + */ + for (uint32_t i = 0U; i < err_record_mappings.num_err_records; i++) { + + const struct err_record_info *info = &err_record_mappings.err_records[i]; + + uint32_t idx_start = info->sysreg.idx_start; + uint32_t num_idx = info->sysreg.num_idx; + const struct ras_aux_data *aux_data = (const struct ras_aux_data *)info->aux_data; + + assert(aux_data != NULL); + + for (uint32_t j = 0; j < num_idx; j++) { + + /* ERR<n>CTLR register value. */ + uint64_t err_ctrl = 0ULL; + /* all supported errors for this node. */ + uint64_t err_fr; + /* uncorrectable errors */ + uint64_t uncorr_errs; + /* correctable errors */ + uint64_t corr_errs; + + /* + * Catch error if something wrong with the RAS aux data + * record table. + */ + assert(aux_data[j].err_ctrl != NULL); + + /* + * Write to ERRSELR_EL1 to select the RAS error node. + * Always program this at first to select corresponding + * RAS node before any other RAS register r/w. + */ + ser_sys_select_record(idx_start + j); + + err_fr = read_erxfr_el1() & ERR_FR_EN_BITS_MASK; + uncorr_errs = aux_data[j].err_ctrl(); + corr_errs = ~uncorr_errs & err_fr; + + /* enable error reporting */ + ERR_CTLR_ENABLE_FIELD(err_ctrl, ED); + + /* enable SError reporting for uncorrectable errors */ + if ((uncorr_errs & err_fr) != 0ULL) { + ERR_CTLR_ENABLE_FIELD(err_ctrl, UE); + } + + /* generate interrupt for corrected errors. */ + if (corr_errs != 0ULL) { + ERR_CTLR_ENABLE_FIELD(err_ctrl, CFI); + } + + /* enable the supported errors */ + err_ctrl |= err_fr; + + VERBOSE("errselr_el1:0x%x, erxfr:0x%llx, err_ctrl:0x%llx\n", + idx_start + j, err_fr, err_ctrl); + + /* enable specified errors, or set to 0 if no supported error */ + write_erxctlr_el1(err_ctrl); + + /* + * Check if all the bit settings have been enabled to detect + * uncorrected/corrected errors, if not assert. + */ + assert(read_erxctlr_el1() == err_ctrl); + } + } +} + +/* + * Function to clear RAS ERR<n>STATUS for corrected RAS error. + * + * This function clears number of 'RAS_ERRORS_PER_CALL' RAS errors at most. + * 'cookie' - in/out cookie parameter to specify/store last visited RAS + * error record index. it is set to '0' to indicate no more RAS + * error record to clear. + */ +void tegra194_ras_corrected_err_clear(uint64_t *cookie) +{ + /* + * 'last_node' and 'last_idx' represent last visited RAS node index from + * previous function call. they are set to 0 when first smc call is made + * or all RAS error are visited by followed multipile smc calls. + */ + union prev_record { + struct record { + uint32_t last_node; + uint32_t last_idx; + } rec; + uint64_t value; + } prev; + + uint64_t clear_ce_status = 0ULL; + int32_t nerrs_per_call = RAS_ERRORS_PER_CALL; + uint32_t i; + + if (cookie == NULL) { + return; + } + + prev.value = *cookie; + + if ((prev.rec.last_node >= RAS_NODE_INDEX_MAX) || + (prev.rec.last_idx >= RAS_NODE_INDEX_MAX)) { + return; + } + + ERR_STATUS_SET_FIELD(clear_ce_status, AV, 0x1UL); + ERR_STATUS_SET_FIELD(clear_ce_status, V, 0x1UL); + ERR_STATUS_SET_FIELD(clear_ce_status, OF, 0x1UL); + ERR_STATUS_SET_FIELD(clear_ce_status, MV, 0x1UL); + ERR_STATUS_SET_FIELD(clear_ce_status, CE, 0x3UL); + + + for (i = prev.rec.last_node; i < err_record_mappings.num_err_records; i++) { + + const struct err_record_info *info = &err_record_mappings.err_records[i]; + uint32_t idx_start = info->sysreg.idx_start; + uint32_t num_idx = info->sysreg.num_idx; + + uint32_t j; + + j = (i == prev.rec.last_node && prev.value != 0UL) ? + (prev.rec.last_idx + 1U) : 0U; + + for (; j < num_idx; j++) { + + uint64_t status; + uint32_t err_idx = idx_start + j; + + if (err_idx >= RAS_NODE_INDEX_MAX) { + return; + } + + write_errselr_el1(err_idx); + status = read_erxstatus_el1(); + + if (ERR_STATUS_GET_FIELD(status, CE) != 0U) { + write_erxstatus_el1(clear_ce_status); + } + + --nerrs_per_call; + + /* only clear 'nerrs_per_call' errors each time. */ + if (nerrs_per_call <= 0) { + prev.rec.last_idx = j; + prev.rec.last_node = i; + /* save last visited error record index + * into cookie. + */ + *cookie = prev.value; + + return; + } + } + } + + /* + * finish if all ras error records are checked or provided index is out + * of range. + */ + *cookie = 0ULL; + return; +} + +/* Function to probe an error from error record group. */ +static int32_t tegra194_ras_record_probe(const struct err_record_info *info, + int *probe_data) +{ + /* Skip probing if not a silicon platform */ + if (!tegra_platform_is_silicon()) { + return 0; + } + + return ser_probe_sysreg(info->sysreg.idx_start, info->sysreg.num_idx, probe_data); +} + +/* Function to handle error from one given node */ +static int32_t tegra194_ras_node_handler(uint32_t errselr, const char *name, + const struct ras_error *errors, uint64_t status) +{ + bool found = false; + uint32_t ierr = (uint32_t)ERR_STATUS_GET_FIELD(status, IERR); + uint32_t serr = (uint32_t)ERR_STATUS_GET_FIELD(status, SERR); + uint64_t val = 0; + + /* not a valid error. */ + if (ERR_STATUS_GET_FIELD(status, V) == 0U) { + return 0; + } + + ERR_STATUS_SET_FIELD(val, V, 1); + + /* keep the log print same as linux arm64_ras driver. */ + ERROR("**************************************\n"); + ERROR("RAS Error in %s, ERRSELR_EL1=0x%x:\n", name, errselr); + ERROR("\tStatus = 0x%llx\n", status); + + /* Print uncorrectable errror information. */ + if (ERR_STATUS_GET_FIELD(status, UE) != 0U) { + + ERR_STATUS_SET_FIELD(val, UE, 1); + ERR_STATUS_SET_FIELD(val, UET, 1); + + /* IERR to error message */ + for (uint32_t i = 0; errors[i].error_msg != NULL; i++) { + if (ierr == errors[i].error_code) { + ERROR("\tIERR = %s: 0x%x\n", + errors[i].error_msg, ierr); + + found = true; + break; + } + } + + if (!found) { + ERROR("\tUnknown IERR: 0x%x\n", ierr); + } + + ERROR("SERR = %s: 0x%x\n", ras_serr_to_str(serr), serr); + + /* Overflow, multiple errors have been detected. */ + if (ERR_STATUS_GET_FIELD(status, OF) != 0U) { + ERROR("\tOverflow (there may be more errors) - " + "Uncorrectable\n"); + ERR_STATUS_SET_FIELD(val, OF, 1); + } + + ERROR("\tUncorrectable (this is fatal)\n"); + + /* Miscellaneous Register Valid. */ + if (ERR_STATUS_GET_FIELD(status, MV) != 0U) { + ERROR("\tMISC0 = 0x%lx\n", read_erxmisc0_el1()); + ERROR("\tMISC1 = 0x%lx\n", read_erxmisc1_el1()); + ERR_STATUS_SET_FIELD(val, MV, 1); + } + + /* Address Valid. */ + if (ERR_STATUS_GET_FIELD(status, AV) != 0U) { + ERROR("\tADDR = 0x%lx\n", read_erxaddr_el1()); + ERR_STATUS_SET_FIELD(val, AV, 1); + } + + /* Deferred error */ + if (ERR_STATUS_GET_FIELD(status, DE) != 0U) { + ERROR("\tDeferred error\n"); + ERR_STATUS_SET_FIELD(val, DE, 1); + } + + } else { + /* For corrected error, simply clear it. */ + VERBOSE("corrected RAS error is cleared: ERRSELR_EL1:0x%x, " + "IERR:0x%x, SERR:0x%x\n", errselr, ierr, serr); + ERR_STATUS_SET_FIELD(val, CE, 1); + } + + ERROR("**************************************\n"); + + /* Write to clear reported errors. */ + write_erxstatus_el1(val); + + /* error handled */ + return 0; +} + +/* Function to handle one error node from an error record group. */ +static int32_t tegra194_ras_record_handler(const struct err_record_info *info, + int probe_data, const struct err_handler_data *const data __unused) +{ + uint32_t num_idx = info->sysreg.num_idx; + uint32_t idx_start = info->sysreg.idx_start; + const struct ras_aux_data *aux_data = info->aux_data; + const struct ras_error *errors; + uint32_t offset; + const char *node_name; + + uint64_t status = 0ULL; + + VERBOSE("%s\n", __func__); + + assert(probe_data >= 0); + assert((uint32_t)probe_data < num_idx); + + offset = (uint32_t)probe_data; + errors = aux_data[offset].error_records; + node_name = aux_data[offset].name; + + assert(errors != NULL); + + /* Write to ERRSELR_EL1 to select the error record */ + ser_sys_select_record(idx_start + offset); + + /* Retrieve status register from the error record */ + status = read_erxstatus_el1(); + + return tegra194_ras_node_handler(idx_start + offset, node_name, + errors, status); +} + + +/* Instantiate RAS nodes */ +PER_CORE_RAS_NODE_LIST(DEFINE_ONE_RAS_NODE) +PER_CLUSTER_RAS_NODE_LIST(DEFINE_ONE_RAS_NODE) +SCF_L3_BANK_RAS_NODE_LIST(DEFINE_ONE_RAS_NODE) +CCPLEX_RAS_NODE_LIST(DEFINE_ONE_RAS_NODE) + +/* Instantiate RAS node groups */ +static struct ras_aux_data per_core_ras_group[] = { + PER_CORE_RAS_GROUP_NODES +}; +CASSERT(ARRAY_SIZE(per_core_ras_group) < RAS_NODE_INDEX_MAX, + assert_max_per_core_ras_group_size); + +static struct ras_aux_data per_cluster_ras_group[] = { + PER_CLUSTER_RAS_GROUP_NODES +}; +CASSERT(ARRAY_SIZE(per_cluster_ras_group) < RAS_NODE_INDEX_MAX, + assert_max_per_cluster_ras_group_size); + +static struct ras_aux_data scf_l3_ras_group[] = { + SCF_L3_BANK_RAS_GROUP_NODES +}; +CASSERT(ARRAY_SIZE(scf_l3_ras_group) < RAS_NODE_INDEX_MAX, + assert_max_scf_l3_ras_group_size); + +static struct ras_aux_data ccplex_ras_group[] = { + CCPLEX_RAS_GROUP_NODES +}; +CASSERT(ARRAY_SIZE(ccplex_ras_group) < RAS_NODE_INDEX_MAX, + assert_max_ccplex_ras_group_size); + +/* + * We have same probe and handler for each error record group, use a macro to + * simply the record definition. + */ +#define ADD_ONE_ERR_GROUP(errselr_start, group) \ + ERR_RECORD_SYSREG_V1((errselr_start), (uint32_t)ARRAY_SIZE((group)), \ + &tegra194_ras_record_probe, \ + &tegra194_ras_record_handler, (group)) + +/* RAS error record group information */ +static struct err_record_info carmel_ras_records[] = { + /* + * Per core ras error records + * ERRSELR starts from 0*256 + Logical_CPU_ID*16 + 0 to + * 0*256 + Logical_CPU_ID*16 + 5 for each group. + * 8 cores/groups, 6 * 8 nodes in total. + */ + ADD_ONE_ERR_GROUP(0x000, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x010, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x020, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x030, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x040, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x050, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x060, per_core_ras_group), + ADD_ONE_ERR_GROUP(0x070, per_core_ras_group), + + /* + * Per cluster ras error records + * ERRSELR starts from 2*256 + Logical_Cluster_ID*16 + 0 to + * 2*256 + Logical_Cluster_ID*16 + 3. + * 4 clusters/groups, 3 * 4 nodes in total. + */ + ADD_ONE_ERR_GROUP(0x200, per_cluster_ras_group), + ADD_ONE_ERR_GROUP(0x210, per_cluster_ras_group), + ADD_ONE_ERR_GROUP(0x220, per_cluster_ras_group), + ADD_ONE_ERR_GROUP(0x230, per_cluster_ras_group), + + /* + * SCF L3_Bank ras error records + * ERRSELR: 3*256 + L3_Bank_ID, L3_Bank_ID: 0-3 + * 1 groups, 4 nodes in total. + */ + ADD_ONE_ERR_GROUP(0x300, scf_l3_ras_group), + + /* + * CCPLEX ras error records + * ERRSELR: 4*256 + Unit_ID, Unit_ID: 0 - 4 + * 1 groups, 5 nodes in total. + */ + ADD_ONE_ERR_GROUP(0x400, ccplex_ras_group), +}; + +CASSERT(ARRAY_SIZE(carmel_ras_records) < RAS_NODE_INDEX_MAX, + assert_max_carmel_ras_records_size); + +REGISTER_ERR_RECORD_INFO(carmel_ras_records); + +/* dummy RAS interrupt */ +static struct ras_interrupt carmel_ras_interrupts[] = {}; +REGISTER_RAS_INTERRUPTS(carmel_ras_interrupts); + +/******************************************************************************* + * RAS handler for the platform + ******************************************************************************/ +void plat_ea_handler(unsigned int ea_reason, uint64_t syndrome, void *cookie, + void *handle, uint64_t flags) +{ +#if RAS_EXTENSION + tegra194_ea_handler(ea_reason, syndrome, cookie, handle, flags); +#else + ERROR("Unhandled External Abort received on 0x%llx at EL3!\n", + read_mpidr_el1()); + ERROR(" exception reason=%u syndrome=0x%lx\n", ea_reason, syndrome); + panic(); +#endif +} diff --git a/plat/nvidia/tegra/soc/t194/plat_secondary.c b/plat/nvidia/tegra/soc/t194/plat_secondary.c index c397c91ba..1cb14add0 100644 --- a/plat/nvidia/tegra/soc/t194/plat_secondary.c +++ b/plat/nvidia/tegra/soc/t194/plat_secondary.c @@ -1,18 +1,23 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ +#include <assert.h> +#include <string.h> + #include <arch_helpers.h> #include <common/debug.h> #include <lib/mmio.h> + #include <mce.h> -#include <string.h> #include <tegra194_private.h> #include <tegra_def.h> #include <tegra_private.h> +extern uint64_t tegra_bl31_phys_base; + #define MISCREG_AA64_RST_LOW 0x2004U #define MISCREG_AA64_RST_HIGH 0x2008U @@ -25,10 +30,14 @@ void plat_secondary_setup(void) { uint32_t addr_low, addr_high; plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); - uint64_t cpu_reset_handler_base, cpu_reset_handler_size; + uint64_t cpu_reset_handler_base, cpu_reset_handler_size, tzdram_addr; + uint64_t src_len_bytes = BL_END - tegra_bl31_phys_base; INFO("Setting up secondary CPU boot\n"); + tzdram_addr = params_from_bl2->tzdram_base + + tegra194_get_cpu_reset_handler_size(); + /* * The BL31 code resides in the TZSRAM which loses state * when we enter System Suspend. Copy the wakeup trampoline @@ -46,11 +55,21 @@ void plat_secondary_setup(void) /* write lower 32 bits first, then the upper 11 bits */ mmio_write_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_LOW, addr_low); + assert(mmio_read_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_LOW) == addr_low); mmio_write_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_HIGH, addr_high); + assert(mmio_read_32(TEGRA_MISC_BASE + MISCREG_AA64_RST_HIGH) == addr_high); /* save reset vector to be used during SYSTEM_SUSPEND exit */ mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_LO, addr_low); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_LO) == addr_low); mmio_write_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_HI, addr_high); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SCRATCH_RESET_VECTOR_HI) == addr_high); + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV72_LO, + (uint32_t)tzdram_addr); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV72_LO) == (uint32_t)tzdram_addr); + mmio_write_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV72_HI, + (uint32_t)src_len_bytes); + assert(mmio_read_32(TEGRA_SCRATCH_BASE + SECURE_SCRATCH_RSV72_HI) == (uint32_t)src_len_bytes); } diff --git a/plat/nvidia/tegra/soc/t194/plat_setup.c b/plat/nvidia/tegra/soc/t194/plat_setup.c index 912dcc6f9..8f7d1e9a1 100644 --- a/plat/nvidia/tegra/soc/t194/plat_setup.c +++ b/plat/nvidia/tegra/soc/t194/plat_setup.c @@ -20,10 +20,11 @@ #include <bl31/interrupt_mgmt.h> #include <mce.h> #include <mce_private.h> +#include <memctrl.h> #include <plat/common/platform.h> +#include <smmu.h> #include <spe.h> #include <tegra_def.h> -#include <tegra_mc_def.h> #include <tegra_platform.h> #include <tegra_private.h> #include <lib/xlat_tables/xlat_tables_v2.h> @@ -32,6 +33,27 @@ #define TEGRA_CONSOLE_SPE_ID 0xFE /******************************************************************************* + * Structure to store the SCR addresses and its expected settings. + ******************************************************************************* + */ +typedef struct { + uint32_t scr_addr; + uint32_t scr_val; +} scr_settings_t; + +static const scr_settings_t t194_scr_settings[] = { + { SCRATCH_RSV68_SCR, SCRATCH_RSV68_SCR_VAL }, + { SCRATCH_RSV71_SCR, SCRATCH_RSV71_SCR_VAL }, + { SCRATCH_RSV72_SCR, SCRATCH_RSV72_SCR_VAL }, + { SCRATCH_RSV75_SCR, SCRATCH_RSV75_SCR_VAL }, + { SCRATCH_RSV81_SCR, SCRATCH_RSV81_SCR_VAL }, + { SCRATCH_RSV97_SCR, SCRATCH_RSV97_SCR_VAL }, + { SCRATCH_RSV99_SCR, SCRATCH_RSV99_SCR_VAL }, + { SCRATCH_RSV109_SCR, SCRATCH_RSV109_SCR_VAL }, + { MISCREG_SCR_SCRTZWELCK, MISCREG_SCR_SCRTZWELCK_VAL } +}; + +/******************************************************************************* * The Tegra power domain tree has a single system level power domain i.e. a * single root node. The first entry in the power domain descriptor specifies * the number of power domains at the highest power level. @@ -66,8 +88,6 @@ const uint8_t *plat_get_power_domain_tree_desc(void) static const mmap_region_t tegra_mmap[] = { MAP_REGION_FLAT(TEGRA_MISC_BASE, 0x4000U, /* 16KB */ (uint8_t)MT_DEVICE | (uint8_t)MT_RW | (uint8_t)MT_SECURE), - MAP_REGION_FLAT(TEGRA_TSA_BASE, 0x20000U, /* 128KB */ - (uint8_t)MT_DEVICE | (uint8_t)MT_RW | (uint8_t)MT_SECURE), MAP_REGION_FLAT(TEGRA_GPCDMA_BASE, 0x10000U, /* 64KB */ (uint8_t)MT_DEVICE | (uint8_t)MT_RW | (uint8_t)MT_SECURE), MAP_REGION_FLAT(TEGRA_MC_STREAMID_BASE, 0x8000U, /* 32KB */ @@ -163,18 +183,18 @@ void plat_enable_console(int32_t id) uint32_t console_clock = 0U; #if ENABLE_CONSOLE_SPE - static console_spe_t spe_console; + static console_t spe_console; if (id == TEGRA_CONSOLE_SPE_ID) { (void)console_spe_register(TEGRA_CONSOLE_SPE_BASE, console_clock, TEGRA_CONSOLE_BAUDRATE, &spe_console); - console_set_scope(&spe_console.console, CONSOLE_FLAG_BOOT | + console_set_scope(&spe_console, CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH); } #else - static console_16550_t uart_console; + static console_t uart_console; if ((id > 0) && (id < TEGRA194_MAX_UART_PORTS)) { /* @@ -190,20 +210,55 @@ void plat_enable_console(int32_t id) console_clock, TEGRA_CONSOLE_BAUDRATE, &uart_console); - console_set_scope(&uart_console.console, CONSOLE_FLAG_BOOT | + console_set_scope(&uart_console, CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH); } #endif } /******************************************************************************* + * Verify SCR settings + ******************************************************************************/ +static inline bool tegra194_is_scr_valid(void) +{ + uint32_t scr_val; + bool ret = true; + + for (uint8_t i = 0U; i < ARRAY_SIZE(t194_scr_settings); i++) { + scr_val = mmio_read_32((uintptr_t)t194_scr_settings[i].scr_addr); + if (scr_val != t194_scr_settings[i].scr_val) { + ERROR("Mismatch at SCR addr = 0x%x\n", t194_scr_settings[i].scr_addr); + ret = false; + } + } + return ret; +} + +/******************************************************************************* * Handler for early platform setup ******************************************************************************/ void plat_early_platform_setup(void) { + const plat_params_from_bl2_t *params_from_bl2 = bl31_get_plat_params(); + uint8_t enable_ccplex_lock_step = params_from_bl2->enable_ccplex_lock_step; + uint64_t actlr_elx; + + /* Verify chip id is t194 */ + assert(tegra_chipid_is_t194()); + + /* Verify SCR settings */ + if (tegra_platform_is_silicon()) { + assert(tegra194_is_scr_valid()); + } + /* sanity check MCE firmware compatibility */ mce_verify_firmware_version(); +#if RAS_EXTENSION + /* Enable Uncorrectable RAS error */ + tegra194_ras_enable(); +#endif + /* * Program XUSB STREAMIDs * ====================== @@ -239,24 +294,59 @@ void plat_early_platform_setup(void) mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_PF_0, TEGRA_SID_XUSB_HOST); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_PF_0) == TEGRA_SID_XUSB_HOST); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_0, TEGRA_SID_XUSB_VF0); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_0) == TEGRA_SID_XUSB_VF0); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_1, TEGRA_SID_XUSB_VF1); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_1) == TEGRA_SID_XUSB_VF1); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_2, TEGRA_SID_XUSB_VF2); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_2) == TEGRA_SID_XUSB_VF2); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_HOST_AXI_STREAMID_VF_3, TEGRA_SID_XUSB_VF3); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_HOST_AXI_STREAMID_VF_3) == TEGRA_SID_XUSB_VF3); mmio_write_32(TEGRA_XUSB_PADCTL_BASE + XUSB_PADCTL_DEV_AXI_STREAMID_PF_0, TEGRA_SID_XUSB_DEV); + assert(mmio_read_32(TEGRA_XUSB_PADCTL_BASE + + XUSB_PADCTL_DEV_AXI_STREAMID_PF_0) == TEGRA_SID_XUSB_DEV); + } + + /* + * Enable dual execution optimized translations for all ELx. + */ + if (enable_ccplex_lock_step != 0U) { + actlr_elx = read_actlr_el3(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL3; + write_actlr_el3(actlr_elx); + /* check if the bit is actually set */ + assert((read_actlr_el3() & DENVER_CPU_ENABLE_DUAL_EXEC_EL3) != 0ULL); + + actlr_elx = read_actlr_el2(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL2; + write_actlr_el2(actlr_elx); + /* check if the bit is actually set */ + assert((read_actlr_el2() & DENVER_CPU_ENABLE_DUAL_EXEC_EL2) != 0ULL); + + actlr_elx = read_actlr_el1(); + actlr_elx |= DENVER_CPU_ENABLE_DUAL_EXEC_EL1; + write_actlr_el1(actlr_elx); + /* check if the bit is actually set */ + assert((read_actlr_el1() & DENVER_CPU_ENABLE_DUAL_EXEC_EL1) != 0ULL); } } /* Secure IRQs for Tegra194 */ static const interrupt_prop_t tegra194_interrupt_props[] = { - INTR_PROP_DESC(TEGRA194_TOP_WDT_IRQ, GIC_HIGHEST_SEC_PRIORITY, + INTR_PROP_DESC(TEGRA_SDEI_SGI_PRIVATE, PLAT_SDEI_CRITICAL_PRI, GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), - INTR_PROP_DESC(TEGRA194_AON_WDT_IRQ, GIC_HIGHEST_SEC_PRIORITY, + INTR_PROP_DESC(TEGRA194_TOP_WDT_IRQ, PLAT_TEGRA_WDT_PRIO, GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE) }; @@ -304,6 +394,9 @@ plat_params_from_bl2_t *plat_get_bl31_plat_params(void) return (plat_params_from_bl2_t *)(uintptr_t)val; } +/******************************************************************************* + * Handler for late platform setup + ******************************************************************************/ void plat_late_platform_setup(void) { #if ENABLE_STRICT_CHECKING_MODE @@ -312,5 +405,45 @@ void plat_late_platform_setup(void) * enabling TZSRAM and TZDRAM */ mce_enable_strict_checking(); + mce_verify_strict_checking(); #endif } + +/******************************************************************************* + * Handler to indicate support for System Suspend + ******************************************************************************/ +bool plat_supports_system_suspend(void) +{ + return true; +} + +/******************************************************************************* + * Platform specific runtime setup. + ******************************************************************************/ +void plat_runtime_setup(void) +{ + /* + * During cold boot, it is observed that the arbitration + * bit is set in the Memory controller leading to false + * error interrupts in the non-secure world. To avoid + * this, clean the interrupt status register before + * booting into the non-secure world + */ + tegra_memctrl_clear_pending_interrupts(); + + /* + * During boot, USB3 and flash media (SDMMC/SATA) devices need + * access to IRAM. Because these clients connect to the MC and + * do not have a direct path to the IRAM, the MC implements AHB + * redirection during boot to allow path to IRAM. In this mode + * accesses to a programmed memory address aperture are directed + * to the AHB bus, allowing access to the IRAM. This mode must be + * disabled before we jump to the non-secure world. + */ + tegra_memctrl_disable_ahb_redirection(); + + /* + * Verify the integrity of the previously configured SMMU(s) settings + */ + tegra_smmu_verify(); +} diff --git a/plat/nvidia/tegra/soc/t194/plat_sip_calls.c b/plat/nvidia/tegra/soc/t194/plat_sip_calls.c index 8873358cd..1eef55912 100644 --- a/plat/nvidia/tegra/soc/t194/plat_sip_calls.c +++ b/plat/nvidia/tegra/soc/t194/plat_sip_calls.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2019-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -12,18 +12,19 @@ #include <common/debug.h> #include <errno.h> #include <mce.h> +#include <mce_private.h> #include <memctrl.h> #include <common/runtime_svc.h> #include <tegra_private.h> #include <tegra_platform.h> +#include <smmu.h> #include <stdbool.h> -extern bool tegra_fake_system_suspend; - /******************************************************************************* * Tegra194 SiP SMCs ******************************************************************************/ -#define TEGRA_SIP_ENABLE_FAKE_SYSTEM_SUSPEND 0xC2FFFE03U +#define TEGRA_SIP_GET_SMMU_PER 0xC200FF00U +#define TEGRA_SIP_CLEAR_RAS_CORRECTED_ERRORS 0xC200FF01U /******************************************************************************* * This function is responsible for handling all T194 SiP calls @@ -37,26 +38,65 @@ int32_t plat_sip_handler(uint32_t smc_fid, void *handle, uint64_t flags) { - int32_t ret = -ENOTSUP; + int32_t ret = 0; + uint32_t i, smmu_per[6] = {0}; + uint32_t num_smmu_devices = plat_get_num_smmu_devices(); + uint64_t per[3] = {0ULL}; (void)x1; (void)x4; (void)cookie; (void)flags; - if (smc_fid == TEGRA_SIP_ENABLE_FAKE_SYSTEM_SUSPEND) { + switch (smc_fid) { + case TEGRA_SIP_GET_SMMU_PER: + + /* make sure we dont go past the array length */ + assert(num_smmu_devices <= ARRAY_SIZE(smmu_per)); + + /* read all supported SMMU_PER records */ + for (i = 0U; i < num_smmu_devices; i++) { + smmu_per[i] = tegra_smmu_read_32(i, SMMU_GSR0_PER); + } + + /* pack results into 3 64bit variables. */ + per[0] = smmu_per[0] | ((uint64_t)smmu_per[1] << 32U); + per[1] = smmu_per[2] | ((uint64_t)smmu_per[3] << 32U); + per[2] = smmu_per[4] | ((uint64_t)smmu_per[5] << 32U); + + /* provide the results via X1-X3 CPU registers */ + write_ctx_reg(get_gpregs_ctx(handle), CTX_GPREG_X1, per[0]); + write_ctx_reg(get_gpregs_ctx(handle), CTX_GPREG_X2, per[1]); + write_ctx_reg(get_gpregs_ctx(handle), CTX_GPREG_X3, per[2]); + + break; + +#if RAS_EXTENSION + case TEGRA_SIP_CLEAR_RAS_CORRECTED_ERRORS: + { /* - * System suspend mode is set if the platform ATF is - * running on VDK and there is a debug SIP call. This mode - * ensures that the debug path is exercised, instead of - * regular code path to suit the pre-silicon platform needs. - * This includes replacing the call to WFI, with calls to - * system suspend exit procedures. - */ - if (tegra_platform_is_virt_dev_kit()) { - tegra_fake_system_suspend = true; - ret = 0; + * clear all RAS error records for corrected errors at first. + * x1 shall be 0 for first SMC call after FHI is asserted. + * */ + uint64_t local_x1 = x1; + + tegra194_ras_corrected_err_clear(&local_x1); + if (local_x1 == 0ULL) { + /* clear HSM corrected error status after all corrected + * RAS errors are cleared. + */ + mce_clear_hsm_corr_status(); } + + write_ctx_reg(get_gpregs_ctx(handle), CTX_GPREG_X1, local_x1); + + break; + } +#endif + + default: + ret = -ENOTSUP; + break; } return ret; diff --git a/plat/nvidia/tegra/soc/t194/plat_smmu.c b/plat/nvidia/tegra/soc/t194/plat_smmu.c index 3b4a3803c..310e95104 100644 --- a/plat/nvidia/tegra/soc/t194/plat_smmu.c +++ b/plat/nvidia/tegra/soc/t194/plat_smmu.c @@ -8,7 +8,6 @@ #include <common/debug.h> #include <smmu.h> #include <tegra_def.h> -#include <tegra_mc_def.h> #define BOARD_SYSTEM_FPGA_BASE U(1) #define BASE_CONFIG_SMMU_DEVICES U(2) @@ -20,276 +19,6 @@ static uint32_t tegra_misc_read_32(uint32_t off) } /******************************************************************************* - * Array to hold SMMU context for Tegra194 - ******************************************************************************/ -static __attribute__((aligned(16))) smmu_regs_t tegra194_smmu_context[] = { - _START_OF_TABLE_, - mc_make_sid_security_cfg(HDAR), - mc_make_sid_security_cfg(HOST1XDMAR), - mc_make_sid_security_cfg(NVENCSRD), - mc_make_sid_security_cfg(SATAR), - mc_make_sid_security_cfg(NVENCSWR), - mc_make_sid_security_cfg(HDAW), - mc_make_sid_security_cfg(SATAW), - mc_make_sid_security_cfg(ISPRA), - mc_make_sid_security_cfg(ISPFALR), - mc_make_sid_security_cfg(ISPWA), - mc_make_sid_security_cfg(ISPWB), - mc_make_sid_security_cfg(XUSB_HOSTR), - mc_make_sid_security_cfg(XUSB_HOSTW), - mc_make_sid_security_cfg(XUSB_DEVR), - mc_make_sid_security_cfg(XUSB_DEVW), - mc_make_sid_security_cfg(TSECSRD), - mc_make_sid_security_cfg(TSECSWR), - mc_make_sid_security_cfg(SDMMCRA), - mc_make_sid_security_cfg(SDMMCR), - mc_make_sid_security_cfg(SDMMCRAB), - mc_make_sid_security_cfg(SDMMCWA), - mc_make_sid_security_cfg(SDMMCW), - mc_make_sid_security_cfg(SDMMCWAB), - mc_make_sid_security_cfg(VICSRD), - mc_make_sid_security_cfg(VICSWR), - mc_make_sid_security_cfg(VIW), - mc_make_sid_security_cfg(NVDECSRD), - mc_make_sid_security_cfg(NVDECSWR), - mc_make_sid_security_cfg(APER), - mc_make_sid_security_cfg(APEW), - mc_make_sid_security_cfg(NVJPGSRD), - mc_make_sid_security_cfg(NVJPGSWR), - mc_make_sid_security_cfg(SESRD), - mc_make_sid_security_cfg(SESWR), - mc_make_sid_security_cfg(AXIAPR), - mc_make_sid_security_cfg(AXIAPW), - mc_make_sid_security_cfg(ETRR), - mc_make_sid_security_cfg(ETRW), - mc_make_sid_security_cfg(TSECSRDB), - mc_make_sid_security_cfg(TSECSWRB), - mc_make_sid_security_cfg(AXISR), - mc_make_sid_security_cfg(AXISW), - mc_make_sid_security_cfg(EQOSR), - mc_make_sid_security_cfg(EQOSW), - mc_make_sid_security_cfg(UFSHCR), - mc_make_sid_security_cfg(UFSHCW), - mc_make_sid_security_cfg(NVDISPLAYR), - mc_make_sid_security_cfg(BPMPR), - mc_make_sid_security_cfg(BPMPW), - mc_make_sid_security_cfg(BPMPDMAR), - mc_make_sid_security_cfg(BPMPDMAW), - mc_make_sid_security_cfg(AONR), - mc_make_sid_security_cfg(AONW), - mc_make_sid_security_cfg(AONDMAR), - mc_make_sid_security_cfg(AONDMAW), - mc_make_sid_security_cfg(SCER), - mc_make_sid_security_cfg(SCEW), - mc_make_sid_security_cfg(SCEDMAR), - mc_make_sid_security_cfg(SCEDMAW), - mc_make_sid_security_cfg(APEDMAR), - mc_make_sid_security_cfg(APEDMAW), - mc_make_sid_security_cfg(NVDISPLAYR1), - mc_make_sid_security_cfg(VICSRD1), - mc_make_sid_security_cfg(NVDECSRD1), - mc_make_sid_security_cfg(VIFALR), - mc_make_sid_security_cfg(VIFALW), - mc_make_sid_security_cfg(DLA0RDA), - mc_make_sid_security_cfg(DLA0FALRDB), - mc_make_sid_security_cfg(DLA0WRA), - mc_make_sid_security_cfg(DLA0FALWRB), - mc_make_sid_security_cfg(DLA1RDA), - mc_make_sid_security_cfg(DLA1FALRDB), - mc_make_sid_security_cfg(DLA1WRA), - mc_make_sid_security_cfg(DLA1FALWRB), - mc_make_sid_security_cfg(PVA0RDA), - mc_make_sid_security_cfg(PVA0RDB), - mc_make_sid_security_cfg(PVA0RDC), - mc_make_sid_security_cfg(PVA0WRA), - mc_make_sid_security_cfg(PVA0WRB), - mc_make_sid_security_cfg(PVA0WRC), - mc_make_sid_security_cfg(PVA1RDA), - mc_make_sid_security_cfg(PVA1RDB), - mc_make_sid_security_cfg(PVA1RDC), - mc_make_sid_security_cfg(PVA1WRA), - mc_make_sid_security_cfg(PVA1WRB), - mc_make_sid_security_cfg(PVA1WRC), - mc_make_sid_security_cfg(RCER), - mc_make_sid_security_cfg(RCEW), - mc_make_sid_security_cfg(RCEDMAR), - mc_make_sid_security_cfg(RCEDMAW), - mc_make_sid_security_cfg(NVENC1SRD), - mc_make_sid_security_cfg(NVENC1SWR), - mc_make_sid_security_cfg(PCIE0R), - mc_make_sid_security_cfg(PCIE0W), - mc_make_sid_security_cfg(PCIE1R), - mc_make_sid_security_cfg(PCIE1W), - mc_make_sid_security_cfg(PCIE2AR), - mc_make_sid_security_cfg(PCIE2AW), - mc_make_sid_security_cfg(PCIE3R), - mc_make_sid_security_cfg(PCIE3W), - mc_make_sid_security_cfg(PCIE4R), - mc_make_sid_security_cfg(PCIE4W), - mc_make_sid_security_cfg(PCIE5R), - mc_make_sid_security_cfg(PCIE5W), - mc_make_sid_security_cfg(ISPFALW), - mc_make_sid_security_cfg(DLA0RDA1), - mc_make_sid_security_cfg(DLA1RDA1), - mc_make_sid_security_cfg(PVA0RDA1), - mc_make_sid_security_cfg(PVA0RDB1), - mc_make_sid_security_cfg(PVA1RDA1), - mc_make_sid_security_cfg(PVA1RDB1), - mc_make_sid_security_cfg(PCIE5R1), - mc_make_sid_security_cfg(NVENCSRD1), - mc_make_sid_security_cfg(NVENC1SRD1), - mc_make_sid_security_cfg(ISPRA1), - mc_make_sid_security_cfg(PCIE0R1), - mc_make_sid_security_cfg(MIU0R), - mc_make_sid_security_cfg(MIU0W), - mc_make_sid_security_cfg(MIU1R), - mc_make_sid_security_cfg(MIU1W), - mc_make_sid_security_cfg(MIU2R), - mc_make_sid_security_cfg(MIU2W), - mc_make_sid_security_cfg(MIU3R), - mc_make_sid_security_cfg(MIU3W), - mc_make_sid_override_cfg(HDAR), - mc_make_sid_override_cfg(HOST1XDMAR), - mc_make_sid_override_cfg(NVENCSRD), - mc_make_sid_override_cfg(SATAR), - mc_make_sid_override_cfg(NVENCSWR), - mc_make_sid_override_cfg(HDAW), - mc_make_sid_override_cfg(SATAW), - mc_make_sid_override_cfg(ISPRA), - mc_make_sid_override_cfg(ISPFALR), - mc_make_sid_override_cfg(ISPWA), - mc_make_sid_override_cfg(ISPWB), - mc_make_sid_override_cfg(XUSB_HOSTR), - mc_make_sid_override_cfg(XUSB_HOSTW), - mc_make_sid_override_cfg(XUSB_DEVR), - mc_make_sid_override_cfg(XUSB_DEVW), - mc_make_sid_override_cfg(TSECSRD), - mc_make_sid_override_cfg(TSECSWR), - mc_make_sid_override_cfg(SDMMCRA), - mc_make_sid_override_cfg(SDMMCR), - mc_make_sid_override_cfg(SDMMCRAB), - mc_make_sid_override_cfg(SDMMCWA), - mc_make_sid_override_cfg(SDMMCW), - mc_make_sid_override_cfg(SDMMCWAB), - mc_make_sid_override_cfg(VICSRD), - mc_make_sid_override_cfg(VICSWR), - mc_make_sid_override_cfg(VIW), - mc_make_sid_override_cfg(NVDECSRD), - mc_make_sid_override_cfg(NVDECSWR), - mc_make_sid_override_cfg(APER), - mc_make_sid_override_cfg(APEW), - mc_make_sid_override_cfg(NVJPGSRD), - mc_make_sid_override_cfg(NVJPGSWR), - mc_make_sid_override_cfg(SESRD), - mc_make_sid_override_cfg(SESWR), - mc_make_sid_override_cfg(AXIAPR), - mc_make_sid_override_cfg(AXIAPW), - mc_make_sid_override_cfg(ETRR), - mc_make_sid_override_cfg(ETRW), - mc_make_sid_override_cfg(TSECSRDB), - mc_make_sid_override_cfg(TSECSWRB), - mc_make_sid_override_cfg(AXISR), - mc_make_sid_override_cfg(AXISW), - mc_make_sid_override_cfg(EQOSR), - mc_make_sid_override_cfg(EQOSW), - mc_make_sid_override_cfg(UFSHCR), - mc_make_sid_override_cfg(UFSHCW), - mc_make_sid_override_cfg(NVDISPLAYR), - mc_make_sid_override_cfg(BPMPR), - mc_make_sid_override_cfg(BPMPW), - mc_make_sid_override_cfg(BPMPDMAR), - mc_make_sid_override_cfg(BPMPDMAW), - mc_make_sid_override_cfg(AONR), - mc_make_sid_override_cfg(AONW), - mc_make_sid_override_cfg(AONDMAR), - mc_make_sid_override_cfg(AONDMAW), - mc_make_sid_override_cfg(SCER), - mc_make_sid_override_cfg(SCEW), - mc_make_sid_override_cfg(SCEDMAR), - mc_make_sid_override_cfg(SCEDMAW), - mc_make_sid_override_cfg(APEDMAR), - mc_make_sid_override_cfg(APEDMAW), - mc_make_sid_override_cfg(NVDISPLAYR1), - mc_make_sid_override_cfg(VICSRD1), - mc_make_sid_override_cfg(NVDECSRD1), - mc_make_sid_override_cfg(VIFALR), - mc_make_sid_override_cfg(VIFALW), - mc_make_sid_override_cfg(DLA0RDA), - mc_make_sid_override_cfg(DLA0FALRDB), - mc_make_sid_override_cfg(DLA0WRA), - mc_make_sid_override_cfg(DLA0FALWRB), - mc_make_sid_override_cfg(DLA1RDA), - mc_make_sid_override_cfg(DLA1FALRDB), - mc_make_sid_override_cfg(DLA1WRA), - mc_make_sid_override_cfg(DLA1FALWRB), - mc_make_sid_override_cfg(PVA0RDA), - mc_make_sid_override_cfg(PVA0RDB), - mc_make_sid_override_cfg(PVA0RDC), - mc_make_sid_override_cfg(PVA0WRA), - mc_make_sid_override_cfg(PVA0WRB), - mc_make_sid_override_cfg(PVA0WRC), - mc_make_sid_override_cfg(PVA1RDA), - mc_make_sid_override_cfg(PVA1RDB), - mc_make_sid_override_cfg(PVA1RDC), - mc_make_sid_override_cfg(PVA1WRA), - mc_make_sid_override_cfg(PVA1WRB), - mc_make_sid_override_cfg(PVA1WRC), - mc_make_sid_override_cfg(RCER), - mc_make_sid_override_cfg(RCEW), - mc_make_sid_override_cfg(RCEDMAR), - mc_make_sid_override_cfg(RCEDMAW), - mc_make_sid_override_cfg(NVENC1SRD), - mc_make_sid_override_cfg(NVENC1SWR), - mc_make_sid_override_cfg(PCIE0R), - mc_make_sid_override_cfg(PCIE0W), - mc_make_sid_override_cfg(PCIE1R), - mc_make_sid_override_cfg(PCIE1W), - mc_make_sid_override_cfg(PCIE2AR), - mc_make_sid_override_cfg(PCIE2AW), - mc_make_sid_override_cfg(PCIE3R), - mc_make_sid_override_cfg(PCIE3W), - mc_make_sid_override_cfg(PCIE4R), - mc_make_sid_override_cfg(PCIE4W), - mc_make_sid_override_cfg(PCIE5R), - mc_make_sid_override_cfg(PCIE5W), - mc_make_sid_override_cfg(ISPFALW), - mc_make_sid_override_cfg(DLA0RDA1), - mc_make_sid_override_cfg(DLA1RDA1), - mc_make_sid_override_cfg(PVA0RDA1), - mc_make_sid_override_cfg(PVA0RDB1), - mc_make_sid_override_cfg(PVA1RDA1), - mc_make_sid_override_cfg(PVA1RDB1), - mc_make_sid_override_cfg(PCIE5R1), - mc_make_sid_override_cfg(NVENCSRD1), - mc_make_sid_override_cfg(NVENC1SRD1), - mc_make_sid_override_cfg(ISPRA1), - mc_make_sid_override_cfg(PCIE0R1), - mc_make_sid_override_cfg(MIU0R), - mc_make_sid_override_cfg(MIU0W), - mc_make_sid_override_cfg(MIU1R), - mc_make_sid_override_cfg(MIU1W), - mc_make_sid_override_cfg(MIU2R), - mc_make_sid_override_cfg(MIU2W), - mc_make_sid_override_cfg(MIU3R), - mc_make_sid_override_cfg(MIU3W), - smmu_make_cfg(TEGRA_SMMU0_BASE), - smmu_make_cfg(TEGRA_SMMU2_BASE), - smmu_bypass_cfg, /* TBU settings */ - _END_OF_TABLE_, -}; - -/******************************************************************************* - * Handler to return the pointer to the SMMU's context struct - ******************************************************************************/ -smmu_regs_t *plat_get_smmu_ctx(void) -{ - /* index of _END_OF_TABLE_ */ - tegra194_smmu_context[0].val = (uint32_t)ARRAY_SIZE(tegra194_smmu_context) - 1U; - - return tegra194_smmu_context; -} - -/******************************************************************************* * Handler to return the support SMMU devices number ******************************************************************************/ uint32_t plat_get_num_smmu_devices(void) diff --git a/plat/nvidia/tegra/soc/t194/plat_trampoline.S b/plat/nvidia/tegra/soc/t194/plat_trampoline.S index 540c2019c..0ff5407e3 100644 --- a/plat/nvidia/tegra/soc/t194/plat_trampoline.S +++ b/plat/nvidia/tegra/soc/t194/plat_trampoline.S @@ -12,7 +12,7 @@ #define TEGRA194_STATE_SYSTEM_SUSPEND 0x5C7 #define TEGRA194_STATE_SYSTEM_RESUME 0x600D -#define TEGRA194_SMMU_CTX_SIZE 0x80D +#define TEGRA194_MC_CTX_SIZE 0xFB .align 4 .globl tegra194_cpu_reset_handler @@ -58,6 +58,13 @@ m_loop1: subs x2, x2, #1 b.ne m_loop1 + /* + * Synchronization barriers to make sure that memory is flushed out + * before we start execution in SysRAM. + */ + dsb sy + isb + boot_cpu: adr x0, __tegra194_cpu_reset_handler_data ldr x0, [x0] @@ -69,8 +76,8 @@ endfunc tegra194_cpu_reset_handler * * 0x0000: secure world's entrypoint * 0x0008: BL31 size (RO + RW) - * 0x0010: SMMU context start - * 0x2490: SMMU context end + * 0x0010: MC context start + * 0x2490: MC context end */ .align 4 @@ -79,14 +86,13 @@ endfunc tegra194_cpu_reset_handler __tegra194_cpu_reset_handler_data: .quad tegra_secure_entrypoint .quad __BL31_END__ - BL31_BASE - .globl __tegra194_system_suspend_state __tegra194_system_suspend_state: .quad 0 .align 4 -__tegra194_smmu_context: - .rept TEGRA194_SMMU_CTX_SIZE +__tegra194_mc_context: + .rept TEGRA194_MC_CTX_SIZE .quad 0 .endr .size __tegra194_cpu_reset_handler_data, \ @@ -98,7 +104,7 @@ __tegra194_cpu_reset_handler_end: .globl tegra194_get_cpu_reset_handler_size .globl tegra194_get_cpu_reset_handler_base - .globl tegra194_get_smmu_ctx_offset + .globl tegra194_get_mc_ctx_offset .globl tegra194_set_system_suspend_entry /* return size of the CPU reset handler */ @@ -115,13 +121,13 @@ func tegra194_get_cpu_reset_handler_base ret endfunc tegra194_get_cpu_reset_handler_base -/* return the size of the SMMU context */ -func tegra194_get_smmu_ctx_offset - adr x0, __tegra194_smmu_context +/* return the size of the MC context */ +func tegra194_get_mc_ctx_offset + adr x0, __tegra194_mc_context adr x1, tegra194_cpu_reset_handler sub x0, x0, x1 ret -endfunc tegra194_get_smmu_ctx_offset +endfunc tegra194_get_mc_ctx_offset /* set system suspend state before SC7 entry */ func tegra194_set_system_suspend_entry diff --git a/plat/nvidia/tegra/soc/t194/platform_t194.mk b/plat/nvidia/tegra/soc/t194/platform_t194.mk index 78766fcbe..339375f83 100644 --- a/plat/nvidia/tegra/soc/t194/platform_t194.mk +++ b/plat/nvidia/tegra/soc/t194/platform_t194.mk @@ -24,28 +24,27 @@ COLD_BOOT_SINGLE_CPU := 1 TZDRAM_BASE := 0x40000000 $(eval $(call add_define,TZDRAM_BASE)) -PLATFORM_CLUSTER_COUNT := 4 -$(eval $(call add_define,PLATFORM_CLUSTER_COUNT)) - -PLATFORM_MAX_CPUS_PER_CLUSTER := 2 -$(eval $(call add_define,PLATFORM_MAX_CPUS_PER_CLUSTER)) - MAX_XLAT_TABLES := 25 $(eval $(call add_define,MAX_XLAT_TABLES)) MAX_MMAP_REGIONS := 30 $(eval $(call add_define,MAX_MMAP_REGIONS)) +# enable RAS handling +HANDLE_EA_EL3_FIRST := 1 +RAS_EXTENSION := 1 + # platform files -PLAT_INCLUDES += -I${SOC_DIR}/drivers/include +PLAT_INCLUDES += -Iplat/nvidia/tegra/include/t194 \ + -I${SOC_DIR}/drivers/include -BL31_SOURCES += drivers/ti/uart/aarch64/16550_console.S \ +BL31_SOURCES += ${TEGRA_GICv2_SOURCES} \ + drivers/ti/uart/aarch64/16550_console.S \ lib/cpus/aarch64/denver.S \ - ${COMMON_DIR}/drivers/bpmp_ipc/intf.c \ - ${COMMON_DIR}/drivers/bpmp_ipc/ivc.c \ - ${COMMON_DIR}/drivers/gpcdma/gpcdma.c \ - ${COMMON_DIR}/drivers/memctrl/memctrl_v2.c \ - ${COMMON_DIR}/drivers/smmu/smmu.c \ + ${TEGRA_DRIVERS}/bpmp_ipc/intf.c \ + ${TEGRA_DRIVERS}/bpmp_ipc/ivc.c \ + ${TEGRA_DRIVERS}/memctrl/memctrl_v2.c \ + ${TEGRA_DRIVERS}/smmu/smmu.c \ ${SOC_DIR}/drivers/mce/mce.c \ ${SOC_DIR}/drivers/mce/nvg.c \ ${SOC_DIR}/drivers/mce/aarch64/nvg_helpers.S \ @@ -58,6 +57,27 @@ BL31_SOURCES += drivers/ti/uart/aarch64/16550_console.S \ ${SOC_DIR}/plat_smmu.c \ ${SOC_DIR}/plat_trampoline.S +ifeq (${USE_GPC_DMA}, 1) +BL31_SOURCES += ${TEGRA_DRIVERS}/gpcdma/gpcdma.c +endif + ifeq (${ENABLE_CONSOLE_SPE},1) -BL31_SOURCES += ${COMMON_DIR}/drivers/spe/shared_console.S +BL31_SOURCES += ${TEGRA_DRIVERS}/spe/shared_console.S +endif + +# RAS sources +ifeq (${RAS_EXTENSION},1) +BL31_SOURCES += lib/extensions/ras/std_err_record.c \ + lib/extensions/ras/ras_common.c \ + ${SOC_DIR}/plat_ras.c +endif + +# SPM dispatcher +ifeq (${SPD},spmd) +# include device tree helper library +include lib/libfdt/libfdt.mk +# sources to support spmd +BL31_SOURCES += plat/common/plat_spmd_manifest.c \ + common/fdt_wrappers.c \ + ${LIBFDT_SRCS} endif diff --git a/plat/nvidia/tegra/soc/t210/drivers/se/se_private.h b/plat/nvidia/tegra/soc/t210/drivers/se/se_private.h index 352107d2c..c44b0fc46 100644 --- a/plat/nvidia/tegra/soc/t210/drivers/se/se_private.h +++ b/plat/nvidia/tegra/soc/t210/drivers/se/se_private.h @@ -1,6 +1,6 @@ /* * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved. - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -15,6 +15,9 @@ * PMC registers */ +/* SC7 context save scratch register for T210 */ +#define PMC_SCRATCH43_REG_OFFSET U(0x22C) + /* Secure scratch registers */ #define PMC_SECURE_SCRATCH4_OFFSET 0xC0U #define PMC_SECURE_SCRATCH5_OFFSET 0xC4U @@ -435,6 +438,7 @@ ((x) & ((0x1U) << SE_TZRAM_OP_REQ_SHIFT)) /* SE Interrupt */ +#define SE_INT_ENABLE_REG_OFFSET U(0xC) #define SE_INT_STATUS_REG_OFFSET 0x10U #define SE_INT_OP_DONE_SHIFT 4 #define SE_INT_OP_DONE_CLEAR \ diff --git a/plat/nvidia/tegra/soc/t210/drivers/se/security_engine.c b/plat/nvidia/tegra/soc/t210/drivers/se/security_engine.c index d5e049126..48608583d 100644 --- a/plat/nvidia/tegra/soc/t210/drivers/se/security_engine.c +++ b/plat/nvidia/tegra/soc/t210/drivers/se/security_engine.c @@ -1,6 +1,6 @@ /* * Copyright (c) 2017-2020, ARM Limited and Contributors. All rights reserved. - * Copyright (c) 2017, NVIDIA CORPORATION. All rights reserved. + * Copyright (c) 2017-2020, NVIDIA CORPORATION. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -20,8 +20,8 @@ * Constants and Macros ******************************************************************************/ -#define TIMEOUT_100MS 100U // Timeout in 100ms -#define RNG_AES_KEY_INDEX 1 +#define TIMEOUT_100MS 100U /* Timeout in 100ms */ +#define RNG_AES_KEY_INDEX 1 /******************************************************************************* * Data structure and global variables @@ -68,14 +68,12 @@ * #--------------------------------# */ -/* Known pattern data */ -static const uint32_t se_ctx_known_pattern_data[SE_CTX_KNOWN_PATTERN_SIZE_WORDS] = { +/* Known pattern data for T210 */ +static const uint8_t se_ctx_known_pattern_data[SE_CTX_KNOWN_PATTERN_SIZE] = { /* 128 bit AES block */ - 0x0C0D0E0F, - 0x08090A0B, - 0x04050607, - 0x00010203, -}; + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f + }; /* SE input and output linked list buffers */ static tegra_se_io_lst_t se1_src_ll_buf; @@ -85,6 +83,9 @@ static tegra_se_io_lst_t se1_dst_ll_buf; static tegra_se_io_lst_t se2_src_ll_buf; static tegra_se_io_lst_t se2_dst_ll_buf; +/* SE1 context buffer, 132 blocks */ +static __aligned(64) uint8_t se1_ctx_buf[SE_CTX_DRBG_BUFER_SIZE]; + /* SE1 security engine device handle */ static tegra_se_dev_t se_dev_1 = { .se_num = 1, @@ -97,10 +98,10 @@ static tegra_se_dev_t se_dev_1 = { /* Setup DST buffers for SE operations */ .dst_ll_buf = &se1_dst_ll_buf, /* Setup context save destination */ - .ctx_save_buf = (uint32_t *)(TEGRA_TZRAM_CARVEOUT_BASE), + .ctx_save_buf = (uint32_t *)&se1_ctx_buf }; -/* SE2 security engine device handle */ +/* SE2 security engine device handle (T210B01 only) */ static tegra_se_dev_t se_dev_2 = { .se_num = 2, /* Setup base address for se */ @@ -112,7 +113,7 @@ static tegra_se_dev_t se_dev_2 = { /* Setup DST buffers for SE operations */ .dst_ll_buf = &se2_dst_ll_buf, /* Setup context save destination */ - .ctx_save_buf = (uint32_t *)(TEGRA_TZRAM_CARVEOUT_BASE + 0x1000), + .ctx_save_buf = (uint32_t *)(TEGRA_TZRAM_CARVEOUT_BASE + 0x1000) }; static bool ecid_valid; @@ -202,18 +203,6 @@ static int32_t tegra_se_operation_complete(const tegra_se_dev_t *se_dev) } /* - * Returns true if the SE engine is configured to perform SE context save in - * hardware. - */ -static inline bool tegra_se_atomic_save_enabled(const tegra_se_dev_t *se_dev) -{ - uint32_t val; - - val = tegra_se_read_32(se_dev, SE_CTX_SAVE_AUTO_REG_OFFSET); - return (SE_CTX_SAVE_AUTO_ENABLE(val) == SE_CTX_SAVE_AUTO_EN); -} - -/* * Wait for SE engine to be idle and clear pending interrupts before * starting the next SE operation. */ @@ -223,6 +212,9 @@ static int32_t tegra_se_operation_prepare(const tegra_se_dev_t *se_dev) uint32_t val = 0; uint32_t timeout; + /* disable SE interrupt to prevent interrupt issued by SE operation */ + tegra_se_write_32(se_dev, SE_INT_ENABLE_REG_OFFSET, 0U); + /* Wait for previous operation to finish */ val = tegra_se_read_32(se_dev, SE_STATUS_OFFSET); for (timeout = 0; (val != 0U) && (timeout < TIMEOUT_100MS); timeout++) { @@ -629,19 +621,19 @@ static int tegra_se_lp_rsakeytable_context_save(tegra_se_dev_t *se_dev) { uint32_t val = 0; int ret = 0; - /* First the modulus and then the exponent must be + /* For T210, First the modulus and then exponent must be * encrypted and saved. This is repeated for SLOT 0 * and SLOT 1. Hence the order: - * SLOT 0 exponent : RSA_KEY_INDEX : 0 * SLOT 0 modulus : RSA_KEY_INDEX : 1 - * SLOT 1 exponent : RSA_KEY_INDEX : 2 + * SLOT 0 exponent : RSA_KEY_INDEX : 0 * SLOT 1 modulus : RSA_KEY_INDEX : 3 + * SLOT 1 exponent : RSA_KEY_INDEX : 2 */ const unsigned int key_index_mod[TEGRA_SE_RSA_KEYSLOT_COUNT][2] = { /* RSA key slot 0 */ - {SE_RSA_KEY_INDEX_SLOT0_EXP, SE_RSA_KEY_INDEX_SLOT0_MOD}, + {SE_RSA_KEY_INDEX_SLOT0_MOD, SE_RSA_KEY_INDEX_SLOT0_EXP}, /* RSA key slot 1 */ - {SE_RSA_KEY_INDEX_SLOT1_EXP, SE_RSA_KEY_INDEX_SLOT1_MOD}, + {SE_RSA_KEY_INDEX_SLOT1_MOD, SE_RSA_KEY_INDEX_SLOT1_EXP}, }; se_dev->dst_ll_buf->last_buff_num = 0; @@ -876,8 +868,8 @@ static int tegra_se_context_save_sw(tegra_se_dev_t *se_dev) /* Write lp context buffer address into PMC scratch register */ if (se_dev->se_num == 1) { - /* SE context address */ - mmio_write_32((uint64_t)TEGRA_PMC_BASE + PMC_SECURE_SCRATCH117_OFFSET, + /* SE context address, support T210 only */ + mmio_write_32((uint64_t)TEGRA_PMC_BASE + PMC_SCRATCH43_REG_OFFSET, ((uint64_t)(se_dev->ctx_save_buf))); } else if (se_dev->se_num == 2) { /* SE2 & PKA1 context address */ @@ -909,7 +901,10 @@ void tegra_se_init(void) /* Generate random SRK to initialize DRBG */ tegra_se_generate_srk(&se_dev_1); - tegra_se_generate_srk(&se_dev_2); + + if (tegra_chipid_is_t210_b01()) { + tegra_se_generate_srk(&se_dev_2); + } /* determine if ECID is valid */ val = mmio_read_32(TEGRA_FUSE_BASE + FUSE_JTAG_SECUREID_VALID); @@ -932,6 +927,13 @@ static void tegra_se_enable_clocks(void) val &= ~ENTROPY_RESET_BIT; mmio_write_32(TEGRA_CAR_RESET_BASE + TEGRA_RST_DEVICES_W, val); + /* + * Switch SE clock source to CLK_M, to make sure SE clock + * is on when saving SE context + */ + mmio_write_32(TEGRA_CAR_RESET_BASE + TEGRA_CLK_RST_CTL_CLK_SRC_SE, + SE_CLK_SRC_CLK_M); + /* Enable SE clock */ val = mmio_read_32(TEGRA_CAR_RESET_BASE + TEGRA_CLK_OUT_ENB_V); val |= SE_CLK_ENB_BIT; @@ -975,43 +977,25 @@ int32_t tegra_se_suspend(void) tegra_se_enable_clocks(); - if (tegra_se_atomic_save_enabled(&se_dev_2) && - tegra_se_atomic_save_enabled(&se_dev_1)) { - /* Atomic context save se2 and pka1 */ + if (tegra_chipid_is_t210_b01()) { + /* It is T210 B01, Atomic context save se2 and pka1 */ INFO("%s: SE2/PKA1 atomic context save\n", __func__); - if (ret == 0) { - ret = tegra_se_context_save_atomic(&se_dev_2); - } - - /* Atomic context save se */ - if (ret == 0) { - INFO("%s: SE1 atomic context save\n", __func__); - ret = tegra_se_context_save_atomic(&se_dev_1); + ret = tegra_se_context_save_atomic(&se_dev_2); + if (ret != 0) { + ERROR("%s: SE2 ctx save failed (%d)\n", __func__, ret); } - if (ret == 0) { - INFO("%s: SE atomic context save done\n", __func__); - } - } else if (!tegra_se_atomic_save_enabled(&se_dev_2) && - !tegra_se_atomic_save_enabled(&se_dev_1)) { - /* SW context save se2 and pka1 */ - INFO("%s: SE2/PKA1 legacy(SW) context save\n", __func__); - if (ret == 0) { - ret = tegra_se_context_save_sw(&se_dev_2); - } - - /* SW context save se */ - if (ret == 0) { - INFO("%s: SE1 legacy(SW) context save\n", __func__); - ret = tegra_se_context_save_sw(&se_dev_1); - } - - if (ret == 0) { - INFO("%s: SE SW context save done\n", __func__); + ret = tegra_se_context_save_atomic(&se_dev_1); + if (ret != 0) { + ERROR("%s: SE1 ctx save failed (%d)\n", __func__, ret); } } else { - ERROR("%s: One SE set for atomic CTX save, the other is not\n", - __func__); + /* It is T210, SW context save se */ + INFO("%s: SE1 legacy(SW) context save\n", __func__); + ret = tegra_se_context_save_sw(&se_dev_1); + if (ret != 0) { + ERROR("%s: SE1 ctx save failed (%d)\n", __func__, ret); + } } tegra_se_disable_clocks(); @@ -1080,5 +1064,8 @@ static void tegra_se_warm_boot_resume(const tegra_se_dev_t *se_dev) void tegra_se_resume(void) { tegra_se_warm_boot_resume(&se_dev_1); - tegra_se_warm_boot_resume(&se_dev_2); + + if (tegra_chipid_is_t210_b01()) { + tegra_se_warm_boot_resume(&se_dev_2); + } } diff --git a/plat/nvidia/tegra/soc/t210/plat_psci_handlers.c b/plat/nvidia/tegra/soc/t210/plat_psci_handlers.c index 12241c2f3..7f73ea506 100644 --- a/plat/nvidia/tegra/soc/t210/plat_psci_handlers.c +++ b/plat/nvidia/tegra/soc/t210/plat_psci_handlers.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -184,6 +185,12 @@ plat_local_state_t tegra_soc_get_target_pwr_state(unsigned int lvl, return target; } +int32_t tegra_soc_cpu_standby(plat_local_state_t cpu_state) +{ + (void)cpu_state; + return PSCI_E_SUCCESS; +} + int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) { u_register_t mpidr = read_mpidr(); @@ -203,12 +210,9 @@ int tegra_soc_pwr_domain_suspend(const psci_power_state_t *target_state) assert((stateid_afflvl1 == PLAT_MAX_OFF_STATE) || (stateid_afflvl1 == PSTATE_ID_SOC_POWERDN)); - if (tegra_chipid_is_t210_b01()) { - - /* Suspend se/se2 and pka1 */ - if (tegra_se_suspend() != 0) { - ret = PSCI_E_INTERN_FAIL; - } + /* Suspend se/se2 and pka1 for T210 B01 and se for T210 */ + if (tegra_se_suspend() != 0) { + ret = PSCI_E_INTERN_FAIL; } } else if (stateid_afflvl1 == PSTATE_ID_CLUSTER_IDLE) { @@ -387,6 +391,15 @@ int tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state) */ tegra_reset_all_dma_masters(); + /* + * Mark PMC as accessible to the non-secure world + * to allow the COP to execute System Suspend + * sequence + */ + val = mmio_read_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE); + val &= ~PMC_SECURITY_EN_BIT; + mmio_write_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE, val); + /* clean up IRAM of any cruft */ zeromem((void *)(uintptr_t)TEGRA_IRAM_BASE, TEGRA_IRAM_A_SIZE); @@ -412,6 +425,11 @@ int tegra_soc_pwr_domain_power_down_wfi(const psci_power_state_t *target_state) return PSCI_E_SUCCESS; } +int32_t tegra_soc_pwr_domain_suspend_pwrdown_early(const psci_power_state_t *target_state) +{ + return PSCI_E_NOT_SUPPORTED; +} + int tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) { const plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); @@ -468,12 +486,14 @@ int tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) tegra_bpmp_resume(); } - /* sc7entry-fw is part of TZDRAM area */ if (plat_params->sc7entry_fw_base != 0U) { + /* sc7entry-fw is part of TZDRAM area */ offset = plat_params->tzdram_base - plat_params->sc7entry_fw_base; tegra_memctrl_tzdram_setup(plat_params->sc7entry_fw_base, plat_params->tzdram_size + offset); + } + if (!tegra_chipid_is_t210_b01()) { /* restrict PMC access to secure world */ val = mmio_read_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE); val |= PMC_SECURITY_EN_BIT; @@ -514,6 +534,13 @@ int tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) } /* + * Mark this CPU as ON in the cpu_powergate_mask[], + * so that we use Flow Controller for all subsequent + * power ups. + */ + cpu_powergate_mask[plat_my_core_pos()] = 1; + + /* * T210 has a dedicated ARMv7 boot and power mgmt processor, BPMP. It's * used for power management and boot purposes. Inform the BPMP that * we have completed the cluster power up. @@ -521,10 +548,11 @@ int tegra_soc_pwr_domain_on_finish(const psci_power_state_t *target_state) tegra_fc_lock_active_cluster(); /* - * Resume PMC hardware block for Tegra210 platforms supporting sc7entry-fw - */ - if (!tegra_chipid_is_t210_b01() && (plat_params->sc7entry_fw_base != 0U)) + * Resume PMC hardware block for Tegra210 platforms + */ + if (!tegra_chipid_is_t210_b01()) { tegra_pmc_resume(); + } return PSCI_E_SUCCESS; } @@ -540,7 +568,6 @@ int tegra_soc_pwr_domain_on(u_register_t mpidr) /* Turn on CPU using flow controller or PMC */ if (cpu_powergate_mask[cpu] == 0) { tegra_pmc_cpu_on(cpu); - cpu_powergate_mask[cpu] = 1; } else { tegra_fc_cpu_on(cpu); } @@ -567,5 +594,16 @@ int tegra_soc_prepare_system_reset(void) /* Wait 1 ms to make sure clock source/device logic is stabilized. */ mdelay(1); + /* + * Program the PMC in order to restart the system. + */ + tegra_pmc_system_reset(); + return PSCI_E_SUCCESS; } + +__dead2 void tegra_soc_prepare_system_off(void) +{ + ERROR("Tegra System Off: operation not handled.\n"); + panic(); +} diff --git a/plat/nvidia/tegra/soc/t210/plat_setup.c b/plat/nvidia/tegra/soc/t210/plat_setup.c index bfa818419..68cd38ec3 100644 --- a/plat/nvidia/tegra/soc/t210/plat_setup.c +++ b/plat/nvidia/tegra/soc/t210/plat_setup.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -118,7 +119,7 @@ static uint32_t tegra210_uart_addresses[TEGRA210_MAX_UART_PORTS + 1] = { ******************************************************************************/ void plat_enable_console(int32_t id) { - static console_16550_t uart_console; + static console_t uart_console; uint32_t console_clock; if ((id > 0) && (id < TEGRA210_MAX_UART_PORTS)) { @@ -135,12 +136,28 @@ void plat_enable_console(int32_t id) console_clock, TEGRA_CONSOLE_BAUDRATE, &uart_console); - console_set_scope(&uart_console.console, CONSOLE_FLAG_BOOT | + console_set_scope(&uart_console, CONSOLE_FLAG_BOOT | CONSOLE_FLAG_RUNTIME | CONSOLE_FLAG_CRASH); } } /******************************************************************************* + * Return pointer to the BL31 params from previous bootloader + ******************************************************************************/ +struct tegra_bl31_params *plat_get_bl31_params(void) +{ + return NULL; +} + +/******************************************************************************* + * Return pointer to the BL31 platform params from previous bootloader + ******************************************************************************/ +plat_params_from_bl2_t *plat_get_bl31_plat_params(void) +{ + return NULL; +} + +/******************************************************************************* * Handler for early platform setup ******************************************************************************/ void plat_early_platform_setup(void) @@ -148,6 +165,15 @@ void plat_early_platform_setup(void) const plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); uint64_t val; + /* Verify chip id is t210 */ + assert(tegra_chipid_is_t210()); + + /* + * Do initial security configuration to allow DRAM/device access. + */ + tegra_memctrl_tzdram_setup(plat_params->tzdram_base, + (uint32_t)plat_params->tzdram_size); + /* platform parameter passed by the previous bootloader */ if (plat_params->l2_ecc_parity_prot_dis != 1) { /* Enable ECC Parity Protection for Cortex-A57 CPUs */ @@ -157,17 +183,22 @@ void plat_early_platform_setup(void) } /* Initialize security engine driver */ - if (tegra_chipid_is_t210_b01()) { - tegra_se_init(); - } + tegra_se_init(); } /* Secure IRQs for Tegra186 */ static const interrupt_prop_t tegra210_interrupt_props[] = { - INTR_PROP_DESC(TEGRA210_WDT_CPU_LEGACY_FIQ, GIC_HIGHEST_SEC_PRIORITY, + INTR_PROP_DESC(TEGRA_SDEI_SGI_PRIVATE, PLAT_SDEI_CRITICAL_PRI, + GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), + INTR_PROP_DESC(TEGRA210_TIMER1_IRQ, PLAT_TEGRA_WDT_PRIO, + GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), + INTR_PROP_DESC(TEGRA210_WDT_CPU_LEGACY_FIQ, PLAT_TEGRA_WDT_PRIO, GICV2_INTR_GROUP0, GIC_INTR_CFG_EDGE), }; +/******************************************************************************* + * Handler for late platform setup + ******************************************************************************/ void plat_late_platform_setup(void) { const plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); @@ -216,6 +247,13 @@ void plat_late_platform_setup(void) val |= PMC_SECURITY_EN_BIT; mmio_write_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE, val); } + + if (!tegra_chipid_is_t210_b01()) { + /* restrict PMC access to secure world */ + val = mmio_read_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE); + val |= PMC_SECURITY_EN_BIT; + mmio_write_32(TEGRA_MISC_BASE + APB_SLAVE_SECURITY_ENABLE, val); + } } /******************************************************************************* @@ -235,3 +273,46 @@ void plat_gic_setup(void) */ tegra_fc_enable_fiq_to_ccplex_routing(); } +/******************************************************************************* + * Handler to indicate support for System Suspend + ******************************************************************************/ +bool plat_supports_system_suspend(void) +{ + const plat_params_from_bl2_t *plat_params = bl31_get_plat_params(); + + /* + * sc7entry-fw is only supported by Tegra210 SoCs. + */ + if (!tegra_chipid_is_t210_b01() && (plat_params->sc7entry_fw_base != 0U)) { + return true; + } else if (tegra_chipid_is_t210_b01()) { + return true; + } else { + return false; + } +} +/******************************************************************************* + * Platform specific runtime setup. + ******************************************************************************/ +void plat_runtime_setup(void) +{ + /* + * During cold boot, it is observed that the arbitration + * bit is set in the Memory controller leading to false + * error interrupts in the non-secure world. To avoid + * this, clean the interrupt status register before + * booting into the non-secure world + */ + tegra_memctrl_clear_pending_interrupts(); + + /* + * During boot, USB3 and flash media (SDMMC/SATA) devices need + * access to IRAM. Because these clients connect to the MC and + * do not have a direct path to the IRAM, the MC implements AHB + * redirection during boot to allow path to IRAM. In this mode + * accesses to a programmed memory address aperture are directed + * to the AHB bus, allowing access to the IRAM. This mode must be + * disabled before we jump to the non-secure world. + */ + tegra_memctrl_disable_ahb_redirection(); +} diff --git a/plat/nvidia/tegra/soc/t210/plat_sip_calls.c b/plat/nvidia/tegra/soc/t210/plat_sip_calls.c index 7e0f5c1d8..904f8d62e 100644 --- a/plat/nvidia/tegra/soc/t210/plat_sip_calls.c +++ b/plat/nvidia/tegra/soc/t210/plat_sip_calls.c @@ -1,5 +1,6 @@ /* * Copyright (c) 2018, ARM Limited and Contributors. All rights reserved. + * Copyright (c) 2020, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause */ @@ -50,24 +51,32 @@ int plat_sip_handler(uint32_t smc_fid, if (!ns) SMC_RET1(handle, SMC_UNK); - switch (smc_fid) { - case TEGRA_SIP_PMC_COMMANDS: - + if (smc_fid == TEGRA_SIP_PMC_COMMANDS) { /* check the address is within PMC range and is 4byte aligned */ if ((x2 >= TEGRA_PMC_SIZE) || (x2 & 0x3)) return -EINVAL; - /* pmc_secure_scratch registers are not accessible */ - if (((x2 >= PMC_SECURE_SCRATCH0) && (x2 <= PMC_SECURE_SCRATCH5)) || - ((x2 >= PMC_SECURE_SCRATCH6) && (x2 <= PMC_SECURE_SCRATCH7)) || - ((x2 >= PMC_SECURE_SCRATCH8) && (x2 <= PMC_SECURE_SCRATCH79)) || - ((x2 >= PMC_SECURE_SCRATCH80) && (x2 <= PMC_SECURE_SCRATCH119))) - return -EFAULT; - + switch (x2) { + /* Black listed PMC registers */ + case PMC_SCRATCH1: + case PMC_SCRATCH31 ... PMC_SCRATCH33: + case PMC_SCRATCH40: + case PMC_SCRATCH42: + case PMC_SCRATCH43 ... PMC_SCRATCH48: + case PMC_SCRATCH50 ... PMC_SCRATCH51: + case PMC_SCRATCH56 ... PMC_SCRATCH57: /* PMC secure-only registers are not accessible */ - if ((x2 == PMC_DPD_ENABLE_0) || (x2 == PMC_FUSE_CONTROL_0) || - (x2 == PMC_CRYPTO_OP_0)) + case PMC_DPD_ENABLE_0: + case PMC_FUSE_CONTROL_0: + case PMC_CRYPTO_OP_0: + case PMC_TSC_MULT_0: + case PMC_STICKY_BIT: + ERROR("%s: error offset=0x%llx\n", __func__, x2); return -EFAULT; + default: + /* Valid register */ + break; + } /* Perform PMC read/write */ if (x1 == PMC_READ) { @@ -78,13 +87,8 @@ int plat_sip_handler(uint32_t smc_fid, } else { return -EINVAL; } - - break; - - default: - ERROR("%s: unsupported function ID\n", __func__); + } else { return -ENOTSUP; } - return 0; } diff --git a/plat/nvidia/tegra/soc/t210/platform_t210.mk b/plat/nvidia/tegra/soc/t210/platform_t210.mk index a11aef4dd..724cfc3c0 100644 --- a/plat/nvidia/tegra/soc/t210/platform_t210.mk +++ b/plat/nvidia/tegra/soc/t210/platform_t210.mk @@ -1,5 +1,6 @@ # # Copyright (c) 2015-2019, ARM Limited and Contributors. All rights reserved. +# Copyright (c) 2020, NVIDIA Corporation. All rights reserved. # # SPDX-License-Identifier: BSD-3-Clause # @@ -22,21 +23,23 @@ $(eval $(call add_define,MAX_XLAT_TABLES)) MAX_MMAP_REGIONS := 16 $(eval $(call add_define,MAX_MMAP_REGIONS)) -ENABLE_WDT_LEGACY_FIQ_HANDLING := 1 -$(eval $(call add_define,ENABLE_WDT_LEGACY_FIQ_HANDLING)) +ENABLE_TEGRA_WDT_LEGACY_FIQ_HANDLING := 1 -PLAT_INCLUDES += -I${SOC_DIR}/drivers/se +PLAT_INCLUDES += -Iplat/nvidia/tegra/include/t210 \ + -I${SOC_DIR}/drivers/se -BL31_SOURCES += drivers/ti/uart/aarch64/16550_console.S \ +BL31_SOURCES += ${TEGRA_GICv2_SOURCES} \ + drivers/ti/uart/aarch64/16550_console.S \ lib/cpus/aarch64/cortex_a53.S \ lib/cpus/aarch64/cortex_a57.S \ - ${COMMON_DIR}/drivers/bpmp/bpmp.c \ - ${COMMON_DIR}/drivers/flowctrl/flowctrl.c \ - ${COMMON_DIR}/drivers/memctrl/memctrl_v1.c \ + ${TEGRA_DRIVERS}/bpmp/bpmp.c \ + ${TEGRA_DRIVERS}/flowctrl/flowctrl.c \ + ${TEGRA_DRIVERS}/memctrl/memctrl_v1.c \ + ${TEGRA_DRIVERS}/pmc/pmc.c \ ${SOC_DIR}/plat_psci_handlers.c \ ${SOC_DIR}/plat_setup.c \ ${SOC_DIR}/drivers/se/security_engine.c \ - ${SOC_DIR}/plat_secondary.c \ + ${SOC_DIR}/plat_secondary.c \ ${SOC_DIR}/plat_sip_calls.c # Enable workarounds for selected Cortex-A57 erratas. @@ -44,7 +47,6 @@ A57_DISABLE_NON_TEMPORAL_HINT := 1 ERRATA_A57_826974 := 1 ERRATA_A57_826977 := 1 ERRATA_A57_828024 := 1 -ERRATA_A57_829520 := 1 ERRATA_A57_833471 := 1 # Enable workarounds for selected Cortex-A53 erratas. @@ -55,3 +57,6 @@ ERRATA_A53_855873 := 1 # Skip L1 $ flush when powering down Cortex-A57 CPUs SKIP_A57_L1_FLUSH_PWR_DWN := 1 + +# Enable higher performance Non-cacheable load forwarding +A57_ENABLE_NONCACHEABLE_LOAD_FWD := 1 |