Development Guidelines
When a task is created, the OpenHarmony LiteOS-M kernel can perform operations, such as locking or unlocking task scheduling, suspending, restoring, and delaying the task, and setting or obtaining the task priority.
Available APIs
The following table describes APIs available for the OpenHarmony LiteOS-M task module. For more details about the APIs, see the API reference.
Table 1 APIs of the task management module
How to Develop
The typical development process of the task module is as follows:
- Use LOS_TaskLock to lock task scheduling and prevent high-priority tasks from being scheduled.
- Use LOS_TaskCreate to create a task.
- Use LOS_TaskUnlock to unlock task scheduling so that tasks can be scheduled by priority.
- Use LOS_TaskDelay to delay a task.
- Use LOS_TaskSuspend to suspend a task.
- Use LOS_TaskResume to resume the suspended task.
NOTE:
- Running idle tasks reclaims the TCBs and stacks in the to-be-recycled linked list.
- The task name is a pointer without memory space allocated. When setting the task name, do not assign the local variable address to the task name pointer.
- The task stack size is 8-byte aligned. Follow the "nothing more and nothing less" principle while determining the task stack size.
- A running task cannot be suspended if task scheduling is locked.
- Idle tasks and software timer tasks cannot be suspended or deleted.
- In an interrupt handler or when a task is locked, the operation of calling LOS_TaskDelay fails.
- Locking task scheduling does not disable interrupts. Tasks can still be interrupted while task scheduling is locked.
- Locking task scheduling must be used together with unlocking task scheduling.
- Task scheduling may occur while a task priority is being set.
- The maximum number of tasks that can be set for the operating system is the total number of tasks of the operating system, not the number of tasks available to users. For example, if the system software timer occupies one more task resource, the number of task resources available to users decreases by one.
- LOS_CurTaskPriSet and LOS_TaskPriSet cannot be used in interrupts or used to modify the priorities of software timer tasks.
- If the task corresponding to the task ID sent to LOS_TaskPriGet has not been created or the task ID exceeds the maximum number of tasks, -1 will be returned.
- Resources such as a mutex or a semaphore allocated to a task must have been released before the task is deleted.
Development Example
This example describes the priority-based task scheduling and use of task-related APIs, including creating, delaying, suspending, and resuming two tasks with different priorities, and locking/unlocking task scheduling. The sample code is as follows:
UINT32 g_taskHiId;
UINT32 g_taskLoId;
#define TSK_PRIOR_HI 4
#define TSK_PRIOR_LO 5
UINT32 Example_TaskHi(VOID)
{
UINT32 ret;
printf("Enter TaskHi Handler.\n");
/* Delay the task for 100 ticks. The task is then suspended, and the remaining task with the highest priority (TaskLo) will be executed.*/
ret = LOS_TaskDelay(100);
if (ret != LOS_OK) {
printf("Delay TaskHi Failed.\n");
return LOS_NOK;
}
/*After 100 ticks elapse, the task is resumed.*/
printf("TaskHi LOS_TaskDelay Done.\n");
/* Suspend the task.*/
ret = LOS_TaskSuspend(g_taskHiId);
if (ret != LOS_OK) {
printf("Suspend TaskHi Failed.\n");
return LOS_NOK;
}
printf("TaskHi LOS_TaskResume Success.\n");
return ret;
}
/* Entry function of low-priority tasks */
UINT32 Example_TaskLo(VOID)
{
UINT32 ret;
printf("Enter TaskLo Handler.\n");
/* Delay the task for 100 ticks. The task is then suspended, and the remaining task with the highest priority will be executed.*/
ret = LOS_TaskDelay(100);
if (ret != LOS_OK) {
printf("Delay TaskLo Failed.\n");
return LOS_NOK;
}
printf("TaskHi LOS_TaskSuspend Success.\n");
/* Resume the suspended task g_taskHiId.*/
ret = LOS_TaskResume(g_taskHiId);
if (ret != LOS_OK) {
printf("Resume TaskHi Failed.\n");
return LOS_NOK;
}
return ret;
}
/* Task entry function used to create two tasks with different priorities */
UINT32 Example_TskCaseEntry(VOID)
{
UINT32 ret;
TSK_INIT_PARAM_S initParam;
/* Lock task scheduling to prevent newly created tasks from being scheduled prior to this task due to higher priority.*/
LOS_TaskLock();
printf("LOS_TaskLock() Success!\n");
initParam.pfnTaskEntry = (TSK_ENTRY_FUNC)Example_TaskHi;
initParam.usTaskPrio = TSK_PRIOR_HI;
initParam.pcName = "TaskHi";
initParam.uwStackSize = LOSCFG_BASE_CORE_TSK_DEFAULT_STACK_SIZE;
/* Create a high-priority task. The task will not be executed immediately after being created, because task scheduling is locked.*/
ret = LOS_TaskCreate(&g_taskHiId, &initParam);
if (ret != LOS_OK) {
LOS_TaskUnlock();
printf("Example_TaskHi create Failed!\n");
return LOS_NOK;
}
printf("Example_TaskHi create Success!\n");
initParam.pfnTaskEntry = (TSK_ENTRY_FUNC)Example_TaskLo;
initParam.usTaskPrio = TSK_PRIOR_LO;
initParam.pcName = "TaskLo";
initParam.uwStackSize = LOSCFG_BASE_CORE_TSK_DEFAULT_STACK_SIZE;
/*Create a low-priority task. The task will not be executed immediately after being created, because task scheduling is locked.*/
ret = LOS_TaskCreate(&g_taskLoId, &initParam);
if (ret != LOS_OK) {
LOS_TaskUnlock();
printf("Example_TaskLo create Failed!\n");
return LOS_NOK;
}
printf("Example_TaskLo create Success!\n");
/* Unlock task scheduling. The task with the highest priority in the Ready queue will be executed.*/
LOS_TaskUnlock();
return LOS_OK;
}
Verification
The development is successful if the return result is as follows:
LOS_TaskLock() Success!
Example_TaskHi create Success!
Example_TaskLo create Success!
Enter TaskHi Handler.
Enter TaskLo Handler.
TaskHi LOS_TaskDelay Done.
TaskHi LOS_TaskSuspend Success.
TaskHi LOS_TaskResume Success.