1 /*
2 * Copyright (C) 2015-2021 Alibaba Group Holding Limited
3 */
4
5 #include <stdio.h>
6 #include <time.h>
7
8 #include <k_api.h>
9 #include <aos/errno.h>
10 #include <aos/kernel.h>
11
12 #include "rhino_p.h"
13
14 #if (RHINO_CONFIG_KOBJ_DYN_ALLOC == 0)
15 #warning "RHINO_CONFIG_KOBJ_DYN_ALLOC is disabled!"
16 #endif
17
18 static unsigned int used_bitmap;
19
20 #if (RHINO_CONFIG_KOBJ_DYN_ALLOC > 0)
21
aos_task_new(const char * name,void (* fn)(void *),void * arg,size_t stack_size)22 aos_status_t aos_task_new(const char *name, void (*fn)(void *), void *arg, size_t stack_size)
23 {
24 int ret;
25
26 ktask_t *task_handle = NULL;
27
28 #if (RHINO_CONFIG_SCHED_CFS > 0)
29 ret = (int)krhino_cfs_task_dyn_create(&task_handle, name, arg, AOS_DEFAULT_APP_PRI,
30 stack_size / sizeof(cpu_stack_t), fn, 1u);
31 #else
32 ret = (int)krhino_task_dyn_create(&task_handle, name, arg, AOS_DEFAULT_APP_PRI,
33 0, stack_size / sizeof(cpu_stack_t), fn, 1u);
34 #endif
35
36 return rhino2stderrno(ret);
37 }
38
aos_task_new_ext(aos_task_t * task,const char * name,void (* fn)(void *),void * arg,size_t stack_size,int32_t prio)39 aos_status_t aos_task_new_ext(aos_task_t *task, const char *name, void (*fn)(void *),
40 void *arg, size_t stack_size, int32_t prio)
41 {
42 int ret;
43 if (task == NULL) {
44 return -EINVAL;
45 }
46 #if (RHINO_CONFIG_SCHED_CFS > 0)
47 ret = (int)krhino_cfs_task_dyn_create((ktask_t **)task, name, arg, AOS_DEFAULT_APP_PRI,
48 stack_size / sizeof(cpu_stack_t), fn, 1u);
49 #else
50 ret = (int)krhino_task_dyn_create((ktask_t **)task, name, arg, prio,
51 0, stack_size / sizeof(cpu_stack_t), fn, 1u);
52 #endif
53 return rhino2stderrno(ret);
54 }
55
aos_task_create(aos_task_t * task,const char * name,void (* fn)(void *),void * arg,void * stack,size_t stack_size,int32_t prio,uint32_t options)56 aos_status_t aos_task_create(aos_task_t *task, const char *name, void (*fn)(void *),
57 void *arg, void *stack, size_t stack_size, int32_t prio, uint32_t options)
58 {
59 int ret;
60 cpu_stack_t *task_stack = NULL;
61 ktask_t *task_obj;
62
63 if (task == NULL) {
64 return -EINVAL;
65 }
66
67 if (stack == NULL) {
68 task_stack = aos_malloc(stack_size * sizeof(cpu_stack_t));
69 if (task_stack == NULL) {
70 return -ENOMEM;
71 }
72 stack = task_stack;
73 }
74
75 task_obj = aos_malloc(sizeof(ktask_t));
76 if (task_obj == NULL) {
77 aos_free(task_stack);
78 return -ENOMEM;
79 }
80
81 *task = task_obj;
82 #if (RHINO_CONFIG_SCHED_CFS > 0)
83 ret = (int)krhino_cfs_task_create(task_obj, name, arg, prio, (cpu_stack_t *)stack,
84 stack_size / sizeof(cpu_stack_t), fn, options & AOS_TASK_AUTORUN);
85 #else
86 ret = (int)krhino_task_create(task_obj, name, arg, prio, 0, (cpu_stack_t *)stack,
87 stack_size / sizeof(cpu_stack_t), fn, options & AOS_TASK_AUTORUN);
88 #endif
89 if ((ret != RHINO_SUCCESS) && (ret != RHINO_STOPPED)) {
90 aos_free(task_stack);
91 aos_free(task_obj);
92 *task = NULL;
93 }
94
95 return rhino2stderrno(ret);
96 }
97
aos_task_exit(int32_t code)98 void aos_task_exit(int32_t code)
99 {
100 (void)code;
101
102 krhino_task_dyn_del(NULL);
103 }
104
aos_task_delete(aos_task_t * task)105 aos_status_t aos_task_delete(aos_task_t *task)
106 {
107 int ret;
108 ktask_t *ktask;
109
110 CHECK_HANDLE(task);
111
112 ktask = (ktask_t *)(*task);
113
114 ret = (int)krhino_task_dyn_del(ktask);
115
116 return rhino2stderrno(ret);
117 }
118 #endif /* RHINO_CONFIG_KOBJ_DYN_ALLOC */
119
aos_task_resume(aos_task_t * task)120 aos_status_t aos_task_resume(aos_task_t *task)
121 {
122 int ret;
123 ktask_t *ktask;
124
125 CHECK_HANDLE(task);
126
127 ktask = (ktask_t *)(*task);
128 ret = krhino_task_resume(ktask);
129
130 return rhino2stderrno(ret);
131 }
132
aos_task_suspend(aos_task_t * task)133 aos_status_t aos_task_suspend(aos_task_t *task)
134 {
135 int ret;
136 ktask_t *ktask;
137
138 CHECK_HANDLE(task);
139 ktask = (ktask_t *)(*task);
140 ret = krhino_task_suspend(ktask);
141
142 return rhino2stderrno(ret);
143 }
144
aos_task_yield()145 aos_status_t aos_task_yield()
146 {
147 int ret;
148 ret = krhino_task_yield();
149 return rhino2stderrno(ret);
150 }
151
aos_task_self()152 aos_task_t aos_task_self()
153 {
154 return (aos_task_t)krhino_cur_task_get();
155
156 }
157
aos_task_name_get(aos_task_t * task,char * buf,size_t buf_size)158 aos_status_t aos_task_name_get(aos_task_t *task, char *buf, size_t buf_size)
159 {
160 const char *name;
161 int str_len, copy_len;
162
163 CHECK_HANDLE(task);
164
165 if (buf == NULL || buf_size == 0) {
166 return -EINVAL;
167 }
168
169 name = ((ktask_t *)*task)->task_name;
170
171 str_len = strlen(name);
172
173 copy_len = (str_len > (buf_size - 1)) ? buf_size - 1 : str_len;
174 memcpy(buf, name, copy_len);
175 return 0;
176
177 }
178
aos_task_key_create(aos_task_key_t * key)179 aos_status_t aos_task_key_create(aos_task_key_t *key)
180 {
181 int i;
182 if (key == NULL) {
183 return -EINVAL;
184 }
185 for (i = RHINO_CONFIG_TASK_INFO_NUM - 1; i >= 0; i--) {
186 if (!((1 << i) & used_bitmap)) {
187 used_bitmap |= 1 << i;
188 *key = i;
189
190 return 0;
191 }
192 }
193
194 return -EINVAL;
195 }
196
aos_task_key_delete(aos_task_key_t key)197 void aos_task_key_delete(aos_task_key_t key)
198 {
199 if (key >= RHINO_CONFIG_TASK_INFO_NUM) {
200 return;
201 }
202
203 used_bitmap &= ~(1 << key);
204 }
205
206 #if (RHINO_CONFIG_TASK_INFO > 0)
aos_task_setspecific(aos_task_key_t key,void * vp)207 aos_status_t aos_task_setspecific(aos_task_key_t key, void *vp)
208 {
209 int ret;
210 ret = krhino_task_info_set(krhino_cur_task_get(), key, vp);
211 return rhino2stderrno(ret);
212 }
213
aos_task_getspecific(aos_task_key_t key)214 void *aos_task_getspecific(aos_task_key_t key)
215 {
216 void *vp = NULL;
217
218 krhino_task_info_get(krhino_cur_task_get(), key, &vp);
219
220 return vp;
221 }
222
aos_msleep(uint32_t ms)223 void aos_msleep(uint32_t ms)
224 {
225 krhino_task_sleep(MS2TICK(ms));
226 }
227
aos_sched_get_priority_max(uint32_t policy)228 uint32_t aos_sched_get_priority_max(uint32_t policy)
229 {
230 return RHINO_CONFIG_PRI_MAX;
231 }
232
aos_task_ptcb_get(aos_task_t * task,void ** ptcb)233 aos_status_t aos_task_ptcb_get(aos_task_t *task, void **ptcb)
234 {
235 CPSR_ALLOC();
236 CHECK_HANDLE(task);
237 if (ptcb == NULL) {
238 return -EINVAL;
239 }
240
241 RHINO_CRITICAL_ENTER();
242 *(ptcb) = ((ktask_t *)*task)->ptcb;
243 RHINO_CRITICAL_EXIT();
244
245 return 0;
246 }
247
aos_task_ptcb_set(aos_task_t * task,void * ptcb)248 aos_status_t aos_task_ptcb_set(aos_task_t *task, void *ptcb)
249 {
250 CPSR_ALLOC();
251 CHECK_HANDLE(task);
252
253 RHINO_CRITICAL_ENTER();
254 ((ktask_t *)*task)->ptcb = ptcb;
255 RHINO_CRITICAL_EXIT();
256
257 return 0;
258 }
259
aos_task_pri_change(aos_task_t * task,uint8_t pri,uint8_t * old_pri)260 aos_status_t aos_task_pri_change(aos_task_t *task, uint8_t pri, uint8_t *old_pri)
261 {
262 kstat_t ret;
263
264 CHECK_HANDLE(task);
265
266 ret = krhino_task_pri_change((ktask_t *)*task, pri, old_pri);
267
268 return rhino2stderrno(ret);
269 }
270
aos_task_pri_get(aos_task_t * task,uint8_t * priority)271 aos_status_t aos_task_pri_get(aos_task_t *task, uint8_t *priority)
272 {
273 CPSR_ALLOC();
274 CHECK_HANDLE(task);
275 if (priority == NULL) {
276 return -EINVAL;
277 }
278
279 RHINO_CRITICAL_ENTER();
280 *priority = ((ktask_t *)*task)->b_prio;
281 RHINO_CRITICAL_EXIT();
282
283 return 0;
284 }
285
aos_task_sched_policy_set(aos_task_t * task,uint8_t policy,uint8_t pri)286 aos_status_t aos_task_sched_policy_set(aos_task_t *task, uint8_t policy, uint8_t pri)
287 {
288 kstat_t ret;
289
290 CHECK_HANDLE(task);
291
292 if (policy != KSCHED_FIFO && policy != KSCHED_RR && policy != KSCHED_CFS) {
293 return -EINVAL;
294 }
295
296 ret = krhino_sched_param_set((ktask_t *)*task, policy, pri);
297 return rhino2stderrno(ret);
298 }
299
aos_task_sched_policy_get(aos_task_t * task,uint8_t * policy)300 aos_status_t aos_task_sched_policy_get(aos_task_t *task, uint8_t *policy)
301 {
302 kstat_t ret = 0;
303
304 CHECK_HANDLE(task);
305 if (policy == NULL) {
306 return -EINVAL;
307 }
308
309 ret = krhino_sched_policy_get((ktask_t *)*task, policy);
310 return rhino2stderrno(ret);
311 }
312
aos_task_sched_policy_get_default()313 uint32_t aos_task_sched_policy_get_default()
314 {
315 #if (RHINO_CONFIG_SCHED_CFS > 0)
316 return KSCHED_CFS;
317 #else
318 return KSCHED_RR;
319 #endif
320 }
321
aos_task_time_slice_set(aos_task_t * task,uint32_t slice)322 aos_status_t aos_task_time_slice_set(aos_task_t *task, uint32_t slice)
323 {
324 kstat_t ret;
325 CHECK_HANDLE(task);
326
327 ret = krhino_task_time_slice_set((ktask_t *)*task, MS2TICK(slice));
328 return rhino2stderrno(ret);
329 }
330
aos_task_time_slice_get(aos_task_t * task,uint32_t * slice)331 aos_status_t aos_task_time_slice_get(aos_task_t *task, uint32_t *slice)
332 {
333 uint32_t time_slice;
334 CPSR_ALLOC();
335 CHECK_HANDLE(task);
336 if (slice == NULL) {
337 return -EINVAL;
338 }
339
340 RHINO_CRITICAL_ENTER();
341 time_slice = ((ktask_t *)*task)->time_slice;
342 RHINO_CRITICAL_EXIT();
343 *slice = (uint32_t)krhino_ticks_to_ms(time_slice);
344
345 return 0;
346 }
347
348 #endif
349
350