Freertos列表与列表项简介:
列表是freertos中一中常用的数据结构,在物理单元上是非连续的、非顺序的,并且是一种双向环形列表。相当于数据结构中的链表!!!
列表的结构体:
列表的结构示意图:
Freertos中相关的API函数:
相关的宏:
相关代码:
#define START_TASK_PRIO 1 /* 任务优先级 */
#define START_STK_SIZE 128 /* 任务堆栈大小 */
TaskHandle_t StartTask_Handler; /* 任务句柄 */
void start_task(void *pvParameters); /* 任务函数 */
/* TASK1 任务 配置
* 包括: 任务句柄 任务优先级 堆栈大小 创建任务
*/
#define TASK1_PRIO 2 /* 任务优先级 */
#define TASK1_STK_SIZE 128 /* 任务堆栈大小 */
TaskHandle_t Task1Task_Handler; /* 任务句柄 */
void task1(void *pvParameters); /* 任务函数 */
List_t TestList;
ListItem_t TestListItem1;
ListItem_t TestListItem2;
ListItem_t TestListItem3;
/******************************************************************************************************/
/**
* @brief FreeRTOS例程入口函数
* @param 无
* @retval 无
*/
void freertos_demo(void)
{
xTaskCreate((TaskFunction_t )start_task, /* 任务函数 */
(const char* )"start_task", /* 任务名称 */
(uint16_t )START_STK_SIZE, /* 任务堆栈大小 */
(void* )NULL, /* 传入给任务函数的参数 */
(UBaseType_t )START_TASK_PRIO, /* 任务优先级 */
(TaskHandle_t* )&StartTask_Handler); /* 任务句柄 */
vTaskStartScheduler();
}
/**
* @brief start_task
* @param pvParameters : 传入参数(未用到)
* @retval 无
*/
void start_task(void *pvParameters)
{
taskENTER_CRITICAL(); /* 进入临界区 */
/* 创建任务1 */
xTaskCreate((TaskFunction_t )task1, /* 任务函数 */
(const char* )"task1", /* 任务名称 */
(uint16_t )TASK1_STK_SIZE, /* 任务堆栈大小 */
(void* )NULL, /* 传入给任务函数的参数 */
(UBaseType_t )TASK1_PRIO, /* 任务优先级 */
(TaskHandle_t* )&Task1Task_Handler); /* 任务句柄 */
vTaskDelete(StartTask_Handler); /* 删除开始任务 */
taskEXIT_CRITICAL(); /* 退出临界区 */
}
/**
* @brief task1
* @param pvParameters : 传入参数(未用到)
* @retval 无
*/
void task1(void *pvParameters)
{
vListInitialise(&TestList);
vListInitialiseItem(&TestListItem1);
vListInitialiseItem(&TestListItem2);
vListInitialiseItem(&TestListItem3);
TestListItem1.xItemValue=10;
TestListItem2.xItemValue=20;
TestListItem3.xItemValue=30;
printf("/**************第二步:打印列表和列表项的地址**************/\r\n");
printf("项目\t\t\t 地址\r\n");
printf("TestList\t\t0x%p\t\r\n", &TestList);
printf("TestList->pxIndex\t0x%p\t\r\n", TestList.pxIndex);
printf("TestList->xListEnd\t0x%p\t\r\n", (&TestList.xListEnd));
printf("ListItem1\t\t0x%p\t\r\n", &TestListItem1);
printf("ListItem2\t\t0x%p\t\r\n", &TestListItem2);
printf("ListItem3\t\t0x%p\t\r\n", &TestListItem3);
printf("/**************************结束***************************/\r\n");
printf("/*****************第三步:列表项 1、2、3 插入列表******************/\r\n");
vListInsert((List_t* )&TestList, /* 列表 */
(ListItem_t* )&TestListItem1); /* 列表项 */
vListInsert((List_t* )&TestList, /* 列表 */
(ListItem_t* )&TestListItem2); /* 列表项 */
vListInsert((List_t* )&TestList, /* 列表 */
(ListItem_t* )&TestListItem3); /* 列表项 */
printf("TestList->pxIndex\t0x%p\t\r\n", TestList.pxIndex);
printf("ListItem1->next\t\t0x%p\t\r\n", TestListItem1.pxNext);
printf("ListItem1->previous\t\t0x%p\t\r\n", TestListItem1.pxPrevious);
/* 移除列表项 */
uxListRemove(&TestListItem1);
printf("ListItem2->next\t\t0x%p\t\r\n", TestListItem2.pxNext);
printf("ListItem2->previous\t\t0x%p\t\r\n", TestListItem2.pxPrevious);
TestList.pxIndex = &TestListItem2;
/* 在末尾插入列表项1,这个函数取决于列表指针指向哪个列表项 */
vListInsertEnd((List_t* )&TestList, /* 列表 */
(ListItem_t* )&TestListItem1);
printf("TestList->pxIndex\t0x%p\t\r\n", TestList.pxIndex);
printf("ListItem1->next\t\t0x%p\t\r\n", TestListItem1.pxNext);
printf("ListItem1->previous\t\t0x%p\t\r\n", TestListItem1.pxPrevious);
while (1)
{
vTaskDelay(10);
}
}