1 /* 2 * Copyright (c) 2022-2023, ARM Limited and Contributors. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7 #include <common/debug.h> 8 #include <emi_mpu.h> 9 #include <mtk_sip_svc.h> 10 11 #define MPU_PHYSICAL_ADDR_SHIFT_BITS (16) 12 13 void set_emi_mpu_regions(void) 14 { 15 struct emi_region_info_t region_info; 16 17 /* BL31 address */ 18 region_info.start = TZRAM_BASE; 19 region_info.end = TZRAM_BASE + TZRAM_SIZE - 1; 20 region_info.region = BL31_EMI_REGION_ID; 21 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 22 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 23 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 24 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 25 FORBIDDEN, FORBIDDEN, FORBIDDEN, SEC_RW); 26 emi_mpu_set_protection(®ion_info); 27 28 /* BL32 address */ 29 region_info.start = BL32_REGION_BASE; 30 region_info.end = BL32_REGION_BASE + BL32_REGION_SIZE - 1; 31 region_info.region = BL32_REGION_ID; 32 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 33 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 34 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 35 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 36 FORBIDDEN, FORBIDDEN, SEC_RW, SEC_RW); 37 emi_mpu_set_protection(®ion_info); 38 39 /* SCP core0 DRAM */ 40 region_info.start = SCP_CORE0_REGION_BASE; 41 region_info.end = SCP_CORE0_REGION_BASE + SCP_CORE0_REGION_SIZE - 1; 42 region_info.region = SCP_CORE0_REGION_ID; 43 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 44 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 45 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION, 46 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 47 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION); 48 emi_mpu_set_protection(®ion_info); 49 50 /* SCP core1 DRAM */ 51 region_info.start = SCP_CORE1_REGION_BASE; 52 region_info.end = SCP_CORE1_REGION_BASE + SCP_CORE1_REGION_SIZE - 1; 53 region_info.region = SCP_CORE1_REGION_ID; 54 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 55 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 56 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION, 57 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 58 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION); 59 emi_mpu_set_protection(®ion_info); 60 61 /* DSP protect address */ 62 region_info.start = DSP_PROTECT_REGION_BASE; 63 region_info.end = DSP_PROTECT_REGION_BASE + DSP_PROTECT_REGION_SIZE - 1; 64 region_info.region = DSP_PROTECT_REGION_ID; 65 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 66 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 67 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 68 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION, 69 FORBIDDEN, FORBIDDEN, FORBIDDEN, NO_PROTECTION); 70 emi_mpu_set_protection(®ion_info); 71 72 /* All default settings */ 73 region_info.start = DRAM_START_ADDR; 74 region_info.end = DRAM_START_ADDR + DRAM_MAX_SIZE - 1; 75 region_info.region = ALL_DEFAULT_REGION_ID; 76 SET_ACCESS_PERMISSION(region_info.apc, LOCK, 77 FORBIDDEN, FORBIDDEN, NO_PROTECTION, NO_PROTECTION, 78 NO_PROTECTION, FORBIDDEN, NO_PROTECTION, NO_PROTECTION, 79 NO_PROTECTION, SEC_R_NSEC_RW, NO_PROTECTION, FORBIDDEN, 80 NO_PROTECTION, NO_PROTECTION, NO_PROTECTION, NO_PROTECTION); 81 emi_mpu_set_protection(®ion_info); 82 } 83 84 int set_apu_emi_mpu_region(void) 85 { 86 struct emi_region_info_t region_info; 87 88 region_info.start = (unsigned long long)APUSYS_SEC_BUF_PA; 89 region_info.end = (unsigned long long)(APUSYS_SEC_BUF_PA + APUSYS_SEC_BUF_SZ) - 1; 90 region_info.region = APUSYS_SEC_BUF_EMI_REGION_ID; 91 92 SET_ACCESS_PERMISSION(region_info.apc, UNLOCK, 93 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 94 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 95 NO_PROTECTION, FORBIDDEN, NO_PROTECTION, FORBIDDEN, 96 FORBIDDEN, FORBIDDEN, FORBIDDEN, SEC_RW); 97 98 return emi_mpu_set_protection(®ion_info); 99 } 100 101 static inline uint64_t get_decoded_phys_addr(uint64_t addr) 102 { 103 return (addr << MPU_PHYSICAL_ADDR_SHIFT_BITS); 104 } 105 106 static inline uint32_t get_decoded_zone_id(uint32_t info) 107 { 108 return ((info & 0xFFFF0000) >> MPU_PHYSICAL_ADDR_SHIFT_BITS); 109 } 110 111 static inline uint32_t get_decoded_set_clear_info(uint32_t info) 112 { 113 return (info & 0x0000FFFF); 114 } 115 116 int emi_mpu_optee_handler(uint64_t encoded_addr, uint64_t zone_size, 117 uint64_t zone_info) 118 { 119 uint64_t phys_addr = get_decoded_phys_addr(encoded_addr); 120 struct emi_region_info_t region_info; 121 enum MPU_REQ_ORIGIN_ZONE_ID zone_id = get_decoded_zone_id(zone_info); 122 uint32_t is_set = get_decoded_set_clear_info(zone_info); 123 124 INFO("encoded_addr = 0x%lx, zone_size = 0x%lx, zone_info = 0x%lx\n", 125 encoded_addr, zone_size, zone_info); 126 127 if (zone_id != MPU_REQ_ORIGIN_TEE_ZONE_SVP) { 128 ERROR("Invalid param %s, %d\n", __func__, __LINE__); 129 return MTK_SIP_E_INVALID_PARAM; 130 } 131 132 if (is_set > 0) { 133 /* SVP DRAM */ 134 region_info.start = phys_addr; 135 region_info.end = phys_addr + zone_size - 1; 136 region_info.region = SVP_DRAM_REGION_ID; 137 SET_ACCESS_PERMISSION(region_info.apc, UNLOCK, 138 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 139 FORBIDDEN, FORBIDDEN, FORBIDDEN, FORBIDDEN, 140 FORBIDDEN, SEC_RW, FORBIDDEN, FORBIDDEN, 141 FORBIDDEN, FORBIDDEN, SEC_RW, SEC_RW); 142 143 emi_mpu_set_protection(®ion_info); 144 } else { /* clear region protection */ 145 emi_mpu_clear_protection(SVP_DRAM_REGION_ID); 146 } 147 148 return 0; 149 } 150