mirror of
https://github.com/ARM-software/arm-trusted-firmware.git
synced 2025-04-16 09:34:18 +00:00
feat(optee): enable transfer list in opteed
Enable handoff to OP-TEE using transfer list. Create transfer list when loading OP-TEE image via non-secure SMC call. Fallback to default handoff args when transfer list is disabled or transfer list signature does not exist. Change-Id: I94bb5b7fdfbb8829016a9d5d9ef5aff993d7cc99 Signed-off-by: Raymond Mao <raymond.mao@linaro.org>
This commit is contained in:
parent
436c66b32a
commit
0e8def996e
4 changed files with 109 additions and 32 deletions
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2013-2017, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -20,9 +20,9 @@
|
|||
* initialize OPTEE context and entry point info for OPTEE.
|
||||
******************************************************************************/
|
||||
void opteed_init_optee_ep_state(struct entry_point_info *optee_entry_point,
|
||||
uint32_t rw, uint64_t pc,
|
||||
uint64_t pageable_part, uint64_t mem_limit,
|
||||
uint64_t dt_addr, optee_context_t *optee_ctx)
|
||||
uint32_t rw, uint64_t pc, uint64_t arg0,
|
||||
uint64_t arg1, uint64_t arg2, uint64_t arg3,
|
||||
optee_context_t *optee_ctx)
|
||||
{
|
||||
uint32_t ep_attr;
|
||||
|
||||
|
@ -54,9 +54,10 @@ void opteed_init_optee_ep_state(struct entry_point_info *optee_entry_point,
|
|||
DAIF_IRQ_BIT |
|
||||
DAIF_ABT_BIT);
|
||||
zeromem(&optee_entry_point->args, sizeof(optee_entry_point->args));
|
||||
optee_entry_point->args.arg0 = pageable_part;
|
||||
optee_entry_point->args.arg1 = mem_limit;
|
||||
optee_entry_point->args.arg2 = dt_addr;
|
||||
optee_entry_point->args.arg0 = arg0;
|
||||
optee_entry_point->args.arg1 = arg1;
|
||||
optee_entry_point->args.arg2 = arg2;
|
||||
optee_entry_point->args.arg3 = arg3;
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2013-2023, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -27,6 +27,7 @@
|
|||
#include <lib/coreboot.h>
|
||||
#include <lib/el3_runtime/context_mgmt.h>
|
||||
#include <lib/optee_utils.h>
|
||||
#include <lib/transfer_list.h>
|
||||
#include <lib/xlat_tables/xlat_tables_v2.h>
|
||||
#if OPTEE_ALLOW_SMC_LOAD
|
||||
#include <libfdt.h>
|
||||
|
@ -37,6 +38,10 @@
|
|||
#include "opteed_private.h"
|
||||
#include "teesmc_opteed.h"
|
||||
|
||||
#if OPTEE_ALLOW_SMC_LOAD
|
||||
static struct transfer_list_header *bl31_tl;
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
* Address of the entrypoint vector table in OPTEE. It is
|
||||
* initialised once on the primary core after a cold boot.
|
||||
|
@ -123,9 +128,13 @@ static int32_t opteed_setup(void)
|
|||
#else
|
||||
entry_point_info_t *optee_ep_info;
|
||||
uint32_t linear_id;
|
||||
uint64_t opteed_pageable_part;
|
||||
uint64_t opteed_mem_limit;
|
||||
uint64_t dt_addr;
|
||||
uint64_t arg0;
|
||||
uint64_t arg1;
|
||||
uint64_t arg2;
|
||||
uint64_t arg3;
|
||||
struct transfer_list_header *tl = NULL;
|
||||
struct transfer_list_entry *te = NULL;
|
||||
void *dt = NULL;
|
||||
|
||||
linear_id = plat_my_core_pos();
|
||||
|
||||
|
@ -150,17 +159,39 @@ static int32_t opteed_setup(void)
|
|||
if (!optee_ep_info->pc)
|
||||
return 1;
|
||||
|
||||
opteed_rw = optee_ep_info->args.arg0;
|
||||
opteed_pageable_part = optee_ep_info->args.arg1;
|
||||
opteed_mem_limit = optee_ep_info->args.arg2;
|
||||
dt_addr = optee_ep_info->args.arg3;
|
||||
if (TRANSFER_LIST &&
|
||||
optee_ep_info->args.arg1 == (TRANSFER_LIST_SIGNATURE |
|
||||
REGISTER_CONVENTION_VERSION_MASK)) {
|
||||
tl = (void *)optee_ep_info->args.arg3;
|
||||
if (transfer_list_check_header(tl) == TL_OPS_NON) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
opteed_init_optee_ep_state(optee_ep_info,
|
||||
opteed_rw,
|
||||
optee_ep_info->pc,
|
||||
opteed_pageable_part,
|
||||
opteed_mem_limit,
|
||||
dt_addr,
|
||||
opteed_rw = GET_RW(optee_ep_info->spsr);
|
||||
te = transfer_list_find(tl, TL_TAG_FDT);
|
||||
dt = transfer_list_entry_data(te);
|
||||
|
||||
if (opteed_rw == OPTEE_AARCH64) {
|
||||
arg0 = (uint64_t)dt;
|
||||
arg2 = 0;
|
||||
} else {
|
||||
arg2 = (uint64_t)dt;
|
||||
arg0 = 0;
|
||||
}
|
||||
|
||||
arg1 = optee_ep_info->args.arg1;
|
||||
arg3 = optee_ep_info->args.arg3;
|
||||
} else {
|
||||
/* Default handoff arguments */
|
||||
opteed_rw = optee_ep_info->args.arg0;
|
||||
arg0 = optee_ep_info->args.arg1; /* opteed_pageable_part */
|
||||
arg1 = optee_ep_info->args.arg2; /* opteed_mem_limit */
|
||||
arg2 = optee_ep_info->args.arg3; /* dt_addr */
|
||||
arg3 = 0;
|
||||
}
|
||||
|
||||
opteed_init_optee_ep_state(optee_ep_info, opteed_rw, optee_ep_info->pc,
|
||||
arg0, arg1, arg2, arg3,
|
||||
&opteed_sp_context[linear_id]);
|
||||
|
||||
/*
|
||||
|
@ -302,6 +333,26 @@ static int create_opteed_dt(void)
|
|||
return fdt_finish(fdt_buf);
|
||||
}
|
||||
|
||||
static int32_t create_smc_tl(const void *fdt, uint32_t fdt_sz)
|
||||
{
|
||||
#if TRANSFER_LIST
|
||||
bl31_tl = transfer_list_init((void *)(uintptr_t)FW_HANDOFF_BASE,
|
||||
FW_HANDOFF_SIZE);
|
||||
if (!bl31_tl) {
|
||||
ERROR("Failed to initialize Transfer List at 0x%lx\n",
|
||||
(unsigned long)FW_HANDOFF_BASE);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (!transfer_list_add(bl31_tl, TL_TAG_FDT, fdt_sz, fdt)) {
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
#else
|
||||
return -1;
|
||||
#endif
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
* This function is responsible for handling the SMC that loads the OP-TEE
|
||||
* binary image via a non-secure SMC call. It takes the size and physical
|
||||
|
@ -326,6 +377,10 @@ static int32_t opteed_handle_smc_load(uint64_t data_size, uint32_t data_pa)
|
|||
entry_point_info_t optee_ep_info;
|
||||
uint32_t linear_id = plat_my_core_pos();
|
||||
uint64_t dt_addr = 0;
|
||||
uint64_t arg0 = 0;
|
||||
uint64_t arg1 = 0;
|
||||
uint64_t arg2 = 0;
|
||||
uint64_t arg3 = 0;
|
||||
|
||||
mapped_data_pa = page_align(data_pa, DOWN);
|
||||
mapped_data_va = mapped_data_pa;
|
||||
|
@ -394,12 +449,36 @@ static int32_t opteed_handle_smc_load(uint64_t data_size, uint32_t data_pa)
|
|||
dt_addr = (uint64_t)fdt_buf;
|
||||
flush_dcache_range(dt_addr, OPTEED_FDT_SIZE);
|
||||
|
||||
if (TRANSFER_LIST &&
|
||||
!create_smc_tl((void *)dt_addr, OPTEED_FDT_SIZE)) {
|
||||
struct transfer_list_entry *te = NULL;
|
||||
void *dt = NULL;
|
||||
|
||||
te = transfer_list_find(bl31_tl, TL_TAG_FDT);
|
||||
dt = transfer_list_entry_data(te);
|
||||
|
||||
if (opteed_rw == OPTEE_AARCH64) {
|
||||
arg0 = (uint64_t)dt;
|
||||
arg2 = 0;
|
||||
} else {
|
||||
arg2 = (uint64_t)dt;
|
||||
arg0 = 0;
|
||||
}
|
||||
arg1 = TRANSFER_LIST_SIGNATURE |
|
||||
REGISTER_CONVENTION_VERSION_MASK;
|
||||
arg3 = (uint64_t)bl31_tl;
|
||||
} else {
|
||||
/* Default handoff arguments */
|
||||
arg2 = dt_addr;
|
||||
}
|
||||
|
||||
opteed_init_optee_ep_state(&optee_ep_info,
|
||||
opteed_rw,
|
||||
image_pa,
|
||||
0,
|
||||
0,
|
||||
dt_addr,
|
||||
arg0,
|
||||
arg1,
|
||||
arg2,
|
||||
arg3,
|
||||
&opteed_sp_context[linear_id]);
|
||||
if (opteed_init_with_entry_point(&optee_ep_info) == 0) {
|
||||
rc = -EFAULT;
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2013-2023, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -113,7 +113,7 @@ void opteed_cpu_on_finish_handler(u_register_t unused)
|
|||
|
||||
opteed_init_optee_ep_state(&optee_on_entrypoint, opteed_rw,
|
||||
(uint64_t)&optee_vector_table->cpu_on_entry,
|
||||
0, 0, 0, optee_ctx);
|
||||
0, 0, 0, 0, optee_ctx);
|
||||
|
||||
/* Initialise this cpu's secure context */
|
||||
cm_init_my_context(&optee_on_entrypoint);
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2013-2023, ARM Limited and Contributors. All rights reserved.
|
||||
* Copyright (c) 2013-2023, Arm Limited and Contributors. All rights reserved.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-3-Clause
|
||||
*/
|
||||
|
@ -148,11 +148,8 @@ void __dead2 opteed_exit_sp(uint64_t c_rt_ctx, uint64_t ret);
|
|||
uint64_t opteed_synchronous_sp_entry(optee_context_t *optee_ctx);
|
||||
void __dead2 opteed_synchronous_sp_exit(optee_context_t *optee_ctx, uint64_t ret);
|
||||
void opteed_init_optee_ep_state(struct entry_point_info *optee_entry_point,
|
||||
uint32_t rw,
|
||||
uint64_t pc,
|
||||
uint64_t pageable_part,
|
||||
uint64_t mem_limit,
|
||||
uint64_t dt_addr,
|
||||
uint32_t rw, uint64_t pc, uint64_t arg0,
|
||||
uint64_t arg1, uint64_t arg2, uint64_t arg3,
|
||||
optee_context_t *optee_ctx);
|
||||
void opteed_cpu_on_finish_handler(u_register_t unused);
|
||||
|
||||
|
|
Loading…
Add table
Reference in a new issue