1 /* 2 * Copyright (c) 2024-2025, Arm Limited and Contributors. All rights reserved. 3 * 4 * SPDX-License-Identifier: BSD-3-Clause 5 */ 6 7 #if CRYPTO_SUPPORT 8 #include <mbedtls/version.h> 9 #endif /* CRYPTO_SUPPORT */ 10 11 #include <plat/arm/common/plat_arm.h> 12 #include <platform_def.h> 13 14 #if CRYPTO_SUPPORT 15 #if defined(IMAGE_BL1) || RESET_TO_BL2 || defined(IMAGE_BL31) 16 static unsigned char heap[TF_MBEDTLS_HEAP_SIZE]; 17 18 #define MBEDTLS_HEAP_ADDR heap 19 #define MBEDTLS_HEAP_SIZE sizeof(heap) 20 #else 21 static struct crypto_heap_info heap_info; 22 23 #define MBEDTLS_HEAP_ADDR heap_info.addr 24 #define MBEDTLS_HEAP_SIZE heap_info.size 25 26 struct transfer_list_entry * 27 arm_transfer_list_set_heap_info(struct transfer_list_header *tl) 28 { 29 struct transfer_list_entry *te = 30 transfer_list_find(tl, TL_TAG_MBEDTLS_HEAP_INFO); 31 assert(te != NULL); 32 33 heap_info = *(struct crypto_heap_info *)transfer_list_entry_data(te); 34 return te; 35 } 36 #endif /* defined(IMAGE_BL1) || RESET_TO_BL2 || defined(IMAGE_BL31) */ 37 38 int __init arm_get_mbedtls_heap(void **heap_addr, size_t *heap_size) 39 { 40 assert(heap_addr != NULL); 41 assert(heap_size != NULL); 42 *heap_addr = MBEDTLS_HEAP_ADDR; 43 *heap_size = MBEDTLS_HEAP_SIZE; 44 45 return 0; 46 } 47 #endif /* CRYPTO_SUPPORT */ 48 49 void arm_transfer_list_dyn_cfg_init(struct transfer_list_header *tl) 50 { 51 struct transfer_list_entry *te; 52 bl_mem_params_node_t *next_param_node = 53 get_bl_mem_params_node(HW_CONFIG_ID); 54 assert(next_param_node != NULL); 55 56 /* 57 * The HW_CONFIG needs to be authenticated via the normal loading 58 * mechanism. Pre-allocate a TE for the configuration and update the 59 * load information so the configuration is loaded directly into the TE. 60 */ 61 te = transfer_list_add(tl, TL_TAG_FDT, PLAT_ARM_HW_CONFIG_SIZE, NULL); 62 assert(te != NULL); 63 64 next_param_node->image_info.h.attr &= ~IMAGE_ATTRIB_SKIP_LOADING; 65 next_param_node->image_info.image_max_size = PLAT_ARM_HW_CONFIG_SIZE; 66 next_param_node->image_info.image_base = 67 (uintptr_t)transfer_list_entry_data(te); 68 69 #if SPMC_AT_EL3 && defined(PLAT_ARM_SPMC_SP_MANIFEST_SIZE) 70 next_param_node = get_bl_mem_params_node(TOS_FW_CONFIG_ID); 71 assert(next_param_node != NULL); 72 73 te = transfer_list_add(tl, TL_TAG_DT_FFA_MANIFEST, 74 PLAT_ARM_SPMC_SP_MANIFEST_SIZE, NULL); 75 assert(te != NULL); 76 77 next_param_node->image_info.h.attr &= ~IMAGE_ATTRIB_SKIP_LOADING; 78 next_param_node->image_info.image_max_size = PLAT_ARM_SPMC_SP_MANIFEST_SIZE; 79 next_param_node->image_info.image_base = 80 (uintptr_t)transfer_list_entry_data(te); 81 #endif /* SPMC_AT_EL3 */ 82 } 83 84 void arm_transfer_list_populate_ep_info(bl_mem_params_node_t *next_param_node, 85 struct transfer_list_header *tl) 86 { 87 uint32_t next_exe_img_id; 88 entry_point_info_t *ep __unused; 89 struct transfer_list_entry *te; 90 assert(next_param_node != NULL); 91 92 while ((next_exe_img_id = next_param_node->next_handoff_image_id) != 93 INVALID_IMAGE_ID) { 94 next_param_node = 95 &bl_mem_params_desc_ptr[get_bl_params_node_index( 96 next_exe_img_id)]; 97 assert(next_param_node != NULL); 98 99 te = transfer_list_add(tl, TL_TAG_EXEC_EP_INFO, 100 sizeof(entry_point_info_t), 101 &next_param_node->ep_info); 102 assert(te != NULL); 103 104 ep = transfer_list_entry_data(te); 105 assert(ep != NULL); 106 107 #if SPMC_AT_EL3 108 if (next_exe_img_id == BL32_IMAGE_ID) { 109 /* 110 * Populate the BL32 image base, size and max limit in 111 * the entry point information, since there is no 112 * platform function to retrieve them in generic 113 * code. We choose arg2, arg3 and arg4 since the generic 114 * code uses arg1 for stashing the SP manifest size. The 115 * SPMC setup uses these arguments to update SP manifest 116 * with actual SP's base address and it size. 117 */ 118 ep->args.arg2 = next_param_node->image_info.image_base; 119 ep->args.arg3 = next_param_node->image_info.image_size; 120 ep->args.arg4 = 121 next_param_node->image_info.image_base + 122 next_param_node->image_info.image_max_size; 123 } 124 #endif /* SPMC_AT_EL3 */ 125 126 next_exe_img_id = next_param_node->next_handoff_image_id; 127 } 128 129 flush_dcache_range((uintptr_t)tl, tl->size); 130 } 131