《单片机原理及运用》开课了(_)!!要好好学习,搞钱啊!!!
文章中安装的Keil软件和Proteus软件在我的个人网盘,这里要感谢吕老师上传的教学文件以及孜孜不倦的教导
文章中涉及的源码,均以我自己的单片机为准,例如我的LED灯有总开关,如果你没有请自行修改代码,祝你学有所成(_),我会注明实际和理论的代码
一、单片机开发与仿真环境搭建
简单的部分我就直接照搬吕老师的课件了,部分需要注意的地方我会做GIF演示,侵删
1.1 Keil 软件
1.1.1 Keil软件的简介
大家安装完Keil软件肯定是要学习使用的,这里不建议将软件汉化,软件本来原生态的样子就很看,要学会适应英化的软件。
Keil C51 是德国 Keil Software 公司(现已被 ARM 收购)推出的 8051 系列的 IDE(Integrated Development,集成开发环境)。它不仅支持汇编语言开发,更支持 C/C++等高级语言开发单片机。其可以完成从工程建立和管理、编译、链接、目标代码生成、软件仿真调试等完整的开发流程。
1.1.2 Keil C51的工作界面

1.1.3 Keil C51建立工程
首先你需要在电脑文件资源管理器中新建一个文件夹用来存放你的工程,下面是新建工程的GIF演示。注意的AT89C52
是吕老师要求的,如果不一样请换成你们的,如果直接找AT89C52
是找不到的,要先找对应的厂商然后点击+
就可以看到相对应的芯片型号了。

1.1.4 建立/编辑C语言源程序文件
下面是GIF演示,比较简单,一定要记得后缀是.c
。

以上,我们就完成了最基本的软件使用,下面是一些进阶使用。
1.1.5 工程的设置
在工程建立后,还需要对工程进行设置。在 μVision5 的上方工具栏中,右击工程名 Target 1 框旁的魔术棒 ,即打开工程设置对话框。啊,好多我也不懂,看老师PPT吧,这些你说重要吧它也不是那么重要,看一遍过去吧。






1.1.6 Keil C51 的Debug
大家都知道Debug在调试程序中重要地位,所以我将Keil C51的Debug单独拿出来学习。
源程序编写完毕后还需要编译和链接才能够进行软件和硬件仿真。① 编译;②排错;在程序的编译/链接中,如果用户程序出现错误,还需要修正错误后重新编译/链接,重新烧录程序查看错误现象,十分消耗时间。因此需要单步调试,一步一步的查看代码运行效果来加快对错误的排查速度。

进入DEBUG模式后,黄色箭头为汇编程序运行位置光标,蓝黄三角形
为当前 C 语言运行位置,指向当前等待运行程序行。其界面如下,其中单个黄色箭头
为汇编程序运行位置光标(汇编一生之痛)。

在 μVision5 中,有 4 种DEBUG运行方式 :单步跟踪(Step Into),单步运行(Step Over),运行到光标处(Run to Cursor line),全速运行(Go)。

下面是使用Debug进行调试的GIF录像,测试用例如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
| #include<reg52.h>
sbit led0 = P0^0; sbit led1 = P0^1; sbit led2 = P0^2; sbit led3 = P0^3;
sbit led4 = P0^4; sbit led5 = P0^5; sbit led6 = P0^6; sbit led7 = P0^7;
void main () { led0 = 0; led1 = 0; led2 = 0; led3 = 0;
led4 = 0; led5 = 0; led6 = 0; led7 = 0;
}
|

1.1.7 存储空间资源的查看和修改
这一部分对我来说还是太早了,先看PPT吧



1.2 Proteus软件
1.2.1 Proteus软件的简介
① Proteus 是英国 Lab Center Electronics 公司推出的用于仿真单片机及其外围设备的EDA工具软件。
② Proteus 与 Keil C51 配合使用,可以在不需要硬件投入的情况下,完成单片机 C 语言应用系统的仿真开发。
③ Proteus 具有高级原理布图(proteus)、混合模式仿真(PROSPICE)、PCB 设计以及自动布线(ARES)等功能。
1.2.2 Proteus简单使用
继续看PPT吧,一定要看啊,我是太懒了就不想打字😀










1.2.3 Proteus 8 与 Keil C51 的联合使用

下面进行基本演示:① 将源程序编译、链接生成HEX
文件,这里需要将工程设置中的Output设置中的Create HEX File
勾选上。


1.2.4 Proteus 画出单片机的最小系统

使用Proteus选择元器件的方法如下

电气连接方法如下

1.2.5 实战教学:流水灯的实现
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
| #include <reg52.h>
sbit LED=P0^0; sbit ADDR0 = P1^0; sbit ADDR1 = P1^1; sbit ADDR2 = P1^2; sbit ADDR3 = P1^3; sbit ENLED = P1^4;
void delay(unsigned int t) { unsigned int i, j; for(i=0;i<t;i++) for(j=0;j<120;j++); }
void led() { int i=0; for(i=0;i<8;i++) { P0=~(0x01<<i); delay(50); } }
void main(){ ENLED = 0; ADDR3 = 1; ADDR2 = 1; ADDR1 = 1; ADDR0 = 0; while(1){ led(); } }
|
搭建如图所示仿真电路,这里采用共阳极二极管接法

