基于本人学习单片机的痛苦经历,特编写本教程,以此献给广大,怎么样编程

怎么样编程 0
http://www.mcufriend.com 前言 QQ:280919249 基于本人学习单片机的痛苦经历,特编写本教程,以此献给广大 的单片机初学者,希望您能从中受益。
作者提示:本教程乃最通俗易懂之单片机教材也,如果您还是看 不懂,请千万不要涉足此行,以免误入歧途,耽误您的前程*_* 拿到这本教程您首先就会想,什么是
IAP教学法?是不是一种什么全新的教学方法?当然不是,我可没有那么大的本事,其实这只是我杜撰的一个新名词,意思就是InApplicationsProgram(在应用中编程),当然这只是针对单片机教学,说法是否正确,还得您说了算。
至于为什么要提这种说法,那我倒想说几句。
大家都知道,学习电子技术是一件非常无聊和枯燥的事情,为什么会有这种想法,就是因为我们传统的教学方法只重理论而忽略了实践,要一个人记住那些空洞而有无聊的理论知识实在不是一件容易的事,好在我们总算熬过来了,不管如何,也多多少少的学习了一些电子基础知识。
接下来我们应该进一步掌握些什么知识呢,凡涉足此行的朋友都知道,那就是单片机。
不过这可不是一件容易的事,倒不是因为单片机很难学,而实在是我们身边很难找到一本专为单片机入门者而编写的教材。
翻一下传统的单片机教材,都好象是为已经懂单片机的人而写的,一般总是以单片机的结构为主线,先讲硬件原理,然后是指令,接着讲软件编程,再是系统扩展和外围器件,最后举一些实例(随便说一点:很多书中的实例都是有错误的),很少涉及单片机的基础知识,如果按照此种学习方法,想进行产品开发,就必须先把所有的知识全部掌握了才可以进行实际应用。
孰不知,单片机不象模拟电路和数字电路那样,只要搞懂了电路原理,再按照产品要求设计好相应的电路就可以了。
它是一种以简单的硬件结构,复杂而有灵活的软件系统来完成设计的通用性产品,不同的设计者只会使用其不同的功能,几乎没有人会把它的全部指令都使用起来,所以学习使用单片机只能靠循序渐进的积累,而不可能先把它全部掌握了再去做产品开发(当然天才就例外了*_*)。
基于以上原因,本人想尝试一种全新的单片机教学方法,打破传统的循序渐进式的教学方法,以单片机的应用为蓝本,结合基本的工业控制系统和实践工作中的具体应用,不分先后顺序,将各条指令贯串于一个又一个的实验中,通过所见即所得的实验来讲解各种指令的编程方法,顺便讲解相关的基本概念,使您尽快地熟悉单片机应用的基本步骤,掌握软件编程的基本方法。
如果您学完了就能成为单片机的入门者,完全可以进行一般产品的开发;下册部分是单片机应用的提高部分,主要学习单片机的系统扩展(比如:ROM和RAM存储器的扩展,并行口的扩展,串行口的扩展,A/D和D/A与单片机的接口)以及相关开发工具和软件的使用(包括KELLC51的应用与调试技巧,硬件仿真器的使用)等等,如果您学完了下册部分,那就得恭喜您成为了单片机开发的高手了,不过单片机的技术是在不断的发展和提高的,您也不要太骄傲哦! 为了尽量把最新的单片机知识和应用成果收录进我们的教程,希望您能不吝赐教,共同来努力把我们的教程不断的改进和完善。
还是那句题外话,技术是靠不断的积累和交流才会进步的,固封自守只会更加落后。
由于时间和精力的限制,我还是希望在您学习本教程之前,自己先熟悉一点相关的电子技术知识,特别是数字电路基础,这对您学习中碰到的相关概念会有很大的帮助。
单片机之友
2 0531-86213622  单片机之友  QQ:280919249 51单片机多功能实验板 单片机之友提供
http://www.mcufriend.comhttp://mcufriend.wy8.net QQ:280919249 本学习板专为单片机爱好者学习MCS-51系列单片机而设计.可直接的实验有:1. 点亮LED 2.各种跑马灯 3.数码管显示数字和字母 4.数码管动态刷新显示5.查询方式按键6.中断方式按键 7.蜂鸣器发声8.单片机奏乐9.外部事件计数10.TTL电平串行通讯11.标准电平串行通讯12.IIC总线存储器读写13.IIC总线时钟芯片操作14.单片机口线有否上拉的区别15.显示驱动芯片的始能和禁止 51单片机编程器 详细介绍可查询http://mcufriend.wy8.net  http://www.mcufriend.com 支持的芯片型号 支持目前最为经典和市场占有量最大的ATMEL公司生产的AT89C51、C52、C55和最新的S51、S52;AT89C1051、2051、4051等芯片。
特别适合于渴望学习51单片机又想尽量减小学习投入的网友。
51单片机多功能试验板  开发板将单片机实验板、编程器、ISP下载线进行合理的组合,开发板上自带MCU采用了串口在系统 开发系统摆脱了传统、繁锁的单片机学习方式,将当今最流行、51最经济有效的学习方案完美地集成在了同一个系统中,是一个快捷、高效、灵活的单片机学习、开发方案。
具有非凡的性价比,是单片机爱好者快速掌握51系列单片机不可多得的工具... 既适合初学者入门学习,也适合专业人员开发51单片机产品的需求,还适用于渴望快速学习和掌握单片机应用技术的所有人员。
编控制配合串行下载编程控制软件,无需各种编程器可轻松地将编译好的代码下载到开发板上的CPU中进行验证或演示,试验过程中无需拔插任何电缆和芯片,整个过程只需利用鼠标操作即可,方便快捷。
烧写完毕即可自动演示,比ISP使用更方便。
同时也可以使用预留的ISP接口连接ISP下载头,对其他MCU进行在系统编程(ISP-In System Programming),对于产品的软件调试或升级,提供快捷的方案。
这样一来,开发系统又可以作为单独的ISP下载线使用了。
本开发系统的阻容元件、三极管为贴片封装,结构更紧凑,性能更稳定可靠开发系统提供了丰富的硬件资源和接口,随机提供了大量的开发源代码,将有助于初学者更好的学习单片机,轻松地迈入单片机的殿堂,领悟单片机给我们带来的无穷魅力。
所有实验例程均提供详细源代码,并且附带详细的注解说明。
开发板的程序和原理图请参考配套光盘。
板载实验资源和接口如下:STC89C51RC单片机8 路LED 4位LED数码管一路继电器控制蜂鸣器4x4矩阵键盘8位拨码开关一体化红外接收头16*2字符型液晶接口ADC0832 2路8位串行AD转换16K bits的I2C串行数据存储器 24C16 电话机的模拟攒机电路电话振铃检测电路电话拨号电路(DTMF发送)拨打电话或手机用的。
DTMF接收电路(可以接收手机或电话按键发出的DTMF信号),可以用来进行电话或手机的远程控制125KHZ的非接触IC卡读卡模块MAX232专用串口通讯电路ISP下载接口外扩接口开发板附带的实验项目:1:跑马灯2:拨码开关输入用LED提示3:点亮数码管4:10路抢答器5:100位计数器6:4位数的计数器(即0-9999的计数器)7:定时器实验8:实用单片机电子钟的制作9:频率计10:继电器控制实验11:按键检测子程序12:16*2 LCD字符液晶模块显示程序13:用实验板拨打电话或手机,LCD显示拨出的电话号码14:用电话或手机远程控制开发板的LED灯15:I2C存储器读写实验16:RS232串口通信实验17:模数转换(AD)程序18:实用的红外线分析仪19:读125KHZ的非接触IC卡程序20:STC51MCU的内部E2PROM的应用程序21:MCU内看门狗的使用开发系统的特色:利用本开发系统的硬件资源和提供的实验程序稍加修改就可以开发更加复杂的程序或产品如:绕线机或其他产品上用的计数器;带万年历的电子时钟;电压表;数据采集器;报警器,当有情况时,可以通过预先存储的电话号码,自动拨打电话报警;电话远程控制电器;密码门锁;还有现在最流行的用非接触IC卡(也称射频卡或感应卡)做的产品:(1):射频感应门锁(2):智能小区智能门禁(3):巡更管理系统(4):考勤系统(5):防盗门,保险柜,密码箱(6):野外个人识别(7):汽车(机动车辆)防盗(8):其它一些需要身份识别和保密的……   单片机之友 QQ:280919249 第一课单片机的概述 因为我们的主要课程是单片机的应用,本来不想讲解单片机的历史与发展(这话说现状更确切些),但为了兼顾大多数朋友,我还是简单的介绍一下这方面的相关知识。

一.单片机的由来 单片机,专业名称—MicroControllerUnit(微控制器件),它是由大名鼎鼎的INTEL公司发明的,最早的系列是MCS-48,后来有了MCS-51,现在还有MCS-96系列,我们经常说的51系列单片机就是MCS-51,它是一种8位的单片机,而MCS-96系列则是一种16位的单片机,至于它们之间有何区别,我们以后会讲到。
后来INTEL公司把它的核心技术转让给了世界上很多的小公司(不过,再小也有几个亿的销售/年哦),所以世界上就有许多公司生产51系列兼容单片机,比如飞利浦的87LPC系列,伟邦的W78L系列,达拉斯的DS87系列,现代的GSM97系列等等,目前在我国比较流行的就是美国ATMEL公司的89C51,它是一种带FlashROM的单片机(至于什么是FlashROM,我在这儿先不作介绍,等以后大家学到相关的知识时自然就会明白),我们的讲座就是以该型号的单片机来作实验的。
讲到这里,也许有的人会问:我平时在各种书上看到全是讲解8031,8051等型号的单片机,它们又有什么不同呢?其实它们同属于一个系列,只是89C51的单片机更新型一点(事实上,89C51目前正在用89S51代替,我们的实验系统采用就是89S52的,兼容89C52)。
这里随便说一下,目前国内的单片机教材都是以8051为蓝本的,尽管其内核也是51系列的,但毕竟8051的单片机已经属于淘汰产品,在市场上也很少见到了,所以由此感叹,国内的高等教育是如此的跟不上时代的发展需要!这话可能会引起很多人的不满,所以大家千万别传出去哦!!!
二.主要单片机的分类 接着上面的话题,再给大家介绍一下我们经常在各种刊物上看到的AVR系列和PIC系列单片机是怎么回事?以便让大家对单片机的发展有一个较全面的认识。
在没有学习单片机之前,这是一个令很多初学者非常困惑的问题,这么多的单片机我该先学哪一种呢? AVR系列单片机也是ATMEL公司生产的一种8位单片机,它采用的是一种叫RISC(精简指令集单片机)的结构,所以它的技术和51系列有所不同,开发设备也和51系列是不通用的,它的一条指令的运行速度可以达到纳秒级(即每秒1000000000次),是8位单片机中的高端产品。
由于它的出色性能,目前应用范围越来越广,大有取代51系列的趋势,所以学完了51系列的,看来必须学会AVR的才行,可叹知识爆炸,人生苦短。
说完了AVR的,再来说说另一种--PIC系列单片机,它是美国MICROCHIP公司,唉,又是老美,叫微芯公司的生产的另一种8位单片机,它采用的也是RISC的指令集,它的指令系统和开发工具与51系列更是不同,但由于它的低价格和出色性能,目前国内使用的人越来越多,国内也有很多的公司在推广它,不过它的影响力远没有51系列的大,所以作为初学者,51系列当然(不,绝对)是首选。
以上几种只是比较多见的系列,其实世界上还有许多的公司生产各种各样的单片机,比如:MOTOROLA的MC68H系列(老牌的单片机),TI的MSP430C系列(极低功耗的单片机),还有日本的TOSHIBA,日立的HITACH,德国的西门子SIEMENS等等,它们都有各自的结构体系,并不与51系列兼容。
为了不搞大家的脑筋,这里就不介绍了,等大家入门了以后自己再去研究它吧!现在我们还是回来了解一下51系列单片机到底是个什么东西,它有那些部分组成,请接着往下看:
三.单片机的结构及组成 单片机到底是一种什么东东,它究竟能做什么呢?其实它就是一种能进行数学和逻辑运算,根据不同使用对象完成不同控制任务的面向控制而设计的集成电路,此话好象有点绕口,没关系,大家都应该知道我们经常使用的电脑吧,在电脑上,我们可以用不同的软件在相同的硬件上实现不同的工作。
比如我们用WORD可以打字,用PROTEL可以设计图纸等等,单片机其实也是如此,同样的芯片可以根据我
5 单片机之友 QQ:280919249 们不同的要求做出截然不同的产品,只不过电脑是面向应用的,而单片机是面向控制的,比如控制一个
指示灯的亮和灭,控制一台电机的启动和停止等等。
那么它的内部究竟由哪些部件组成的呢?大家都知道我们的电脑有很多的零件,比如CPU(中央处理器),RAM(内存),ROM(程序存储器),输入输出设备(并行串行口)等等,在单片机中这些部件都有,而且还把它们全部做到了一块芯片上(这就是单片机名称的由来)。
讲到这里,您一定会想,这么多零件集成在一块芯片上,那为什么单片机的价格会这么便宜(89S51每块才10元左右),其实原因很简单----功能有强弱,就象我们平时用的PLC,控制一台数控机床要用128点的,而控制一台电机有几点的就足够了,另外这种芯片的产量很大,技术也非常的成熟,自然价格也就很低了。
那么单片机是如何来工作的,我们学习单片机又需要做哪些准备呢?对于一个初学者来说这是很有必要了解的:
四.学习单片机的准备工作 首先您需要一台电脑,这是最基本的,配置嘛,P2以上的就可以了;然后您需要一套开发单片机的软件,这个软件叫KEILC51,它是美国KeilSoftware公司专门为MCS-51系列单片机开发的第三方软件,它的免费测试版可在上下载,也可以在各种单片机网站上下载,最新版本是V7.09,安装时选择Uvision2,虽然有2K代码的限制,但足以满足我们学习的需要;其次,您还需要一台编程器,它是一种把程序写进单片机芯片的设备,这种设备品种很多,操作也很简单,大家既可以买现成的产品(价格从200多元到2000多元的都有),也可以自己制作;有了这两样东西还不行,为了看到程序执行的结果,我们还需要一块实验板。
好在现在出现了一种支持在线下载的单片机,只要满足一定的外部条件, 就能够直接把汇编的程序下载到目标单片机中。
经过反复的实验,我们开发 设计了这样的一套实验系统,它采用了一套集源代码编辑、软件汇编、程序 下载于一体的专业软件,采用具有在线下载功能的
FLASHROM单片机89S52, 配合本教程,可以完成教程中的每一个实验。
这样既免去了您添置编程器和 仿真器等设备的昂贵费用,又可以直接在实验板上看到程序执行的结果,更 由于采用的是FLASHROM的存储器,烧写次数可以达到1000次以上。
具体 电路图在教程的最后面附录中。
单片机之友 QQ:280919249单片机硬件结构和开发过程 从这一课开始,我们就要正式开始学习单片机了(如果你还没准备好,我们也不等了☺)。
前面我们曾经提到过单片机的内部结构是由CPU、ROM、RAM等等组成,它们的内部结构我们以后再讲,这一课让我们先来看看它的外部引脚(既硬件结构),看下面的图,这就是我们要实验用的89C51单片机的外部引脚图,给大家简单介绍一下。

