理解FreeRtos的链表

想弄明白freertos内部是如何工作的?

从哪里入手呢?那么先看看TASK吧。结果发现TASK里面调用了LIST。然后看了几篇文章,发现至少有两篇文章说,首先要弄懂LIST,也就是需要弄懂链表。于是找谭浩强的C语言看了看。说这种是单链表,如下

STRUCT  student {
      DATA;
      next * student_ptr;
}

而这种是双链表,如下

STRUCT student {
      DATA;
      next       *student_ptr;
      previous *student_Ptr;
}

可见,链表是靠内存的真实物理地址来寻址的,地址找到了,那么所对应的数据也就找到了。


那么知道了这些,如何读懂链表的那些函数呢?就是freertos源码里面的list.C。

可以发现,list.C和LIST.H包含了所有的list函数。可见很清晰,隔离做的不错。

list.C可以看到 作者很久没有更新了,尽管freertos版本经常更新。list.C里面仅仅有5个函数

void vListInitialise( xList *pxList );

void vListInitialiseItem( xListItem *pxItem );

void vListInsert( xList *pxList, xListItem *pxNewListItem );

void vListInsertEnd( xList *pxList, xListItem *pxNewListItem );

void vListRemove( xListItem *pxItemToRemove );


如此少的函数,直接读源码吧,并查阅了一些资料,感觉比较好的有

FreeRTOS高级篇1---FreeRTOS列表和列表项

FreeRTOS 内核中的链表

FreeRTOS代码剖析之5:链表管理list.c


看了这些以后,发现还是迷迷糊糊。

原因就是我对链表太陌生了。一直以来我写程序从来不用链表的,链表用了就可能出错。与写出安全的程序是相违背的。但这次是为了读懂代码,所以不得不硬头皮想办法。

最好的办法就是弄个简单的例子,用keil 、MDK运行一下。

#include "list.h"


xList list;
xListItem item1 = {1};
xListItem item2 = {2};
xListItem item3 = {3};
xListItem item4 = {4};


int main(void)
{

  vListInitialise((xList *) &list);
  
  vListInitialiseItem( (xListItem *) &item1);
  vListInitialiseItem( (xListItem *) &item2);
  vListInitialiseItem( (xListItem *) &item3);
  vListInitialiseItem( (xListItem *) &item4);

  vListInsertEnd((xList *) & (list), &item1);
  vListInsertEnd((xList *) & (list), &item2);
  vListInsertEnd((xList *) & (list), &item3);
  vListInsertEnd((xList *) & (list), &item4);
  
  vListRemove(&item3);
  
  while (1);
}

这样就彻底理解了。当然说起来轻巧,弄这个例子过程也比较曲折。

另外,如果随意(不按照item的顺序)的 添加删除ITEM,可能就会在

for( pxIterator = ( xListItem * ) &( pxList->xListEnd ); pxIterator->pxNext->xItemValue <= xValueOfInsertion; pxIterator = pxIterator->pxNext )

就是这句话停在了这里出不来。


好了,到点吃饭了,有空再议。


 ==================================================

再举个例子吧,这次不按照1/2/3/4顺序添加,当然Freertos是按照顺序的。

例子如下:

#include "list.h"  
  
  
xList list;  
xListItem item1 = {1};  
xListItem item2 = {2};  
xListItem item3 = {3};  
xListItem item4 = {4};  
  
  
int main(void)  
{  
  
  vListInitialise((xList *) &list);  
    
  vListInitialiseItem( (xListItem *) &item1);  
  vListInitialiseItem( (xListItem *) &item2);  
  vListInitialiseItem( (xListItem *) &item3);  
  vListInitialiseItem( (xListItem *) &item4);  
  
  vListInsertEnd((xList *) & (list), &item1); //【a】 
  vListInsertEnd((xList *) & (list), &item4); //【b】 
  vListInsertEnd((xList *) & (list), &item3); // 【c】
  
  
	vListInsert((xList *) & (list), (xListItem *)&item2); //[D]
	
	vListRemove(&item4); //[E]
  
  while (1);
}


    



  • 1
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
FreeRTOS提供了一种简单的链表实现,用于管理任务和其他数据结构。这个链表是通过使用FreeRTOS提供的列表管理函数来处理的。 在FreeRTOS中,链表被称为列表(List),可以在任务之间共享和访问。以下是一些常用的列表管理函数: 1. `vListInitialise()`:初始化一个链表。使用此函数必须在使用链表之前调用。 2. `vListInitialiseItem()`:初始化要插入链表的列表项。 3. `vListInsert()`:将一个列表项插入到链表中。可以选择按照优先级顺序插入。 4. `vListRemove()`:从链表中移除一个列表项。 5. `listGET_OWNER_OF_NEXT_ENTRY()`:获取下一个列表项的所有者。 下面是一个使用FreeRTOS链表的示例: ```c // 定义一个任务控制块结构体 typedef struct { char name[10]; TaskHandle_t handle; uint32_t priority; } TaskControlBlock; // 创建一个链表头 List_t taskList; void vTaskFunction(void *pvParameters) { // 任务函数代码... } int main() { // 初始化链表 vListInitialise(&taskList); // 创建任务并将任务控制块插入链表 TaskControlBlock tcb1 = {"Task 1", NULL, 2}; xTaskCreate(vTaskFunction, "Task 1", configMINIMAL_STACK_SIZE, &tcb1, tcb1.priority, &tcb1.handle); vListInsert(&taskList, &(tcb1.handle).xStateListItem); TaskControlBlock tcb2 = {"Task 2", NULL, 1}; xTaskCreate(vTaskFunction, "Task 2", configMINIMAL_STACK_SIZE, &tcb2, tcb2.priority, &tcb2.handle); vListInsert(&taskList, &(tcb2.handle).xStateListItem); // 遍历链表 ListItem_t *pxIterator; TaskControlBlock *pxTCB; pxIterator = listGET_HEAD_ENTRY(&taskList); while (pxIterator != NULL) { pxTCB = (TaskControlBlock *)listGET_LIST_ITEM_OWNER(pxIterator); printf("Task name: %s\n", pxTCB->name); pxIterator = listGET_NEXT(pxIterator); } vTaskStartScheduler(); return 0; } ``` 通过上面的示例,你可以看到如何使用FreeRTOS链表来管理任务。请注意,在实际使用中,你可能需要根据你的需求进行适当的修改和调整。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值