1 /*
2 * Copyright (c) 2009-2022 Huawei Technologies Co., Ltd. All rights reserved.
3 *
4 * UniProton is licensed under Mulan PSL v2.
5 * You can use this software according to the terms and conditions of the Mulan PSL v2.
6 * You may obtain a copy of Mulan PSL v2 at:
7 * http://license.coscl.org.cn/MulanPSL2
8 * THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND,
9 * EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT,
10 * MERCHANTABILITY OR FIT FOR A PARTICULAR PURPOSE.
11 * See the Mulan PSL v2 for more details.
12 * Create: 2009-12-22
13 * Description: 任务模块的内部头文件
14 */
15 #ifndef PRT_TASK_EXTERNAL_H
16 #define PRT_TASK_EXTERNAL_H
17
18 #include "prt_task.h"
19 #include "prt_lib_external.h"
20 #include "prt_list_external.h"
21 #include "prt_sys_external.h"
22 #include "prt_err_external.h"
23 #include "prt_tick_external.h"
24 #include "prt_cpu_external.h"
25 #include "prt_mem_external.h"
26
27 struct TagOsRunQue {
28 U32 taskReadyListBitMap;
29 /* 优先级bit位表 */
30 U32 tskChildBitMap[OS_GET_WORD_NUM_BY_PRIONUM(OS_TSK_NUM_OF_PRIORITIES)];
31 struct TagListObject readyList[OS_TSK_NUM_OF_PRIORITIES];
32 };
33
34 struct TagOsTskSortedDelayList {
35 /* 延时任务链表 */
36 struct TagListObject tskList;
37 };
38
39 /*
40 * 任务线程及进程控制块的结构体统一定义。
41 */
42 struct TagTskCb {
43 /* 当前任务的SP */
44 void *stackPointer;
45 /* 任务状态,后续内部全改成U32 */
46 U32 taskStatus;
47 /* 任务的运行优先级 */
48 TskPrior priority;
49 /* 保留字段 */
50 U16 reserved2;
51 /* 任务栈大小 */
52 U32 stackSize;
53 TskHandle taskPid;
54
55 /* 任务栈顶 */
56 uintptr_t topOfStack;
57
58 /* 任务入口函数 */
59 TskEntryFunc taskEntry;
60 /* 任务Pend的信号量指针 */
61 void *taskSem;
62
63 /* 任务的参数 */
64 uintptr_t args[4];
65 #if (defined(OS_OPTION_TASK_INFO))
66 /* 存放任务名 */
67 char name[OS_TSK_NAME_LEN];
68 #endif
69 /* 任务栈配置标记 */
70 U16 stackCfgFlg;
71 U16 reserved;
72 /* 信号量链表指针 */
73 struct TagListObject pendList;
74 /* 任务延时链表指针 */
75 struct TagListObject timerList;
76
77 #if defined(OS_OPTION_EVENT)
78 /* 任务事件 */
79 U32 event;
80 /* 任务事件掩码 */
81 U32 eventMask;
82 #endif
83
84 /* 任务记录的最后一个错误码 */
85 U32 lastErr;
86 /* 任务恢复的时间点(单位Tick) */
87 U64 expirationTick;
88 };
89
90 /*
91 * 任务信息表节点数据结构
92 */
93 struct TagTskMonNode {
94 /* 撑死/饿死的时间点(tick) */
95 U64 expiredTick;
96 /* 撑死/饿死标记 */
97 U32 flag;
98 /* 撑死/饿死检测标记 */
99 U32 ckFlag;
100 /* 检测类型 */
101 U32 ckStyles;
102 /* 保留(对齐) */
103 U32 reserved;
104 };
105
106 typedef void (*TskCoresleep)(void);
107 typedef void (*TaskNameGetFunc)(U32 taskId, char **taskName);
108 typedef U32 (*TaskNameAddFunc)(U32 taskId, const char *name);
109
110 extern U16 g_uniTaskLock;
111 extern TskHandle g_idleTaskId;
112 extern struct TagOsRunQue g_runQueue;
113 extern struct TagTskCb *g_runningTask;
114 extern struct TagTskCb *g_highestTask;
115 extern struct TagOsTskSortedDelayList g_tskSortedDelay;
116
117 extern U32 g_tskMaxNum;
118 extern U32 g_tskBaseId;
119 extern struct TagTskCb *g_tskCbArray;
120 extern struct TskModInfo g_tskModInfo;
121 extern struct TagTskMonNode *g_tskMonList;
122
123 extern TskEntryFunc g_tskIdleEntry;
124 extern TaskNameAddFunc g_taskNameAdd;
125 extern TaskNameGetFunc g_taskNameGet;
126
127 extern volatile TskCoresleep g_taskCoreSleep;
128
129 #define OS_TSK_PARA_0 0
130 #define OS_TSK_PARA_1 1
131 #define OS_TSK_PARA_2 2
132 #define OS_TSK_PARA_3 3
133
134 /* 定义任务的缺省优先级 */
135 #define OS_TSK_DEFAULT_PRIORITY 20
136 #define OS_TSK_PRIO_BIT_MAP_POW 5
137 #define OS_TSK_STACK_TOP_MAGIC 0xAAAAAAAA
138
139 #define OS_TSK_PRIO_RDY_BIT 0x80000000U
140
141 #define OS_TASK_LOCK_DATA g_uniTaskLock
142 #define IDLE_TASK_ID g_idleTaskId
143 #define RUNNING_TASK g_runningTask
144 #define TSK_GET_INDEX(taskId) ((taskId) - g_tskBaseId)
145
146 /* 内核进程的进程及线程调度控制块使用同一类型 */
147 #define OS_MAX_TCB_NUM (g_tskMaxNum + 1 + 1) // 1个IDLE,1个无效任务
148
149 #define OS_TSK_DELAY_LOCKED_DETACH(task) ListDelete(&(task)->timerList)
150 #define CHECK_TSK_PID_OVERFLOW(taskId) (TSK_GET_INDEX(taskId) >= (g_tskMaxNum + 1))
151
152 /* 定义任务的缺省任务栈大小 */
153 #define OS_PST_ZOMBIE_TASK (&g_tskCbArray[OS_MAX_TCB_NUM - 1])
154 #define TSK_IS_UNUSED(tsk) ((tsk)->taskStatus == OS_TSK_UNUSED)
155 #define TSK_STATUS_TST(tsk, statBit) (((tsk)->taskStatus & (statBit)) != 0)
156 #define TSK_STATUS_CLEAR(tsk, statBit) ((tsk)->taskStatus &= ~(statBit))
157 #define TSK_STATUS_SET(tsk, statBit) ((tsk)->taskStatus |= (statBit))
158 #define OS_TSK_LOCK() (OS_TASK_LOCK_DATA++)
159 #define GET_TCB_PEND(ptr) LIST_COMPONENT(ptr, struct TagTskCb, pendList)
160 #define GET_TCB_HANDLE(taskPid) (((struct TagTskCb *)g_tskCbArray) + TSK_GET_INDEX(taskPid))
161 // 保留一个idle task。最大任务handle为FE,FF表示硬中断线程。
162 #define MAX_TASK_NUM ((1U << OS_TSK_TCB_INDEX_BITS) - 2) // 254
163 #define OS_TSK_BLOCK (OS_TSK_DELAY | OS_TSK_PEND | OS_TSK_SUSPEND | OS_TSK_QUEUE_PEND | \
164 OS_TSK_EVENT_PEND)
165
166 // 设置任务优先级就绪链表主BitMap中Bit位,每32个优先级对应一个BIT位,即Bit0(优先级0~31),Bit1(优先级32~63),依次类推。
167 #define OS_SET_RDY_TSK_BIT_MAP(priority) \
168 (OS_TSK_PRIO_RDY_BIT >> ((priority) >> OS_TSK_PRIO_BIT_MAP_POW))
169 // 清除任务优先级就绪链表主BitMap中Bit位,每32个优先级对应一个BIT位,即Bit0(优先级0~31),Bit1(优先级32~63),依次类推。
170 #define OS_CLR_RDY_TSK_BIT_MAP(priority) \
171 (~(OS_TSK_PRIO_RDY_BIT >> ((priority) >> OS_TSK_PRIO_BIT_MAP_POW)))
172
173 // 设置任务优先级就绪链表子BitMap中Bit位,每个优先级对应一个BIT位。
174 #define OS_SET_CHILD_BIT_MAP(priority) \
175 (OS_TSK_PRIO_RDY_BIT >> ((priority) % OS_WORD_BIT_NUM))
176 // 清除任务优先级就绪链表子BitMap中Bit位,每个优先级对应一个BIT位。
177 #define OS_CLR_CHILD_BIT_MAP(priority) \
178 (~(OS_TSK_PRIO_RDY_BIT >> ((priority) % OS_WORD_BIT_NUM)))
179
180 extern void OsTaskScan(void);
181 extern void OsTskSchedule(void);
182 extern void OsTskEntry(TskHandle taskId);
183 extern void OsTaskExit(struct TagTskCb *tsk);
184 extern void OsTskReadyAdd(struct TagTskCb *task);
185 extern void OsTskReadyDel(struct TagTskCb *taskCb);
186 extern void OsTskSwitchHookCaller(U32 prevPid, U32 nextPid);
187 extern void OsTskTimerAdd(struct TagTskCb *taskCb, uintptr_t timeout);
188
189 extern U32 OsTskMaxNumGet(void);
190 extern U32 OsTaskDelete(TskHandle taskPid);
191 extern U32 OsTaskCreateOnly(TskHandle *taskPid, struct TskInitParam *initParam);
192
193 extern void OsTskScheduleFast(void);
194 extern void OsTskScheduleFastPs(uintptr_t intSave);
195
196 /*
197 * 模块内内联函数定义
198 */
OsTskHighestSet(void)199 OS_SEC_ALW_INLINE INLINE void OsTskHighestSet(void)
200 {
201 U32 rdyListIdx;
202 struct TagListObject *readyList = NULL;
203 U32 childBitMapIdx;
204
205 /* find the highest priority */
206 /* get valid Child BitMap according to the ReadyListBitMap */
207 childBitMapIdx = OsGetLmb1(g_runQueue.taskReadyListBitMap);
208
209 /* get the ready list task priority idx in the Child BitMap */
210 rdyListIdx = OsGetLmb1(g_runQueue.tskChildBitMap[childBitMapIdx]);
211
212 /* get task ready list according to the task priority */
213 readyList = &(g_runQueue.readyList[OS_GET_32BIT_ARRAY_BASE(childBitMapIdx) + rdyListIdx]);
214
215 g_highestTask = GET_TCB_PEND(OS_LIST_FIRST(readyList));
216 }
217
OsTskReadyAddBgd(struct TagTskCb * task)218 OS_SEC_ALW_INLINE INLINE void OsTskReadyAddBgd(struct TagTskCb *task)
219 {
220 OsTskReadyAdd(task);
221 }
222
223 #endif /* PRT_TASK_EXTERNAL_H */
224