一.单片机的引脚功能
1.VCC(40):电源+5V。

2.VSS(20):接地,也就是GND。

3.XTL1(19)和XTL2(18):振荡电路。
单片机是一种时序电路,必须有脉冲信号才能工作,在它的内部有一个时钟产生电路,有两种振荡方式,一种是内部振荡方式,只要接上两个电容和一个晶振即可;另一种是外部振荡方式,采用外部振荡方式时,需在XTL2上加外部时钟信号(详细的内容将在以后的课程中专门介绍)。

4.PSEN(29):片外ROM选通信号,低电平有效。

5.ALE/PROG(30):地址锁存信号输出端/EPROM编程脉冲输入端。
至于它们的作用我们暂时不去管它,等以后学到相关的知识时再来研究它。
这也许就是本教程区别于其他教材的最大特点----先实践后理论,尽量用实验结果来总结理论知识,因为单片机是一种通用的产品,它的功能设计是为了满足大多数使用者的要求,换句话说,不同的使用者只会使用其相关的功能,几乎不可能把全部的功能都用起来,因此我们完全不必象学习其他电子技术那样,把单片机的全部知识都搞懂了再去开发产品。
这话前面好象说过了!
6.RST/VPD
(9):复位信号输入端/备用电源输入端。
什么是复位信号,为什么要加复位信号?当然也暂时不去管它。

7.EA/VPP(31):内/外部ROM选择端。
在30、9脚的功能上不知大家注意没有,都有一个/,什么意思呢?这是引脚的第二功能,也就是说,该引脚既可以作前面的功能,也可以作后面的功能,至于它是如何工作的,我们暂时也别去研究它。

8 单片机教程 (MCS-51系列)
8.P0口(39-32):双向I/O口。

9.P1口(1-8):准双向通用I/0口。
10.P2口(21-28):准双向I/0口。
11.P3口(10-17):多用途口。
I/O就是英文IN/OUT的缩写,这些引脚的功能想必大家也都明白了,(就是输入/输出的意思), 这32个I/O口就是留给我们作连接外围电路用的,那么它们之间有些什么不同呢?这个问题稍微有点 复杂,我们将在以后的课程中专门来学习。
现在我们先来往下看:
二.单片机的电路连接和开发过程 看附图,这就是我们做实验用的电路图,想必大家都能看得懂吧。
接下来就让我们通过一个实验 来看看单片机是如何工作的?我们的实验是让一个
LED灯亮起来,亮哪一个?这就随便你了,比如我们 就让LED1亮起来吧,仔细看一下电路图,LED1接在什么地方呢?接在单片机的P1.0的引脚(也就是
1 脚)上,那么按照该电路图的连接方法,当1脚为高电平时,LED1是不亮的;只有当1脚为低电平时, LED1才会亮起来,怎样才能让1脚由高电平变为低电平呢?我们让人做事,就必须对她说一声,也就 是发布命令,想让单片机工作,也得发布命令,不过在计算机中那叫指令,我们要让1脚变为低电平的 指令是CLRP1.0(让1脚变为高电平的指令是SETBP1.0),这就是我们通常所说的源代码,(这是我 们开发产品的第一步—源代码编辑);怎么做呢?我们首先得打开实验软件,屏幕出现一个浏览器的软件窗口,点击左边的扩展实验,选中实验16—自动温度控制器,再点击工具栏里的调试按钮,弹出一个记事本对话框,写入CLRP1.0;(☺分号必须在英文状态下输入),输入完毕后选择文件→保存即可;那么单片机能读懂这条指令吗?当然不能,接下来我们还有一件事情要做,就是把这句指令翻译成单片 机能读懂的东西,单片机能读懂什么呢?它其实只懂一样--就是数字,因此,我们就把CLRP1.0翻译 成C2H,90H,至于为什么要翻译成这样,这当然是INTEL公司规定好的,我们就不需要去研究它了。
这 个过程我们叫作编译,(这是我们开发产品的第二步),那么指令是怎么编译过来的呢?这就得靠专业的 软件了,我们做实验使用的软件就有此功能,只要点击工具栏上的编译按钮,稍等片刻即出现一个编 译信息窗口,如果编译通过就会有编译完成,结果如下:0
个警告,0个错误的编译信息,如果编译错 误则会出现编译错误的信息,并提示错误的行号;编译完了之后通常要进行程序仿真(这是第三步), 当然我们的实验程序很简单是不需要仿真的;接下来怎么才能把编译通过的指令写入单片机中呢?这通 常需要借助于一种硬件工具,叫编程器(也叫烧录器),不过我们的实验板采用的是具有串行下载功能 的单片机,所以您只要直接点击快捷工具栏上的下载按钮,程序就进入了实验板(这是第四步—编程)。

自此就完成了单片机开发的全过程。
全部工作结束后,我们看到了什么?接P1.0(1脚)的LED1亮了起来;改变源代码,变成SETBP1.0; 进行编译,下载,看看结果是不是LED1不亮了。
怎么样,不难吧!!! 最后让我们来思考一个问题,当我们用编程器把编译后的指令写入单片机时,单片机就开始执行 这条指令,那么这条指令就一定在单片机内部的某个地方,它究竟在哪里呢?单片机的内部结构又是怎 么样的呢?这将是我们第三课要讨论的内容—单片机的内部结构(一)……半导体存储器。


三.本课总结 本课主要讲述了单片机开发的整个过程,这个过程包括第一步—编辑源代码,第二步—编译源代码,第三步—程序仿真,第四步—芯片烧写(亦称编程),希望大家记住这四步,这是非常关键的;单片机的硬件原理其实并不复杂,本来嘛,单片机的设计就是为了通用和灵活,所以开发单片机最重要的 就是软件的编写,以后我会慢慢地教大家学习更多的软件知识。

四.第2课习题 1.89C51的电源电压是多少伏?
2.熟练掌握编译软件的使用方法。

9 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第三课单片机的内部结构(一) 单片机的内部究竟有哪些部分组成的,它们都有些什么作用呢?让我们看下面的图: 这就是单片机的内部方框图,让我们先来了解其中的ROM存储器:
一.半导体存储器ROM
1.几个基本概念 上一课我们讲到了把编译后的指令下载到单片机后这条指令一定在单片机内的某个地方,那么它 究竟在哪里呢?原来它就放在一个叫程序存储器的地方,英文名称ROM(全称为ReadOnlyMemory), 叫只读存储器。
它是一个什么东西呢?在讨论这个问题之前,让我们先来看几个物理现象:
(1)数和物理现象的关系 不知大家是否还记得,在学习数字电路时我们曾用一盏灯的亮和灭来表示电平的高和低,即用“1” 来表示高电平,用“0”来表示低电平,如果现在有两盏灯那它会有几种状态呢?请看下面的表: ¤ ¤
0 0
0 1
1 0
1 1 两盏灯的组合就是四种状态:00,01,10,11。
如此看来灯的亮和灭这种物理现象同数字确实有 着某种联系,如果我们把它们按一定的规律排列好,那么电平的高或低就可以用数字来表示了,换句话 说:不同的数字可以代表不同数量灯的电平高或低。
比如:0000,0001,0010,0011,0100,0101,0110, 0111,1000,1001,1010,1011,1100,1101,1110,1111
这十六种组合就可以代表四盏灯的状态, 能理解吗?
(2)位及字节的含义 10 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 在单片机中,一盏灯(实际上是一根线)我们称它为一位,它有两种状态(“0”或“1”),分别 对应电平的高或低,它是单片机最基本的数量单位,用BIT来表示。
8盏灯(八根线)有256种状态, 这8盏灯(也就是8位)我们把它称为一个字节,用BYTE表示。
至于为什么要怎么规定,这就不需要 你我操心了,我们只要记住就可以了。
那么单片机是如何来储存这些数字所代表的字节的状态的呢?接 着往下看:
2.半导体存储器的工作原理
(1)存储器的内部构造 看下面的图,这就是半导体存储器的结构简图:(图中有
4个字节)
(2)存储器的工作原理存储器就是用来存放数据的地方,它其实是利用电平的高或低来存放数据的,也就是说,它实际上存放的是电平的高或低的状态,而不是我们所习惯上认为的“1234”这样的数字。
那它是如何工作的呢?看上面的图,这就是存储器的内部结构示意图,一个存储器就象一个小抽屉,一个小抽屉里有8个小盒子,每个小盒子用来存放1位“电荷”,电荷通过与它相连的电线传进来或释放掉,至于电荷在小盒子里是怎样存放的,这就不用我们操心了,您可以把电线想象成水管,小盒子里的电荷就象是水,那就好理解了,存储器中的1个小抽屉我们把它称之为1个“单元”,相当于1个字节,而1个小盒子就相当于1位。
有了这么一个构造,我们就可以开始存放数据了,比如我们要放进一个数据“00011010”,我们只要把第2号、第4号和第5号小盒子里存满电荷,而其它小盒子里的电荷给放掉就行了。
可是问题又出来了,一个存储器有好多相同的单元,线是并联着的(看D7-D0),在放入电荷的时候,会将电荷放入所有的字节单元中,而释放电荷的时候,会把每个单元中的电荷都放掉,这样的话,不管存储器有多少个字节单元,都只能放同一个数,这当然不是我们所希望的。
因此,我们要在结构上稍作变化,看上面的图,在每个单元上有根线与译码器相连,我想要把数据放进哪个单元,就通过译码器给哪个单元发 11 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 一个信号,由译码器的通过这根线把相应的开关打开,这样电荷就可以自由地进出了。
那么这样是不是 就能随意地向存储器写入或者读出数据了呢?其实还不能,继续看上面的图,与D7-D0相连的还有一个 控制器,它是用来干什么的呢?这根线叫写入/读出控制线,当我们向存储器写入数据时,必须先把这 个开关切换到写入端;而要读出数据时,就得先把开关切换到读出端;而片选端则是为了区分不同的存 储器设置的。
这里没搞明白,没关系,后面还有介绍,先让我们来看看译码器是如何工作的?
3.半导体存储器的译码 简单介绍一下:我们知道,1
根线可以代表2种状态;2根线可以代表4种状态;3根线可以代表 8种;256种状态又需要几根线代表?8根线,所以一片6264存储器我们只需要16根线就可以了。

