1 /*
2  * Copyright (C) 2015-2020 Alibaba Group Holding Limited
3  */
4 
5 #include <stdio.h>
6 #include <stdlib.h>
7 
8 #include <aos/kernel.h>
9 
10 #if AOS_COMP_CLI
11 #include "aos/cli.h"
12 #endif
13 
14 /**
15  * 该示例使用任务管理函数来控制任务的执行状态,具体场景为任务2因等待某个信号量进入阻塞状态,而此时被任务1将其挂起,则任务2仍然是处于阻塞状态,\n\r
16  * 如果在此过程中等到信号量,则任务2会解除阻塞进入挂起状态;如果未等到信号量,则任务2恢复状态后仍然处于阻塞状态。\n\r
17  * 示例说明如下:
18  *   1. 在t0时刻,任务task1、task2分别通过aos_task_new()和aos_task_new_ext()函数调用被创建,之后task1进入就绪状态,而task2处于挂起状态。
19  *   2. Task1得到运行后,在t1时刻调用aos_task_resume()将task2恢复,task2进入就绪状态,之后task1通过调用aos_msleep()进入休眠状态,task2因为task1休眠而获得CPU执行权,task2运行后因等待信号量进入阻塞状态。
20  *   3. Task1在t2时刻因延迟到期得到运行,并调用aos_task_suspend()将task2挂起,task2此时的状态为阻塞挂起。之后task1通过调用aos_msleep()进入休眠状态。
21  *   4. Task2在t3时刻因延迟到期得到运行,并调用aos_task_resume()将task2恢复,此时task2的状态为阻塞状态。之后task1通过调用aos_msleep()进入休眠状态。
22  *   5. Task1在t4时刻因延迟到期得到运行,并调用aos_sem_signal()释放信号量,这时task2因等到信号量而进入就绪状态。待到task1再次进入休眠转改后task2得到运行,进入运行状态。
23  */
24 
25 /* module name used by log print */
26 #define MODULE_NAME "aos_task_example"
27 
28 /* sem handle for synchronize of task1 and task2 */
29 static aos_sem_t g_testsync_sem;
30 
31 /* task handle for task1 and task2*/
32 static aos_task_t task1_handle;
33 static aos_task_t task2_handle;
34 
35 /* task entry for task1*/
task1_entry()36 void task1_entry()
37 {
38     aos_status_t status;
39 
40     printf("[%s]task1 is running!\n", MODULE_NAME);
41     printf("[%s]task1 resume task2!\n", MODULE_NAME);
42 
43     status = aos_task_resume(&task2_handle);
44 
45     if (0 != status)
46     {
47         printf("[%s]task1 resume task2 failed(%ld)!\n", MODULE_NAME, status);
48     }
49     printf("[%s]task1 start to sleep and release CPU!\n", MODULE_NAME);
50     aos_msleep(10000);
51 
52     printf("[%s]task1 suspend task2!\n", MODULE_NAME);
53     if (0 != aos_task_suspend(&task2_handle))
54     {
55         printf("[%s]task1 resume task2 failed!\n", MODULE_NAME);
56     }
57     printf("[%s]task1 start to sleep and release CPU!\n", MODULE_NAME);
58     aos_msleep(10000);
59 
60     printf("[%s]task1 resume task2 again!\n", MODULE_NAME);
61     status = aos_task_resume(&task2_handle);
62 
63     if (0 != status)
64     {
65         printf("[%s]task1 resume task2 failed(%ld)!\n", MODULE_NAME, status);
66     }
67 
68     printf("[%s]task1 start to sleep and release CPU!\n", MODULE_NAME);
69     aos_msleep(10000);
70     printf("[%s]task1 signal a semphone!\n", MODULE_NAME);
71     aos_sem_signal(&g_testsync_sem);
72     printf("[%s]task1 start to sleep and release CPU!\n", MODULE_NAME);
73     aos_msleep(10000);
74     aos_task_exit(0);
75 }
76 
77 /* task entry for task2*/
task2_entry()78 void task2_entry()
79 {
80     printf("[%s]task2 is running!\n", MODULE_NAME);
81     if (0 != aos_sem_wait(&g_testsync_sem, AOS_WAIT_FOREVER))
82     {
83         printf("[%s]task2 wait semphone failed!\n", MODULE_NAME);
84     }
85 
86     printf("[%s]task2 get semphone and is running!\n", MODULE_NAME);
87     aos_task_exit(0);
88 }
89 
90 /* task example init function*/
aos_task_example(int argc,char ** argv)91 static void aos_task_example(int argc, char **argv)
92 {
93     aos_status_t status;
94 
95     status = aos_sem_new(&g_testsync_sem, 0);
96     if (status != 0)
97     {
98         printf("[%s]sem new failed, err=%ld\n", MODULE_NAME, status);
99         return;
100     }
101 
102     status = aos_task_create(&task2_handle, "task2", task2_entry, NULL, NULL, 4096, 50, AOS_TASK_NONE);
103     if (status != 0) {
104         aos_sem_free(&g_testsync_sem);
105         printf("[%s]create %s error\n", MODULE_NAME, "task2");
106         return;
107     }
108 
109     status = aos_task_create(&task1_handle, "task1", task1_entry, NULL, NULL, 4096, 50, AOS_TASK_AUTORUN);
110     if (status != 0) {
111         aos_sem_free(&g_testsync_sem);
112         printf("[%s]create %s error\n", MODULE_NAME, "task1");
113         return;
114     }
115 
116 }
117 
118 #if AOS_COMP_CLI
119 /* reg args: fun, cmd, description*/
120 ALIOS_CLI_CMD_REGISTER(aos_task_example, task_example, aos task example)
121 #endif