北航ARM9嵌入式系统实验实验三uCOS-II实验

阅读: 评论:0

北航ARM9嵌⼊式系统实验实验三uCOS-II实验
实验三 uCOS-II实验
⼀、实验⽬的
在内核移植了uCOS-II 的处理器上创建任务
⼆、实验内容
感应钎焊
1)运⾏实验⼗,在超级终端上观察四个任务的切换。
2)任务1~3,每个控制“红”、“绿”、“蓝”⼀种颜⾊的显⽰,适当增加OSTimeDly()的时间,且优先级⾼的任务延时时间加长,以便看清三种颜⾊。
3)引⼊⼀个全局变量BOOLEAN ac_key,解决完整刷屏问题。
4)任务4管理键盘和超级终端,当键盘有输⼊时在超级终端上显⽰相应的字符。
三、预备知识
1)掌握在EWARM 集成开发环境中编写和调试程序的基本过程。
2)了解ARM920T 处理器的结构。
3)了解uCOS-II 系统结构。
四、实验设备及⼯具
1)2410s教学实验箱
2)ARM ADS1.2集成开发环境
钨铜电触头3)⽤于ARM920T的JTAG仿真器
4)串⼝连接线
五、实验原理及说明
所谓移植,指的是⼀个操作系统可以在某个微处理器或者微控制器上运⾏。虽然uCOS-II的⼤部分源代码是⽤C语⾔写成的,仍需要⽤C语⾔和汇编语⾔完成⼀些与处理器相关的代码。⽐如:uCOS-II在读写处理器、寄存器时只能通过汇编语⾔来实现。因为uCOS-II 在设计的时候就已经充分考虑了可移植性,所以,uCOS-II的移植还是⽐较容易的。
要使uCOS-II可以正常⼯作,处理器必须满⾜以下要求:
(1)处理器的C编译器能产⽣可重⼊代码
可重⼊的代码指的是⼀段代码(如⼀个函数)可以被多个任务同时调⽤,⽽不必担⼼会破坏数据。也就是说,可重⼊型函数在任何时候都可以被中断执⾏,过⼀段时间以后⼜可以继续运⾏,⽽不会因为在函数中断的时候被其他的任务重新调⽤,影响函数中的数据。
(2)在程序中可以打开或者关闭中断
在uCOS-II中,可以通过OS_ENTER_CRITICAL()或者OS_EXIT_CRITICAL()宏来控制系统关闭或者打开中断。这需要处理器的⽀持,在ARM920T的处理器上,可以设置相应的寄存器来关闭或者打开系统的所有中断。
(3)处理器⽀持中断,并且能产⽣定时中断(通常在10Hz~1000Hz之间)
uCOS-II是通过处理器产⽣的定时器的中断来实现多任务之间的调度的。在ARM920T的处理器上可以产⽣定时器中断。
(4)处理器⽀持能够容纳⼀定量数据的硬件堆栈
(5)处理器有将堆栈指针和其它CPU寄存器存储和读出到堆栈(或者内存)的指令。
uCOS-II进⾏任务调度的时候,会把当前任务的CPU寄存器存放到此任务的
堆栈中,然后,再从另⼀个任务的堆栈中恢复原来的⼯作寄存器,继续运⾏另⼀个任务。所以,寄存器的⼊栈和出栈是uCOS-II多任务调度的基础。
下图说明了uC/OS 的结构以及它与硬件的关系
uCOS-II硬件和软件体系结构
2)uCOS-II在S3C2410X上的移植
多功能电源插座
电动黄包车(1)设置os_cpu.h中与处理器和编译器相关的代码
包括与编译相关的数据类型,⽤于实现开关中断的OS_ENTER_CRITICAL 和OS_EXIT_CRITICAL两个函数,制定堆栈⽣长⽅式的OS_STX_GROWTH.
(2)⽤C语⾔编写6个操作系统相关的函数(OS_CPU_C.C)
OSTaskSTKInit堆栈结构初始化函数、OSTaskCreateHook该函数允许⽤户或使⽤移植实例的⽤户扩展uCOS-II功能、OSTaskDelHook任务删除时调⽤、OSTaskSWHook任务切换时调⽤、OSTaskStatHook统计功能扩展,OSTimeTickHook时钟节拍时会被调⽤。
(3)⽤汇编语⾔编写4个与处理器相关的函数(OS_CPU.ASM)
OSStartHighRdy运⾏优先级最⾼的就绪任务、OS_TASK_SW任务级的任务切换函数、OSIntCtxSw中断级的任务切换函数、OSTickISR时钟节拍中断。
(4)时钟节拍中断功能实现
多任务操作系统的任务调度是基于时钟节拍中断的,uCOS-II也需要处理器提供⼀个定时器中断来产⽣节拍,借以实现时间的延时和期满功能。但在本系统移植uCOS-II时,时钟节拍中断的服务函数并⾮uCOS-II⽂献中提到的OSTickISR(),⽽直接是C 语⾔编写的OSTimeTick()。本系统uCOS-II 移植时占⽤的时钟资源是TIMER1。
在平台初始化函数ARMTargetInit()中,调⽤uHALr_InitTimers()函数初始化TIMER4相关寄存器;调⽤
uHALr_InstallSystemTimer(void)开始系统时钟,其中通过语句SetISR_Interrupt(IRQ_TIMER4, TimerTickHandle, NULL)将TimerTickHandle函数设置为TIMER4 的中断服务函数。这些函数在⽂件U
HAL.C 以及ISR.C中。
程序中必须在开始多任务调度之后再允许时钟节拍中断,即在OSStart()调⽤过后,uCOS-II运⾏的第⼀个任务中启动节拍中断。如果在调⽤OSStart()启动多任务调度之前就启动时钟节拍中断,uCOS-II运⾏状态可能不确定⽽导致崩溃。
本系统是在系统任务SYS_Task中调⽤uHALr_InstallSystemTimer()函数设置TIMER4的IRQ中断的,从⽽启动时钟节拍。SYS_Task()在⽂件OSAddTask.C中定义,⽤户不必创建。
(5)硬件初始化和配置⽂件
STARTUP⽬录下的⽂件还包括中断处理,时钟,串⼝通信等基本功能函数。
在⽂件main.c 中给出了应⽤程序的基本框架,包括初始化和多任务的创建,启动等。
任务创建⽅法如下:
A、在程序开头定义任务堆栈,任务函数声明和任务优先级:
OS_STK TaskName_Stack[STACKSIZE]={0, }; //任务堆栈
void TaskName(void *Id); //任务函数
#define TaskName_Prio N //任务优先级
B、在main()函数中调⽤OSStart()函数之前⽤下列语句创建任务:
OSTaskCreate(TaskName,(void*)0,(OS_STK*)&TaskName_Stack[STACKSIZE -1],TaskName_Prio);
OSTaskCreate()函数的原型是:INT8U OSTaskCreate (void (*task)(void *pd), void *p_arg, OS_STK *ptos, INT8U prio);
需要将任务函数TaskName,任务堆栈TaskName_Stack,任务优先级TaskName_Prio三个参数传给OSTaskCreate()函数。根据任务函数的内容决定堆栈⼤⼩,宏STACKSIZE定义为4KB,可以在此基数上乘倍。任务优先级越⾼,TaskName_Prio值越⼩;uCOS-II可以管理64个任务,由OSInit()创建的空闲任务的优先级最低为63;uCOS-II保留4个最⾼和4个最低优先级,⽤户任务可以使⽤其余56个优先级值。
C、编写任务函数内容:
void TaskName(void *Id)
{
//添⼊任务初始化语句
for(;;)
{ //添⼊任务循环内容
OSTimeDly(SusPendTime);//挂起⼀定时间,以使其他任务可以占⽤CPU }
}
uCOS-II⾄少要有⼀个任务,这⾥已经创建⼀个系统任务SYS_Task,启动系统时钟和多任务切换。为了验证uCOS-II多任务切换的进⾏,再编写两个简单的
任务,分别在超级终端上输出。
(6)以上任务完成后便可以编译并移植uCOS-II
六、实验步骤
1)以实验⼗为模板,将实验六inc⽬录下的LCD320.H 和src⽬录下的LCD640.C拷到模板下的相应⽬录,将LCD640.C加⼊⼯程中。
2)包含以下头⽂件#include “inc/lcd320.h”。
3)改LCD640.C ⽂件中包含头⽂件的路径。#include "../inc/drv/reg2410.h"
汽水热交换器
4)声明引⽤的变量extern U32 LCDBufferII2[LCDHEIGHT][LCDWIDTH];
七、主程序
#include"../ucos-ii/includes.h" /* uC/OS interface */
#include "../ucos-ii/add/osaddition.h"
#include "../inc/drivers.h"
#include "../inc/sys/lib.h"
#include "../src/gui/gui.h"
#include
#include
#include "..//inc/lcd320.h"
//#pragma import(__use_no_semihosting_swi) // ensure no functions that use semihosting
OS_EVENT *MboxSem;
///******************任务定义***************///
/*OS_STK SYS_Task_Stack[STACKSIZE]= {0, }; //system task刷新任务堆栈
#define SYS_Task_Prio 1
void SYS_Task(void *Id);*/
OS_STK task1_Stack[STACKSIZE]={0, }; //Main_Test_Task堆栈
void Task1(void *Id); //Main_Test_Task
#define Task1_Prio 12
OS_STK task2_Stack[STACKSIZE]={0, }; //test_Test_Task堆栈
void Task2(void *Id); //test_Test_Task
#define Task2_Prio 15
OS_STK task3_Stack[STACKSIZE]={0, }; //test_Test_Task堆栈
void Task3(void *Id); //test_Test_Task
#define Task3_Prio 17
OS_STK task4_Stack[STACKSIZE]={0, }; //test_Test_Task堆栈
void Task4(void *Id); //test_Test_Task
#define Task4_Prio 11
/**************已经定义的OS任务*************
#define SYS_Task_Prio 1
#define Touch_Screen_Task_Prio 9
#define Main_Task_Prio 12
#define Key_Scan_Task_Prio 58
#define Lcd_Fresh_prio 59
#define Led_Flash_Prio 60
***************************************/////////
#define rUTRSTAT0 (*(volatile unsigned *)0x50000010)
#define RdURXH0() (*(volatile unsigned char *)0x50000024)
#define WrUTXH0(ch) (*(volatile unsigned char *)0x50000020)=(unsigned char)(ch)
#define RdURXH0() (*(volatile unsigned char *)0x50000024)
#define TRUE 1
#define FALSE 0
extern U32 LCDBufferII2[LCDHEIGHT][LCDWIDTH];
BOOLEAN ac_key;
char *c,err=0;
///*****************事件定义*****************///
void display(U32 jcolor);
void Uart_SendByten(U8);
char Uart_Getchn(char* Revdata, int timeout);
/////////////////////////////////////////////////////
// Main function. //
int main(void)
{
ARMTargetInit(); // do target (uHAL based ARM system) initialisation OSInit(); // needed by uC/OS-II // LCD_Init();
ac_key=1;
//OSInitUart();
//initOSMessage();
//initOSDC();
//LoadFont();
//#endif
//loadsystemParam();
// create the tasks in uC/OS and assign increasing //
// the pipeline has the highest priority. //
织物整理剂
//LCD_printf("Create task \n");
//OSTaskCreate(SYS_Task,(void*)0,(OS_STK*)&SYS_Task_Stack[STACKSIZ E-1], SYS_Task_Prio); OSTaskCreate(Task1, (void *)0, (OS_STK *)&task1_Stack[STACKSIZE-1], Task1_Prio); OSTaskCreate(Task2, (void *)0, (OS_STK *)&task2_Stack[STACKSIZE-1], Task2_Prio); OSTaskCreate(Task3, (void *)0, (OS_STK *)&task3_Stack[STACKSIZE-1], Task3_Prio); OSTaskCreate(Task4, (void *)0, (OS_STK *)&task4_Stack[STACKSIZE-1], Task4_Prio); OSAddTask_Init(0);
BSPprintf(0,"\n");
//LCD_printf("\n");
//LCD_printf("Entering \n");
//LCD_ChangeMode(DspGraMode);
OSStart(); // start the OS //
// never reached //
return 0;
}//main
////////////////////////////////////////////////////////////////////////////////////////////////////////////////// void Task1(void *Id)
{
for(;;){
if(ac_key==1)
{ ac_key=0;
BSPprintf(0,"run task1\n");
display(0x000000f8); //显⽰红⾊
ac_key=1;
}
OSTimeDly(300);
}

本文发布于:2023-06-27 12:16:26,感谢您对本站的认可!

本文链接:https://patent.en369.cn/patent/3/154953.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

标签:任务   函数   中断   时钟   堆栈
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2022 Comsenz Inc.Powered by © 369专利查询检索平台 豫ICP备2021025688号-20 网站地图