blob: 925967b292fad1e09cd92531b32499fd18a5d794 [file] [log] [blame]
Ken Liu91d44da2018-09-20 22:42:31 +08001/*
Summer Qin66f1e032020-01-06 15:40:03 +08002 * Copyright (c) 2018-2020, Arm Limited. All rights reserved.
Ken Liu91d44da2018-09-20 22:42:31 +08003 *
4 * SPDX-License-Identifier: BSD-3-Clause
5 *
6 */
7#ifndef __TFM_THREAD_H__
8#define __TFM_THREAD_H__
9
Ken Liu5a2b9052019-08-15 19:03:29 +080010#include <stdint.h>
11#include <stddef.h>
David Hu50711e32019-06-12 18:32:30 +080012#include "tfm_arch.h"
Ken Liu91d44da2018-09-20 22:42:31 +080013#include "cmsis_compiler.h"
14
Summer Qin66f1e032020-01-06 15:40:03 +080015/* State code */
16#define THRD_STATE_CREATING 0
17#define THRD_STATE_RUNNING 1
18#define THRD_STATE_BLOCK 2
19#define THRD_STATE_DETACH 3
20#define THRD_STATE_INVALID 4
Ken Liu91d44da2018-09-20 22:42:31 +080021
22/* Security attribute - default as security */
23#define THRD_ATTR_SECURE_OFFSET 16
24#define THRD_ATTR_SECURE (0)
25#define THRD_ATTR_NON_SECURE (1 << THRD_ATTR_SECURE_OFFSET)
26
27/* Lower value has higher priority */
28#define THRD_PRIOR_MASK 0xFF
29#define THRD_PRIOR_HIGHEST 0x0
30#define THRD_PRIOR_MEDIUM 0x7F
31#define THRD_PRIOR_LOWEST 0xFF
32
33/* Error code */
34#define THRD_SUCCESS 0
35#define THRD_ERR_INVALID_PARAM 1
36
37/* Thread entry function type */
Summer Qin66f1e032020-01-06 15:40:03 +080038typedef void *(*tfm_core_thrd_entry_t)(void *);
Ken Liu91d44da2018-09-20 22:42:31 +080039
40/* Thread context */
Summer Qin66f1e032020-01-06 15:40:03 +080041struct tfm_core_thread_t {
42 tfm_core_thrd_entry_t pfn; /* entry function */
Ken Liu5a2b9052019-08-15 19:03:29 +080043 void *param; /* entry parameter */
Summer Qincb190872020-01-06 16:08:26 +080044 uintptr_t stk_btm; /* stack bottom (lower address) */
45 uintptr_t stk_top; /* stack top (higher address)*/
Ken Liu5a2b9052019-08-15 19:03:29 +080046 uint32_t prior; /* priority */
Summer Qin66f1e032020-01-06 15:40:03 +080047 uint32_t state; /* state */
Ken Liu91d44da2018-09-20 22:42:31 +080048
Summer Qind2ad7e72020-01-06 18:16:35 +080049 struct tfm_arch_ctx_t arch_ctx; /* State context */
Summer Qin66f1e032020-01-06 15:40:03 +080050 struct tfm_core_thread_t *next; /* next thread in list */
Ken Liu91d44da2018-09-20 22:42:31 +080051};
52
53/*
54 * Initialize a thread context with the necessary info.
55 *
56 * Parameters :
57 * pth - pointer of caller provided thread context
58 * pfn - thread entry function
59 * param - thread entry function parameter
Summer Qincb190872020-01-06 16:08:26 +080060 * stk_top - stack pointer top (higher address)
61 * stk_btm - stack pointer bottom (lower address)
Ken Liu91d44da2018-09-20 22:42:31 +080062 *
63 * Notes :
64 * Thread contex rely on caller allocated memory; initialize members in
65 * context. This function does not insert thread into schedulable list.
66 */
Summer Qin66f1e032020-01-06 15:40:03 +080067void tfm_core_thrd_init(struct tfm_core_thread_t *pth,
68 tfm_core_thrd_entry_t pfn, void *param,
Summer Qincb190872020-01-06 16:08:26 +080069 uintptr_t stk_top, uintptr_t stk_btm);
Ken Liu91d44da2018-09-20 22:42:31 +080070
Summer Qin66f1e032020-01-06 15:40:03 +080071/*
72 * Set thread priority.
Ken Liu91d44da2018-09-20 22:42:31 +080073 *
74 * Parameters :
75 * pth - pointer of thread context
76 * prior - priority value (0~255)
77 *
78 * Notes :
79 * Set thread priority. Priority is set to THRD_PRIOR_MEDIUM in
Summer Qin66f1e032020-01-06 15:40:03 +080080 * tfm_core_thrd_init().
Ken Liu91d44da2018-09-20 22:42:31 +080081 */
Summer Qin66f1e032020-01-06 15:40:03 +080082void __STATIC_INLINE tfm_core_thrd_set_priority(struct tfm_core_thread_t *pth,
83 uint32_t prior)
Ken Liu91d44da2018-09-20 22:42:31 +080084{
85 pth->prior &= ~THRD_PRIOR_MASK;
86 pth->prior |= prior & THRD_PRIOR_MASK;
87}
88
89/*
90 * Set thread security attribute.
91 *
92 * Parameters :
93 * pth - pointer of thread context
94 * attr_secure - THRD_ATTR_SECURE or THRD_ATTR_NON_SECURE
95 *
96 * Notes
97 * Reuse prior of thread context to shift down non-secure thread priority.
98 */
Summer Qin66f1e032020-01-06 15:40:03 +080099void __STATIC_INLINE tfm_core_thrd_set_secure(struct tfm_core_thread_t *pth,
100 uint32_t attr_secure)
Ken Liu91d44da2018-09-20 22:42:31 +0800101{
102 pth->prior &= ~THRD_ATTR_NON_SECURE;
103 pth->prior |= attr_secure;
104}
105
106/*
Summer Qin66f1e032020-01-06 15:40:03 +0800107 * Set thread state.
Ken Liu91d44da2018-09-20 22:42:31 +0800108 *
109 * Parameters :
110 * pth - pointer of thread context
Summer Qin66f1e032020-01-06 15:40:03 +0800111 * new_state - new state of thread
Ken Liu91d44da2018-09-20 22:42:31 +0800112 *
113 * Return :
114 * None
115 *
116 * Notes :
Summer Qin66f1e032020-01-06 15:40:03 +0800117 * Thread state is not changed if invalid state value inputed.
Ken Liu91d44da2018-09-20 22:42:31 +0800118 */
Summer Qin66f1e032020-01-06 15:40:03 +0800119void tfm_core_thrd_set_state(struct tfm_core_thread_t *pth, uint32_t new_state);
Ken Liu91d44da2018-09-20 22:42:31 +0800120
121/*
Summer Qin66f1e032020-01-06 15:40:03 +0800122 * Get thread state.
Ken Liu91d44da2018-09-20 22:42:31 +0800123 *
124 * Parameters :
125 * pth - pointer of thread context
126 *
127 * Return :
Summer Qin66f1e032020-01-06 15:40:03 +0800128 * State of thread
Ken Liu91d44da2018-09-20 22:42:31 +0800129 */
Summer Qin66f1e032020-01-06 15:40:03 +0800130uint32_t __STATIC_INLINE tfm_core_thrd_get_state(struct tfm_core_thread_t *pth)
Ken Liu91d44da2018-09-20 22:42:31 +0800131{
Summer Qin66f1e032020-01-06 15:40:03 +0800132 return pth->state;
Ken Liu91d44da2018-09-20 22:42:31 +0800133}
134
135/*
136 * Set thread state return value.
137 *
138 * Parameters :
139 * pth - pointer of thread context
140 * retval - return value to be set for thread state
141 *
142 * Notes :
143 * This API is useful for blocked syscall blocking thread. Syscall
144 * could set its return value to the caller before caller goes.
145 */
Summer Qin66f1e032020-01-06 15:40:03 +0800146void __STATIC_INLINE tfm_core_thrd_set_retval(struct tfm_core_thread_t *pth,
147 uint32_t retval)
Ken Liu91d44da2018-09-20 22:42:31 +0800148{
Summer Qind2ad7e72020-01-06 18:16:35 +0800149 TFM_STATE_RET_VAL(&pth->arch_ctx) = retval;
Ken Liu91d44da2018-09-20 22:42:31 +0800150}
151
152/*
153 * Validate thread context and insert it into schedulable list.
154 *
155 * Parameters :
156 * pth - pointer of thread context
157 *
158 * Return :
159 * THRD_SUCCESS for success. Or an error is returned.
160 *
161 * Notes :
162 * This function validates thread info. It returns error if thread info
Summer Qin66f1e032020-01-06 15:40:03 +0800163 * is not correct. Thread is avaliable after successful tfm_core_thrd_start().
Ken Liu91d44da2018-09-20 22:42:31 +0800164 */
Summer Qin66f1e032020-01-06 15:40:03 +0800165uint32_t tfm_core_thrd_start(struct tfm_core_thread_t *pth);
Ken Liu91d44da2018-09-20 22:42:31 +0800166
167/*
168 * Get current running thread.
169 *
170 * Return :
171 * Current running thread context pointer.
172 */
Summer Qin66f1e032020-01-06 15:40:03 +0800173struct tfm_core_thread_t *tfm_core_thrd_get_curr_thread(void);
Ken Liu91d44da2018-09-20 22:42:31 +0800174
175/*
176 * Get next running thread in list.
177 *
178 * Return :
179 * Pointer of next thread to be run.
180 */
Summer Qin66f1e032020-01-06 15:40:03 +0800181struct tfm_core_thread_t *tfm_core_thrd_get_next_thread(void);
Ken Liu91d44da2018-09-20 22:42:31 +0800182
183/*
Ken Liu483f5da2019-04-24 10:45:21 +0800184 * Start scheduler for existing threads
185 *
186 * Parameters:
187 * pth - pointer of the caller context collecting thread
188 *
189 * Notes :
190 * This function should be called only ONCE to start the scheduler.
191 * Caller needs to provide a thread object to collect current context.
192 * The usage of the collected context is caller defined.
193 */
Summer Qin66f1e032020-01-06 15:40:03 +0800194void tfm_core_thrd_start_scheduler(struct tfm_core_thread_t *pth);
Ken Liu483f5da2019-04-24 10:45:21 +0800195
196/*
Ken Liu91d44da2018-09-20 22:42:31 +0800197 * Activate a scheduling action after exception.
198 *
199 * Notes :
200 * This function could be called multiple times before scheduling.
201 */
Summer Qin66f1e032020-01-06 15:40:03 +0800202void tfm_core_thrd_activate_schedule(void);
Ken Liu91d44da2018-09-20 22:42:31 +0800203
204/*
Summer Qind2ad7e72020-01-06 18:16:35 +0800205 * Save current architecture context into 'prev' thread and switch to 'next'.
Ken Liu91d44da2018-09-20 22:42:31 +0800206 *
207 * Parameters :
Summer Qind2ad7e72020-01-06 18:16:35 +0800208 * p_actx - latest caller context
Ken Liu91d44da2018-09-20 22:42:31 +0800209 * prev - previous thread to be switched out
210 * next - thread to be run
211 *
212 * Notes :
213 * This function could be called multiple times before scheduling.
214 */
Summer Qind2ad7e72020-01-06 18:16:35 +0800215void tfm_core_thrd_switch_context(struct tfm_arch_ctx_t *p_actx,
Summer Qin66f1e032020-01-06 15:40:03 +0800216 struct tfm_core_thread_t *prev,
217 struct tfm_core_thread_t *next);
Ken Liu91d44da2018-09-20 22:42:31 +0800218
Ken Liu91d44da2018-09-20 22:42:31 +0800219#endif