1. 什么是操作系统
使用目的:多个任务同时运行,在复杂的工程项目中使用。
举例:8051控制3小灯,A小灯亮2秒灭2秒,B小灯亮3秒灭3秒,C小灯亮5秒灭5秒。怎么编程?
传统程序都是顺序进行的,那么你编程的时候会要把A,B,C3灯的亮灭次序规划。
操作系统编程:任务1控制A灯亮灭,任务2控制B灯亮灭,任务3控制C灯亮灭,然后三个任务同时运行。
一般来说在嵌入式芯片上使用的操作系统都是微型的实时操作系统,称为RTOS。
8051芯片上可以运行的操作系统:RTX51。
ARM芯片(stm32系列)上常用的操作系统:uCOS,FreeRTOS,RT-thread。
2. RTX51
2.1 Keil设置
- 选择工程选项
- 选择RTX-51 Tiny
- 增加头文件
include <rtx51tiny.h>
- 从任务0创建多任务,然后多个任务同时运行。
例如:创建任务1os_create_task (1);
os_wait
函数。os_wait (K_TMO, 5, 0);
等待延时5个滴答时间,默认1个滴答时间是0.01秒,在12MHZ的单片机下。
如果想修改滴答时间,请修改 CONF_TNY.A51 文件中的INT_CLOCK EQU 10000
例如,如果改为INT_CLOCK EQU 1000
,那么滴答时间就是0.001秒。
该函数使用的滴答数只能是 0-255。os_send_signal (3);
函数
给3号任务发送了一个信号。os_wait (K_SIG, 0, 0);
函数
等到一个信号到来。
2. 例子
3.1 多灯闪烁
8051控制3小灯,A小灯亮1秒灭1秒,B小灯亮2秒灭2秒,C小灯亮3秒灭3秒,硬件如图:

代码:
#include <reg51.h>
#include <rtx51tny.h>
sbit led0 = P2 ^ 0;
sbit led1 = P2 ^ 1;
sbit led2 = P2 ^ 2;
job0() _task_ 0
{
os_create_task(1);
os_create_task(2);
while (1)
{
led0 = !led0;
os_wait(K_TMO, 100, 0);
}
}
job1() _task_ 1
{
while (1)
{
led1 = !led1;
os_wait(K_TMO, 200, 0);
}
}
job3() _task_ 2
{
while (1)
{
led2 = !led2;
os_wait(K_TMO, 200, 0);
os_wait(K_TMO, 100, 0);
}
}
3.2 按键控制秒表
8051控制1个按键和两位的数码管,两位数码管从启动开始每秒加1,按键按下数码管显示的秒数暂停,再按下显示的秒数继续走时。
注:Keil的中文乱码解决进入Edit>Configuration…>Editor,选择Encoding 为 UFT-8。
硬件如图:

代码:
// 按键控制2位数码管
#include <reg51.h>
#include <rtx51tny.h>
sbit key = P1 ^ 0;
sbit bit0 = P3 ^ 0;
sbit bit1 = P3 ^ 1;
unsigned char num = 0;
unsigned char start = 0;
// 任务0 : 显示功能
disp() _task_ 0
{
unsigned char seg_code[] = {0xc0, 0xf9, 0xa4, 0xb0, 0x99, 0x92, 0x82, 0xf8, 0x80, 0x90};
os_create_task(1);
os_create_task(2);
while (1)
{
bit0 = 1;
bit1 = 0;
P2 = seg_code[num / 10];
os_wait(K_TMO, 1, 0);
P2 = 0xff;
bit0 = 0;
bit1 = 1;
P2 = seg_code[num % 10];
os_wait(K_TMO, 1, 0);
P2 = 0xff;
}
}
// 任务1: 计时功能
time() _task_ 1
{
while (1)
{
os_wait(K_TMO, 250, 0);
os_wait(K_TMO, 250, 0);
os_wait(K_TMO, 250, 0);
os_wait(K_TMO, 250, 0);
if (start == 1)
{
num++;
}
if (num == 100)
{
num = 0;
}
}
}
// 任务2:按键功能
press() _task_ 2
{
unsigned char now_key = 1, old_key = 1;
while (1)
{
old_key = now_key;
now_key = key;
if (old_key == 0 && now_key == 1)
{
start = !start;
}
}
}