自己动手写一个简易操作系统(基于51单片机)
背景介绍
大一学了51单片机,对于单片机的一些常用外设有了一定的了解。之后,大家都在说当前最流行的单片机是stm32,所以我抽出了暑假的时间的时间学习了stm32单片机,刚开始学的时候真的很痛苦,在坚持了一个星期之后,我慢慢找到了自信,stm32单片机实际上和51是一样的,只是需要配置的寄存器多了一点。在刚开始学的时候,经常在配置的时候无法配置完全,导致无法得到预期的实验效果,但是实际上,大家没必要过分纠结于配置,完全可以直接参考别人使用该功能的配置方式。我们应该将心思放在功能的开发上,而不是纠结于前期简单的配置。在熟悉使用stm32之后,开始接触操作系统ucos,过程中一直觉得自己似懂非懂,所以我在想为什么我自己不利用51写一个简易操作系统,来加深自己的理解。初期写出的操作系统不用考虑通信等高级功能,只需要写出可以调度多个任务的操作系统即可,下面给大家介绍一下我自己写的操作系统 (写的不太好,仅供大家参考)。
系统实现
实现简易操作系统,主要需要实现三个函数:
创建任务函数(将定义的任务的执行入口保存起来,供调度使用)任务延时函数(每一个任务执行后,都需要加入延时函数,否则低优先级的任务没有机会执行)中断调度函数(提供时间片调度)1 创建任务函数介绍
int OSTaskCreate(unsigned int Task, unsigned char* pStack, unsigned char TaskID)
{
unsigned char i = 0, j = 0;
*pStack++ = Task & 0xFF; //低八位地址(51单片机入栈向上,出栈向下)
*pStack = Task >> 8; //高八位地址
os_enter_critical();
TaskCB[TaskID].OSTaskStackButtom = (unsigned char)pStack + 13;
TaskCB[TaskID].OSWaitTick = 0;
TASK_READY(TaskID); //将该优先级的任务在全局变量中标记为就绪
os_exit_critical();
return 0;
}
入口参数:
unsigned int Task ---- 任务函数的入口地址
unsigned char* pStack ---- 任务函数的堆栈,主要用来保存现场参数
unsigned char TaskID ----- 任务优先级
2 任务延时函数
void OSTimeDly(unsigned int time)
{
TaskCB[CurrentTaskID].OSWaitTick = time; //将任务的延时时间赋值给任务控制块
task_sw(); //任务调度
}
static void task_sw()
{
os_enter_critical();
TASK_BLOCK(CurrentTaskID); //将当前任务的就绪状态取消
#pragma asm //将现场的关键参数存入堆栈
PUSH ACC
PUSH B
PUSH DPH
PUSH DPL
PUSH PSW
MOV PSW,#00H
PUSH AR0
PUSH AR1
PUSH AR2
PUSH AR3
PUSH AR4
PUSH AR5
PUSH AR6
PUSH AR7
#pragma endasm
TaskCB[CurrentTaskID].OSTaskStackButtom = SP ; //将当前任务的堆栈位置保存,用于下次恢复该任务
CurrentTaskID = Task_High(); //找出处于就绪态的最高优先级的任务
SP = TaskCB[CurrentTaskID].OSTaskStackButtom;
#pragma asm
POP AR7
POP AR6
POP AR5
POP AR4
POP AR3
POP AR2
POP AR1
POP AR0
POP PSW
POP DPL
POP DPH
POP B
POP ACC
#pragma endasm
os_exit_critical(); //离开时会把SP的当前位置的值送入PC指针,所以最高优先级的任务得以运行
}
3 中断调度函数
void TF0_isr() interrupt 1
{
TH0 = 56320/256;
TL0 = 56320%256;
TaskCB[CurrentTaskID].OSTaskStackButtom = SP; //被中断的任务的现场已经压入堆栈,所以只需保存SP
CurrentTaskID = Task_Ready_High(); //取出就绪中优先级最高的任务
SP = TaskCB[CurrentTaskID].OSTaskStackButtom;
#pragma asm
POP AR7
POP AR6
POP AR5
POP AR4
POP AR3
POP AR2
POP AR1
POP AR0
POP PSW
POP DPL
POP DPH
POP B
POP ACC
RETI
#pragma endasm
}
总结:
以上三个函数就是一个简易操作系统的关键函数,大家可以自己动手实现一下。这对大家学习ucos有很大的帮助,同时也为学习linux系统打下基础。
后续我会继续完善这个简易操作系统,添加通信等功能,希望大家可以关注我,共同进步。
【操作系统】如何给单片机写一个嵌入式操作系统
提到操作系统,那一定是一个高大上的东西,实际上也确实是这样的,但是操作系统也有广义和狭义之分,广义的操作系统:通常不仅包含操作系统内核,还包括附带的应用软件和各种中间件,比如,windows操作系统就包含IE,word等等软件。狭义的操作系统一般是指操作系统内核,不包含在内核基础之上开发的其他软件。我们就从狭义的操作系统内核开始吧,千里之行,始于内核!
一、操作系统现状分析
常用的嵌入式操作系统,大致有下面几个:
1.VxWorks
VxWorks操作系统是WinRiver(美国风河系统)公司于1983年设计开发的一种嵌入式实时操作系统(RTOS),它具有良好的持续发展能力、高性能的内核以及友好的用户开发环境,在嵌入式实时操作系统领域牢牢地占据着一席之地。
VxWorks所具有的显著特点是:可靠性、实时性和可裁剪性。
它支持多种处理器,如X86、i960、Sun Sparc、Motorola MC68xxx、MIPS、PowerPC等。
2.Windows Embedded
Windows CE是微软针对个人计算机以外的计算机产品所研发的嵌入式操作系统,而CE则为Customer Embedded的缩写。该操作系统是一种针对小容量、移动式、智能化、32位、连接设备的模块化实时嵌入式操作系统。针对掌上设备、无线设备的动态应用程序和服务提供了一种功能丰富的操作系统平台。但Windows CE的嵌入不够实时,它属于软实时操作系统,目前也开始应用在中文手机的研究开发之中。
由于该操作系统与Windows有相似的背景,而且界面也比较统一,因此也得到了大家比较好的认可。该操作系统的基本内核需要至少200KB的ROM。
3.嵌入式Linux(最主流)
Linux操作系统源于一位芬兰大学生——Linus Torvalds的课余作品。当时,Linus Torvalds正在学习计算机科学家Andrew S.Tanenbaum开发的Minix操作系统,但发现Minix的功能很不完善,于是就编写了一个保护模式下的操作系统,这就是Linux的原型。
最开始,Linux被定位于黑客用的操作系统,并被放至FTP服务器上供人们自由下载。
Linux的内核小、功能强大、运行稳定、系统健壮、效率高,易于定制裁剪,在价格上极具竞争力。Linux不仅支持X86CPU,还可以支持其他数十种CPU芯片。
4.嵌入式实时内核uC/OS(推荐)
uC/OS与Linux一样,是一款公开源代码的免费实时内核,已在各个领域得到了广泛的应用。uC/OS的特点如下:
(1)具有RTOS的基本性能;
(2)代码尺寸小,结构简明;
(3)易学、易移植;
uC/OS提供完善的嵌入式实时内核的源代码,并对该代码作详尽的解释。而商业上的实时操作系统不但价格昂贵,而且其中很多都是所谓的黑盒子,即不提供源代码。
5.RT-thread
RT-Thread 是一款主要由中国开源社区主导开发的开源实时操作系统(许可证GPLv2)。实时线程操作系统不仅仅是一个单一的实时操作系统内核,它也是一个完整的应用系统,包含了实时、嵌入式系统相关的各个组件:TCP/IP协议栈,文件系统,libc接口,图形用户界面等。
6.FreeRTOS
FreeRTOS是一个迷你的实时操作系统内核。作为一个轻量级的操作系统,功能包括:任务管理、时间管理、信号量、消息队列、内存管理、记录功能、软件定时器、协程等,可基本满足较小系统的需要,可以运行在RAM较小的单片机上。
7.其他嵌入式操作系统
(1)Palm OS
Palm OS是一款32位的嵌入式操作系统,它的界面采用触控式。优势在于本身是一套专门为掌上电脑编写的操作系统。
(2)QNX
QNX是唯一可以将实时POSIX环境外加一个完全的窗口系统安装在1MB以下的闪储或只读存储器上的操作系统。
上面的操作系统直接可用于单片机的也就是us/OS-II和freeRTOS,它们对内存的占用很低,其它即使能运行,也需要单片机外扩RAM等存储器,需要更多的存储空间。
二、为什么要写单片机操作系统
最近的项目中,需要异步处理一些事件,比如说,按键按下点亮LED,松开按键3秒钟后LED再灭掉。我现在的做法是维护一个定时器列表,10ms为周期的定时器,在中断服务程序中去检查哪些任务时间到了,就去调用任务对应的函数。这样我在按键松开的时间加入一个3秒钟的定时器,3秒钟时间到,就去调用相应的函数,灭掉LED。这实际上和OS中的基于时间片分时调度简化,只是不需要切换,也不考虑执行了多长时间。
原型为:AddTask(pFunction,timer)
这样做可以降低我在主循环中代码逻辑的复杂度,但是需要维护一个定时器列表,而且要保证在一个定时器中期内(10ms),所有的任务能够运行完成,不能应对复杂任务。写一个单片机操作系统的想法也就产生了。
三、如何开始写单片机操作系统
先不考调所谓的调度算法,从任务切换入手,只要完成了如何切换任务,也就打下了基础,至于怎么切换以及切换的算法优劣都是锦上添花的事情。
千里之行始于行动,开始干吧,仅以此文作为开始。
相关问答
什么是 单片机系统 ?1单片机:单片机就是将CPU、存储器、定时计数器、I/O接口电路等集成在一个芯片。也叫单片微型计算机。2单片机系统:以单片机为核心的控制系统。3单片机应用系...
什么是 单片机 ?它由哪几部分组成?什么是 单片机 应用 系统 ?二者...单片机是一种路芯片,模集成电路技术把具有数处理器CPU随机存储器RAM、只读存储器ROM、多种I/O口和中断系统、定时器/计时器等功能(可能还包括显示驱...
单片机 有操作 系统 么?可以这么来说当我们运行的程序不是“足够”复杂,是我们人为可以控制的情况下在单片机中是不需要操作系统的,直接写程序,操作硬件就可以完成各种我们所需要...
单片机 开发 系统 的构成及各部分的作用-ZOL问答也就是说将计算机的所有功能都集成在一块芯片内的芯片都可以称之为单片机说白了就是一块集成IC内部包含中央处理器CPU、程序存储器ROM、数据存储器RAM、I/O口...
什么是 单片机 最小 系统 ?主要包括哪两部分电路?单片机由中央处理器(含部分特殊功能寄存器)、内部RAM、程序存储器、各种外设(IO端口、定时器、串行接口、中断处理电路等等)及对应控制寄存器、时钟电路、复...
我在焊 单片机 最小 系统 好像数据烧 写 不进去 是不是虚焊的起因...1、烧写器驱动是否安装;2、单片机是否烧坏;3、电源是否正负极接反(容易烧坏单片机);4、EA端是否接高电平(VCC);最好用万用表测一下需要焊接的每一个引脚...
单片机系统 开发如何入门?单片机是一门更偏重于动手的技术,需要涉及的基础知识比较多,学了这么多年的理论知识突然要应用起来发现难度很大无从下手。所谓万事开头难,所以学习单片机要趁...
单片机 最小 系统 原理?单片机最小系统,或者称为最小应用系统,是指用最少的元件组成的单片机可以工作的系统。对51系列单片机来说,最小系统一般应该包括:单片机、晶振电路、复位电...
英语翻译用 单片机 实现高精度宽范围的温度测量的 系统 摘要:本...[最佳回答]Realizesthehighaccuracywidthscopetemperaturesurveysystemwiththemonolithicintegratedcircu...
最小 系统 应包括哪些组成部分,并画出8051 单片机 ?如果你对单片机型号没有要求,那么我就以51为例,画一个最简单的单片机系统板给你看看。最小系统板,分三部分:外部晶振电路,给单片机提供工作时钟源;外部复...