1、第5章嵌入式操作系统 第5章嵌入式操作系统 5.1 引言引言5.2 嵌入式操作系统概述嵌入式操作系统概述5.3 操作系统的基本概念操作系统的基本概念5.4 C/OS-简介简介5.5 C/OS-内核结构内核结构5.6 C/OS-在在ARM上的移植上的移植5.7 基于基于C/OS-构建的构建的TCP/IP/PPP协议栈协议栈思考与练习题思考与练习题 第5章嵌入式操作系统 5.1 引引 言言 嵌入式系统采用的操作系统一般是实时操作系统(Real Time Operating System,RTOS),它是嵌入式应用软件的基础和开发平台。RTOS一般是一段嵌入在目标代码中的软件,用户的其他应用程序都建
2、立在它的基础上。RTOS的引入,解决了嵌入式软件开发标准化的难题。随着嵌入式系统中软件比重不断上升、应用程序越来越大,对开发人员、应用程序接口、程序档案的组织管理成为一个大的课题。引入RTOS相当于引入了一种新的管理模式,对于开发单位和开发人员都是一个提高。基于RTOS开发出的程序,具有较高的可移植性,可以实现90%以上的设备独立,一些成熟的通用程序还可以作为专用库函数产品推向社会。第5章嵌入式操作系统 嵌入式软件的函数化、产品化能够促进嵌入式软件模块的复用性,从而降低系统的研发成本。C/OS-是一个可裁减的、源代码公开的嵌入式实时操作系统。它提供任务调度、任务间的通信与同步、任务管理、时间管
3、理和内存管理等基本功能,现在已经应用于多个领域,非常适合实时操作系统的教学。第5章嵌入式操作系统 5.2 嵌入式操作系统概述嵌入式操作系统概述 5.2.1 5.2.1 嵌入式实时操作系统嵌入式实时操作系统一般的,嵌入式操作系统是指支持嵌入式系统工作的操作系统,它在知识体系和技术结构上与通用操作系统没有太大区别。通用操作系统只注重平均性能,如对于整个系统来说,所有任务的平均响应时间是关键,并不关心单个任务的响应时间;而实时系统强调的是实时性,即系统的正确性不仅依赖于计算结果,也依赖于结果产生的时间。因此,实时系统是指一个能够在指定的或者确定的时间内,实现系统功能和对外部或内部、同步或异步事件作出
4、响应的系统。图5-1形象地体现了两者之间的关系。第5章嵌入式操作系统 图5-1 实时操作系统与嵌入式操作系统的关系 第5章嵌入式操作系统 嵌入式实时操作系统是嵌入在系统目标代码中的软件,并在系统启动之后运行。用户的其他应用程序是运行在这个软件平台基础之上的多个任务。实时操作系统根据各个任务的要求,进行资源管理、任务调度、中断响应等。并且,在嵌入式实时操作系统中,每个任务根据重要性不同具有不同的优先级,系统根据各个任务的优先级来动态地切换各个任务,从而保证对实时性的要求。因此,嵌入式实时操作系统可以理解为一个标准内核,它将CPU时间、中断、定时器等资源都封装起来,留给用户标准的API接口。在这个
5、基础上,用户通过使用这些内核提供的API函数进行程序开发,最终完成各个任务的协调工作。第5章嵌入式操作系统 5.2.2 典型的嵌入式操作系统典型的嵌入式操作系统 1 1VxWorksVxWorksVxWorks操作系统是美国WindRiver公司于1993年设计开发的一种嵌入式实时操作系统。VxWorks拥有良好的持续发展能力、高性能的内核以及友好的用户开发环境,是目前嵌入式系统领域中使用最广泛、市场占有率最高的实时操作系统。VxWorks支持多种处理器,如x86、i960、Sun Sparc、Power PC、Motorola MC68xxx、MIPS RX000、Strong ARM等。V
6、xWorks操作系统基于微内核结构,由400多个相对独立、短小精悍的目标模块组成,用户可以根据需要增加或删减适当模块来裁剪和配置系统,其链接器可按应用的需要来动态链接目标模块。大多数的VxWorks API是专有的,采用GNU的编译和调试器。第5章嵌入式操作系统 VxWorks以其良好的可靠性和卓越的实时性被广泛地应用在通信、军事、航空、航天等高精尖技术及实时性要求极高的领域中,如通信卫星、军事演习、导弹制导和飞机导航等。尤其在美国的F-16、FA-18战斗机,B-12隐形轰炸机和爱国者导弹上,甚至美国JPL实验室研制的著名“索杰纳”火星探测器上也使用了VxWorks。第5章嵌入式操作系统 2
7、 2Windows CEWindows CE Microsoft Windows CE是从整体上为有限资源的平台而设计的多线程、完整优先权、多任务的嵌入式操作系统。Windows CE主要针对小容量、移动式、智能化、32位、连接设备的模块化实时应用。高度模块化使得Windows CE能够对掌上设备、无线设备、专用工业控制器的用户电子设备等进行定制,并使得Windows CE能在多种处理器体系结构上运行,尤其适用于那些对内存占用空间具有一定限制的设备。Windows CE操作系统的基本内核至少需要200 KB的ROM。它能够支持Win32 API子集、多种用户界面硬件、多种串行和网络通信技术、C
8、OM/OLE和其他进程间通信的先进方法。而且,Microsoft公司为Windows CE提供了Platform Builder和Embedded Visual Studio开发工具。第5章嵌入式操作系统 Windows CE有5个主要的模块:(1)内核模块:支持进程和线程处理及内存管理等基本服务。(2)内核系统调用接口模块:允许应用软件访问操作系统提供的服务。(3)文件系统模块:支持DOS等格式的文件系统。(4)图形窗口和事件子系统模块:控制图形显示并提供Windows GUI界面。(5)通信模块:允许与其他设备进行信息交换。第5章嵌入式操作系统 需要指出的是,Windows CE嵌入式操作
9、系统不是一个硬实时操作系统,但它最大的优点是能够提供与PC机类似的图形用户界面和主要的应用程序。它的界面内容大多是在Windows里出现的标准部件,包括桌面、任务栏、窗口、图标和控件等。因此,只要是对PC机上的Windows比较熟悉的用户,都能很快学会使用基于Windows CE嵌入式操作系统的嵌入式设备。第5章嵌入式操作系统 3 3pSOSpSOSpSOS是ISI(Intergrated Systems Inc.)公司研发的产品。ISI最早成立于1980年,pSOS在其成立后不久即被推出,是世界上最早的实时操作系统之一,也是最早进入中国市场的实时操作系统。ISI公司于2000年被WindRi
10、ver公司兼并。第5章嵌入式操作系统 pSOS是一个模块化、高性能、完全可扩展的实时操作系统,专为嵌入式微处理器设计,提供了一个完全的多任务环境,在定制的或是商业化的硬件上提供高性能和高可靠性,可以让开发者根据操作系统的功能和内存需求定制每一个应用所需的子系统。pSOS包含单处理器支持模块(pSOS)、多处理器支持模块(pSOSm)、文件管理器支持模块(PHILE)、TCP/IP通信包(PNA)、流式通信模块(OPEN)、图形界面、Java、HTTP等。开发者可以利用它来实现从简单的单个独立设备到复杂的、网络化的多处理器系统。第5章嵌入式操作系统 4 4QNXQNXQNX是加拿大QNX公司的产
11、品。大多数RTOS都是从68 K的CPU上开发成熟,然后再移植到x86体系上的。而QNX是直接在x86体系上开发出来的,只是近几年才在68 K等CPU上使用。QNX是一个实时、可扩充的操作系统。它部分遵循POSIX相关标准,如POSIX.1b实时扩展。QNX提供了一个很小的微内核以及一些可选的配合进程;其内核仅提供4种服务:进程调度、进程间通信、底层网络通信和中断处理;其进程在独立的地址空间运行;所有其他的操作系统服务都实现为协作的用户进程。因此,QNX内核非常小巧(QNX4.x约为12 KB),而且运行速度极快。QNX灵活的结构可以使用户根据实际的需求,将系统配置成微小的嵌入式操作系统或是包
12、括几百个处理器的超级虚拟机操作系统。第5章嵌入式操作系统 5 5Palm OS Palm OS 3COM公司的Palm OS在掌上电脑和PDA市场上占有很大的市场份额。Palm OS有开放的操作系统应用程序接口(API),开发商可以根据需要自行开发所需的应用程序。目前共有3500多个应用程序可以运行在Palm Pilot(Palm OS平台)上,其中大部分应用程序为其他厂商和个人开发,从而使Palm Pilot的功能得以不断增多。这些应用软件包括计算器、各种游戏、电子宠物、地理信息等。在开发环境方面,可以在Windows 95/98以上及Macintosh上安装Palm Pilot Deskt
13、op。此外,Palm Pilot可以与流行的PC平台上的应用程序(如Word、Excel等)进行数据交换。第5章嵌入式操作系统 6 6嵌入式嵌入式LinuxLinuxLinux是一种免费的、源代码完全开放的、符合POSIX标准规范的操作系统。随着Linux的迅速发展,嵌入式Linux现在已经有许多版本,包括硬实时的嵌入式Linux(如新墨西哥工学院的RT-Linux堪萨斯大学的KURT-Linux)和一般的嵌入式Linux版本(如(CLinux、PocketLinux等)。其中,RT-Linux通过把Linux任务优先级设为最低,而所有实时任务的优先级都高于它,最终达到既兼容通常的Linux任
14、务又保证强实时性能的目的。第5章嵌入式操作系统 另外一种常用的嵌入式Linux(CLinux是针对没有MMU的处理器而开发的,已被广泛使用在ColdFire、ARM、MIPS、SPARC、SuperH等没有MMU的微处理器上。虽然(CLinux的内核比Linux2.0内核小得多,但它保留了Linux操作系统稳定性好、网络能力优异以及对文件系统的支持等主要优点。(CLinux与标准Linux最大的区别在于内存管理。标准Linux是针对有MMU的处理器而设计的,它将虚拟地址送到MMU,然后把虚拟地址映射为物理地址;通过赋予每个任务不同的虚拟物理地址转换映射,支持不同任务之间的保护。第5章嵌入式操作
15、系统 而(CLinux是针对没有MMU的处理器,不能使用处理器的虚拟内存管理技术,它对内存的访问是直接的,即它对地址的访问不需要经过MMU,而是直接送到地址线上输出;所有程序中访问的地址都是实际的物理地址;对内存空间不提供保护,各个进程实际上共享一个运行空间。在实现上,(CLinux专为嵌入式系统做了许多小型化的工作。第5章嵌入式操作系统 7.(C/OS-7.(C/OS-(C/OS-是一个完整的,源码公开的,可移植、固化、裁剪的占先式实时多任务内核,主要面向中小型嵌入式系统,具有执行效率高、占用空间小、可移植性强、实时性能优良和可扩展性强等特点。(C/OS-结构小巧,最小内核可编译至2 KB(
16、虽然这样的内核没有太大的实用性),即使包含全部功能,编译后也仅有610 KB,因而非常适用于小型控制系统。(C/OS-具有良好的兼容性,如系统本身不支持文件系统,但是如果需要,也可以自行加入文件系统的内容。此外,(C/OS-是用ANSI的C语言编写的,包含一小部分汇编语言代码,使之可供不同架构的微处理器使用。至今,从8位到16位,(C/OS-已在超过49种不同架构的微处理器上成功移植。第5章嵌入式操作系统(C/OS-是基于实时内核(C/OS的,和(C/OS版本V1.11(C/OS的最终版)是向上兼容的。目前,世界上已有很多人在各个领域中使用(C/OS及(C/OS-,这些领域包括:照相机行业(如
17、数码相机)、航空业、高端音响、医疗器械、电子乐器、发动机控制、网络设备、高速公路电话系统、自动提款及工业机器人等。更因为(C/OS-完全公开源代码,所以国内外很多高等院校都将其用于实时系统教学。第5章嵌入式操作系统 8国内著名的嵌入式实时操作系统国内著名的嵌入式实时操作系统(1)Delta OS:Delta OS是全中文的嵌入式实时操作系统,提供强实时和嵌入式多任务的内核。Delta OS的特点是任务响应时间快速、确定,不随任务负载大小改变;绝大部分的代码由C语言编写,具有很好的移植性。它适用于内在要求较大、可靠性要求较高的嵌入式系统。Delta OS主要包括:嵌入式实时内核DeltaCORE
18、、嵌入式TCP/IP组件DeltaNET、嵌入式文件系统DeltaFILE以及嵌入式图形用户接口DeltaGUI等。同时,它还提供了一整套的嵌入式开发套件LamdaTOOL。Delta OS是国内嵌入式领域不可多得的一整套嵌入式开发应用解决方案,已成功应用于通信、网络、信息家电等多个领域。第5章嵌入式操作系统(2)Hopen OS:Hopen OS由一个体积很小的内核以及一些可以根据需要自行定制的系统模块组成。其核心Hopen Kernel的规模一般为10 KB左右,占用空间小,并具有实时、多任务、多线程的系统特征。(3)HBOS:HBOS系统是浙江大学自主研制开发的全中文实时操作系统。它具有
19、实时、多任务等特征,能提供浏览器、网络通信核图形窗口等服务,还可供进行一定的定制或二次开发,并能为应用软件开发提供API接口支持。HBOS系统可用于信息家电、智能设备和仪器仪表等领域开发应用。在HBOS系统平台下,已经成功地开发出机顶盒和数据采集等系统。第5章嵌入式操作系统 5.3 操作系统的基本概念操作系统的基本概念 5.3.1 5.3.1 多进程和多线程多进程和多线程许多嵌入式系统并不是单纯地完成一种功能。例如,在一个电话应答机系统中,需要把记录通话信息和操作用户控制面板定义为不同的任务,因为它们不仅在逻辑上进行的是不同的操作,而且完成的速度也不同。这些不同的任务构成了应答机系统功能的各个
20、部分,为了完成多个任务而组织程序结构的需要,引入了进程的概念。第5章嵌入式操作系统 一个进程可以简单地认为是一个程序的唯一执行。进程是顺序执行的,而且CPU一次只能执行一个进程。但是,当确定了一个进程的完整状态后,就可以强制CPU停止执行当前进程而执行另一个进程。通过改变CPU中的程序计数器,使其指向新进程的代码,同时将新进程的数据移入寄存器和主存中,就可以实现进程的切换。这样,就能够使多个进程同时存在于CPU中。在嵌入式系统中,一个进程的常用形式是线程。线程在CPU的寄存器中有各自不同的值集合,但是共存于一个主存储空间中。线程普遍应用于嵌入式系统中(即任务),这样可以避免存储管理单元的复杂,
21、节约存储管理单元的消耗。第5章嵌入式操作系统 5.3.2 5.3.2 任务任务在嵌入式系统中,一个任务也称作一个线程,是一个程序,该程序在运行时可以认为CPU完全只属于该程序自己。在实时应用程序的设计过程中,要考虑如何将应用功能合理地划分为多个任务,让每个任务完成一定的功能,成为整个应用的一部分。每个任务都被赋予一定的优先级,有自己的一套CPU寄存器和栈空间(如图5-2所示)。第5章嵌入式操作系统 图5-2 多任务堆栈与CPU寄存器 第5章嵌入式操作系统 一般的,每一个任务都是一个无限的循环,可以处在以下五种状态之一:(1)休眠态(Dormant):是指任务驻留在内存的程序空间中,并未被多任务
22、内核所调度。(2)就绪态(Ready):是指任务已经准备好,可以运行,但是由于该任务的优先级比正在运行的任务的优先级低,还暂时不能运行。(3)运行态(Running):是指任务获得了CPU的控制权,正在运行中。基于优先级调度的实时内核总是让处于就绪态的优先级最高的任务运行。第5章嵌入式操作系统(4)挂起态(Pending):也叫作等待事件态(waiting),是指任务在等待某一事件的发生(如等待某外设的I/O操作、等待定时脉冲的到来、等待超时信号的到来以结束目前的等待,等等)。正在运行的任务由于调用了延时函数或等待某事件发生而将自身挂起,就处于挂起态。(5)被中断态(Interrupt):是指
23、发生中断时,CPU提供相应的中断服务,原来正在运行的任务暂不能运行,而进入了被中断状态。第5章嵌入式操作系统 5.3.3 5.3.3 任务切换任务切换任务切换(Context Switch)是指CPU寄存器内容切换。当多任务内核决定运行另外的任务时,它保存正在运行的任务的当前状态,即当前CPU寄存器中的全部内容;内核将这些内容保存在该任务的当前状态保存区,也就是该任务自己的栈区之中(这个过程称为“入栈”)。入栈工作完成后,把将要运行的任务的当前状态从该任务的栈中装入CPU寄存器(这个过程称为“出栈”),并开始这个任务的运行。这样,就完成了一次任务切换。任务切换过程增加了应用程序的额外负荷,CP
24、U的内部寄存器越多,额外负荷就越重。任务切换所需要的时间取决于CPU有多少寄存器要入栈。第5章嵌入式操作系统 5.3.4 5.3.4 内核内核多任务系统中,内核负责管理各个任务,为每个任务分配CPU的使用时间,并且负责任务间的通信。内核提供的基本服务是任务切换,通过提供必不可少的系统服务,诸如信号量管理、邮箱、消息队列及时间延时等,使得CPU的利用更为有效。此外,实时内核允许将应用程序划分成若干个任务并对它们进行管理(如任务切换、调度、任务间的同步和通信,等等),因而使用实时内核可以大大简化应用系统的设计。第5章嵌入式操作系统 但是,内核本身也增加了应用程序的额外负荷,因为内核提供的服务需要一
25、定的执行时间。额外负荷的多少取决于用户调用这类服务的频率。在设计得较好的应用系统中,内核占用2%5%的CPU负荷。再有,内核是加在用户应用程序中的软件,因而会增加ROM(程序代码空间)的用量,而内核本身的数据结构还会增加RAM(数据空间)的用量。更主要的是,每个任务都要有自己的栈空间,这会占用相当多的内存(由任务的数量决定)。单片机一般不能运行实时内核,就是因为单片机的RAM非常有限。第5章嵌入式操作系统 5.3.5 任务调度任务调度 1 1非占先式内核非占先式内核非占先式内核(non-preemptive kernel)中各个任务彼此合作,共享CPU。在一个任务的运行过程中,除了中断,不能在
26、该任务未运行完时抢占该任务的CPU控制权。中断服务可使一个高优先级的任务由挂起态变为就绪态,但中断服务以后,CPU的使用权交回给原来被中断了的任务,直到该任务主动释放CPU的控制权,一个新的高优先级的任务才能运行。图5-3表示非占先式内核的运行情况。第5章嵌入式操作系统 图5-3 非占先式内核 第5章嵌入式操作系统 图5-3中,1:任务在运行过程中被中断。2:若此时中断开着,则CPU进入中断服务子程序(ISR)。3:ISR做事件处理,使一个更高优先级的任务进入就绪态。4:中断服务完成后,使CPU回到原来被中断的任务。5:继续执行该任务。6:直到该任务完成,释放CPU的使用权给其他任务。7:看到
27、有高优先级的任务处于就绪态,内核做任务切换,高优先级的任务才开始处理ISR标志的事件。第5章嵌入式操作系统 非占先式内核的优点包括:(1)响应中断快。(2)可以使用不可重入函数。由于任务运行过程中不会被其他任务抢占,该任务使用的子函数不会被重入,因此不必担心其他任务正在使用该函数而造成数据破坏。(3)共享数据方便。第5章嵌入式操作系统 2 2占先式内核占先式内核当系统响应时间很重要时,须使用占先式内核。在占先式内核中,最高优先级的任务一旦就绪,便能得到CPU的使用权。当一个运行着的任务使一个比它优先级高的任务进入就绪态时,当前任务被挂起,那个高优先级的任务立刻得到CPU的使用权开始运行。如果是
28、中断服务子程序使一个高优先级的任务进入就绪态,则当中断完成时,被中断的任务被挂起,优先级高的任务开始运行。占先式内核的执行过程如图5-4所示。第5章嵌入式操作系统 图5-4 占先式内核 第5章嵌入式操作系统 图5-4中,1:任务在运行过程中被中断。2:若此时中断开着,则CPU进入中断服务子程序(ISR)。3:ISR做事件处理,使一个更高优先级的任务进入就绪态。当ISR完成时,进入内核提供的一种服务(内核提供的一个函数被调用)。4:这个函数识别出有一个高优先级的任务(更重要的任务)进入就绪态,内核做任务切换。5:执行高优先级的任务直到该任务完成,而不再运行原来被中断了的任务。6:内核看到原来的低
29、优先级的任务要运行,进行另一次任务切换。7:被中断了的任务继续运行,直到该任务完成。第5章嵌入式操作系统 5.3.6 5.3.6 任务间的通信与同步任务间的通信与同步在多任务的实时系统中,一项工作可能需要多个任务或多个任务与多个中断处理程序共同完成。那么,它们之间必须协调工作、互相配合,必要时还要交换信息。实时内核提供了任务间的通信与同步机制以解决这个问题。1 1任务间的通信任务间的通信多任务实时系统中,任务间或中断服务与任务间常常需要交换信息,这种信息传递称为任务间的通信(inter task communication)。任务间的通信有两个途径:共享数据结构和消息机制。第5章嵌入式操作系统
30、 1)共享数据结构实现任务间通信的最简单方法是使用共享数据结构,尤其是多个任务在同一地址空间下的情形。共享数据结构的类型可以是全局变量、指针、缓冲区等。在使用共享数据结构时,必须保证共享数据结构使用的排它性,即保证每个任务或中断服务子程序独享该数据结构。否则,会导致竞争或对数据时效的破坏。因此,在使用共享数据结构时,必须实现存取的互斥机制。实现对共享数据结构操作的互斥常常采用以下方法:开/关中断、禁止任务切换以及信号量(semaphore)机制等。第5章嵌入式操作系统(1)开/关中断。开/关中断实现数据共享保护是指在进行共享数据结构的访问时先进行关中断操作,在访问完成后再开中断。这种方法简单、
31、易实现,是中断服务子程序中共享数据结构的唯一方法。但是,如果关中断的时间太长,则可能影响整个实时系统的中断响应时间和中断延迟时间。第5章嵌入式操作系统(2)禁止任务切换。禁止任务切换是指在进行共享数据的操作前,先禁止任务切换,操作完成后再允许任务切换。这种方式虽然实现了共享数据的互斥,但是实时系统的多任务切换在此时被禁止了,应尽量少使用。需要注意的是,尽管禁止任务切换,但任务进行共享数据操作时,中断服务子程序此时仍然可以抢占CPU的使用权。因此,这种方式只适合任务间的共享数据结构的互斥。第5章嵌入式操作系统(3)信号量。在多任务实时操作系统中,信号量也被广泛用来进行任务间的通信和同步。但是,信
32、号量的使用应该有所节制,不能让所有的互斥处理都使用信号量机制实现,因为信号量机制是有一定系统开销的。对于简单的数据共享,如果处理时间很短,使用开/关中断实现而不需要使用信号量。只有涉及系统消耗比较大的共享数据操作时,才考虑使用信号量,因为如果此时使用开/关中断,就可能会影响系统的中断响应时间。第5章嵌入式操作系统 2)消息机制(1)消息邮箱。消息通常是内存空间的一个数据结构,通常是一个指针型变量。一个任务或一个中断服务子程序通过内核服务,可以把一则消息放到邮箱里去;同样的,一个或多个任务通过内核服务可以接收这则消息。每个邮箱都有相应的正在等待的任务列表。要得到消息的任务如果发现邮箱是空的,就被
33、挂起,并被放入到该邮箱的等待消息的任务列表中,直到接收到消息。通常,内核允许设定等待超时,如果等待时间已到仍没有收到消息,任务就进入就绪态并返回等待超时的出错信息。如果消息放入邮箱中,则内核或者把消息传递给等待消息的任务列表中优先级最高的任务(基于优先级),或者把消息传给最先开始等待消息的任务(基于先进先出)。第5章嵌入式操作系统(C/OS-II只支持基于优先级的分配算法,内核一般提供以下邮箱服务:邮箱内消息内容的初始化;将消息放入邮箱(POST);等待消息进入邮箱(PEND);从邮箱中得到消息。第5章嵌入式操作系统(2)消息队列。消息队列实际上是邮箱阵列,在消息队列中允许存放多个消息。对消息
34、队列的操作和对消息邮箱的操作基本相同。通常,内核中提供的消息队列服务包括:消息队列初始化;放一则消息到队列中去(POST);等待一则消息的到来(PEND);从队列中等到消息。第5章嵌入式操作系统 2 2任务间同步任务间同步任务间的同步是指异步环境下的一组并发执行任务因各自的执行结果互为对方的执行条件,因而任务之间需要互发信号,以使各任务按一定的速度执行。任务同步也常常使用信号量。与任务间的通信不同,信号量的使用不再作为一种互斥机制,而是代表某个特定的事件是否发生。任务的同步分为单向同步和多向同步。第5章嵌入式操作系统(1)单向同步。如图5-5所示,图中用一面旗帜或称作一个标志来表示信号量。这个
35、标志表示某一事件的发生(不再是保证互斥条件),用来实现同步机制的信号量初始化为0。这种类型的同步称作单向同步(unilateral rendezvous)。图中,一个任务在等待(PEND)某个事件发生时,查看该事件的信号量是否非0;另一个任务或中断服务子程序在进行操作时,当该事件发生后,将该信号量设置为1;等待该事件的任务查询到信号量的变化,代表该事件已发生,任务得以继续自身的运行。第5章嵌入式操作系统 图5-5 用信号量使任务与中断服务(或任务)单向同步 第5章嵌入式操作系统(2)双向同步。两个任务可以用两个信号量同步它们的行为,如图5-6所示。这种同步称为双向同步(bilateral re
36、ndezvous)。双向同步与单向同步类似,但是双向同步不可能在任务与ISR之间实施,因为ISR运行时不可能等待一个信号量。第5章嵌入式操作系统 图5-6 两个任务用两个信号量双向同步 第5章嵌入式操作系统 5.3.7 5.3.7 操作系统的结构和功能操作系统的结构和功能为了满足嵌入式应用,嵌入式实时操作系统可以根据实际应用环境的要求对内核进行裁剪和重新配置。一般的,实时操作系统总是由以下几个重要部分组成:实时内核、网络组件、文件系统和图形用户接口等,其体系结构如图5-7所示。第5章嵌入式操作系统 图5-7 嵌入式实时操作系统的体系结构 第5章嵌入式操作系统 5.4.1 C/OS-5.4.1
37、C/OS-概述概述C/OS-读作“micro C O S 2”,即“微控制器操作系统版本2”。C/OS-是一个免费的、源代码公开的嵌入式实时多任务内核,是专门为嵌入式应用设计的RTOS,提供了实时系统所需的基本功能。C/OS-的全部功能的核心部分代码只占用8.3 KB,用户还可以针对自己的实际系统对C/OS-进行裁剪(最少可达2.7 KB)。C/OS-只提供了诸如任务调度、任务管理、时间管理、内存管理、中断管理和任务间的同步与通信等实时内核的基本功能,没有提供输入/输出管理、文件系统、图形用户接口及网络组件之类的额外服务。但是,由于C/OS-的可移植性和开源性,用户可以根据实际应用添加所需要的
38、服务。5.4 C/OS-简介简介 第5章嵌入式操作系统 C/OS-是在PC机上开发的,C编译器使用的是Borland C/C+3.1版。而PC机是大家最熟悉的开发环境,因此在PC机上学习和使用C/OS-非常方便。此外,C/OS-作为一个源代码公开的嵌入式实时内核,对开发者学习和使用实时操作系统提供了极大的帮助。许多开发者已成功地把C/OS-应用于自己的嵌入式系统中,从而使得C/OS-获得了快速的发展。从最早的COS,以及后来的C/OS和C/OS-V2.00,到现在的C/OS-V2.52,该内核已经有十余年的发展历史,在诸多领域得到了广泛应用。许多行业中C/OS-成功应用的实例,也进一步说明了该
39、内核的实用性和可靠性。第5章嵌入式操作系统 5.4.2 C/OS-5.4.2 C/OS-的特点的特点1 1源代码公开源代码公开2可移植性可移植性(portable)3可固化可固化(ROMable)4可裁剪可裁剪(scalable)5占先式占先式(preemptive)6多任务多任务 7可确定性可确定性 8任务栈任务栈 9系统服务系统服务 10中断管理中断管理 11稳定性与可靠性稳定性与可靠性 第5章嵌入式操作系统 5.4.3 5.4.3 C/OS-C/OS-的软件体系结构的软件体系结构C/OS-的软件体系结构以及与硬件的关系如图5-8所示,其软件体系主要包括以下4个部分:(1)应用软件层:在应
40、用程序中使用C/OS-时,用户开发设计的应用代码。(2)与应用相关的配置代码:与应用软件相关的、C/OS-的配置代码。包括两个头文件,这两个头文件分别定义了与应用相关的控制参数和所有相关的头文件。第5章嵌入式操作系统(3)与处理器无关的核心代码:包括与处理器无关的10个源代码文件和1个头文件。其中,10个源代码文件分别实现了C/OS-内核结构,即内核管理、事件管理、消息邮箱管理、内存管理、互斥型信号量管理、消息队列管理、信号量管理、任务管理、定时管理和内核管理。(4)与处理器相关的设置代码:与处理器相关的源代码,包括1个头文件、1个汇编文件和一个C文件。在不同处理器上移植C/OS-时,需要根据
41、处理器的类型对这部分代码重新编写。可以在 C/OS-的网站www.C/OS-.com中查找移植范例,也可以阅读处理器的移植代码进行编译。第5章嵌入式操作系统 图5-8 C/OS-软件体系结构 第5章嵌入式操作系统 5.5 C/OS-内核结构内核结构 5.5.1 5.5.1 临界段临界段代码的临界段critical sections)是指处理时不可分割的代码。一旦这部分代码开始执行,就不允许任何中断进入。与其他内核一样,C/OS-为了处理临界段代码,也需要关中断,处理完毕后,再开中断。关中断能够使C/OS-避免有其他任务或中断服务同时进入临界段代码。但是,关中断的时间会影响用户系统对实时事件的响
42、应特性,它是实时内核开发商提供的最重要的指标之一。C/OS-努力使关中断时间降至最短,但在具体使用C/OS-时,关中断的时间很大程度上取决于微处理器的结构以及编译器所生成的代码质量。第5章嵌入式操作系统 微处理器一般都具有关中断/开中断指令,用户使用的C语言编译器必须具有能够在C中直接实现关中断/开中断操作的机制。有些C编译器允许在用户的C源代码中插入汇编语言的语句,即通过插入微处理器指令来实现关中断/开中断的操作;而有些编译器把从C语言中关中断/开中断的操作放在语言扩展部分,从C语言中直接关中断/开中断。C/OS-通过定义两个宏(macros)OS_ENTER_CRITICAL()和OS_E
43、XIT_CRITICAL(),来实现关中断和开中断的操作,从而避免了不同C编译器厂商选择不同的方法处理关中断和开中断。第5章嵌入式操作系统 OS_ENTER_CRITICAL()和OS_EXIT_CRITICAL()总是成对使用的,它们把临界段代码封装起来,实现对应用程序中的临界段代码的保护,具体用法如以下代码所示。.OS_ENTER_CRITICAL()/*C/OS-II临界段代码 */OS_EXIT_CRITICAL();.第5章嵌入式操作系统 在使用OS_ENTER_CRITICAL()和OS_EXIT_CRITICAL()时要特别小心,如果在调用一些如OSTimeDel()之类的功能函
44、数之前关中断会导致应用程序崩溃(死机)。这是因为任务被挂起一段时间直到挂起时间到,但由于中断被关掉了,就无法得到时钟节拍中断服务(即一直处于挂起状态)。显然,所有的挂起类(PEND)调用都有这类问题。作为一条普遍使用的规则是:调用C/OS-II的功能函数时,中断应当总是开着的。第5章嵌入式操作系统 5.5.2 5.5.2 任务任务在C/OS-II中,任务通常是一个无限的循环。任务就像其他C函数一样,有返回值类型和参数,但它绝不返回任何数据,因此返回参数类型必须定义成void。当任务开始执行时,会给用户代码传递一个形式参数。这个参数是一个指向void的指针,以允许用户应用程序向该任务传递任何类型
45、的参数。任务的函数结构必须是以下两种形式之一:第5章嵌入式操作系统(1)执行无限循环的任务。void YourTask(void*pdata)任务初始化代码;for(;)用户代码;/*调用C/OS-II的功能函数,如下列函数之一 */OSMboxPend();OSQPend();OSSemPend();OSFlagPend();OSTaskSuspend(OS_PRIO_SELF);第5章嵌入式操作系统 OSTimeDly();OSTimeDlyHMSM();.用户代码;第5章嵌入式操作系统(2)执行一次后自我删除的任务。void YourTask(void*pdata)用户代码;OSTask
46、Del(OS_PRIO_SELF);第5章嵌入式操作系统 对于后一种执行自我删除的任务来说,任务代码并非真的删除了,而是C/OS-简单地不再理会这个任务了。这个任务的代码也不会再运行,而且也绝不会返回。C/OS-可以管理多达64个任务,但建议保留4个最高优先级和4个最低优先级的任务,供以后C/OS-的版本使用。目前C/OS-使用了2个优先级别:OS_LOWEST_PRIO(空闲任务)和OS_LOWEST_PRIO-1(统计任务)。必须给每个任务赋予不同的优先级,优先级号可以为0OS_LOWEST_PRIO-2。优先级号越低,任务的优先级越高。第5章嵌入式操作系统 5.5.3 5.5.3 任务控
47、制块任务控制块OS_TCBOS_TCBC/OS-对任务的管理是通过任务控制块TCB(Task Control Blocks)进行的。任务控制块是一个数据结构(OS_TCB),全部存放在RAM中。在创建任务时,该任务的TCB被赋值;当任务的CPU使用权被剥夺时,C/OS-用OS_TCB来保存该任务的状态(即当前CPU寄存器的值);当任务再次被调度,重新得到CPU使用权时,能够从任务控制块中恢复该任务的执行状态,确保任务从当时被中断的那一点继续执行。OS_TCB的结构如下所示:第5章嵌入式操作系统 typedef struct os_tcb OS_STK *OSTCBStkPtr;/*指向当前任务
48、堆栈栈顶的指针*/#if OS_TASK_CREAT_EXT_EN /*OS_TASK_CREAT_EXT_EN为1时下列数据有效*/void*OSTCBExtPtr;/*指向用户定义的任务控制块扩展*/OS_STK *OSTCBStkBottom;/*指向任务堆栈栈底的指针*/INT32U OSTCBStkSize;/*堆栈中可容纳的指针元数目*/INT16U OSTCBOpt;/*指向任务堆栈栈底的指针*/INT16U OSTCBId;/*存储任务的识别码*/#endif struct os_tcb*OSTCBNext;/*指向任务OS_TCB双向链表中后一个元素*/struct os_t
49、cb*OSTCBPrev;/*指向任务OS_TCB双向链表中前一个元素*/第5章嵌入式操作系统#if(OS_Q_EN0)&(OS_MBOX_QS0)|(OS_MBOX_EN0)|(OS_SEM_EN0)|(OS_MUTEX_EN0)OS_EVENT *OSTCBEventPtr;/*指向事件控制块的指针*/#endif#if (OS_Q_EN0)&(OS_MBOX_QS0)|(OS_MBOX_EN0)void *OSTCBMsg;/*指向传递给任务的消息的指针*/#endif#if OS_TASK_DEL_EN0 OS_FLAG_NODE*OSTCBFlagNode;/*指向事件标志节点的指针
50、*/#endif 第5章嵌入式操作系统 INT16U OSTCBDly;/*用于设置任务延时或等待的最多时钟节拍数*/INT8U OSTCBStat;/*任务的状态字*/INT8U OSTCBPrio;/*任务的优先级*/INT8U OSTCBX,OSTCBY,OSTCBBitX,OSTCBBitY;/*加速任务进入就绪态的过程*/OS_TCB 第5章嵌入式操作系统 5.5.4 5.5.4 任务调度任务调度 C/OS-是占先式实时内核,优先级最高的任务一旦进入就绪态,立即拥有CPU的控制权并开始运行。C/OS-的调度器(scheduler)就是用来查找准备就绪的优先级最高的任务并进行任务切换。