4.存储器的选片及总线的概念 至此,译码的问题解决了,让我们再来关注另外一个问题:送入每个字节的8根线又是从什么地 方来的呢?它就是从单片机的外部引脚上接过来的,一般这8根线除了接一个存储器之外,还要接其它的器件,这样问题又出来了,这8根线既然不是存储器和单片机之间专用的,如果总是将某个单元接在这8根线上,就不行了,比如这个存储器单元中的数值是“FFH”,另一个存储器的单元是“00H”,那么这根线到底是处于高电平,还是低电平?岂不是要打架看谁历害了?所以我们必须让它们分离。
办法当然也简单,当外面的线接到集成电路的引脚上来后,不直接接到各单元去,中间再加一组开关就行了。
这组开关就是前面提到的控制器(看前面的图),平时我们让开关打开着,如果确实是要向这个存储器中写入数据,或要从存储器中读出数据,再让开关切换到相应的位置就行了。
这组开关由三根引线选择:读控制端、写控制端和片选端,要将数据写入,先由控制器选中该片,然后发出相应的写信号,开关切换到相应的位置,并将传过来的数据(电荷)写入片中;如果要读信号,先选中该片,然后发出读信号,开关也切换到相应的位置上,数据就被送出去了;另外读和写信号还同时受到译码器的控制,由于片选端的不同,所以虽有读或写信号,但没有片选信号,所以另一个存储器就不会“误会”而开门,造成冲突,那么会不会同时选中两个存储器呢?只要是设计好的系统就不会,因为它是由计算机来控制的,如果真的出现同时选中两个存储器的话,那就是电路出故障了。
如此看来,存储器要想写入或者读出数据还真是不简单,不过好在这些都是由计算机自动完成的,不需要我们去操心。
从上面的介绍中我们已经看到,用来传递数据的8根线(51单片机是8根)并不是专用的,而是很多器件大家共用的,所以我们把它们称之为数据总线(总线英文名为BUS),即公交车道,谁都可以走;而16根地址线(51单片机共有16根地址线,这些以后会讲解,这里不必死记硬背)也是连在一起的,我们把它们称之为地址总线,看上面的图。
对于本小节的内容,如果您一时还无法理解,没有关系,继续往下看好了,我们在以后的课程中还会详细的介绍,这里只要您稍微的了解一下就可以了!!! 12 单片机之友 QQ:280919249 单片机教程 (MCS-51系列)
5.半导体存储器的分类 第一课中我们提到过,89C51是一种带FlashROM的单片机,什么是FlashROM?它到底是一种 什么东西呢?ROM我们已经知道,是只读存储器,所谓只读,从字面上理解那就是只可以从里面读出数 据,而不能写进去,它类似于我们的书本,发到我们手里之后,我们只能读里面的内容,不可以随意更 改书本上的内容。
ROM
就是单片机中用来存放程序的地方,前面我们下载到单片机的指令就放在这个地 方。
讲到这里大家也许会感到困惑,既然ROM是只读存储器,那么指令又是如何进入其中的呢?其实所 谓的只读只是针对正常工作情况下而言,也就是在使用这块存储器的时候,而不是指制造这块芯片的时 候,只要让存储器满足一定的条件就能把数据预先写进去,这个道理也很好理解,书本拿到我们手里是 不能改了,但当它还是原材料--白纸的时候,我们完全可以由印刷厂把内容印上去嘛。
前面的编程就是 这么回事! Flash
ROM是一种快速存储式只读存储器,这种程序存储器的特点就是既可以电擦写,而且掉电 后程序还能保存,编程寿命可以达到几千至几万次,所以我们的实验系统是可以反复烧写的,您尽管使 用。
目前新型的单片机都采用这种程序存储器;当然,除了这种程序存储器外,还有两种早期的程序存 储器产品,简单介绍一下:PROM,EPROM
和EEPROM,PROM称之为可编程只读存储器,就象我们的练习 本,买来的时候是空白的,可以写东西上去,可一旦写上去,就擦不掉了,所以它只能写一次,要是写 错了,就报废了,习惯上我们把带这种程序存储器的单片机称为
OTP型单片机,如果您的产品批量生产, 又要求价格比较低的话,带这种程序存储器的单片机是非常合适的;EPROM,称之为紫外线擦除的可编 程只读存储器,它里面的内容写上去之后,如果觉得不满意,可以用一种特殊的方法去掉后重写,就是 用紫外线照射,紫外线就象“消字灵”,可以把字去掉,然后再重写,当然消的次数多了,也就不灵光 了,所以这种芯片可以擦除的次数也是有限的——几百次吧,电脑上的
BIOS芯片采用的就是这种结构的存储器;EEPROM,前一种存储器的擦写要用紫外线,而这种存储器可以直接用电擦写,比较方便数据 的改写,它有点类似于FLASH存储器,但比FLASH存储器速度要慢,现在新型的外部扩展存储器都是都 是这种结构。
有关这几种程序存储器的使用和原理,我们将在下册中详细的介绍,这里就不多讲了。
总之一句, 不管哪种程序存储器,它们的作用都只有一个----就是用来存放程序(也就是我们为单片机编写的指 令)。
了解了
ROM,让我们再来简单讲讲另一种存储器,叫随机存取存储器,也叫内存,英文缩写为RAM (RandomessMemory),它是一种既可以随时改写,也可以随时读出里面数据的存储器,类似于我 们上课用的黑板,可以随时写东西上去,也可以用黑板擦随时擦掉重写,它也是单片机中重要的组成部 分,单片机中有很多的功能寄存器都与它有关,详细内容后面再讲。

二.本课总结 本课主要讲述了单片机的两种半导体存储器—只读存储器
ROM和随机存储器RAM的工作原理,它们是单片机的重要组成部分,了解它的内部结构对我们学习单片机是很有帮助的。
不过如果您一时对本 课的内容还无法搞得很明白,也没有关系,随着学习的深入,我们还会慢慢地讲解相应的基础知识,可 千万不要放弃哟?我在没有学会单片机之前也是如此囫囵吞枣的。

三.
3课习题
1.半导体存储器分为几大类?
2.ROM存储器的作用是什么?
3.什么是位?什么是字节?
4.为什么8根线在单片机中会有256种状态?它是如何出来的? 5.89C51的ROM有多少字节的容量? 13 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第四课单片机的内部结构(二) 上一节课我们讲了半导体存储器ROM和RAM的内部结构,大家是否觉得有些枯燥了,这一课让我 们先来做一个实验:
一.LED灯闪烁的实验程序 还记得第二课中的实验吗?这个实验在实际应用中太没有意义了,接下来我们要让LED1不断的 闪烁,就象高楼上或者大海中用的航标灯。
怎么才能让LED1不断的闪烁呢?实际上就是让它亮几秒, 再灭几秒,也就是让P1.0交替地输出高电平或低电平,怎样来实现这个功能,按照前面所学的知识, 我们写出下面的程序:CLRP1.0;SETBP1.0;编译后下载到单片机…… 结果不行,为什么?这里有两个问题:首先计算机执行指令的速度很快,执行完第1条指令后LED1 是灭了,但在极短的时间内又去执行第2条指令,LED1又亮了,我们根本无法看到灯曾经灭过;第
个问题是当执行完第2条指令后,不会再去执行第1条指令了,因为单片机执行指令的过程是一条一条 地顺序执行的。
如何解决这两个问题呢?我们可以作如下的设想:第
一,执行完第1条指令后让单片机延时一段 时间(几秒或零点几秒),然后再去执行第2条指令,这样就可以看到LED1曾经灭过了;第
二,让单片 机执行完全部指令后再返回去执行第1条指令,如此不断的循环就可以达到我们的要求了。
实验程序如下: 主程序 MAIN:SETBP1.0 ;(1) LCALLDELAY;(2) CLRP1.0 ;(3) LCALLDELAY;(4) LJMPMAIN;(5) 子程序 DELAY:MOVR7,#250;(6) D1:MOVR6,#250;(7) D2:DJNZR6,D2 ;(8) DJNZR7,D1 ;(9) RET ;(10) END .(11) 还记得软件的使用方法吗?调试,写入源代码,编译,下载到单片机,看看是不是我们想要的 结果…… 在分析这段程序之前,先来说明几个标点符号的意义:
1.分号在这里起一个分隔符的作用,表示 这条指令到此为止;
2.括号内的数字在这里是为了解释程序用的,实际的编译过程中是没有意义的,也 就是说没有也是一样的,只是为了程序的可读性更强,我们一般会在分号的后面加上程序的注释文字(后 面我们会用到);
3.特别☺:程序中的标点符号只能在英文状态下输入,当使用中文输入时,必须切换 到半角状态,不然编译软件会出错。
接下来我们分析一下这段程序:按照我们的要求,第
1条,让灯灭,第2条应该是延时,第3条 是让灯亮,第4条和第2条一样也应该是延时,第5条应当返回去执行第1条指令。
看一下上面的程序, 第1条我们已经懂了,是让LED1灭,第2条和第4条我们等一下讨论,第5条是LJMPMAIN,LJMP 是一条指令,意思是转移,转移到什么地方去呢?看一下LJMP后面跟着什么,是MAIN,什么地方有MAIN, 在第1条指令的开头就是MAIN,所以第5条指令的意思就是跳转到MAIN(即第1条指令处继续执行), 如此一来,就不断地重复执行这些指令。
那么MAIN又是什么意思呢?它实际上是我们为这段程序起的 14 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 一个名称,专业术语叫标号,既然是一个名称那可不可以用JIGUO,CHINA等等的其他名字呢?当然可 以,这完全取决于您的需要(☺:不过也有一些是不能采用的,我们以后再讲)。
再来分析第2条和第4条指令,看看它们是如何实现延时的?LCALLDELAY,LCALL也是一条指令,这条指令叫做调用子程 序指令,看看LCALL后面跟着的是什么--DELAY,哪里有DELAY,在第6条指令的开头,很显然这也是 一个标号,这条指令的作用就是当执行到这条指令时就转去执行LCALL后面标号所在处的程序,如果在 执行程序时遇到RET指令(RET叫返回指令),就返回到LCALL指令的下面一条(即第3条指令)处继 续执行,在第9条指令后确实有RET指令,那么在执行完第2条指令后就应该去执行第6.7.8.9条指令, 之后遇到第10条指令:RET,执行完这条指令后就回去执行第3条指令,将P1.0清零,也就是让LED1 亮,然后再去执行第4条指令,执行完后又回到6.7.8.9.10条指令,最后执行第5条指令:LJMPMAIN, 也就是我们刚才说的跳转到第1条,将P1.0置位,就是让LED1灭掉。
如此周而复始,LED1就不断的 闪烁。
好好理解这段文字,务必把它搞清楚!!! 从标号DELAY处(即第6条)开始到RET的这一段指令我们称之为子程序,它是一段延时程序, 至于延时多长时间,我们会在以后的课程中学习。
程序的最后一条是END,它不是指令,它只是告诉编 译软件整个程序到此结束了,它叫“伪指令”。
在大家以后的编程中,写完程序都要加上这一条。
在上面的程序中我们知道了从标号DELAY开始的子程序是一段延时程序,那么它又是如何工作的 呢?在了解它的工作过程之前我们必须先知道其中的一些符号,就从R7开始吧,它是单片机内部的
个重要组成部分,叫工作寄存器,什么是工作寄存器?下面我们就来讲解这个问题:
二.工作寄存器 上一课我们已经讲过,在单片机中有许多的功能寄存器和半导体存储器
RAM有关,那么工作寄存 器又属于哪一部分呢?它是用来干什么的呢?要搞清楚这个问题,让我们先从日常生活中的一个例子说 起,比如我们要做一道数学题123+456,您会马上得出答案:579,接下来再看一道题:123+456+789, 要你马上得出答案就不那么容易了,通常我们会怎么做呢?一般总是先把123+456的结果579写在一张 纸上,然后再算579+789=1368,这1368就是我们想要的最终结果,而579只是为了得到最终结果而暂 时记下来的中间结果,单片机中做运算和我们生活中做运算一样,也需要把中间结果放在某个地方,那 么计算机把它放在哪儿呢?前面我们提到的ROM(只读存储器)中,不行!因为ROM是用来存放程序的, 它只能写进去,不能读出来(再次提醒一下,这只是相对而已),所以只能放在单片机的另一个区域—RAM中(即随机存取存储器)中。
R7就是RAM区域中划出的一部分。
知道了R7,接下来让我们来分析一下 这段子程序(延时程序)。

