冷冻机厂家
免费服务热线

Free service

hotline

010-00000000
冷冻机厂家
热门搜索:
成功案例
当前位置:首页 > 成功案例

当嵌入式操作系统FreeRTOS的原理与实

发布时间:2021-09-11 23:37:31 阅读: 来源:冷冻机厂家

嵌入式操作系统FreeRTOS的原理与实现

在嵌入式领域中,嵌入式实时操作系统正得到越来越广泛的应用。采用嵌入式实时操作系统(rtos)可以更合理、更有效地利用cpu的资源,简化应用软件的设计,缩短系统开发时间,更好地保证系统的实时性和可靠性。由于rtos需占用一定的系统资源(尤其是ram资源),只有μc/os-ii、embo下面大家了解1下这款实验机的用处和优势体现在那里s、salvo、freertos等少数实时操作系统能在小ram单片机上运行。相对于c/os-ii、embos等商业操作系统,freertos操作系统是完全免费的操作系统,具有源码公开、可移植、可裁减、调度策略灵活的特点,可以方便地移植到各种单片机上运行,其最新版本为2.6版。

1 freertos操作系统功能

作为一个轻量级的操作系统,freertos提供的功能包括:任务管理、时间管理、信号量、消息队列、内存管理、记录功能等,可基本满足较小系统的需要。freertos内核支持优先级调度算法,每个任务可根据重要程度的不同被赋予一定的优先级,cpu总是让处于就绪态的、优先级最高的任务先运行。freert0s内核同时支持轮换调度算法,系统允许不同的任务使用相同的优先级,在没有更高优先级任务就绪的情况下,同一优先级的任务共享cpu的使用时间。

freertos的内核可根据用户需要设置为可剥夺型内核或不可剥夺型内核。当freertos被设置为可剥夺型内核时,处于就绪态的高优先级任务能剥夺低优先级任务的cpu使用权,这样可保证系统满足实时性的要求;当freertos被设置为不可剥夺型内核时,处于就绪态的高优先级任务只有等当前运行任务主动释放cpu的使用权后才能获得运行,这样可提高cpu的运行效率。

2 freertos操作系统的原理与实现

2. 1任务调度机制的实现

任务调度机制是嵌入式实时操作系统的一个重要概念,也是其核心技术。对于可剥夺型内核,优先级高的任务一旦就绪就能剥夺优先级较低任务的cpu使用权,提高了系统的实时响应能力。不同于μc/os-ii,freertos对系统任务的数量没有限制,既支持优先级调度算法也支持轮换调度算法,因此freertos采用双向链表而不是采用查任务就绪表的方法来进行任务调度。系统定义的链表和链表节点数据结构如下所示:

typedef struct xlist{ //定义链表结构

unsigned portshorpt usnumberofitems;

//usnumberofitems为链表的长度,为0表示链表为空

volatile xlistitem * pxhead;//pxhead为链表的头指针

volatile xlistitem * pxindex; //pxindex指向链表当前结点的指针

volatile xlistitem xlistend; //xlistend为链表尾结点

}xlist;