然后对C源码进行编译生成HEX
文件,之后导入芯片中


1.3 STC-ISP软件
1.3.1 STC-ISP软件的简介
STC-ISP是一款又 STC 研发的单片机程序下载烧录软件,是针对 STC 系列单片机而设计的,可下载 STC89 系列、STC12 系列和 STC15 等系列的 STC 单片机,使用简便。





1.3.2 STC-ISP软件的使用
安装好STC-ISP和驱动后,当我们电脑插上板子之后,打开设备管理器,查看端口,我这里是COM12




1.3.3 实战教学: 点亮第一个LED灯
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21
| #include<reg52.h>
sbit LED = P2^0; sbit ADDR0 = P1^0; sbit ADDR1 = P1^1; sbit ADDR2 = P1^2; sbit ADDR3 = P1^3; sbit ENLED = P1^4;
void main() { ENLED = 0; ADDR3 = 1; ADDR2 = 1; ADDR1 = 1; ADDR0 = 0; LED = 0; while(1); }
|



二、实战教学以及作品展示
2.1 数码管
2.1.1 数码管原理
pass
2.1.2 静态数码管显示
1 2 3 4 5 6 7 8 9 10 11 12
|
#include<reg52.h>
void seg() { P2 = 0x3F; }
void main(){ seg(); while(1); }
|

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
|
unsigned char s[] = {0x3F, 0x06, 0x5B, 0x4F, 0x66, 0x6D, 0x7D, 0x07, 0x7F, 0x6F};
void delay(unsigned int n) { unsigned int i = 0,j = 0; for (i=0; i<n; i++) for(j=0; j<120; j++); }
void seg() { int i=0; for(i=0; i<10; i++) { P2 = s[i]; delay(800); } }
void main() { while(1) { seg(); } }
|

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44
|
#include<reg52.h>
unsigned char code LedChar[] = {0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8, 0x80, 0x90, 0x88, 0x83, 0xC6, 0xA1, 0x86, 0x8E};
sbit ADDR0 = P1^0; sbit ADDR1 = P1^1; sbit ADDR2 = P1^2; sbit ADDR3 = P1^3; sbit ENLED = P1^4;
void main() { unsigned char cnt = 0; unsigned char sec = 0; ENLED = 0; ADDR3 = 1; ADDR2 = 0; ADDR1 = 0; ADDR0 = 0; TMOD = 0x01; TH0 = 0xB8; TL0 = 0x00; TR0 = 1; while(1) { if (TF0 == 1) { TF0 = 0; TH0 = 0XB8; TL0 = 0x00; cnt++; if (cnt >= 50){ cnt = 0; P0 = LedChar[sec]; sec++; if (sec >= 16){ sec = 0; } } } } }
|
2.1.3 动态数码管显示
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
| #include<reg52.h>
unsigned char str[] = {0x76, 0x79, 0x38, 0x38, 0x3F}; unsigned char wei[] = {0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x80};
void delay(unsigned int n) { unsigned int i = 0,j = 0; for (i=0; i<n; i++) for(j=0; j<120; j++); }
void seg() { int i=0; for(i=0; i<5; i++) { P3 = ~wei[i]; P2 = str[i]; delay(5); } }
void main() { while(1) { seg(); } }
|

1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63
| #include<reg52.h>
sbit ADDR0 = P1^0; sbit ADDR1 = P1^1; sbit ADDR2 = P1^2; sbit ADDR3 = P1^3; sbit ENLED = P1^4;
unsigned char code LedChar[] = {0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8, 0x80, 0x90, 0x88, 0x83, 0xC6, 0xA1, 0x86, 0x8E}; unsigned char LedBuff[6] = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}; void main() { unsigned char i = 0; unsigned int cnt = 0; unsigned long sec = 0; ENLED = 0; ADDR3 = 1; TMOD = 0x01; TH0 = 0xFC; TL0 = 0x67; TR0 = 1; while(1) { if (TF0 == 1) { TF0 = 0; TH0 = 0xFC; TL0 = 0x67; cnt++; if (cnt >= 1000) { cnt = 0; sec++; LedBuff[0] = LedChar[sec%10]; LedBuff[1] = LedChar[sec/10%10]; LedBuff[2] = LedChar[sec/100%10]; LedBuff[3] = LedChar[sec/1000%10]; LedBuff[4] = LedChar[sec/10000%10]; LedBuff[5] = LedChar[sec/100000%10]; } if (i == 0){ ADDR2 = 0; ADDR1 = 0; ADDR0 = 0; i++; P0 = LedBuff[0]; } else if (i == 1) { ADDR2 = 0; ADDR1 = 0; ADDR0 = 1; i++; P0 = LedBuff[1]; } else if (i == 2) { ADDR2 = 0; ADDR1 = 1; ADDR0 = 0; i++; P0 = LedBuff[2]; } else if (i == 3) { ADDR2 = 0; ADDR1 = 1; ADDR0 = 1; i++; P0 = LedBuff[3]; } else if (i == 4) { ADDR2 = 1; ADDR1 = 0; ADDR0 = 0; i++; P0 = LedBuff[4]; } else if (i == 5) { ADDR2 = 1; ADDR1 = 0; ADDR0 = 1; i = 0; P0 = LedBuff[5]; } } } }
|
### 2.2