三.LED灯闪烁程序子程序的分析 首先看第6条,MOVR7,#250,这也是一条指令,意思是传递数据。
我们知道在日常生活中,要 传递一件东西就必须要有一个传递者,一个接受者和被传递的东西,那么在单片机中是怎么区分它们的 呢?在这条指令中,R7
是接受者,250就是要传递的东西(单片机中要传递的东西当然是数字了),这 里传递者被省略了(顺便提一下,并不是每条指令都能省略的,事实上大部分的指令都要有传递者), 这样一来,这条指令的意思也很清楚了:就是把
250这个数传递给R7这个工作寄存器(也就是把250 这个数送入R7中),这样执行完这条指令后R7中的值就应该是250,我们可以用DUBG8051这个软件来 验证一下,看是不是符合。
讲到这里,不知大家注意没有,在250这个数的前面有个#,它是什么意思 呢?这个#就说明250是一个被传递的数的本身,而不是传递者。
看懂了MOVR7,#250,那么MOVR6, #250也应该很清楚了。
接着看第8条DJNZR6,D2,这又是另一条指令,我们来看一下DJNZ后面跟着什么,一个是R6, 一个是D2,R6我们已经知道了,再找一下D2,D2在本行的开头,我们已经学过,它是标号。
那么这条 指令是怎么执行的呢?它的执行过程是这样的:它将后面的值(即工作寄存器R6中的值)减
1,然后 查一下这个值是否等于“0”,如果等于“0”就往下执行,如果不等于“0”就转移,转移到什么地方去 呢?大家应该明白了,实际上这条指令的执行结果就是在原地转250次;当R6中的值等于“0”之后, 程序就去执行第9条指令,也就是DJNZR7,D1,大家自行分析一下这条指令的结果(是不是转去执 行MOVR6,#250,同时R7中的值减1),这段子程序的最终执行结果就是DJNZR6,#250这条指令被 15 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 执行了250*250=62500次,执行这么多次干吗?就是为了延时。

四.本课总结 大家可以改变一下MOVR6,#250这条指令中的值(注意☺:不能大于255,为什么,以后会讲到)或者改变一下标号的名称,看是不是符合上面的分析。
接下来提一个问题:通过实验我们看到了 LED1在闪烁,是因为DJNZR6,#250这条指令被执行了250*250=62500次,执行那么多次究竟需要多 长时间呢?下一课我们就将讨论这个问题。
这里有必要介绍一下DUBG8051这个软件,它是一个专为8051单片机设计的仿真软件,配合MON51 仿真机能进行51单片机的仿真,拥有这样一套设备在过去可是非常奢侈的,不过现在已经很少有人使 用它了,原因是目前市场出现了许多兼容KEILC51的仿真器,它们的功能更先进,MON51只能属于被 淘汰产品。
不过作为单片机初学者,使用DUBG8051还是很有意义的,因为用它可以帮助我们理解单片 机的内部结构和程序的执行结果,在我们实验套件的随机光盘中,有这个软件。

五.第4课习题
1.什么是主程序?什么是子程序?
2.标号的含义是什么?
3.单片机是如何执行程序的?
4.工作寄存器属于ROM单元还是RAM单元?
5.在实验中如果没有RET指令会出现什么情况?
6.理解指令LCALL、LJMP、DJNZ的意义。

7.掌握DUBG8051软件的使用方法。
16 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第五课单片机的内部结构(三) 上一课中,我们提到了DJNZR6,#250这条指令被执行了250*250=62500次,就产生了延时,那么这个时间是多少呢?它又是如何计算出来的呢?这一课就来讨论这个问题。

一.单片机的时序
1.时序的由来我们已经知道单片机执行指令的过程就是顺序地从ROM(程序存储器)中取出指令一条一条的顺 序执行,然后进行一系列的微操作控制,来完成各种指定的动作。
它在协调内部的各种动作时必须要有一定的顺序,换句话说,就是这一系列微操作控制信号在时间上要有一个严格的先后次序,这种次序就是单片机的时序。
这就好比我们学校上课时用的电铃,为了保证课堂秩序,学校就必须在铃声的统一协调下安排各个课程和活动。
那么单片机的时序是如何规定的呢?接着往下看:
2.时序的周期计算机每访问一次存储器的时间,我们把它称为一个机器周期,它是一个时间基准,就象我们日 常生活中使用的秒一样,计算机中一个机器周期包括12个振荡周期,什么是振荡周期?一个振荡周期是多少时间?振荡周期就是振荡源的周期,也就是我们使用的晶振的时间周期,一个12M的晶振,它的时间周期是多少,如果电子技术学得好的朋友应该不难算出(T=1/f),也就是1/12(微秒),那么使用12M晶振的单片机,它的一个机器周期就应该等于12*1/12(微秒),也就是1μ
S。
在MCS-51系列单片机中,有些指令只要一个机器周期,而有些指令则需要两个或三个机器周期,另外还有两条指令需要4个机器周期,这也不难理解,你在家擦地板的话总比擦桌子的时间要长,不过我可是大男子主义,从来不做家务的。
开句玩笑!!!如何衡量指令执行时间的长短?我们就要用到一个新的概念:指令周期—即执行一条指令所需的机器周期,INTEL公司规定了每一条指令执行的机器周期,当然这不需要我们非把它记住,不过在这里DJNZ指令我们是要记住的,它是双周期指令,执行一次需要两个机器周期,即2μ
S。
(12M晶振的话),回到我们上一课的实验,延时的时间就应该算出来了吧,是62500*2μS=125000μ
S,也就是125mS。
这么大的数字也就0.125S,怪不得LED1闪烁的这么快。
(这里给大家出个题目:在上一课的实验中,如何延长闪烁的时间?想想看,怎么做?当然,不会也没关系)。

二.单片机的时钟电路 大家已经知道,单片机是在一定的时序控制下工作的,那么时序和时钟又有什么关系呢?时钟是时序的基础,单片机本身就如同一个复杂的同步时序电路,为了保证同步工作方式的实现,电路就要在唯一的时钟信号控制下按时序进行工作。
那么单片机内的时钟是如何产生的呢?
1.内部时钟电路 17 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 在MCS-51单片机的内部有一个高增益的反相放大器,其输入端为引脚XTL1(19),输出端为XTL2 (18),我们只要在外部接上两个电容和一个晶振,就能构成一个稳定的自激振荡器,它的内部电路的 工作原理就不介绍了,这里主要讲一下电容和晶振的选择,看上面的图,晶振的大小与单片机的振荡频 率有关,我们到串行接口时再详细讲解,电容的大小影响着振荡器振荡的稳定性和起振的快速性,通常 选择
10-30P的瓷片电容或校正电容;另外在设计电路时,晶振和电容应尽可能的靠近芯片,以减少PCB 板的分布电容保证振荡器振荡工作的稳定性,提高系统的抗干扰能力。

2.外部时钟电路 除了内部时钟方式外,单片机还可以采用外部引入时钟的振荡方式,什么时候需要采用外部时钟 方式呢?当我们的系统由多片单片机组成时,为了保证各单片机之间时钟信号的同步,就应当引入唯
的公用的外部脉冲信号作为各单片机的振荡脉冲,此时应将
XTAL2悬空不用,外部脉冲信号由XTAL1 引入,如上右图所示,外部信号的高低电平持续时间应大于20m
S,这是大虾们的作品,在此就不介绍 了。

三.本课总结 本课的内容比较少,我就罗嗦一下,讲几句题外话。
我是一个只有初中毕业,没有读过多少书的 人,从小就爱好无线电,记得很小的时候,当通讯兵的父亲带回来几本电子方面的书籍,从此就迷上了 无线电,那种痴迷程度决不亚于现在的小孩迷恋游戏机,至今仍然清楚的记得,曾经因为装成功一台

6 管收音机而兴奋的几天几夜没睡好觉。
那个时候,我国的电子工业还刚刚起步,买一个3AX31的三极管 都要特地跑到市区,而且价格奇贵,几乎要用去一个月的零化钱,当时最愿意去的地方就是上海的虬江 路电子旧货市场,因为在那里可以淘到好多旧的电子元件。
初中毕业以后,在当地根本就找不到一家电 子企业,只好在镇上开了一家电器修理店,也就是这几年,边干边做地学了不少在今天已根本无法再学 得进去的“电子,空穴,移位,寄存,施密特”等等理论知识,由于身边没有一个可以请教的老师,为 了加深学习的印象,所以只好一边做实验一边学理论,尽管进度很慢,但效果竟然还不错,好在当时搞 家电修理的收入还可以,加上没有家庭负担,也就这么过来了。
随后的几年,做过工人,也当过老师,但更多的时间是在搞技术开发,这些年来,看到很多的昔 日同学靠导腾房地产或者做生意发了财,可自己依然还在这个领域默默无闻的钻研着,但我还是没有后 悔,也从来没有想过改行,因为电子技术那众多迷人而未知的领域常常会使我深深地陷入其中,以至无 法自拔,也感叹自己搞了这么多年,还只是一个入门者。
现在老是听到有些年轻的朋友说我要速成单片机,速成
C语言,速成什么什么的,每当我看到或 听到这些话的时候,总有一种说不出的滋味。
现在的社会,什么都讲究个效率,这本来没有错,但学
项技术也能速成,实在让人有点不知道说什么好。
就单片机而言,即使你现在只有
15,6岁,也很有天 赋,想把现在的几种主流单片机都搞懂并很好的应用到实践中去,没有个几年恐怕也难,更何况单片机 的技术是在不断发展的,你想跟也来不及。
不过,话又说回来,我不是要打击大家的学习积极性,单片机是一种非常宽泛的技术,它的设计 是为了满足大多数的需要,换言之,即使你并没有把全部的知识都理解得很深透,或者说没有把每种单 片机都搞懂,也没关系,你一样可以在实际的产品开发种应用它,因为几乎没有一个产品会把全部的指 令都用起来。
好了,废话讲了半天,还是言归正传吧,希望大家课后多交流,因为在我看来,技术只有不断的 交流,才会有进步,闭门造车只有“S”路一条。

四.
5课习题
1.什么是单片机的机器周期?什么是振荡周期?什么是指令周期?它们之间的关系是怎么样的?
2.什么是单片机的时序?
3.单片机有几种振荡方式?
4.简述单片机内部时钟的产生过程。
18 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第六课单片机的内部结构(四) 在前一课中,我们讲述了单片机的时序和时钟,大家是不是又觉得有些头疼了,下面让我们再来 做两个实验放松一下。

一.单片机I/O口的输出实验
1.实验程序 程序如下: LOOP:MOVP1,#0FFH; LCALLDELAY; MOVP1,#00H; LCALLDELAY; LJMPLOOP; DELAY:MOVR7,#250; D1:MOVR6,#250; D2:DJNZR6,D2; DJNZR7,D1; RET ; END。
还是老规矩,调试,写入源代码,编译,下载,看到了什么?8只LED灯都在闪烁(注意:前面 的实验是让一个LED灯闪烁),分析一下程序:
2.程序分析 这段程序和前面的程序比较,有两处不同,第1条,原来是SETBP1.0,现在改为MOVP1,#0FFH, 第3条,原来是CLRP1,现在改为MOVP1,#00H。
为什么这样改了之后就变成了8只LED灯同时闪 烁了?原来P1代表了P1.7-P1.0的全部,我们把它当作一个存储器单元(即一个字节),不过对一个存 储器单元送数就应该用MOV指令了;在这里P1(P1.7-P1.0)接的是LED灯(也就是负载),它起到了 一个输出端的作用。
那如果把P1改为P2或P3或P4行不行呢?答案是肯定的,为什么?我们稍后再谈, 接着看第2个实验。

二.单片机I/O口的输入实验
1.实验程序 程序如下: MAIN:MOVP3,#0FFH; LOOP:MOVA,P3 ; MOVP1,A; LJMPLOOP; END. 同样的方法把程序下载到单片机,按下第1个按钮,第1个LED灯亮了,按下第2个按钮,第
2 个LED灯亮了,松开按钮,相应的灯就灭了,是不是有点象工业控制中的点动控制原理。
分析一下这个 程序:
2.程序分析 看附图的硬件接线图,有4个按钮分别接到了P3.2,P3.3,P3.4,P3.5,引脚上。
再来分析一下 程序,第1条,使P3口(包括P3.7-P3.0)全部为高电平(为什么MOVP3,#0FFH能使P3口全部为高 电平,我们在下一课中讨论);第2条MOVA,P3;MOV我们已经知道,是送数的意思,这条指令的意 思就是把P3口的数送到A中去,A是什么呢?我们也可以把它看成一个中间单元,就象R7寄存器一样, 第3条指令就是把A中的数送到P1口去;第4条是循环,这些我们都已经见过,当我们按下P3.2所连 19 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 接的按钮时,#0FFH这个数就被送到了A中,通过程序又送到了P1,使P1.2输出低电平,LED3就亮了, 按下P3.3-P3.5连接的按钮,对应的LED4-LED6也亮了,松开按钮,相应的LED灯就灭了。
如果把按钮 接到P2.0-P2.7或P4.0-P4.7可不可以呢?当然可以。
所以在这里P3口又起到了一个输入端的作用。
由上面两个实验我们得出结论,凡是以P开头的管脚都可以用作输入输出口,在89C51中这32 个管脚我们就称之为并行口。
它们实际上就是特殊功能存储器SFR(什么是特殊功能寄存器,我们后面 再讲)中的四个,记作P0,P1,P2,P3,它们都是双向通道,即既可以作为输出口,也可以作为输入 口,作输出时数据可以锁存,作输入时数据可以缓冲,那么它们是怎么实现输入输出功能的呢?继续往 下看。

三.
单片机并行口的结构分析 先来看看输入结构:
1.输入结构I/O口作为输入口时有两种工作方式,即所谓的读端口与读引脚。
读端口时实际上并不从外部读入数据,而是把端口锁存器的内容读入到内部总线,经过某种运算或变换后再写回到端口锁存器。
比如取反,置位,清零等等指令;而读端口时才真正地把外部的数据读入到内部总线,图中的两个三角形表示的就是输入缓冲器,CPU将根据不同的指令,分别发出“读端口”或“读引脚”信号,以完成不同的操作,这是硬件自动完成的,不需要我们操心。
读引脚时,也就是把端口作为外部输入线时,首先要通过外部指令把端口锁存器置“1”,然后再实行读引脚操作,否则就可能读入出错。
为什么?看上面的图,如果不对端口置“1”,端口锁存器原来的状态有可能为“0”(Q端为
0,Q^为1)加到场效应管栅极的信号为“1”,该场效应管就导通,对地呈现低阻抗,此时即使引脚上输入的信号为“1”,也会因端口的低阻抗而使信号变低,使得外加的“1”信号读入后不一定是“1”,若先执行置“1”操作,则可以使场效应管截止,引脚信号直接加到三态缓冲器中,实现正确的读入。
由于在输入操作时还必须附加一个准备动作,所以这类I/O口被称为“准双向”口,MCS-51的P0,P1,P2,P3口作为输入/输出口时都是“准双向”口。
接下来让我们再看另一个问题,从图中可以看出,这四个端口还有一个差别,除了P1口外,P0,P2,P3口都还有第二功能,这些第二功能又是作什么用的呢?下面我们就来讲解这个问题:
2.端口的工作原理 20 单片机之友 QQ:280919249 单片机教程 (MCS-51系列)
(1)
P0口 先来看P0口,从图中可以看到,P0口的内部有一个2选1的选择器,受内部信号的控制,如果 在图中的位置则处在I/O口工作方式,此时相当于一个“准双向口”,输入时须先将口置“1”,每根口 线可以独立定义为输入或输出,但是须在口线上加上拉电阻。
如果将开关往另一个方向,则就是另一个 功能—作为地址/数据复用总线用,此时不能逐位定义为输入/输出,它有两种用法:当作数据总线用时, 输入
8位数据;而当作地址总线用时,则输出8位地址。
再强调一点,当P0口作为地址/数据总线用之 后,就再也不能作I/O口使用了。
讲到这里,也许大家会感到困惑,什么叫作地址/数据复用?这其实 是当单片机的并行口不够用时,需要扩展输入输出口时的一种用法,具体如何使用,这就比较复杂了, 我们只能留到下册课程中再来给大家讲解,这里大家只要了解一下就可以了。
知道了
P0口,再来看P1 口。

(2)
P1口 同P0不同,P1口只能作为I/O口使用,但它的内部有一个上拉电阻,所以连接外围负载时不需 要外接上拉电阻,这一点P1,P2,P3都一样,务必请大家注意。

(3)
P2口 P2口作为I/O口线用时,与P0口一样,当内部开关向另一个方向时,即作地址输出时,可以输 出程序存储器或外部数据存储器的高8位地址,并与P0口输出的低地址一起构成16位的地址线,从而 可以分别寻址64K的程序存储器或外部数据存储器,同样地址线是8位一起自动输出的,不能象I/O 口线那样逐位定义。

(4)
P3口 P3口作为I/O口线用时,同P1口相同,也是“准双向口”;不同的是,P3口的每一位都有另
种功能,也叫第二功能,各位的功能如下,它们的具体作用我们用到时再详细解释。
端口位 第二功能 注释 P3.0 RXD 串行口输入 P3.1 TXD 串行口输出 P3.2 INTO 外部中断

0 P3.3 INT1 外部中断
1 P3.4 T0 计数器0计数输入 P3.5 T1 计数器1计数输入 P3.6 WR 外部RAM写入选通信号 P3.7 RD 外部RAM读出选通信号 讲到这里,也许您会问?既然单片机的引脚有第二功能,那么CPU是如何来区分的呢?这是一个 令许多初学者困惑的问题,几乎没有一本教科书提到过这个问题,其实单片机的第二功能是不需要人工 干预的,也就是说只要CPU执行到相应的指令,就自动转成了第二功能。
了解了各个I/O口的功能和作 用,再来给大家讲解一下单片机I/O与外围电路的连接方法。
这可是蛮重要的哦!
四.单片机I/O口的连接方法 当单片机的I/O口作输出时可以直接与外部设备连接,不过由于在实际的应用中,由于其驱动电 流是有限的(P0口10mA,P1,P2,P3口20mA),所以我们常常需要通过接口电路来扩展它的驱动能力, 在单片机的后向通道控制系统中,常用的功率控制器件有机械继电器、晶闸管、固态继电器等等,下面 我们将以机械继电器和固态继电器的应用为例介绍其具体的使用方法。

1.
单片机与机械继电器的接口 我们知道,单片机的一个I/O口只能灌入20mA的电流,所以往往不足以驱动一些功率开关(比如 稍大一点的机械继电器等),此时,就应该采用必要的扩展电路,如何来实现单片机与机械继电器的接 口呢?其实很简单,我们通常采用下面的接法(如图),为了防止前向通道信号的干扰,常采用一些光 电隔离器件,比如光电耦合器
4N25,PC814等,当单片机的P1.0脚输出为低电平时,光藕受电导通, Q1饱和开通,继电器吸合,负载电路接通。
这里请注意☺:P0-P3口作输出控制端时,应尽量采用低电 平控制方法,这是因为在低电平时,I/O口允许灌入的电流比高电平时要大,一般情况下,低电平的灌 21 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 入电流为高电平的4倍。
另外为了防止电压间的互相干扰,继电器的工作电压VDD与单片机的工作电压VCC不要使用同
个电源,接地端也不要连在一起,即所谓的模拟地与数字地分开,驱动管的电流要大于继电器的工作电 流,其他的元件就不讲了,大家自行分析一下。
讲了单片机与继电器的接口,再来介绍与固态继电器的 接口方法,接着往下看:
2.
单片机与固态继电器的接口 普通继电器由于开关速度慢、易跳火、易机械磨损,通常用于要求不高的场合,在某些特殊应用 场合,比如防火、防爆等系统中,则应采用固态继电器。
固态继电器是一种无触点的电子继电器,它的 输入端只要很小的控制电流,可以与单片机的
I/O口直接连接;输出则采用双向晶闸管控制,其输入输 出间均通过内部光电耦合器隔离,可以防止信号间的干扰,是单片机接口的理想器件,随着其技术的成 熟,应用的广泛,价格也已经非常的便宜,1A/250V
的目前在10元左右,它与单片机的连接方法如图 所示,当“-”端所接的P1.0为低电平时,SSR导通,负载工作。
除了以上两种连接方法外,单片机与TTL,CMOS管等都可以连接,具体的方法这里就不介绍了,大家可以自行找一下相关的资料。

五.本课总结 输入和输出口(简称I/O口)是单片机与外部电路接口的唯一途径,四个并行口的结构是有一定区别的,如何根据系统的设计要求和产品用途来正确、灵活地使用是初学者必须掌握的基本功,我们必须好好搞清楚它的功能和用途。

六.第6课习题
1.P0,P1,P2,P3口的驱动电流分别是多少?
2.什么是输入?什么是输出?
3.找本数字电路的书,了解一下D触发器的原理。
22 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第七课单片机的内部结构(五) 在上一课中,我们讲到了指令MOVP3,#0FFH能使P3口全部为高电平,而在第四课中LED灯闪烁程序中给R7送数用的指令是MOVR7,#250,那么这#250和#0FFH到底有什么不同?它们又代表什么意思呢?这一课就来讨论这个问题。
在讲解之前,让我们先来复习一下数字电路中学过的数制概念:
一.数制
1.十进制数(DecimalNumber)在日常生活中,我们表示数的多少用的是十进制数,即0,1,2,3,4,5,6,7,8,
9。
它遵循 “逢十进
一,借一当十”的原则,通常我们把计数符号的个数叫做基数,十进制的基数就是
十。
比如一个十进制数5847=5*1000+8*100+4*10+7*
1,它的每一个数码都有一个系数1000,100,10, 1;这个系数叫做权或位权。
十进制数虽然非常符合我们的使用习惯,但计算机中却无法采用,因为计算机只能有两种状态:“0”和“1”,所以我们还得应用二进制数。

2.二进制数(BinaryNumber)二进制的基数为二,0和
1,它遵循的是“逢二进
一,借一当二”的进借位原则。
也就是当某位 计数到两个数时就向高位进“1”,同时本位变为“0”。
比如二进制数1100=1*23+1*22+0*21+0*20,二进制数只有0和1两个数,正好代表了计算机中电路 的两种状态,所以它在计算机中被广泛应用。
下面是二进制的加法和乘法运算规则:加法:0+0=0;1+0=0+1=1;1+1=10乘法:0*0=0;1*0=0*1=0;1*1=1二进制数虽然在计算机中处理很方便,但当位数较多时,就不容易记忆和书写了,所以计算机中 又有了十六进制数。

3.十六进制数(HexadecimalNumber)十六进制也遵循两个规则,一是有十六个基数,即0,1,2,3,4,5,6,7,8,
9,A,
B,C,
D, E,F;另一个规则是“逢十六进
一,借一当十六”。
比如我们前面提到的#0FFH就是一个十六进制数,#--我们已经明白了,它表示的是传递数的本身, “H”叫数制简码,它表示这个数是十六进制数,为什么前面我在标题后面都加了英文注释,相信大家也应该明白了吧(这里随便提一下,二进制简码B和十进制简码D通常是可以省略的,我们以后的课程中用到的数都是这样写的),那么0FFH这个十六进制数的表示方法是怎么样的呢?用十进制表示0FFH=F*161+F*160,即等于255。
(大家也许会疑问?这里的“0”到哪里去了呢?原来,在单片机中,当我们用十六进制格式表示一个数时,如果高位的数字为“A-F”时,高位前面就得加上个“0”,不然,编译软件会出错,就象#0FFH。

二.进制之间的转换 十进制有使用比较习惯的特点,二进制有易于表示和运算方便的特点,十六进制又有表示位数较多的特点,但有时我们常常要把十进制数转换成二进制数或十六进制数来处理;把二进制数逆转换成十六进制数,如何进行这种转换呢?下面就举几个例子:
1.十进制数与非十进制数之间的转换
(1)非十进制数转换为十进制数具体做法是:将一个非十进制数按权展开成一个多项式,每项是该位数码与相应权值之积,把多项式按十进制的规则进行计算求和,所得的结果就是该数的十进制形式。
比如:二进制数1011B转换成十进制为1*23+0*22+1*21+1*20=8+2+1=11D,再比如:十六进制数FFH转换成十进制为255D。

(2)十进制数转换为非十进制数十进制数转换为非十进制数时,可将其分为整数部分和小数部分分别进行转换,最后将结果合并 23 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 为目的数。
为了简单,我这里只讲整数部分的转换。
这种转换叫做除基取余法,具体做法是用欲转换数 制的基数去除十进制数的整数部分,第一次除所得余数为目的数的最低位,把得到的商再除以该基数, 所得余数为目的数的次低位,依次类推,继续上面的过程,直至商位为

0,此时所得余数为目的数的最 高位。
比如:将十进制数53D转换成二进制数为53D=110101B。
2└53 2└26……
1 2└13……
0 2└6……
1 2└3……
0 2└1……
1 0……
1 2.二进制数与十六进制数之间的转换 四位二进制共有16种组合,而这16种组合正好与十六进制数的16个基数一致,所以每4位
进制数对应一位十六进制数,我们只要把二进制数的整数部分自右向左每4位一组,最后不足4位的用 0补足;小数部分自左向右每4位一组,最后不足4位的在右面补
0,再将每4位二进制数对应的十
进制数写出即可。
相反,如果将十六进制数转换为二进制数只需将每位十六进制数写成对应的4位二进 制数即可。
比如:将1101011B转换成十六进制数为D6H,再比如:将F0FH转换成二进制数为111100001111B。
十进制数012345678910111213141516 二进制数000000010010001101000101011001111000100110101011110011011110111110000 十六进制数0123456789ABCDEF10 上面的表格就是二进制数、十进制数和十六进制数之间的对应关系。

三.立即数的写法 通过前面一小节的讲解,我们已经懂了,MOVR7,#250和MOVR7,#OFFH中#250和#0FFH原来 是十进制数250D和十六进制数FFH的区别,在单片机中,通常我们把这个数称之为立即数,那么如果 我在编写指令时把立即数#0FFH写成二进制数(即11111111)或用十进制写法(255)是不是可以呢? 当然可以,立即数既可以是二进制数,也可以是十进制数或十六进制数。
不过有一点再重复一遍:那就 是当用十六进制格式表示一个立即数时,如果高位的数字为“A-F”时,高位前面要加上个“0”,请大 家务必记住了。
这里再讲一下,关于数制以及二进制、十进制和十六进制数的关系,大家可以在以后的实践中慢 慢去理解和掌握,如果您一时记不住,千万不要刻意地去死记硬背!下面让我们来讨论另一个问题: 24 单片机之友 QQ:280919249 单片机教程 (MCS-51
系列)
四.存储器的地址 什么是存储器的地址,地址和数据又有什么关系呢?这个问题往往让初学者非常的难以理解,既 然单片机存储器内存放的是数据,为什么还要有地址的概念?让我们从生活中的一个例子谈起:大家都 知道寄信是怎么回事吧!我们要寄一封信就必须写好信的内容,然后在信的封面写上详细地址,邮局才 能按地址把它寄出去;我们给单片机送数也一样,除了要给出立即数(犹如信的内容),还必须知道这 个数送达的地址(犹如信的地址或邮政编码),所以就必须给每个寄存器(即半导体存储器)都规定不 同的地址,只不过在单片机中地址的编码也是用数字来表示的,那么单片机中有多少个寄存器呢?它们 的地址又是如何规定的呢? 前面我们学过,单片机有两种存储器,即只读存储器
ROM和随机存储器RAM,它们都被规定了各 自的地址,我们把它称做寻址空间。
既然是空间,就必然有一个范围的概念,接下来就让我们看看MCS-51 单片机中程序存储器ROM的寻址范围:
1.内部R0M的寻址范围 89C51的内部有4K的FLASHROM空间,其寻址范围为000H-0FFH(16*16*16),这4K的ROM空 间就是用来存放我们为单片机编写的程序的,单片机执行指令时就是一条一条地顺序地从ROM中寻找指 令进行执行。
了解了ROM的寻址范围,让我们接着来看另一种存储器:内部RAM的寻址范围 单片机的内部RAM共有256个字节,寻址范围为00H-FFH(即16*16),它被分为两个部分:第
部分从00H-7FH共128个字节是真正的RAM区,可以用来读写各种数据,在这128个字节中,又分成
个区域:第一个区域00H-1FH安排了4组工作寄存器,每组用8个字节,共32个字节,分别为R0-R7, 当然在同一时刻,只能用其中的一组工作寄存器,怎么来控制它,就要用程序状态字PWS中的RS0、RS1 两位,(这我们后面再讲);第二个区域20H-2FH共16个字节除了可以作为一般的RAM单元读写外,还 可以对每个字节的每一位(即每一个抽屉中的每一个小盒子)进行操作,并且对这些位都规定了固定的 位地址:从20H单元的第0位开始到2FH单元的第7位结束共128位;第三个区域就是一般的RAM单元, 地址为30H-7FH,共80个字节;第二部分从80H-FFH是专门用于特殊功能寄存器(SFR)的,89C51共 用21个特殊功能寄存器(这些我们都将在下一课中讲解),它们每个也都有8位,这部分的128个字节 并没有全部用完。
为了加深印象,大家可以打开DBUG8051软件看一下它们的内部组成。

五.本课总结 本课主要讲述了数据与地址两个概念,其中第一部分的内容在学习数字电路时大家应该学过,我 这里把与单片机有关的内容再讲解一下,目的是希望各位能掌握这些知识,因为它对我们学习单片机是 非常有用的;地址也是单片机中一个非常重要的概念,在我们以后的学习中,大家会发现,每一个存储 器都与地址有关。

六.
7课习题
1.二进制、十进制、十六进制的规则分别是什么?
2.什么叫立即数?
3.单片机RAM的寻址空间为多少?它包括哪两个部分?
4.单片机ROM的寻址空间为多少?
5.把下面的立即数转换成二进制: 100;250;100H;4AH;FFH
6.把下面的立即数转换成十进制: 0001;0011;1111;A0H;FFH
7.把下面的立即数转换成十六进制: 100;255;;00111100;11110101 25 单片机之友 QQ:280919249 单片机教程 (MCS-51
系列) 第八课单片机的内部结构(六) 前面我们已经讲过,R7,R6是工作寄存器,P0,P1,P2,P3是并行口,那么单片机中还有些什 么东西?它们的结构又是怎么样的呢?这就是本课要讨论的问题。

一.单片机的特殊功能寄存器 看第三课的单片机内部结构图,在单片机中,除了前面介绍的RAM,ROM,P0-P3和CPU外,方框 内的还有许多其他的东西它们被称为特殊功能寄存器,英文简写SFR,下表例出的就是MCS-51单片机 中几个常用的特殊功能寄存器。
这一课我们先来介绍几个:
二.几个常用的特殊功能寄存器
1.累加器ACC 通常用A表示,它是一个什么东西呢?我们知道单片机在做运算时它的中间结果需要放在某个地 方,这个地方就是累加器,它的名字很特殊,功能也很特殊,几乎所有的运算类指令都离不开它。

2.寄存器
B B寄存器在做乘法时用来存放一个乘数,在做除法时用来存放一个除数,不做乘除法时随你怎么 用。

3.程序状态字PSW 它是一个很重要的东西,里面放了CPU工作时的很多状态,知道它就可以了解CPU当前的工作状 态,它有点象平时看书用的目录,我们浏览它就可以了解一本书的内容。
它是一个8位的寄存器,用到 了其中的7位。
其格式如下: D7 D6 D5 D4 D3 D2 D1 D0 CY AC F0 RS1 RS0 0V
P 下面来逐位介绍它的功能:
(1)CY:进位标志位 MCS-51
是一种8位的单片机,它的运算结果只能表示到28(即0-255),但我们有时候的运算结 果要超过255,怎么办呢?就要用CY位。
例如:79H+87H(01111001+01010111)=100000000,这里的 “1”就进到了CY中去了。

(2)AC:半进位标志位 当D3位向D4位进位/借位时,AC=
1,通常用于十进制调整运算中。

(3)F0:用户自定义标志位 由编程人员自行决定,什么时候用,什么时候不用。

(4)RS1、RS0:工作寄存器组选择位 RS1 RS0 工作寄存器组
0 0 0组(00H-07H)
0 1 1组(08H-0FH)
1 0 2组(10H-17H)
1 1 3组(18H-1FH) 前面讲到单片机共有四个工作寄存器组(0组-3组),它们就是由RS1,RS0来控制,这两位就在 这里,它共有四种组合状态,看上面的表格:每个工作寄存器组有8个字节,分别记为R0-R7,当然在 某一时刻,CPU只使用其中的一组。
假设PSW为“10”(即00010001),那么RS1=
1,RS0=
0,则用到了第2组寄存器组(地址10H-17H), RO-R7即为10H-17H,用DUBG8051软件输入数值,看看内部RAM中地址为10H-17H中的值是不是为输入 值。
(5)0V:溢出标志位 什么时候溢出,我们讲到定时器时再研究。
26 单片机之友 QQ:280919249 单片机教程 (MCS-51系列)
(6)P:奇偶检验位 每次运算结束后若A中二进制数“1”的个数为奇数,则P=
1,否则P=
0。
例:某运算结果是58H(01011000),显然“1”的个数为奇数,所以P=
1。

4.DPTR(DPH,DPL):数据指针 数据指针是一个16位的寄存器,我们可以用它来访问外部RAM,也可以访问外部ROM中的表格, 具体应用以后再讲。

5.SP:堆栈指针: 让我们先来理解一下堆栈是什么意思?你在家洗碗吗?我们洗好碗之后,是怎么放的呢?一般总 是先洗的放在下面,晚洗的放在上面,然后用的时候呢,总是晚放上去的先用,先放上去的后用;如果 你不洗碗不要紧,知道码头上仓库里堆的货物吗?一般也是先进去的后出来,而后进去的先出来,这种 符合“先进后出,后进先出”存放规则的现象我们就把它叫做“堆栈”。
(其实栈在中文中的意思就是码 头)。
在单片机中,我们可以在内部
RAM中构造出(注意☺:是可以构造)这样一个区域,这个区域存放数据的规则就符合堆栈中“先进后出,后进先出”的原则。
为什么要有这样一个区域呢?存储器本身 不也同样可以存放数据吗?是的,知道了存储器地址确实可以读出它里面的内容,但如果我们要读出的 是一批数据,每一个数据都要给出一个地址就会很麻烦,为了简化操作就可以利用堆栈的存放方法来读 取数据,具体的应用我们将在十五课中结合具体实验来讲,这里只是让大家先了解一下。
那么堆栈在单 片机的什么地方?也就是说把
RAM空间的哪一块区域作为堆栈呢?这就不好定了,因为51系列单片机 是一种通用的单片机,每个人的实际需要各不相同,有人需要多一些堆栈,而有人则不需要那么多堆栈, 所以INTEL公司就干脆不分了,把分的权利让给用户(编程者),也就是说我们可以根据自已的需要来 决定,所以单片机中堆栈的位置是可以变化的,而这种变化就体现在SP中值的变化,看下面的图,SP 中的值等于27H不就相当于是一个指针指向27H单元吗?这就是堆栈指针的由来。
31H 31H 30H 30H 29H 28H 27H ←SP 29H 28H 第一个数据 27H 26H 26H 25H 25H 24H 24H 当然在
MCS-51单片机中,☺:指针开始所指的位置并非就是数据存放的位置,而是数据存放的前 一个位置。
例如一开始堆栈指针是指向27H单元的,那么第一个数据的存放位置就在28H单元中,而不 是27H单元中,这一点请大家注意。

6.电源控制寄存器PCON 单片机在以电池供电的系统中,有时为了节电,我们需要让它尽量降低电源的消耗,所以单片机 就有多种的工作方式,其中一种就是低功耗方式,PCON寄存器就是用来控制单片机进入低功耗方式的, 有关这方面的知识我们将在下一课的课程中详细介绍。

三.本课总结 以上几个寄存器只是单片机中最常用的几个SFR,其他的特殊功能寄存器,我们将在具体应用时 再作详细的介绍。

四.第8课习题
1.累加器A的作用是什么?
2.什么是堆栈?堆栈存放数据的规则是什么?
3.单片机中有几组工作寄存器?它们的字节地址是什么?
4.简述PSW各位的作用。
27 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第九课单片机的工作方式 上一课中,我们提到了单片机的工作方式,单片机究竟有几种工作方式,它们又是如何工作的呢?这一课就来讨论这个问题。

一.单片机的工作方式 单片机共有复位、程序执行、低功耗和编程与加密四种工作方式,下面分别加以介绍。

1.复位方式
(1)为什么要复位 大家知道,单片机执行程序时总是从地址0000H开始的,所以在进入系统时必须对CPU进行复位,也叫初始化;另外由于程序运行中的错误或操作失误使系统处于死锁状态时,为了摆脱这种状态,也需要进行复位,就象电脑死机了要重新启动一样。

(2)复位的原理单片机复位的方法其实很简单,只要在RST引脚(9脚)上加一个持续时间为24个振荡周期(即两个机器周期)的高电平就可以了。
如果晶振为12M,计算一下这个持续脉冲需要多长时间?
(3)如何进行复位 复位操作有上电自动复位、按键复位和外部脉冲复位3种方法,它们的电路分别如下: 上电自动复位是通过外部复位电路的电容充电来实现的,看图
1,当电源刚接通时电容C对下拉电阻开始充电,由于电容两边的电压不能突变,所以RTS端维持高电平,只要这个充电时间不超过1ms,就可以实现对单片机的自动上电复位,即接通电源就完成了系统的初始化,在实际的工程应用中,如果没有特殊要求,一般都采用这种复位方式;按键复位的电路如图2所示,它其实就是在上电复位的基础上加了R2和SA,这种电路一般用在需要经常复位的系统中;外部脉冲复位的电路如图3所示,外部复位通常用于要求比较高的系统,比如希望系统死锁后能自动复位。
外部复位是由专门的集成电路来实现的,也就是我们通常俗称的“看门狗”电路,这种电路有很多,它们不但能完成对单片机的自动复位功能,而且还有管理电源、用作外部存储器等功能,比如X25045,MAX813L等等就是比较常用的此类芯片,关于这方面的内容我们将留到下册的教程中再来给大家详细讲解。
现在让我们先来看看单片机复位后,它的内部会有些什么变化呢?看下面的表: 28 单片机之友 QQ:280919249 单片机教程 (MCS-51
系列)
(4)复位后的状态 这就是单片机复位后内部系统的状态,上面的有些符号我们暂时还看不懂,不过没关系,等以后 学到了相关的知识后您自然就会明白了。

2.程序执行方式 寄存器
PCACCBPSWSP DPTRP0-P3TMODTCON TL0TH0TL1TH1SCONSBUFPCON 单片机的初始化状态 复位时的内容0000H00H00H00H07H0000HFFH XX0000B0X000000B 00H00H00H00H00H不定0XXX0000B 程序执行是单片机的基本工作方式,由于复位后PC=0000,所以程序就从地址0000H开始执行, 此时单片机就根据指令的要求完成一系列的操作控制,比如前面讲的让LED灯闪烁起来,不过在实际使 用中,程序并不会从0000H开始执行,而总是安排一条跳转指令,比如LJMPSTART,为什么要这样安 排,我们讲到中断时再来解释。

3.低功耗操作方式 在以电池供电的系统中,有时为了降低电池的功耗,在程序不运行时就要采用低功耗方式,低功 耗方式有两种—待机方式和掉电方式。
低功耗方式是由电源控制寄存器PCON(上一课我们提到过的)来控制的。
电源控制寄存器是一个 逐位定义的8位寄存器,其格式如下, MSB SB SMOD -- -- -- GF1 GF0 PD IDL 其中:SMOD为波特率倍增位,在串行通讯时用;GF1为通用标志位1;GF0为通用标志位0;PD 为掉电方式位,PD=
1,进入掉电方式;IDL为待机方式位,IDL=
1,进入待机方式。
也就是说只要执行 一条指令让PD位或IDL位为1就可以了。
那么单片机是如何进入或退出掉电工作方式和待机工作方式 的。
我们来介绍一下:
(1)待机方式 ①进入待机方式 当使用指令使PCON寄存器的IDL=
1,则进入待机工作方式。
此时CPU停止工作,但时钟信号仍提 供给RAM,定时器,中断系统和串行口;同时堆栈指针SP,程序计数器PC,程序状态字PSW,累加器 ACC以及全部的通用寄存器都被冻结起来;单片机的消耗电流从24mA降为3.7mA,这样就可以节省电源 的消耗。
②退出待机方式 退出待机方式可以采用引入中断的方法,在中断程序中安排一条RETI的指令就可以了,什么是 中断,我们现在还不知道,当然这没关系。
其实待机方式和我们使用电脑时的睡眠方式有异曲同工之妙。

(2)掉电方式 29 :0531-86213622 单片机之友 QQ:280919249 单片机教程 (MCS-51
系列) ①进入待机方式 当使用指令使PCON寄存器的PD=
1,则进入掉电工作方式,此时单片机的一切工作都停止,只有 内部RAM的数据被保持下来;掉电方式下电源可以降到2V,耗电仅50uA。
此时就相当于把显示器和硬 盘也关闭了。
②退出待机方式 退出掉电工作方式的唯一方法是复位,不过应在电源电压恢复到正常值后再进行复位,复位时间 要大于10mS,在进入掉电方式前,电源电压是不能降下来的,因此可靠的单片机电路最好要有电源检 测电路。
显然掉电方式和待机方式是两种不同的低功耗工作方式,前者可以在无外部事件触发时降低电 源的消耗,而后者则在程序停止运行时才使用。
关于单片机的低功耗的方式就简单的讲这些,更详细的内容也留到下册再讲解,因为那都是大虾 们的作品。

4.
编程和加密方式 单片机的编程与加密是由专门的设备来完成的,这种设备称为编程器或烧录器,类似的产品有很 多,功能也不尽相同,如果您有兴趣,我将在以后给您介绍一款51系列单片机编程器的自制方法。
这里给大家简单介绍一下单片机的加密,加密是为了保护编程者的劳动成果而设计的一种工作方 式,不过有矛必然有盾,现在的高手实在是很多,听说即使用OTP特种加密方式,也能解密,不过能加 密总比不加密的好,所以大家在选择编程器时应尽量采用具有加密功能的产品。

二.本课总结 这一课我们讲述了单片机的工作方式,对于初学者来说除了复位方式外,其他的只要稍微有点了 解就可以了。

三.第9课习题
1.单片机有几种工作方式?
2.为什么要进行复位?复位后的状态是什么?
3.如何对单片机进行复位?
4.找一套编程器的软件自己先熟悉一下。
30 :0531-86213622 单片机之友 QQ:280919249 单片机教程 (MCS-51
系列) 第十课单片机的寻址 这一课让我们来了解一下单片机的寻址方式,这对大家掌握指令会有很大的帮助,什么是单片机 的寻址?单片机有几种寻址方式?请往下看: 我们已经知道,单片机的工作过程就是一条一条地从
ROM存储器中取出指令然后执行相关的操作, 那么一条指令究竟有哪几部分组成?它又包括哪些内容?一般来说一条指令总是有操作码字段和操作 数字段两部分组成,看下面两条指令,MOVR7,#250;MOVP1,#0FFH,这是我们以前学过的指令,在 这两条指令中MOV就是操作码字段,R7和P1就是操作数地址字段,而#0FFH我们称为常数(也就是立即 数),单片机执行指令时就根据指令中给出的地址寻找实际的操作数,不能理解,没关系,继续往下看。

一.单片机的寻址 先来看下面的实验: 程序
程序
MAIN:SETBP1.0 ;(1) MAIN:SETBP1.0 ;
(1) MOV30H,#255; LCALLDELAY;(2) LCALLDELAY ;
(2) CLRP1.0 ;(3) CLRP1.0 ;(3) MOV30H,#200; LCALLDELAY;(4) LCALLDELAY ;(4) AJMPMAIN;(5) AJMPMAIN ;(5) DELAY:MOVR7,#250;(6) DELAY:MOVR7,30H;(6) D1:MOVR6,#250;(7) D1:MOVR6,#250;(7) D2:DJNZR6,D2;(8) D2:DJNZR6,D2;(8) DJNZR7,D1;(9) DJNZR7,D1;(9) RET ;(10) RET ;(10) END ;(11) END ;(11) 程序一就是我们以前做过的LED灯闪烁的实验,我们已经知道每次调用延时程序的时间都是相同 的(125mS),如果现在提出这样的要求:灯亮后延时时间为125mS灯灭,灯灭后又延时100mS秒灯亮, 如此循环,这样的程序还能满足要求吗?显然不能,怎么办?我们可以把它改成程序
二,也就是先把
个数送入30H,在子程序中R7中的值并不固定,而是根据30H单元中传过来的数来确定,这样就可以 满足要求,大家自行分析一下这个程序。
从这里我们可以得出结论,在数据传递中要找到被传递的数,很多时候,这个数并不能直接给出, 而是需要变化,这就引出了一个概念:如何寻找操作数,我们把寻找操作数所在单元地址的过程称之为 寻址。
在实验一中,我们直接使用数所在单元的地址找到了操作数,所以称之为直接寻址。
而在实验
中,我们是把数先放在工作寄存器中,从工作寄存器中寻找数据,这种方式则称之为寄存器寻址。
例如: MOV
R7,30H,就是把工作寄存器30H单元中的数送到R7中,这就是寄存器寻址。
接下来提一个问题:我们知道,工作寄存器就是内存单元的一部份,如果我们选择工作寄存器组
0,则R0就是RAM的00H单元,那么这样一来,MOVA,00H,和MOVA,R0不就没什么区别了吗?为 什么要加以区分呢?的确,这两条指令执行的结果是完全相同的,都是将00H单元中的内容送到A中去, 但是执行的过程不同,执行第1条指令需要2个周期;而执行第2条则只需要1个周期,第1条指令变 成最终的目标码要两个字节(E5H00H),而第2条则只要一个字节(E8h)就可以了。
也许有朋友会问,不就差了一个周期吗,为什么怎么斤斤计较!如果是12M晶振的话,也就1个 微秒,一个字节又能有多少呢?当然如果这条指令只执行一次,也许无所谓,但一条指令如果执行上 1000次,就是1毫秒,如果要执行1000000次,就是1S的差别,这就很可观了,单片机要做的就是实 时控制,所以必须如此“斤斤计较”。
再来看另一个问题,现在我们已经知道,寻找操作数可以通过直接给的方式(立即寻址)和直接 31 单片机教程 (MCS-51
系列) 给出数所在单元地址的方式(直接寻址),这就够了吗?看下面的问题,要求从30H单元开始,取20 个数,分别送入累加器A中。
就我们目前掌握的办法,要从30H单元取数,就用MOVA,30H,那么下 一个数呢?是31H单元的,怎么取呢?还是只能用MOVA,31H,那么20个数,不是得20条指令才能 写完吗?这里只有20个数,如果要送200个或2000个数,那岂不要写上200条或2000条命令?
这未免 太笨了吧。
为什么会出现这样的状况?因为我们只会把地址写在指令中,所以就没办法了,如果我们不 是把地址直接写在指令中,而是把地址放在另外一个寄存器单元中,根据这个寄存器单元中的数值决定 该到哪个单元中取数。
比如,当前这个寄存器中的值是
30H,那么就到30H单元中去取,如果是31H就 到31H单元中去取,就可以解决这个问题了。
怎么个解决法呢?既然看的是寄存器中的值,那么我们就 可以通过一定的方法让这里面的值发生变化,比如取完一个数后,将这个寄存器单元中的值加
1,还是 执行同一条指令,可是取数的对象却不一样了。
看下面的例子: MOVR7,#20;
(1) MOVR0,#30H;
(2) LOOP:MOVA,@R0;
(3) INCR0 ;
(4) DJNZR7,LOOP;
(5) 这个例子中的大部份指令我们是能看懂的,第1条,是将立即数20送到R7中,执行完后R7中 的值应当是20;第2条是将立即数30H送入R0工作寄存器中,所以执行完后,R0单元中的值是30H; 第3条,是看一下R0单元中是什么值,把这个值作为地址,取这个地址单元的内容送入A中,此时, 执行这条指令的结果就相当于执行MOVA,30H;第4条,没学过,就是把R0中的值加
1,因此执行完 后,R0中的值就是31H了;第5条,学过,将R7中的值减
1,看是否等于“0”,不等于“0”,则转到 标号LOOP处继续执行,因此,执行完这句后,将转去执行MOVA,@R0这一条,此时相当于执行了MOV A,31H(因为此时的R0中的值已是31H了);如此,直到R7中的值逐次相减等于“0”,也就是循环20 次为止,就实现了我们的要求:从30H单元开始将20个数据送入A中。
这是另一种寻找数据的方法, 由于数据是间接被找到的,所以把这种寻址方式称之为寄存器间址寻址。
(注意☺,在间址寻址中,只能用R0或R1来存放等待寻找的数据)。
除了以上几种寻址方法外,单片机还有变址寻址,相对寻址和位寻址共七种寻址方式。
这些您暂 时可以不去深究它,我们以后会结合具体的实验再来详细介绍,这里只是为了归类,所以才把它们例举 在一起。

二.寻址方式举例
1.直接寻址 直接寻址时,指令中的地址码部分直接给出了操作数的有效地址。
例如:MOV
A,4FH ;A←(4FH) 可用于直接寻址的空间有内部RAM的低128字节(包括其中的位寻址区与特殊功能寄存器)。

2.寄存器直接寻址 寄存器寻址时,指令中地址码给出的是某一通用寄存器的编号,寄存器的内容为操作数。
例如:MOVA,R7 ;A←(R7) 可用于寄存器寻址的空间有R0-R7,ACC,CY(位),DPTR,
B。

3.寄存器间接寻址 寄存器间接寻址时,指令中给出的寄存器的内容为操作数的地址,而不是操作数本身。
例如:MOVA,@R0 ;A←[(R1)] 可用于寄存器间接寻址的空间只能是R0和R1,用DPTR或PC可间接寻址64K字节外部的RAM或 ROM.
4.立即寻址 立即寻址时,指令中地址码部分给出的就是操作数本身。
例如:MOVA,#0FFH ;A←0FFH 32 单片机教程 (MCS-51系列) 可用于立即寻址的空间有
5.变址寻址 变址寻址时,指定变址寄存器的内容与指令中给出的偏移量相加DPTR所得的结果作为操作数的 地址。
例如:MOVCA,@A+DPTR;A←[(A)+(DPTR)]。
无论用DPTR或PC作为基准指针,变址寻址只适用于程序存储器(即ROM),通常用于读取数据表。

6.相对寻址 相对寻址时,由程序计数器PC提供的基准地址与指令中提供的偏移量rel相加,得到操作数的 地址。
例如:SJMPrel ;PC←(PC)+2+rel
7.位寻址 位寻址时,操作数是二进制数的某一位,其位地址出现在指令中。
例如:SETBbit ;(bit)←
1 可用于位寻址的空间有内部RAM的可位寻址区和SFR(特殊功能寄存器)中的字节地址可以被
8 整除(即地址以0、
8、F结尾)的寄存器空间。

三.本课总结 这一课主要讲述了单片机的寻址方式,寻址是单片机中一个非常重要的概念,单片机执行指令实 际上就是到不同的地址空间寻找操作数的过程,请大家务必搞清寻址的概念和寻址的方法。
到本课为止,我们已经连续讲了很多单片机的基本概念,可能有些朋友会觉得很难,我这里可以 告诉大家,如果您有这种感觉,那绝对是好事,因为学习使用单片机本来就不是一朝一夕的事,需要长 期的结累和实践,只有持之以恒,才能取得最后的胜利!其实世上很多事都是如此。
不过话又说回来,当碰到一时无法理解的概念和知识时,如何来搞懂它呢?对于单片机学习来说, 我可以给大家介绍一个简单的好方法:那就是先放着再说,继续往下学,等学会了后面的概念时你会突 然发现有很多原来的不懂的东西会变得非常的简单。
试试看,不要停留,继续往下看!
四.
第10课习题
1.什么是单片机的寻址?单片机有几种寻址方式?
2.单片机的指令有几部分组成?
3.直接寻址和间接寻址的区别在哪里?
4.写一段从0AH单元开始,把20个数送入A中的程序。
33 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第十一课单片机的指令(一) 指令就是编程者给单片机下的命令,也就是我们平常所说的单片机软件,前面我们已经陆续地讲到了一些指令,但还远远不够,从这一课开始就要全面的讲解指令了,希望大家多动手实验,巩固所学的知识,说实在的,其实单片机并不难学。
为了让大家比较容易记忆,按照常规分类,我把单片机的111条指令分成了五类—即数据传递类指令、算术运算类指令、逻辑运算类指令、控制转移类指令和位操作指令。
这一课先来看数据传递类指令:
一.数据传递类指令 数据传递类指令是单片机中用的最多的指令,在51系列单片机的111条指令中共有28条是数据传递类指令,前面我们已经学到了几条,比如MOVR1,#250;MOVA,R6等,那么它们是怎么分类的呢?请往下看:
1.以累加器为目的操作数的指令
(1)MOVA,Rn
(2)MOVRn,A
(3)MOVA,direct
(4)MOVA,@Ri
(5)MOVA,#data 指令
(1)把Rn中的数送入累加器
A,Rn代表工作寄存器R0-R7(以后我们只要写到Rn都代表R0-R7,这一点请大家记住了);指令
(2)则相反,把工作寄存器中的数送入累加器A中;指令
(3)是把直接地址中的数送入累加器A中,driect就代表直接地址(以后也相同);而指令
(4)就是上一课我们讲的寄存器间接寻址,什么意思?这里再重复一遍,就是看一下工作寄存器中是什么值,把这个值作为地址,把这个地址中的数送入累加器A中,Ri代表什么意思呢?就是工作寄存器R0或者R1(以后如果写Ri都代表R0或R1);第
(5)条指令就是把立即数(也叫常数)直接送入累加器A中,很显然data就代表立即数(以后也相同),其实这个我们以前提到过,加#的数就代表送入的是这个数的本身。
接下来举几个实例加以说明,大家可以用DUBG8051这个软件验证一下:
A.MOVR7,#250;MOVA,R7;将工作寄存器R7中的值250送入
A,R7中的值保持不变。

B.MOVA,#250;MOVR7,A;将A中的值250送入工作寄存器R7,A中的值保持不变。

C.MOV30H,#250;MOVA,30H;将内存30H单元中的值250送入A,30H单元中的值保持不变。

D.MOV20H,#250;MOVR0,#20;MOVA,@R0;先看R0中是什么值,把这个值作为地址,并将这个地址单元中的值送入A中。
执行命令前R0中的值为20H,则是将20H单元中的值250送入A中。

E.MOVA,#250;将立即数250送入A中,执行完本条指令后,A中的值是250。

2.以寄存器Rn为目的操作数的指令
(1)MOVRn,A
(2)MOVRn,direct
(3)MOVRn,#data 举几个实例大家自行分析一下:
A.MOVR7,A;
B.MOVR7,30H;
C.MOVR7,#20; 这组指令功能是把源地址单元中的内容送入工作寄存器,源操作数不变。

3.以直接地址为目的操作数的指令 34 单片机教程 (MCS-51系列)
(1)MOVdirect,
A 例如:MOV30H,A(将累加器A中的数送入内存单元30H)
(2)MOVdirect,Rn 例如:MOV30H,R7(将寄存器R7中的数送入内存单元30H)
(3)MOVdirect,direct 例如:MOV30H,20H(将内存单元20H中的数送入内存单元30H)
(4)MOVdirect,@Ri 例如:MOV30H,@R0(看一下R0中是什么值,把这个值作为地址,并将这个地址单元中的值送 入A中。
如执行指令前R0中的值为20H,则是将20H单元中的值送入A中)。

(5)MOVdirect,#data 例如:MOV30H,#20(将立即数20送入内存单元30H)
4.以间接地址为目的操作数的指令
(1)MOV@Ri,
A
(2)MOV@Ri,direct
(3)MOV@Ri,#data16 这三条指令就不介绍了,大家自行分析一下,不过有一点希望大家记住,Ri只能用工作寄存器R0或 者R1。

5.十六位数的传递指令 MOVDPTR,#data16 指令说明:这是51单片机中唯一的一条16位立即数传递指令,大家知道51系列单片机是一种8位单片机,8位单片机所能表示的最大数只能是28=0-255。
讲到这里大家应该明白了,为什么我们前面 的实验中立即数不能大于255。
如果现在有个数是1234H(即二进制0001001000110100),我们要把 它送入DPTR,该怎么办呢?当然有办法,INTEL公司已经把DPTR分成了两个寄存器,DPH和DPL(看
下前面的特殊功能寄存器介绍),我们只要把12H(高8位)送入DPH,把34H(低8位)送入DPL中去就可 以了,所以执行指令MOVDPTR,#1234H和执行指令MOVDPH,#12H
(1);MOVDPL,#34H
(2);是 一样的。

二.指令练习 请写出下列每条指令的执行结果,并用DUBG8051软件进行验证,看结果是否正确。

1.MOV12H,#34H
2.MOVR0,#23H
3.MOVR7,#22H
4.MOVR1,12H
5.MOVA,@R0
6.MOV34H,@R1
7.MOV45H,34H
8.MOV12H,DPH
9.MOVR0,DPL
三.本课总结 本课主要讲述了以累加器为目的操作数的指令,以寄存器为目的操作数的指令,以直接地址为目 的操作数的指令,以间接地址为目的操作数的指令和一个十六位数的数据传递类指令,这些指令有的我 们前面已经学到过,希望大家用
DUBG8051软件多练习,以加强对数据及指令的认识。

四.第11课习题
1.Rn,Ri,direct,data分别代表什么?举例说明。

2.地址30H和数据30H有什么区别?
3.DPTR是什么?#data16代表什么? 35 单片机教程 (MCS-51系列) 第十二课单片机的指令(二) 接着上一课的数据传递类指令,这一课继续讲解其他的数据类指令。
提示:下面的内容我们下册中才会用到,这里只是为了把数据传递类指令讲完,才提前把它们讲一下,您不知道也没关系。

一.数据传递类指令
6.累加器A与片外RAM之间的数据传递类指令什么是片外RAM(即片外数据存储器)呢?单片机不是有内部RAM吗?为什么还要片外RAM呢? 难道单片机的内部RAM还不够用吗?的确如此,当单片机的内部RAM不够时,我们就要扩充RAM空间。
那么单片机能扩充多少的外部RAM空间呢?89C51单片机的片外RAM可以扩展到64K,即从0000H-FFFFH,那么它是怎样和累加器A进行数据传递的?它们之间的传递指令共有以下四条:
(1)MOVXA,@Ri
(2)MOVX@Ri,A
(3)MOVXA,@DPTR
(4)MOVX@DPTR,
A 指令说明:
A.在51系列单片机中,与外部存储器RAM传递数据的只可以是累加器
A,所有要送入或读出外部RAM的数据必须先送到A中去,在此我们可以看出内外部RAM的区别了:内部RAM间可以直接进行数据的传递,而外部RAM则不行。
比如,要将外部RAM中某一单元(设为100H单元的数据)送入另一个单元(设为200H单元),就必须先将100H单元中的内容读入
A,然后再送到200H单元中去。
在这里有一个问题:CPU是如何区分内、外部RAM的?大家看这里的四条指令,其操作码都是MOVX,而内部RAM的操作码则是MOV,CPU就是根据不同的指令来自动区分读写内、外部RAM的。

B.要读出或写入外部的RAM,当然还必须知道外部RAM的地址,在后两条指令中,地址是被直接放在DPTR中的;而前两条指令由于Ri(即R0或R1)只是一个8位的寄存器,所以只能提供低8位的地址。
不过有时我们要扩展的外部RAM数量比较少(少于或等于256个字节),提供低8位的地址也就足够了。

C.使用时应当首先将要读出或写入的地址送入DPTR或Ri中,然后再用读写指令。
举例:将外部RAM中100H单元中的内容送入外部RAM中200H单元中。
MOVDPTR,#0100HMOVXA,@DPTRMOVDPTR,#0200HMOVX@DPTR,A7.累加器A与片外ROM之间的数据传递类指令MOVCA,A+@DPTR前一小节讲了累加器A与外部RAM之间的数据传递类指令,接下来再来讲讲片外ROM与累加器A之间的数据传递类指令。
在讲解之前,先来了解一下内部ROM和外部ROM的组成,89C51的内部有4K的FLASHROM空间,其地址为000H-FFFH,片外可以扩展到64K(OOOOH-FFFFH),在这64K的ROM空间中,有4K字节的地址是片内和片外公用的(即000H-FFFH),而1000H-FFFFH的空间是片外ROM专用的。
讲到这里大家就会问:既然有4K的地址是公用的,那么CPU是如何区分的呢?不知大家是否还记得,在第二讲单片机的硬件电路中,有一个引脚EA(即31脚),当EA=
1,CPU从片内ROM的4K字节中取指令,如果地址超过了4K(FFFH),单片机就自动转向片外ROM取指令,大家注意☺:这个过程是自动完成的,不需要人工干预;而当EA=0时,CPU只从片外ROM取指令。
讲到这里,不知大家注意☺没有,当使用外部ROM和外部RAM时,它们的寻址空间都是0000H-FFFFH,也就是说它们在地址上是重叠的,那么CPU在读取指令时又是如何来区分当前是从ROM取指令还是从 36 单片机教程 (MCS-51系列) RAM取指令呢?请大家来看第二课的89C51单片机硬件电路图,29脚是PSEN,当我们置位PSEN时(即 PSEN=1),CPU就读取外部ROM指令;而要从外部RAM读取指令时就置位WR(即16脚)或RD(即17脚), 这样即使ROM地址和RAM地址是重叠的,也不会出现混乱。
这里又有一个问题了,16脚和17脚不是并 行口P3.6和P3.7吗?如果我们把它当作第二功能WR和RD来使用,CPU又是如何来区分的呢?这个问 题我们前面已经讲过了,这里再重复一遍:单片机引脚的第二功能是不需要人工干预的,也就是说只要 CPU执行到相应的指令,就自动转成了第二功能。
了解了片外ROM的读取指令原理,再来看片外ROM与 累加器A之间的数据传递指令(注意☺:ROM只能读取指令,而不能写入数据,这一点和RAM是不同的)。
MOVCA,A+@DPTR 指令说明:
A.本指令是将ROM中的数送入A中。
通常称其为查表指令,常用此指令来查一个已做好在ROM中 的表格。

B.此条指令引出一个新的寻址方法:变址寻址。
本指令是要在ROM的一个地址单元中找出数据, 显然必须知道这个单元的地址,这个单元的地址是这样确定的:在执行本指令前DPTR中有
个数,A中也有一个数,执行指令时,将A和DPTR中的数加起来,就成为要查找的数的单元地 址。

C.查找到的结果被放在A中,因此,本条指令执行前后,A中的值不一定相同。
举例:有一个数在R0中,要求用查表的方法确定它的平方值(此数取值范围是0-5) MOVDPTR,#TAB MOVA,R0 MOVCA,@A+DPTR . . TAB:DB0,1,4,9,16,25 设R0中的值为“2”,送入A中,而DPTR中的值则为“TAB”,则最终确定的ROM单元的地址就是 “TAB+2”,也就是到“TAB+2”这个单元中去取数,取到的是“4”(Db后面的第三个数)。
其它数据也 可以次类推。
从这里可以看出,我们使用了标号(象TAB等)来代替具体的ROM单元地址,事实上,标号的真实含义就是地址的数值,在这里它就代表了TAB+
0,TAB+
1,……TAB+25这几个数据在ROM中的存放位置;而我们以前学过的如LCALLDELAY指令,DELAY代表的是以DELAY为标号的那段程序在ROM中存放的起始地址,CPU就是根据这个起始地址才找到指令的,无法理解是吗?没关系,让我们先来看几个符号的含义就会明白了。

二.单片机的伪指令 (注意☺:伪指令不是单片机指令)我们前面简单提到过,END是伪指令,那么到底什么是伪指令?它在单片机中有什么作用呢?接下来我们就来讨论这个问题,伪指令是单片机中用来给寄存器定义 或者赋值的特殊指令为什么要用伪指令呢?让我们来看下面的实验:
1.DB—定义字节伪指令
它的功能是从程序存储器ROM单元的某个地址开始,存入一组规定好的8位二进制常数。
例如:ORG2000H; TAB:DB45H,48H,10;34H;以上指令经汇编后,将对从2000H开始的若干ROM单元赋值,即(2000H)=45H,(2001H)=48H,(2002H)=0AH,(2003H)=34H。
讲到这里,有的人会问:在这些指令中,我直接用MOV2000H,45H;MOV2001H,48H……不就得了,干吗要用DB指令呢?是的,从理论上讲,两者的效果是一样的,只是因为我们现在的程序都很短,单片机不可能只做这些简单的工作,当程序比较长时,这些指 令的意义就不一样了。
除了刚刚提到的END和DB伪指令外,单片机中还有那些伪指令呢?下面简单讲解一下:
2.DW—定义字伪指令 37 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 在计算机中,一个字由两个字节组成,也就是说,如果一个字节可以表示一个8位数的话,那么一个字就可以表示一个十六位的数(关于这方面的问题我们留到下册中再来讨论,这里就不讲了,以免 增加大家的学习难度),如此一来,这条伪指令的功能也就清楚了,就是从指定的ROM单元开始,定义若干个16位常数;上一课我们已经讲过,51系列单片机要存放一个16位的常数就必须把这个数分成两个8位数据来存放,通常我们把一个16位数的高8位放入低地址,而把低8位放入高地址(注意☺:这两个地址必须是紧挨着的)。
例如:ORG3000H;ABC:DW2345H,0A859H; 程序经汇编后,(3000H)=23H,(3001H)=45H,(3002H)=A8,(3003H)=59H。
注意☺:象0A859H这样的数值在写法上,A的前面一定要加上个
0。

3.DS—保留空间伪指令它的功能是从指定的地址开始,保留若干个字节的ROM空间留作它用。
例如:ORG2000H; ABC:DS08H;LOOP:MOVA,30H;汇编以后,从2000H开始,将保留8个ROM单元留作它用,那么以LOOP为标号的指令就存放在2008H单元中。
这里有一点请大家注意☺:这几条伪指令都只能对程序存储器(ROM)起作用,而不能用它们来对数据存储器(RAM)进行赋值或做其他的工作。
至于它们到底有什么作用,我们什么时候才需要用到它们?我们将在下册的实验中再作讲解。
现在让我们通过一段程序来解释一下查表程序 的使用方法,这可是一定要学会的。
例如:MOVDPTR,#100H; MOVA,R0 ; MOVCA,@A+DPTR; . . ORG0100H ; DB0,1,4,9,16,25; 如果R0中的值为“2”,则最终地址为“100H+2”即“102H”,到102H单元中找到的是“4”。
这 个可以看懂了吧,那为什么不这样写程序,要用标号呢?不是增加疑惑吗?如果用标号写的话,在写程 序时,就必须确定这张表格在ROM中的具体位置。
如果写完程序后,又想在这段程序前插入一段程序, 那么这张表格的位置就又要变了(要改ORG100H这条指令),如果我们是经常需要修改程序的,那多 麻烦,所以就用标号来替代,只要一编译程序,位置就自动发生变化,我们把这件事交给计算机去做了。

8.堆栈的操作指令 什么是堆栈,我们前面已经介绍过了,那么堆栈是如何进行数据传递的呢?对堆栈的操作指 令有
2条:
(1)PUSHdirect
(2)POPdirect 第1条指令称之为推入,就是将direct中的内容送入到堆栈中;第2条指令称之为弹出,就是 将堆栈中的内容送回到direct中。
推入指令的执行过程是:首先将SP中的值加
1,然后把SP中的值 当作地址,将direct中的值送进以SP中的值为地址的RAM单元中。
例如:MOVSP,#5FH; MOVA,#100; MOVB,#20; PUSHACC ; PUSHB ; 38 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 这段指令的执行过程是这样的:将SP中的值加
1,即变为60H,然后将A中的值(#100)送到60H 单元中,因此执行完PUSHACC这条指令后,内存60H单元的值就是100,同样,执行PUSHB时,是 将SP+
1,即变为61H,然后将B中的值送入到61H单元中,即执行完本条指令后,61H单元中的值变为 20。
这是推入,那么弹出又是怎么样的呢?请看下面的例子: MOVSP,#5FH; MOVA,#100; MOVB,#20; PUSHACC ; PUSHB ; POPB ; POPACC ; POP指令的执行是这样的:首先将SP中的值作为地址,并将此地址中的数送到POP指令后面的那 个direct中,然后SP减
1。
上面程序的执行过程是:将SP中的值(现在是61H)作为地址,取61H 单元中的数值(现在是20),送到B中,所以执行完POPB指令后B中的值是20,然后将SP减
1,那 么此时SP的值就变为60H,然后执行POPACC,将SP中的值(60H)作为地址,从该地址中取数(现 在是100),并送到ACC中,所以执行完本条指令后,ACC中的值是100。
这有什么意义呢?ACC中的值本来就是100,B中的值本来就是20,是的,在本例中,的确没有 意义,但在实际工作中,推入堆栈结束后(即执行指令PUSHB后)往往要执行其他的指令,而且这些 指令会把A中的值和B中的值改掉,所以在程序执行结束后,如果我们要把A和B中的值恢复原值,那 么这些指令就有意义了,具体应用我们将在以后的课程中讲到。
这里还有一个问题,如果不用堆栈,比 如说在PUSHACC指令处用MOV60H,
A,在PUSHB处用指令MOV61H,
B,然后用MOVA,60H, MOVB,61H来替代两条POP指令,不也一样吗?是的,从结果上看是一样的,但是从过程看是不一样 的,PUSH和POP指令都是单字节,单周期指令,而MOV指令则是双字节,双周期指令。
更何况,堆栈 的作用不止于此,所以一般的单片机上都设有堆栈,而我们在编写子程序,需要保存数据时,通常也采 用堆栈的方法来实现。

9.其他的数据传递类指令
(1)XCH

A,Rn
(2)XCHA,direct
(3)XCHA,@Ri
(4)XCHDA,@Ri
(5)MOVCA,A+PC 前面的4条指令是进行数据交换用的,第1条,寄存器与累加器交换;第2条直接地址与累加器 交换;第3条间接RAM与累加器交换;第4条间接RAM与累加器的低4位交换;第5条是累加器与代码 字节之间的数据传递类指令,这些指令作为初学者可能暂时还用不上,所以就不介绍了,大家只要了解 一下就可以了,等下册中我们再来详细的讨论。

三.本课总结 到本课为止,数据传递类指令全部讲解完了,在单片机的指令中,数据传递类指令是使用最多的 指令,因此这部分的内容是必须掌握的,如何来使用这些指令,我们将在以后的课程中结合具体的实验 加以介绍。
为了加深印象,大家可以用
DUBG8051软件对上述指令进行反复练习,用实验结果来加深课 堂知识。

四.第12课习题
1.单片机是如何区分片外RAM和片外ROM的?又是如何区分片外ROM和片内ROM的?
2.简述推入堆栈和弹出堆栈的操作过程。
39 单片机之友 QQ:280919249 单片机教程 (MCS-51系列) 第十三课单片机的指令(三) 算术、逻辑运算类指令也是单片机中极为重要的指令系统,在很多教科书中都把它们归为一类,实际上它们还是有区别的,为了让大家便于记忆,这里把它们分了开来。
在单片机中,算术运算类指令有24条;逻辑运算类指令有25条。
这一课我们先来讲解算术运算类指令,下面我们分别加以讲解:
一.算术运算类指令
1。
不带进位的加法指令
(1)ADDA,Rn;例:ADDA,R7
(2)ADDA,@Ri;例:ADDA,@R1
(3)ADDA,direct;例:ADDA,30H
(4)ADDA,#data;例:ADDA,#30H 指令说明:这些指令的意思就是把后面的值与A中的值相加,结果送到A中去。
举例:MOVA,30H; ADDA,10H;执行结果A=40H2。
带进位的加法指令
(1)ADDCA,Rn;例:ADDCA,R7
(2)ADDCA,@Ri;例:ADDCA,@R1
(3)ADDCA,direct;例:ADDCA,30H
(4)ADDCA,#data;例:ADDCA,#30H指令说明:这些指令的作用都是将A中的值和其后面的值相加,并且加上进位位CY中的值。
为什么要这样做呢?我们知道51单片机是一种8位单片机,所以只能做8位的数学运算,也就是说最大运算的范围只能是0-255,这在实际工作中是不够的,因此就要进行扩展,怎么扩展,就是将2个8位的数学运算合起来,成为一个16位的运算,这样可以表达的数的范围就能达到0-65535。
如何合并呢?其实很简单,让我们看一个十进制数的加法例子:66+78,这两个数相加,我们根本不会在意它的过程,但事实上我们是这样做的:先做6+8(低位),然后再做6+
7,这是高位。
做了两次加法,只是我们做的时候并没有刻意分成两次加法来做罢了,或者说我们并没有意识到我们做了两次加法,之所以要分成两次来做,是因为这两个数超过了一位数所能表达的范置(0-9)。
在做低位时产生了进位,我们通常的办法是在适当的位置点一下,然后在做高位加法时将这

标签: #cpu #变速箱 #吃了 #优缺点 #ios14.3怎么样 #质量 #本田 #cpb