struct xlist_item { //定义链表结点的结构

port tick type xitem value;

//xitem value的值用于实现时间管理

//port tick type为时针节拍数据类型,

//可根据需要选择为16位或32位

volatile struct xlist_item * pxnext;

//指向链表的前一个结点

void * pvowner;//指向此链表结点所在的任务控制块

void * pvcontainer;//指向此链表结点所在的链表};

freertos中每个任务对应于一个任务控制块(tcb),其定义如下所示:

typedef struct tsktaskcontrolblock {

portstack_type * pxtopofstack;

//指向任务堆栈结束处

portstack_type * pxstack;

//指向任务堆栈起始处

unsigned portshort usstackdepth; //定义堆栈深度

signed portchar pctaskname[tskmax_task_name_len];//任务名称

unsigned portchar ucpriority; //任务优先级

xlistitem xgenericlistitem;

//用于把tcb插入就绪链表或等待链表

xlistitem xeventlistitem;

//用于把tcb插入事件链表(如消息队列)

unsigned portchar uctcbnumber; //用于记录功能

}tsktcb;

freertos钢丝和钢丝绳厂商需向用户展现其产品的质量、安全性和性能定义就绪任务链表数组为xlist pxready—taskslists[portmax_priorities]。其中portmax_priorities为系统定义的最大优先级。若想使优先级为n的任务进入就绪态,需要把此任务对应的tcb中的结点xgenericlistltem插入到链表pxreadytaskslists[n]中,还要把xgenericlistitem中的pvcontainer指向pxreadytaskslists[n]方可实现。

当进行任务调度时,调度算法首先实现优先级调度。系统按照优先级从高到低的顺序从就绪任务链表数组中寻找usnumberofitems第一个不为0的优先级,此优先级即为当前最高就绪优先级,据此实现优先级调度。若此优先级下只有一个就绪任务,则此就绪任务进入运行态;若此优先级下有多个就绪任务,则需采用轮换调度算法实现多任务轮流执行。

若在优先级n下执行轮换调度算法,系统先通过执行(pxreadytaskslists[n])→pxindex=(pxreadytasks-lists[n])→pxlndex→pxnext语句得到当前结点所指向的下一个结点,再通过此结点的pvowner指针得到对应的任务控制块,最后使此任务控制块对应的任务进入运行态。由此可见,在freertos中,相同优先级任务之间的切换时间为一个时钟节拍周期。

以图l为例,设系统的最大任务数为pottmax_priorities,在某一时刻进行任务调度时,得到pxreadytaskslists[i].usnumberofitems=o(i=2...portmax_priorities)以及pxreadytaskslists[1]。usnumberofitems=3。由此内核可知当前最高就绪优先级为l,且此优先级下已有三个任务已进入就绪态.由于最高就绪优先级下有多个就绪任务,系统需执行轮换调度算法实现任务切换;通过指针pxlndex可知任务l为当前任务,而任务l的pxnext结点指向任务2,因此系统把pxindex指向任务2并执行任务2来实现任务调度。当下一个时钟节拍到来时,若最高就绪优先级仍为1,由图l可见,系统会把pxindex指向任务3并执行任务3。

为了加快任务调度的速度,frecrtos通过变量uctopreadypriotity跟踪当前就绪的最高优先级。当把一个任务加入就绪链表时,如果此任务的优先级高于uctopreadypriority,则把这个任务的优先级赋予uctopreadypriority。这样当进行优先级调度时,调度算法不是从portmax_priorities而是从uctopready-priority开始搜索。这就加快了搜索的速度,同时缩短了内核关断时间。

2.2 任务管理的实现

实现多个任务的有效管理是操作系统的主要功能。freertos下可实现创建任务、删除任务、挂起任务、恢复任务、设定任务优先级、获得任务相关信息等功能。下面主可以改动横梁的移动速度要讨论freertos下任务创建和任务删除的实现。当调用staskcreate()函数创建一个新的任务时,freertos首先为新任务分配所需的内存。若内存分配成功,则初始化任务控制块的任务名称、堆栈深度和任务优先级,然后根据堆栈的增长方向初始化任务控制块的堆栈。接着,freertos把当前创建的任务加入到就绪任务链表。若当前此任务的优先级为最高,则把此优先级赋值给变量uctopreadypriorlty(其作用见2.1节)。若任务调度程序已经运行且当前创建的任务优先级为最高,则进行任务切换.

不同于μc/os—ii,freertos下任务删除分两步进行。当用户调用vtaskdelete()函数后,执行任务删除的第一步:freertos先把要因此删除的任务从就绪任务链表和事件等待链表中删除,然后把此任务添加到任务删除链表,若删除的任务是当前运行任务,系统就执行任务调度函数,至此完成任务删除的第一步。当系统空闲任务即prvldletask()函数运行时,若发现任务删除链表中有等待删除的任务,则进行任务删除的第二步,即释放该任务占用的内存空间,并把该任务从任务删除链表中删除,这样才彻底删除了这个任务。值得注意的是,在freertos中,当系统被配置为不可剥夺内核时,空闲任务还有实现各个任务切换的功能。

通过比较μc/os-ii和freertos的具体代码发现,采用两步删除的策略有利于减少内核关断时间,减少任务删除函数的执行时间,尤其是当删除多个任务的时候。

2.3 时间管理的实现

freertos提供的典型时间管理函数是vtaskdelay(),调用此函数可以实现将任务延时一段特定时间的功能。在freert0s中,若一个任务要延时xtickstodelay个时钟节拍,系统内核会把当前系统已运行的时钟节拍总数(定义为xtickcount,32位长度)加上xtickstodelay得到任务下次唤醒时的时钟节拍数xtimetowake。然后,内核把此任务的任务控制块从就绪链表中删除,把xtimetowake作为结点值赋予任务的xitemvalue,再根据xtimetowake的值把任务控制块按照顺序插入不同的链表。若xtimetowake>xtickcount,即计算中没有出现溢出,内核把任务控制块插入到pxdelayedtasklist链表;若xtimetowake

杭州定做工作服
杭州定做职业装
杭州工作服订制
杭州工作服订做