大学四级成绩查询时间:实时操作系统uC/OS一Ⅱ在ARM上的移植—软件仿真

来源:百度文库 编辑:中财网 时间:2024/05/01 10:23:09

实时操作系统uC/OS一Ⅱ在ARM上的移植—软件仿真

 

摘 要:介绍了实时操作系统uC/OS—II的特点 ,讨论了其在 LPC2106上移植的可能性, 成功通过软件仿真地将uC/OS—II移植到LPC2106上, 并通过例程验证了移植代码的正确性。

 

注:本文是引用期刊“实时操作系统uC/OS—II在ARM上的移植,作者:王晓鸣、王树新 、张宏伟”结合了网上的程序实现了对系统移植的软件仿真。

 

0:引  言

目前嵌入式系统在家电、移动电话、PDA等各种领域的应用日益广泛,程序设计也越来越复杂,这就需要采用一个通用的嵌入式操作系统来对其进行管理和控制。移植 了操作系统 的嵌入式系统开发,可大大减 轻程序员的负担,操作系统提供了多任务的管理功能,  只需专注于每个任务的管理。对于不同的应用,可以按照相同的步骤完成系统设计。如果更换硬件平台,则只需要对操作系统进行少量的移植工作,与硬件无关的应用代码完全无需修改,同时,可增强代码的可读性、可维护性和可扩展性。uC/OS—II是一个可裁减的、源代码开放 的、结构小巧、可剥夺型的实时多任务内核,它提供任务调度、任务间的通信与同步、 任务管理、 时间管理和内存管理 等基本功能。将uC/OS—II移植到嵌入式处理器上,  对于提高产品质量、 缩短开发周期和降低成本等方面有着重 要的意 义。本 文主要介 绍uC/OS—II在飞利浦的一款AR M7TDMI的嵌入式处理器LPC2106应用。  

 

1 嵌入式操作系统 uC/OS—II

1.1    uC/OS—II简介

uC/OS—II是一种性能优良源码公开且被广泛应用的免费嵌入式操作系统,它结构小巧、具有基于优先级的抢占式实时多任务内核,绝大部分代码是用ANSI C语言编写的,与硬件相关部分用汇编语言编写,使之可供不同构架的微处理器使用。只要有标准的ANSI C交叉编译器,有汇编器、链接器等软件工具,就可以将 uC/OS—II嵌入到开发的产品中。

uC/OS—II是面向中小型嵌入式系统,具有执行效率高、占用空间小、实时性能优良和可扩展性强等特点,包含全部功能模块的内核大约为10kB。如果经过裁减只保留核心代码,则可压缩到3kB左右。严格地 说uC/OS—II只是一个实时操作系统内核,它仅仅包含了任务调度、任务管理、时间管理、内存管理和任务间的通信和同步等基本功能,没有提供输入输出管理、文件系统、网络等额外的服务。但由于uC/OS—II良好的可扩展性和源码开放,这些非必需的功能完全可以由用户自己根据需要分别实现。 

1.2    uC/OS—II的工作原理

uC/OS—II的工作流程如图 1所示:首先进行操作系统初始化,主要完成任务控制块(TCB)初始化;然后就可以开始创建新任务、初始化任务堆栈区;最后调用OSSTART()函数, 启动多任务调度 。在多任务调度开始后,启动时钟节拍源开始计时。此节拍源为系统提供周期性的时钟中断信号、实现延时和超时确认。当时钟中断来临时,系统把当前正在执行的任务挂起,保护现场,进行中断处理,判断有无任务延时到期。若有,则使该任务进入就绪态,并对所有进入就绪态的任务的优先级进行比较,通过任务切换去执行最高优先级的任务。若没有别的任务进入就绪态,则恢复现场继续执行原任务 。另一种调度方式是任务级的调度,即通过发软中断命令或依靠处理器在任务执行中调度。如任务要等待信号量或一个正在执行的任务被挂起时,就需要在此任务中调度,找出目前处于就绪态的优先级最高的任务去执行。当没有任何任务进入就绪态时,就去执行空任务。

 

1.3  UC/OS的移植要求

UC/OS的正常运行需要处理器平台满足以下要求:
a)处理器的C编译器能产生可重入代码。                                                    
b)用C语言就可以打开和关闭中断。
c)处理器支持中断,并且能产生定时中断(通常在10至100Hz之间)。         
d)处理器支持能够容纳一定量数据(可能是几千字节)的硬件堆栈。
e)处理器有将堆栈指针和其它CPU寄存器读出和存储到堆栈或内存中的指令。

我们的KEILADS均支持UC/OS的要求。因此可以在LPC2000系列上移值。

 

 

2     基于LPC1602的软件仿真电路

