blob: 144349ad21bc6591a80869bc6955a335ad674a72 [file] [log] [blame]
Achin Gupta4a8bfdb2021-10-04 20:13:36 +01001/*
Yann Gautier3b064382024-06-05 10:46:33 +02002 * Copyright (c) 2022-2025, Arm Limited and Contributors. All rights reserved.
Achin Gupta4a8bfdb2021-10-04 20:13:36 +01003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 */
6
7#include <assert.h>
8#include <inttypes.h>
9#include <stdint.h>
10
11#include <arch_features.h>
12#include <arch_helpers.h>
13#include <bl32/tsp/tsp.h>
14#include <common/bl_common.h>
15#include <common/debug.h>
16#include <lib/spinlock.h>
17#include <plat/common/platform.h>
18#include <platform_tsp.h>
19#include "tsp_private.h"
20
21#include <platform_def.h>
22
23/*******************************************************************************
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010024 * Per cpu data structure to populate parameters for an SMC in C code and use
25 * a pointer to this structure in assembler code to populate x0-x7.
26 ******************************************************************************/
27static smc_args_t tsp_smc_args[PLATFORM_CORE_COUNT];
28
29/*******************************************************************************
30 * Per cpu data structure to keep track of TSP activity
31 ******************************************************************************/
32work_statistics_t tsp_stats[PLATFORM_CORE_COUNT];
33
34smc_args_t *set_smc_args(uint64_t arg0,
35 uint64_t arg1,
36 uint64_t arg2,
37 uint64_t arg3,
38 uint64_t arg4,
39 uint64_t arg5,
40 uint64_t arg6,
41 uint64_t arg7)
42{
43 uint32_t linear_id;
44 smc_args_t *pcpu_smc_args;
45
46 /*
47 * Return to Secure Monitor by raising an SMC. The results of the
48 * service are passed as an arguments to the SMC.
49 */
50 linear_id = plat_my_core_pos();
51 pcpu_smc_args = &tsp_smc_args[linear_id];
52 write_sp_arg(pcpu_smc_args, SMC_ARG0, arg0);
53 write_sp_arg(pcpu_smc_args, SMC_ARG1, arg1);
54 write_sp_arg(pcpu_smc_args, SMC_ARG2, arg2);
55 write_sp_arg(pcpu_smc_args, SMC_ARG3, arg3);
56 write_sp_arg(pcpu_smc_args, SMC_ARG4, arg4);
57 write_sp_arg(pcpu_smc_args, SMC_ARG5, arg5);
58 write_sp_arg(pcpu_smc_args, SMC_ARG6, arg6);
59 write_sp_arg(pcpu_smc_args, SMC_ARG7, arg7);
60
61 return pcpu_smc_args;
62}
63
64/*******************************************************************************
65 * Setup function for TSP.
66 ******************************************************************************/
Harrison Mutai32d9e8e2025-02-21 11:50:48 +000067void tsp_setup(u_register_t arg0, u_register_t arg1, u_register_t arg2,
68 u_register_t arg3)
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010069{
Yann Gautierae770fe2024-01-16 19:39:31 +010070 /* Enable early console if EARLY_CONSOLE flag is enabled */
71 plat_setup_early_console();
72
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010073 /* Perform early platform-specific setup. */
Harrison Mutai32d9e8e2025-02-21 11:50:48 +000074 tsp_early_platform_setup(arg0, arg1, arg2, arg3);
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010075
76 /* Perform late platform-specific setup. */
77 tsp_plat_arch_setup();
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010078}
79
80/*******************************************************************************
81 * This function performs any remaining bookkeeping in the test secure payload
82 * before the system is switched off (in response to a psci SYSTEM_OFF request).
83 ******************************************************************************/
84smc_args_t *tsp_system_off_main(uint64_t arg0,
85 uint64_t arg1,
86 uint64_t arg2,
87 uint64_t arg3,
88 uint64_t arg4,
89 uint64_t arg5,
90 uint64_t arg6,
91 uint64_t arg7)
92{
93 uint32_t linear_id = plat_my_core_pos();
94
95 /* Update this cpu's statistics. */
96 tsp_stats[linear_id].smc_count++;
97 tsp_stats[linear_id].eret_count++;
98
Achin Gupta4a8bfdb2021-10-04 20:13:36 +010099 INFO("TSP: cpu 0x%lx SYSTEM_OFF request\n", read_mpidr());
Yann Gautier3b064382024-06-05 10:46:33 +0200100 INFO("TSP: cpu 0x%lx: %u smcs, %u erets requests\n", read_mpidr(),
Achin Gupta4a8bfdb2021-10-04 20:13:36 +0100101 tsp_stats[linear_id].smc_count,
102 tsp_stats[linear_id].eret_count);
Achin Gupta4a8bfdb2021-10-04 20:13:36 +0100103
104 /* Indicate to the SPD that we have completed this request. */
105 return set_smc_args(TSP_SYSTEM_OFF_DONE, 0, 0, 0, 0, 0, 0, 0);
106}
107
108/*******************************************************************************
109 * This function performs any remaining bookkeeping in the test secure payload
110 * before the system is reset (in response to a psci SYSTEM_RESET request).
111 ******************************************************************************/
112smc_args_t *tsp_system_reset_main(uint64_t arg0,
113 uint64_t arg1,
114 uint64_t arg2,
115 uint64_t arg3,
116 uint64_t arg4,
117 uint64_t arg5,
118 uint64_t arg6,
119 uint64_t arg7)
120{
121 uint32_t linear_id = plat_my_core_pos();
122
123 /* Update this cpu's statistics. */
124 tsp_stats[linear_id].smc_count++;
125 tsp_stats[linear_id].eret_count++;
126
Achin Gupta4a8bfdb2021-10-04 20:13:36 +0100127 INFO("TSP: cpu 0x%lx SYSTEM_RESET request\n", read_mpidr());
Yann Gautier3b064382024-06-05 10:46:33 +0200128 INFO("TSP: cpu 0x%lx: %u smcs, %u erets requests\n", read_mpidr(),
Achin Gupta4a8bfdb2021-10-04 20:13:36 +0100129 tsp_stats[linear_id].smc_count,
130 tsp_stats[linear_id].eret_count);
Achin Gupta4a8bfdb2021-10-04 20:13:36 +0100131
132 /* Indicate to the SPD that we have completed this request. */
133 return set_smc_args(TSP_SYSTEM_RESET_DONE, 0, 0, 0, 0, 0, 0, 0);
134}
135
136/*******************************************************************************
137 * TSP smc abort handler. This function is called when aborting a preempted
138 * yielding SMC request. It should cleanup all resources owned by the SMC
139 * handler such as locks or dynamically allocated memory so following SMC
140 * request are executed in a clean environment.
141 ******************************************************************************/
142smc_args_t *tsp_abort_smc_handler(uint64_t func,
143 uint64_t arg1,
144 uint64_t arg2,
145 uint64_t arg3,
146 uint64_t arg4,
147 uint64_t arg5,
148 uint64_t arg6,
149 uint64_t arg7)
150{
151 return set_smc_args(TSP_ABORT_DONE, 0, 0, 0, 0, 0, 0, 0);
152}