blob: d707346547bae078a5ac1a07f206476d0fc1b365 [file] [log] [blame]
Miklos Balint386b8b52017-11-29 13:12:32 +00001/*
Gyorgy Szing40a7af02019-02-06 14:19:47 +01002 * Copyright (c) 2017-2019, Arm Limited. All rights reserved.
Miklos Balint386b8b52017-11-29 13:12:32 +00003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7
8#ifndef __SPM_API_H__
9#define __SPM_API_H__
10
11/* This file contains the apis exported by the SPM to tfm core */
Mate Toth-Pal3db437a2018-06-22 16:15:13 +020012#include "tfm_api.h"
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010013#include "spm_partition_defs.h"
Miklos Balint386b8b52017-11-29 13:12:32 +000014#include "secure_fw/core/tfm_secure_api.h"
15
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010016#define SPM_INVALID_PARTITION_IDX (~0U)
17
Summer Qineb537e52019-03-29 09:57:10 +080018/* Privileged definitions for partition thread mode */
19#define TFM_PARTITION_PRIVILEGED_MODE 1
20#define TFM_PARTITION_UNPRIVILEGED_MODE 0
21
Miklos Balint386b8b52017-11-29 13:12:32 +000022enum spm_err_t {
23 SPM_ERR_OK = 0,
Mate Toth-Pal349714a2018-02-23 15:30:24 +010024 SPM_ERR_PARTITION_DB_NOT_INIT,
25 SPM_ERR_PARTITION_ALREADY_ACTIVE,
26 SPM_ERR_PARTITION_NOT_AVAILABLE,
Hugues de Valonf704c802019-02-19 14:51:41 +000027 SPM_ERR_INVALID_PARAMETER,
Miklos Balint386b8b52017-11-29 13:12:32 +000028 SPM_ERR_INVALID_CONFIG,
29};
30
Mate Toth-Pal65291f32018-02-23 14:35:22 +010031enum spm_part_state_t {
Mate Toth-Pal349714a2018-02-23 15:30:24 +010032 SPM_PARTITION_STATE_UNINIT = 0,
33 SPM_PARTITION_STATE_IDLE,
34 SPM_PARTITION_STATE_RUNNING,
Mate Toth-Pal4341de02018-10-02 12:55:47 +020035 SPM_PARTITION_STATE_HANDLING_IRQ,
Mate Toth-Pal349714a2018-02-23 15:30:24 +010036 SPM_PARTITION_STATE_SUSPENDED,
37 SPM_PARTITION_STATE_BLOCKED,
38 SPM_PARTITION_STATE_CLOSED
Mate Toth-Pal65291f32018-02-23 14:35:22 +010039};
40
Mate Toth-Pal59398712018-02-28 17:06:40 +010041enum spm_part_flag_mask_t {
Edison Aibb614aa2018-11-21 15:15:00 +080042 SPM_PART_FLAG_APP_ROT = 0x01,
43 SPM_PART_FLAG_PSA_ROT = 0x02,
44 SPM_PART_FLAG_IPC = 0x04
Mate Toth-Pal59398712018-02-28 17:06:40 +010045};
46
Miklos Balint386b8b52017-11-29 13:12:32 +000047/**
Mate Toth-Pal3db437a2018-06-22 16:15:13 +020048 * \brief Holds the iovec parameters that are passed to a service
49 *
50 * \note The size of the structure is (and have to be) multiple of 8 bytes
51 */
52struct iovec_args_t {
53 psa_invec in_vec[PSA_MAX_IOVEC]; /*!< Array of psa_invec objects */
54 size_t in_len; /*!< Number psa_invec objects in in_vec
55 */
56 psa_outvec out_vec[PSA_MAX_IOVEC]; /*!< Array of psa_outvec objects */
57 size_t out_len; /*!< Number psa_outvec objects in out_vec
58 */
59};
60
61/**
Mate Toth-Pal18b83922018-02-26 17:58:18 +010062 * \brief Runtime context information of a partition
63 */
64struct spm_partition_runtime_data_t {
65 uint32_t partition_state;
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010066 uint32_t caller_partition_idx;
Mate Toth-Pal21a74c92018-04-13 14:05:41 +020067 int32_t caller_client_id;
Mate Toth-Pal18b83922018-02-26 17:58:18 +010068 uint32_t share;
Mate Toth-Pal18b83922018-02-26 17:58:18 +010069 uint32_t stack_ptr;
Miklos Balintace4c3f2018-07-30 12:31:15 +020070 uint32_t lr;
Mate Toth-Pal2a6f8c22018-12-13 16:37:17 +010071 int32_t iovec_api; /*!< Whether the function in the partition
72 * had been called using the iovec API.
73 * FIXME: Remove the field once this is the
74 * only option
75 */
Mate Toth-Pal3db437a2018-06-22 16:15:13 +020076 struct iovec_args_t iovec_args;
77 psa_outvec *orig_outvec;
Mate Toth-Pal4341de02018-10-02 12:55:47 +020078 uint32_t *ctx_stack_ptr;
79 /*
80 * FIXME: There is a 'signal_mask' defined in the structure
81 * 'tfm_spm_ipc_partition_t'. It should be eliminated, and the IPC
82 * implementation should use the 'signal_mask' define in this structure.
83 * However currently the content of 'spm_partition_runtime_data_t' structure
84 * is not maintained by the IPC implementation. This is to be fixed with the
85 * effort of restructuring common code among library and IPC model.
86 */
87 uint32_t signal_mask;
Mate Toth-Pal18b83922018-02-26 17:58:18 +010088};
89
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010090
Mate Toth-Pal18b83922018-02-26 17:58:18 +010091/**
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010092 * \brief Returns the index of the partition with the given partition ID.
Miklos Balint386b8b52017-11-29 13:12:32 +000093 *
Mate Toth-Pal349714a2018-02-23 15:30:24 +010094 * \param[in] partition_id Partition id
Miklos Balint386b8b52017-11-29 13:12:32 +000095 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +010096 * \return the partition idx if partition_id is valid,
97 * \ref SPM_INVALID_PARTITION_IDX othervise
98 */
99uint32_t get_partition_idx(uint32_t partition_id);
100
Miklos Balintdd02bb32019-05-26 21:13:12 +0200101#if (TFM_LVL != 1) || defined(TFM_PSA_API)
Summer Qind00e4db2019-05-09 18:03:52 +0800102/**
103 * \brief Get bottom of stack region for a partition
104 *
105 * \param[in] partition_idx Partition index
106 *
107 * \return Stack region bottom value
108 *
109 * \note This function doesn't check if partition_idx is valid.
110 */
111uint32_t tfm_spm_partition_get_stack_bottom(uint32_t partition_idx);
112
113/**
114 * \brief Get top of stack region for a partition
115 *
116 * \param[in] partition_idx Partition index
117 *
118 * \return Stack region top value
119 *
120 * \note This function doesn't check if partition_idx is valid.
121 */
122uint32_t tfm_spm_partition_get_stack_top(uint32_t partition_idx);
Miklos Balintdd02bb32019-05-26 21:13:12 +0200123#endif
Summer Qind00e4db2019-05-09 18:03:52 +0800124
Miklos Balintdd02bb32019-05-26 21:13:12 +0200125#if (TFM_LVL != 1) && !defined(TFM_PSA_API)
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100126/**
127 * \brief Configure isolated sandbox for a partition
128 *
129 * \param[in] partition_idx Partition index
130 *
Miklos Balint386b8b52017-11-29 13:12:32 +0000131 * \return Error code \ref spm_err_t
132 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100133 * \note This function doesn't check if partition_idx is valid.
Miklos Balint386b8b52017-11-29 13:12:32 +0000134 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100135enum spm_err_t tfm_spm_partition_sandbox_config(uint32_t partition_idx);
Miklos Balint386b8b52017-11-29 13:12:32 +0000136
137/**
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100138 * \brief Deconfigure sandbox for a partition
Miklos Balint386b8b52017-11-29 13:12:32 +0000139 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100140 * \param[in] partition_idx Partition index
Miklos Balint386b8b52017-11-29 13:12:32 +0000141 *
142 * \return Error code \ref spm_err_t
143 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100144 * \note This function doesn't check if partition_idx is valid.
Miklos Balint386b8b52017-11-29 13:12:32 +0000145 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100146enum spm_err_t tfm_spm_partition_sandbox_deconfig(uint32_t partition_idx);
Miklos Balint386b8b52017-11-29 13:12:32 +0000147
148/**
Mate Toth-Pal21a74c92018-04-13 14:05:41 +0200149 * \brief Get the start of the zero-initialised region for a partition
150 *
151 * \param[in] partition_idx Partition idx
152 *
153 * \return Start of the zero-initialised region
154 *
155 * \note This function doesn't check if partition_idx is valid.
156 */
157uint32_t tfm_spm_partition_get_zi_start(uint32_t partition_idx);
158
159/**
160 * \brief Get the limit of the zero-initialised region for a partition
161 *
162 * \param[in] partition_idx Partition idx
163 *
164 * \return Limit of the zero-initialised region
165 *
166 * \note This function doesn't check if partition_idx is valid.
167 * \note The address returned is not part of the region.
168 */
169uint32_t tfm_spm_partition_get_zi_limit(uint32_t partition_idx);
170
171/**
172 * \brief Get the start of the read-write region for a partition
173 *
174 * \param[in] partition_idx Partition idx
175 *
176 * \return Start of the read-write region
177 *
178 * \note This function doesn't check if partition_idx is valid.
179 */
180uint32_t tfm_spm_partition_get_rw_start(uint32_t partition_idx);
181
182/**
183 * \brief Get the limit of the read-write region for a partition
184 *
185 * \param[in] partition_idx Partition idx
186 *
187 * \return Limit of the read-write region
188 *
189 * \note This function doesn't check if partition_idx is valid.
190 * \note The address returned is not part of the region.
191 */
192uint32_t tfm_spm_partition_get_rw_limit(uint32_t partition_idx);
193
194/**
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200195 * \brief Save stack pointer for partition in database
196 *
197 * \param[in] partition_idx Partition index
198 * \param[in] stack_ptr Stack pointer to be stored
199 *
200 * \note This function doesn't check if partition_idx is valid.
201 */
Gyorgy Szing40a7af02019-02-06 14:19:47 +0100202void tfm_spm_partition_set_stack(uint32_t partition_idx, uint32_t stack_ptr);
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200203#endif
204
205/**
Summer Qinb4a854d2019-05-29 15:31:22 +0800206 * \brief Get the id of the partition for its index from the db
207 *
208 * \param[in] partition_idx Partition index
209 *
210 * \return Partition ID for that partition
211 *
212 * \note This function doesn't check if partition_idx is valid.
213 */
214uint32_t tfm_spm_partition_get_partition_id(uint32_t partition_idx);
215
216/**
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200217 * \brief Get the flags associated with a partition
218 *
219 * \param[in] partition_idx Partition index
220 *
221 * \return Flags associated with the partition
222 *
223 * \note This function doesn't check if partition_idx is valid.
224 */
225uint32_t tfm_spm_partition_get_flags(uint32_t partition_idx);
226
Summer Qinb4a854d2019-05-29 15:31:22 +0800227#ifndef TFM_PSA_API
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200228/**
Mate Toth-Pal4341de02018-10-02 12:55:47 +0200229 * \brief Save interrupted partition context on ctx stack
230 *
231 * \param[in] partition_idx Partition index
232 *
233 * \note This function doesn't check if partition_idx is valid.
234 * \note This function doesn't whether the ctx stack overflows.
235 */
236void tfm_spm_partition_push_interrupted_ctx(uint32_t partition_idx);
237
238/**
239 * \brief Restores interrupted partition context on ctx stack
240 *
241 * \param[in] partition_idx Partition index
242 *
243 * \note This function doesn't check if partition_idx is valid.
244 * \note This function doesn't whether the ctx stack underflows.
245 */
246void tfm_spm_partition_pop_interrupted_ctx(uint32_t partition_idx);
247
248/**
249 * \brief Save handler partition context on ctx stack
250 *
251 * \param[in] partition_idx Partition index
252 *
253 * \note This function doesn't check if partition_idx is valid.
254 * \note This function doesn't whether the ctx stack overflows.
255 */
256void tfm_spm_partition_push_handler_ctx(uint32_t partition_idx);
257
258/**
259 * \brief Restores handler partition context on ctx stack
260 *
261 * \param[in] partition_idx Partition index
262 *
263 * \note This function doesn't check if partition_idx is valid.
264 * \note This function doesn't whether the ctx stack underflows.
265 */
266void tfm_spm_partition_pop_handler_ctx(uint32_t partition_idx);
267
268/**
Mate Toth-Pal18b83922018-02-26 17:58:18 +0100269 * \brief Get the current runtime data of a partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100270 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100271 * \param[in] partition_idx Partition index
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100272 *
Mate Toth-Pal18b83922018-02-26 17:58:18 +0100273 * \return The runtime data of the specified partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100274 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100275 * \note This function doesn't check if partition_idx is valid.
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100276 */
Mate Toth-Pal18b83922018-02-26 17:58:18 +0100277const struct spm_partition_runtime_data_t *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100278 tfm_spm_partition_get_runtime_data(uint32_t partition_idx);
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100279
280/**
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100281 * \brief Returns the index of the partition that has running state
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100282 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100283 * \return The index of the partition with the running state, if there is any
284 * set. 0 otherwise.
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100285 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100286uint32_t tfm_spm_partition_get_running_partition_idx(void);
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100287
288/**
Miklos Balintace4c3f2018-07-30 12:31:15 +0200289 * \brief Save stack pointer and link register for partition in database
290 *
291 * \param[in] partition_idx Partition index
292 * \param[in] stack_ptr Stack pointer to be stored
293 * \param[in] lr Link register to be stored
294 *
295 * \note This function doesn't check if partition_idx is valid.
296 */
297void tfm_spm_partition_store_context(uint32_t partition_idx,
298 uint32_t stack_ptr, uint32_t lr);
299
300/**
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100301 * \brief Set the current state of a partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100302 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100303 * \param[in] partition_idx Partition index
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100304 * \param[in] state The state to be set
305 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100306 * \note This function doesn't check if partition_idx is valid.
Gyorgy Szing40a7af02019-02-06 14:19:47 +0100307 * \note The state has to have the value set of \ref spm_part_state_t.
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100308 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100309void tfm_spm_partition_set_state(uint32_t partition_idx, uint32_t state);
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100310
311/**
Miklos Balint6a139ae2018-04-04 19:44:37 +0200312 * \brief Set the caller partition index for a given partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100313 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100314 * \param[in] partition_idx Partition index
Miklos Balint6a139ae2018-04-04 19:44:37 +0200315 * \param[in] caller_partition_idx The index of the caller partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100316 *
Miklos Balint6a139ae2018-04-04 19:44:37 +0200317 * \note This function doesn't check if any of the partition_idxs are valid.
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100318 */
Miklos Balint6a139ae2018-04-04 19:44:37 +0200319void tfm_spm_partition_set_caller_partition_idx(uint32_t partition_idx,
320 uint32_t caller_partition_idx);
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100321
322/**
Mate Toth-Pal21a74c92018-04-13 14:05:41 +0200323* \brief Set the caller client ID for a given partition
324*
325* \param[in] partition_idx Partition index
326* \param[in] caller_client_id The ID of the calling client
327*
328* \note This function doesn't check if any of the partition_idxs are valid.
329*/
330void tfm_spm_partition_set_caller_client_id(uint32_t partition_idx,
331 int32_t caller_client_id);
332
333/**
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100334 * \brief Set the buffer share region of the partition
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100335 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100336 * \param[in] partition_idx Partition index
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100337 * \param[in] share The buffer share region to be set
338 *
339 * \return Error code \ref spm_err_t
340 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100341 * \note This function doesn't check if partition_idx is valid.
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100342 * \note share has to have the value set of \ref tfm_buffer_share_region_e
343 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100344enum spm_err_t tfm_spm_partition_set_share(uint32_t partition_idx,
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100345 uint32_t share);
Mate Toth-Pal65291f32018-02-23 14:35:22 +0100346
347/**
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200348 * \brief Set the iovec parameters for the partition
349 *
350 * \param[in] partition_idx Partition index
351 * \param[in] args The arguments of the secure function
352 *
353 * args is expected to be of type int32_t[4] where:
354 * args[0] is in_vec
355 * args[1] is in_len
356 * args[2] is out_vec
357 * args[3] is out_len
358 *
Hugues de Valonf704c802019-02-19 14:51:41 +0000359 * \return Error code \ref spm_err_t
360 *
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200361 * \note This function doesn't check if partition_idx is valid.
362 * \note This function assumes that the iovecs that are passed in args are
363 * valid, and does no sanity check on them at all.
364 */
Hugues de Valonf704c802019-02-19 14:51:41 +0000365enum spm_err_t tfm_spm_partition_set_iovec(uint32_t partition_idx,
366 const int32_t *args);
Mate Toth-Pal3db437a2018-06-22 16:15:13 +0200367
368/**
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100369 * \brief Execute partition init function
Miklos Balint386b8b52017-11-29 13:12:32 +0000370 *
371 * \return Error code \ref spm_err_t
372 */
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100373enum spm_err_t tfm_spm_partition_init(void);
Miklos Balint386b8b52017-11-29 13:12:32 +0000374
375/**
Mate Toth-Pal349714a2018-02-23 15:30:24 +0100376 * \brief Clears the context info from the database for a partition.
Miklos Balint386b8b52017-11-29 13:12:32 +0000377 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100378 * \param[in] partition_idx Partition index
Miklos Balint386b8b52017-11-29 13:12:32 +0000379 *
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100380 * \note This function doesn't check if partition_idx is valid.
Miklos Balint386b8b52017-11-29 13:12:32 +0000381 */
Mate Toth-Pal52674ab2018-02-26 09:47:56 +0100382void tfm_spm_partition_cleanup_context(uint32_t partition_idx);
Mate Toth-Pal4341de02018-10-02 12:55:47 +0200383
384/**
385 * \brief Set the signal mask for a given partition
386 *
387 * \param[in] partition_idx Partition index
388 * \param[in] signal_mask The signal mask to be set for the partition
389 *
390 * \note This function doesn't check if any of the partition_idxs are valid.
391 */
392void tfm_spm_partition_set_signal_mask(uint32_t partition_idx,
393 uint32_t signal_mask);
Summer Qinb4a854d2019-05-29 15:31:22 +0800394#endif /* !defined(TFM_PSA_API) */
395
396/**
397 * \brief Initialize partition database
398 *
399 * \return Error code \ref spm_err_t
400 */
401enum spm_err_t tfm_spm_db_init(void);
Miklos Balint386b8b52017-11-29 13:12:32 +0000402
Edison Aib5571352019-03-22 10:49:52 +0800403/**
404 * \brief Change the privilege mode for partition thread mode.
405 *
406 * \param[in] privileged Privileged mode,
407 * \ref TFM_PARTITION_PRIVILEGED_MODE
408 * and \ref TFM_PARTITION_UNPRIVILEGED_MODE
409 *
410 * \note Barrier instructions are not called by this function, and if
411 * it is called in thread mode, it might be necessary to call
412 * them after this function returns (just like it is done in
413 * jump_to_ns_code()).
414 */
415void tfm_spm_partition_change_privilege(uint32_t privileged);
416
Miklos Balint386b8b52017-11-29 13:12:32 +0000417#endif /*__SPM_API_H__ */