LPC1602是PHILIPS公司推出的一款功能强大、超低功耗且具有ARM7TDMI内核的32位微控制器。 它具有丰富的片上资源,完全可以满足一般的工业控制需要,同时还可以减少系统硬件设计的复杂度,提高系统的稳定性。它的工作原理主要是用ARM7芯片LPC1602为内核,与一系列外围器件连接起来。这里所用到的电路图如下:

仿真是的结果:

将ADS1.2编译运行后生成的test.hex文件导入到ARM芯片中去,按下key1按键的结果。

 

 

 

 

3     软件部分

这次仿真我用了老师上课讲的ADS1.2,和protues软件来实现的,ADS1.2是用来编写程序并生成目标代码。用Protues来模拟真实的开发板。

ADS1.2中的程序示意(编译后屋错误):

主要看一下主函数程序:

/****************************************************************************

* File:Main.C

* 功能:计数器,通过两个按键来控制加减计数器,并输出数码管显示.。

****************************************************************************/

#include  "config.h"

#define CON 0x000000ff    //控制P0.0~P0.7

 

 

#define  TASK_STK_SIZE                  64

OS_STK        Main_TaskStk[TASK_STK_SIZE];

OS_STK        Task0Stk[TASK_STK_SIZE];

 

 

void  Main_Task(void *data);

void  Task0(void *data);

/****************************************************************************

* 名称:main()

* 功能:主函数,启动多任务环境

****************************************************************************/

 int main (void)

{

    OSInit();

 

    OSTaskCreate(Main_Task, (void *)0, &Main_TaskStk[TASK_STK_SIZE - 1], 0);

    OSStart();

    return 0;

}

/****************************************************************************

* 名称:Main_Task()

* 功能:初始化目标板,建立其他任务

****************************************************************************/

 void  Main_Task(void *pdata)

      {

      pdata=pdata;

      TargetInit();

      OSTaskCreate(Task0, (void *)0, &Task0Stk[TASK_STK_SIZE - 1], 1);

      PINSEL0=0x0;

      IODIR=CON;

      IOCLR=CON;

      OSTaskSuspend(OS_PRIO_SELF);

      }

/****************************************************************************

* 名称:Task0()

* 功能:任务

****************************************************************************/

void  Task0(void *pdata)

{   uint16 temp;

    pdata=pdata;

    temp=0;

   for(;;)

           {

           if((IOPIN&0x00030000)!=0x00030000)

            OSTimeDly(OS_TICKS_PER_SEC/50);

           if((IOPIN&0x00030000)!=0x00030000)

                 {

                 if((IOPIN&0x00030000)==0x00020000)

                      temp++;

                 if((IOPIN&0x00030000)==0x00010000)

                      temp--;

                 while((IOPIN&0x00030000)!=0x00030000);

                 IOCLR=CON;

                 IOSET=temp;

                 }    

           }

OSTaskResume(0);

}

该程序中一共启用的两个任务:

第一个任务,其实只要是用来启用第二个任务Task0(按键任务),然后就自己挂起了。

void  Main_Task(void *pdata)

      {

      pdata=pdata;

      TargetInit();

      OSTaskCreate(Task0, (void *)0, &Task0Stk[TASK_STK_SIZE - 1], 1);

      PINSEL0=0x0;

      IODIR=CON;

      IOCLR=CON;

      OSTaskSuspend(OS_PRIO_SELF);

      }

第二个任务:查询两个按键,如果上面那个按键按下则显示增1,按下下面的则相反。

部分程序:

if((IOPIN&0x00030000)!=0x00030000)

{

      if((IOPIN&0x00030000)==0x00020000)

           temp++;

      if((IOPIN&0x00030000)==0x00010000)

           temp--;

      while((IOPIN&0x00030000)!=0x00030000);

           IOCLR=CON;

           IOSET=temp;

      }    

这里显示没有用另外的任务,而是使用IOSET来实现的。

 

4     总结

由于没有开发板一直不能进行移植实验,且之前没有学习过操作系统移植方面知识,对具体怎样移植很是迷惑,之前(考虑到电脑的装系统和软件安装)认为系统移植是不是先把系统下载到RAM中,然后再把编写好的程序再下载到ARM中,思路很是混乱。经过长时间的上网查资料,下相关的文档、软件以及程序现在才稍微理解了些。

 

我对系统移植的理解:

系统移植就是利用一些编程好的程序来辅助运行我们要实现的功能。比如说那些OS_CPU.H、OS_CPU_a.s、OS_CPU.c函数并不是用来直接下载到ARM版中的,而是你编写的具体函数在运行的时候会用到这些函数。而使用这些函数的好处时,实现切换任务之间的控制,而不在是像单片机那时的中断响应方式。

 

这里不能添加附件,所以程序没有全部给出,如果需要可以问我要。。。