μc/os iii 链表以及vs freertos

1)uCOS-III内核中的链表大多是不循环的双向链表(有头有尾),在插入和删除操作时,要考虑特殊情况(比如插入表头、插入表尾等特殊情况)。
而freertos内核中的链表为双向循环链表,并引入了xListEnd保证了链表永远非空,所以每个元素的插入和删除都是作为表中的一般元素(非表头和表尾)进行的,操作效率要高一些

在这里插入代码片
#include <stdio.h>

typedef struct pend_data  PEND_DATA;
struct pend_data{
    PEND_DATA * prev;
    PEND_DATA * next;
    int prio;
};

typedef struct pend_list PEND_LIST;
struct pend_list{
    PEND_DATA * head;
    PEND_DATA * tail;
    int num;
};

void list_insert_prio(PEND_LIST * list, PEND_DATA * data)
{
    PEND_DATA * nn = NULL;
    if (list->num == 0) {
        list->num = 1;
        data->prev = NULL;
        data->next = NULL;
        list->head = data;
        list->tail = data;
    } else {
        list->num ++;
        nn = list->head;
        while(nn) {
            if (data->prio > nn->prio)
                break;
            else {
                nn = nn->next;
            }
        }
        if (nn == NULL) {
            // at tail
            PEND_DATA * tmp = list->tail;
            list->tail = data;
            data->next = NULL;
            data->prev = tmp;
            tmp->next = data;
        } else {
            if (nn->prev == NULL) {
                // at first
                PEND_DATA * tmp = list->head;
                list->head = data;                data->prev = NULL;
                data->next = tmp;
                tmp->prev = data;
            }else {
                // between
                PEND_DATA * tmp = nn->prev;
                tmp->next = data;
                data->prev = tmp;
                data->next = nn;
                nn->prev = data;
            }
        }
    }

}

int main()
{
    PEND_LIST list1 = {NULL, NULL, 0};
    PEND_DATA d1 = {NULL, NULL, 3};
    PEND_DATA d2 = {NULL, NULL, 1};
    PEND_DATA d3 = {NULL, NULL, 2};
    list_insert_prio(&list1, &d1);
    list_insert_prio(&list1, &d2);
    list_insert_prio(&list1, &d3);

    printf("num = %d\n", list1.num);
    PEND_DATA * tmp = list1.head;
    while(tmp){
        printf("prio = %d\n", tmp->prio);
        tmp = tmp->next;
    }
}                                      

2)在消息投递时,如果有任务在消息队列的pend列表中等待,uC/OS-III的做法是直接将该消息post给等待的任务并把它就绪,整个消息不会经过消息队列。而FreeRTOS的做法是将该消息放置到消息队列中,然后检查是否有任务正等待接收消息,如果有,就将其就绪,由就绪的任务去主动获取该消息。

FreeRTOS的做法实现了投递消息与取出消息的解耦,但这带来了一个问题,就是当某个任务投递完一个消息,并使A任务就绪了,而在A任务执行前,又有一个高优先级的B任务从这个消息队列中取出了该消息,那么A任务在以后试图从消息队列中取出消息时,会出现失败,这是FreeRTOS中所有内核对象的pend操作都可能会出现的情况,内核的做法是会重新计算超时时间,只要没超时,就重新阻塞(按新的阻塞时间),这种设计会降低内核的执行效率。在uC/OS-III中,每一次的消息post操作,要么消息被post到了消息队列上,要么消息被post给了任务,操作结果是明确的,操作过程是高效的。
原文链接:https://blog.csdn.net/weixin_41213648/article/details/88249890

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值