diff options
author | Varun Wadekar <vwadekar@nvidia.com> | 2015-03-13 14:19:11 +0530 |
---|---|---|
committer | Varun Wadekar <vwadekar@nvidia.com> | 2015-03-31 10:06:15 +0530 |
commit | 77199df7bceba229a8a2f9b8473088f969737d85 (patch) | |
tree | 529ad624c4001da3d8ff9d52e6840ab0e8098bdf /services | |
parent | 220383153c582b8b1d26b21ab2f240143a0558f5 (diff) |
Register NS shared memory for SP's activity logs and TA sessions
This patch registers NS memory buffer with the secure payload using
two different functions IDs - REGISTER_LOGBUF, REGISTER_REQBUF.
a. The SP uses the log-buffer to store its activity logs, in a
pre-decided format. This helps in debugging secure payload's issues.
b. The SP uses the req-buffer to get the parameters required by
sessions with Trusted Applications.
Change-Id: I6b0247cf7790524132ee0da24f1f35b1fccec5d5
Signed-off-by: Varun Wadekar <vwadekar@nvidia.com>
Diffstat (limited to 'services')
-rw-r--r-- | services/spd/tlkd/tlkd_main.c | 83 |
1 files changed, 82 insertions, 1 deletions
diff --git a/services/spd/tlkd/tlkd_main.c b/services/spd/tlkd/tlkd_main.c index 65466aa2..8d2d437e 100644 --- a/services/spd/tlkd/tlkd_main.c +++ b/services/spd/tlkd/tlkd_main.c @@ -186,6 +186,7 @@ uint64_t tlkd_smc_handler(uint32_t smc_fid, void *handle, uint64_t flags) { + cpu_context_t *ns_cpu_context; uint32_t ns; /* Passing a NULL context is a critical programming error */ @@ -197,11 +198,91 @@ uint64_t tlkd_smc_handler(uint32_t smc_fid, switch (smc_fid) { /* + * This is a request from the non-secure context to: + * + * a. register shared memory with the SP for storing it's + * activity logs. + * b. register shared memory with the SP for passing args + * required for maintaining sessions with the Trusted + * Applications. + */ + case TLK_REGISTER_LOGBUF: + case TLK_REGISTER_REQBUF: + if (!ns || !tlk_args_results_buf) + SMC_RET1(handle, SMC_UNK); + + /* + * This is a fresh request from the non-secure client. + * The parameters are in x1 and x2. Figure out which + * registers need to be preserved, save the non-secure + * state and send the request to the secure payload. + */ + assert(handle == cm_get_context(NON_SECURE)); + + /* Check if we are already preempted */ + if (get_std_smc_active_flag(tlk_ctx.state)) + SMC_RET1(handle, SMC_UNK); + + cm_el1_sysregs_context_save(NON_SECURE); + + /* + * Verify if there is a valid context to use. + */ + assert(&tlk_ctx.cpu_ctx == cm_get_context(SECURE)); + + /* + * Mark the SP state as active. + */ + set_std_smc_active_flag(tlk_ctx.state); + + /* Save args for use by the SP on return */ + store_tlk_args_results(smc_fid, x1, x2, x3); + + /* + * We are done stashing the non-secure context. Ask the + * secure payload to do the work now. + */ + cm_el1_sysregs_context_restore(SECURE); + cm_set_next_eret_context(SECURE); + SMC_RET0(&tlk_ctx.cpu_ctx); + + /* + * This is a request from the SP to mark completion of + * a standard function ID. + */ + case TLK_REQUEST_DONE: + if (ns || !tlk_args_results_buf) + SMC_RET1(handle, SMC_UNK); + + /* + * Mark the SP state as inactive. + */ + clr_std_smc_active_flag(tlk_ctx.state); + + /* Get a reference to the non-secure context */ + ns_cpu_context = cm_get_context(NON_SECURE); + assert(ns_cpu_context); + + /* + * This is a request completion SMC and we must switch to + * the non-secure world to pass the result. + */ + cm_el1_sysregs_context_save(SECURE); + + /* + * We are done stashing the secure context. Switch to the + * non-secure context and return the result. + */ + cm_el1_sysregs_context_restore(NON_SECURE); + cm_set_next_eret_context(NON_SECURE); + SMC_RET1(ns_cpu_context, tlk_args_results_buf->args[0]); + + /* * This function ID is used only by the SP to indicate it has * finished initialising itself after a cold boot */ case TLK_ENTRY_DONE: - if (ns) + if (ns || !tlk_args_results_buf) SMC_RET1(handle, SMC_UNK); /* |