单片机程序设计Word文档下载推荐.docx
《单片机程序设计Word文档下载推荐.docx》由会员分享,可在线阅读,更多相关《单片机程序设计Word文档下载推荐.docx(31页珍藏版)》请在冰豆网上搜索。
13、双数据指针;
14、掉电标识符。
引脚说明:
AT89S52引脚图DIP封装
P0口:
P0口是一个8位漏极开路的双向I/O口。
作为输出口,每位能驱动8个TTL逻辑电平。
对P0端口写“1”时,引脚用作高阻抗输入。
当访问外部程序和数据存储器时,P0口也被作为低8位地址/数据复用。
在这种模式下,P0不具有内部上拉电阻。
在flash编程时,P0口也用来接收指令字节;
在程序校验时,输出指令字节。
程序校验时,需要外部上拉电阻。
P1口:
P1口是一个具有内部上拉电阻的8位双向I/O口,p1输出缓冲器能驱动4个TTL逻辑电平。
对P1端口写“1”时,内部上拉电阻把端口拉高,此时可以作为输入口使用。
作为输入使用时,被外部拉低的引脚由于内部电阻的原因,将输出电流(IIL)。
此外,P1.0和P1.1分别作定时器/计数器2的外部计数输入(P1.0/T2)和定时器/计数器2的触发输入(P1.1/T2EX)。
在flash编程和校验时,P1口接收低8位地址字节。
引脚号第二功能:
P1.0T2(定时器/计数器T2的外部计数输入),时钟输出
P1.1T2EX(定时器/计数器T2的捕捉/重载触发信号和方向控制)
P1.5MOSI(在系统编程用)
P1.6MISO(在系统编程用)
P1.7SCK(在系统编程用)
P2口:
P2口是一个具有内部上拉电阻的8位双向I/O口,P2输出缓冲器能驱动4个TTL逻辑电平。
对P2端口写“1”时,内部上拉电阻把端口拉高,此时可以作为输入口使用。
在访问外部程序存储器或用16位地址读取外部数据存储器(例如执行MOVX@DPTR)时,P2口送出高八位地址。
在这种应用中,P2口使用很强的内部上拉发送1。
在使用8位地址(如MOVX@RI)访问外部数据存储器时,P2口输出P2锁存器的内容。
在flash编程和校验时,P2口也接收高8位地址字节和一些控制信号。
P3口:
P3口是一个具有内部上拉电阻的8位双向I/O口,p3输出缓冲器能驱动4个TTL逻辑电平。
对P3端口写“1”时,内部上拉电阻把端口拉高,此时可以作为输入口使用。
P3口亦作为AT89S52特殊功能(第二功能)使用,如下表所示。
在flash编程和校验时,P3口也接收一些控制信号。
端口引脚第二功能:
P3.0RXD(串行输入口)
P3.1TXD(串行输出口)
P3.2INTO(外中断0)
P3.3INT1(外中断1)
P3.4TO(定时/计数器0)
P3.5T1(定时/计数器1)
P3.6WR(外部数据存储器写选通)
P3.7RD(外部数据存储器读选通)
此外,P3口还接收一些用于FLASH闪存编程和程序校验的控制信号。
RST:
复位输入。
当振荡器工作时,RST引脚出现两个机器周期以上高电平将是单片机复位。
ALE/PROG:
当访问外部程序存储器或数据存储器时,ALE(地址锁存允许)输出脉冲用于锁存地址的低8位字节。
一般情况下,ALE仍以时钟振荡频率的1/6输出固定的脉冲信号,因此它可对外输出时钟或用于定时目的。
要注意的是:
每当访问外部数据存储器时将跳过一个ALE脉冲。
对FLASH存储器编程期间,该引脚还用于输入编程脉冲(PROG)。
如有必要,可通过对特殊功能寄存器(SFR)区中的8EH单元的D0位置位,可禁止ALE操作。
该位置位后,只有一条MOVX和MOVC指令才能将ALE激活。
此外,该引脚会被微弱拉高,单片机执行外部程序时,应设置ALE禁止位无效。
PSEN:
程序储存允许(PSEN)输出是外部程序存储器的读选通信号,当AT89S52由外部程序存储器取指令(或数据)时,每个机器周期两次PSEN有效,即输出两个脉冲,在此期间,当访问外部数据存储器,将跳过两次PSEN信号。
EA/VPP:
外部访问允许,欲使CPU仅访问外部程序存储器(地址为0000H-FFFFH),EA端必须保持低电平(接地)。
需注意的是:
如果加密位LB1被编程,复位时内部会锁存EA端状态。
如EA端为高电平(接Vcc端),CPU则执行内部程序存储器的指令。
FLASH存储器编程时,该引脚加上+12V的编程允许电源Vpp,当然这必须是该器件是使用12V编程电压Vpp。
XTAL1:
振荡器反相放大器和内部时钟发生电路的输入端。
XTAL2:
振荡器反相放大器的输出端。
四、单片机硬件设计:
4.1电路图如下:
图4.1数字温度计原理图
单片机最小系统描述:
电源:
单片机电源用+5V供电,
晶振回路:
选用12MHz的晶振和两个30pf的电容
复位电路:
用10uf的电解电容和6.8K电阻组成复位电路。
单片机最小系统可以在上图中看到。
本实验选用了数字温度传感器DS18B20,以下对它加以描述。
4.2温度传感器工作原理
1)DS18B20的性能特点
DS18B20温度传感器是美国DALLAS半导体公司最新推出的一种改进型智能温度传感器。
与传统的热敏电阻等测温元件相比,它能直接读出被测温度,并且可根据实际要求通过简单的编程实现9~12位数字值读书方式。
DS18B20的性能特点如下:
●独特的单线接口仅需要一个端口引脚进行通信;
●多个DS18B20可以并联在唯一的三线上,实现多点组网功能;
●不需要外部器件;
●可通过数据线供电,电压范围为3.0~5.5V;
●零待机功耗;
●温度以9~12位数字量读出;
●用户可定义的非易失性温度报警设置;
●报警搜索命令识别并标志超过程序限定温度(温度报警条件)的器件;
●负电压特性,电源极性接反时,温度计不会因发热而烧毁,只是不能正常工作。
2)DS18B20测温原理
如图4.2所示,图中低温系数振荡器的振荡频率受温度的影响很小,用于产生固定频率
的脉冲信号送给减法计数器1;
高温系数振荡器随温度变化其震荡频率明显改变,所产生的信号作为减法计数器2的脉冲输入。
图中还隐含着计数门,当计数门打开时,DS18B20就对低温系数振荡器产生的时钟脉冲
进行计数,进而完成温度测量。
计数门的开启时间由高温度系数振荡器来决定,每次测量前,首先将-55℃所对应的一个基数分别置入减法计数器1和温度寄存器中,减法计数器1和温度寄存器被预置在-55℃所对应的一个基数。
减法计数器1对低温度系数振荡器产生的脉冲信号进行减法计数,当减法计数器1的预置值减到0时,温度寄存器的值将加1,减法计数器1的预置将重新被装入,并重新开始对低温度系数振荡器产生的脉冲信号进行计数。
如此循环,直到减法计数器2计数到0时,停止温度寄存器值的累加,此时温度寄存器的值就是所测温度值。
图4.8中的斜率累加器用于补偿和修正测温过程中的非线形性,其输出用于修正减法计数器的预置值,只要计数门仍未关闭就重复上述过程,直到温度寄存器值达到被测温度值。
另外,由于DS18B20单向通信功能是分时完成的,有严格的时隙概念,因此读/写时序很重要。
系统对DS18B20的各种操作必须按协议进行。
操作协议为:
初始化DS18B20(发复位脉冲)→发ROM功能命令→发存储器操作命令→处理数据。
DS18B20与单片机的接口电路
DS18B20可以采用两种方式供电:
一种是采用电源供电方式,此时DS18B20的第1脚接地,第2脚作为信号线,第3脚接电源;
另一种是寄生电源供电方式,如图4.9所示。
单片机端口接单线总线,为保证在有效的DS18B20时钟周期内提供足够的电流,可用于一个MOSFET管来完成对总线的上拉。
当DS18B20处于写存储器操作和温度A/D转换操作时,总线上必须有强的上拉,上拉开启时间最长为500ms。
采用寄生电源供电方式时,VDD和GND端均接地。
由于单线制只有一根线,因此发送接口必须是三态的。
五、用Protel99SE原理图设计和PCB板的制作
在这次课程设计中我负责画原理图和PCB图纸。
此次我们设计的电路原理图还是挺简单的,不过画到Protel中碰到了不少问题,我借了几本Protel99SE的参考书加以学习,画图中有许多细微问题是在XX中都难以得到解答,经过不断尝试,不断试用英文版的功能,我通过了一道道难关。
终于在各方面努力下完成了原理图绘制,元器件绘制,封装绘制,原理图导入PCB板,PCB板手工布局,PCB板手工布线,单片板的设计。
以下对我碰到的问题予以描述:
由于在常用元器件库中找不到晶振,我在元器件库中画了个晶振,通过加载自己的元器件库把晶振画到了原理图中,但是在设计好封装,导入PCB板后晶振的封装引脚没有任何电气连接关系。
这个问题我找了很久,重新连线,重新导入,都没成功。
后来无意中看到画的单片机的电气引脚,我才注意到自己画的晶振没有只用蓝色线向两边引出却没有加电气引脚,于是我修改了晶振,保存后重新加载到原理图中,再导入PCB板晶振果然有了电气连接关系。
我自己在元器件库里画了所需的9012三极管,画了三个引脚,把它放进原理图中,导入PCB板后,发现3个引脚中有1,3管脚有电气关系,2管脚没有。
这个问题我也找了很久,最后无意中发现2管脚的电气引脚和1,3管脚的放置方向相反,于是赶紧把2的方向反过来,保存后再导入PCB板,果然2管脚有了电气连接关系。
原电路图中要用到4个单数码管显示,但是元器件库中的单个数码管我觉得少了选通管脚,故在原理图绘制中4个9012三极管的选通信号不直接到数码管哪里,于是我干脆按照我们买回来的4位共阳数码管画了,这是我已经认识到元器件的绘制只是一个符号,不是很严格要求,只要不漏掉管脚就行了,所以可以在原理图中看出4位共阳数码管画的别扭,明显是自己画的。
画封装。
有些元器件的封装在网上可以查到,但有些没能查到,所以我干脆自己按实物画了封装。
在原理图中,4位共阳数码管和AT89S52单片机的封装是我画的。
我用尺子量了元器件的尺寸,到PCB封装库中把基本单位改为毫米,然后细心地画了封装,双击线段可以设置线段的坐标,用Ctrl+M可以检查线段的长度,这样画出了合乎实物的封装。
不过在做好电路板硬件调试时发现数码管引脚弄错了,我再查网上的资料,对比自己画的封装,果然是我把封装的焊盘引脚的标号放错了,于是只能直接在电路板上切断铜走线,用飞线跳线予以纠正。
画单片机的封装也挺特殊,因为考虑到后来要随时把单片机取出,故我画的是40脚单片机插槽的封装。
PCB板布线工作也一波三折。
开始我看元器件不多,直接使用了自动布线,一下子完成了双面布线,以为这样完了。
但后来要制作实物电路板,此简单电路用双面板实为把工作复杂化,于是为了设计单面板,我开始手工布线。
开始一条蓝色线连好后总是变成白色或绿色,让人失望至极,过了许久后,自己随意设置了一番,终于连出蓝色导线。
考虑实物要求,我把导线宽度设置为1mm。
布线快收尾时,电源线,地线和个别线总是会交叉,难以协调,在他人指点和自己一番思考后学会了果断跳线飞线,意思是PCB板上留着不连接,到了做成实物后用导线去连接。
之后的工作是填充,这一步简单很快可以完成。
虽然自己全部完成了画图任务,在实验室成功把PCB图通过转印纸附到了铜板上,后来做出的铜板走线在学长指点下还是有些不足不完美的地方,不过这第一块板也是情理之中的。
下面附上一些我画的图:
4位共阳LED数码管
晶振
4位共阳LED数码管封装
AT89S52封装
原理图导入PCB后的图
PCB正面图
布线图
PCB板完成后的图
六、制板过流程:
6.1流程
此次做板,我了解了各个流程,自己参与了电路板腐蚀,管脚焊接,用导线进行飞线跳线,有了很多的经验,收获了许多知识。
我亲身经历的基本流程是:
PCB板图纸打印到转印纸→转印纸包在铜板上通过160度的过塑机两次→用氯化铁溶液腐蚀铜片上未经石墨覆盖的铜→砂纸擦去石墨显现覆盖的铜→用打孔机打出元器件管脚的孔→安装元器件→焊好管脚→电路板调试检查线路通电情况不断布线。
6.2硬件调试
这次做板进行了基本的电路板调试,如用小灯检查电路板通电情况,最后保证了各条线路是通电的。
不过未能进行进一步的调试,如用万用表测各个管脚的电压,用示波器观察单片机各引脚的输出电平,这是遗憾的地方,一方面自己的疏忽,另一方面是后来时间有限,以及没能接触使用先进设备。
七、系统程序的设计
系统程序主要包括主程序、读出温度子程序、温度转换命令子程序、计算温度子程序和显示数据刷新子程序等。
7.1主程序
主程序的主要功能是负责温度的实时显示、读出并处理DS18B20的测量温值。
度测量每1S进行一次。
主程序见附录一。
主程序流程图如图4.10所示。
7.2读出温度子程序
读出温度子程序的主要功能是读出RAM中的9字节。
在读出时必须进行CRC校验,校验有错时不进行温度数据的改写。
读出温度子程序流程图如图4.11所示。
7.3温度转换命令子程序
温度转换命令子程序主要是发温度转换开始命令。
当采用12位分辨率时,转换时间约为750ms。
在本程序设计中,采用1s显示程序延时法等待转换的完成。
温度转换令子程序流程图如图4.12所示。
7.4计算温度子程序
计算温度子程序将RAM中读取值进行BCD码得转换运算,并进行温度值正负的判定。
计算温度子程序流程图如图4.13所示。
7.5显示数据刷新子程序
显示数据刷新子程序主要是缓冲器中的显示数据进行刷新操作,党最高数据显示位为0时,将符号显示位移入下一位。
显示数据刷新子程序流程图如图4.14所示。
八、软件调试:
我们用仿真程序把源程序代码放到单片机后运行,仿真软件通过了,可以显示温度。
但是把程序通过下载器烧到单片机,再把单片机插进自己设计的电路板中,程序不能运行。
找杨老师指导后,原来是我们软件调试工作还有很多没能做成。
这也是一个遗憾和不足的地方。
程序:
TIMELEQU0E0H;
20ms,定时器0时间常数
TIMEHEQU0B1H
TEMPHEADEQU36H
BITSTDATA20H
TIME1SOKBITBITST.1
TEMPONEOKBITBITST.2
TEMPLDATA26H
TEMPHDATA27H
TEMPHCDATA28H
TEMPLCDATA29H
TEMPDINBITP3.7
ORG0000H
LJMPSTART
ORG00BH
LJMPT0IT
ORG100H
START:
MOVSP,#60H
CLSMEM:
MOVR0,#20H
MOVR1,#60H
CLSMEM1:
MOV@R0,#00H
INCR0
DJNZR1,CLSMEM1
MOVTMOD,#00100001B;
定时器0I工作方式1(16位)
MOVTH0,#TIMEL
MOVTL0,#TIMEH;
20ms
SJMPINIT
ERROR:
NOP
INIT:
SETBET0
SETBER0
SETBEA
MOVPSW,#00H
CLRTEMPONEOK
LJMPMAIN
T0IT:
PUSHPSW
MOVPSW,#10H
MOVTH0,TIMEH
MOVTL0,TIMEL
INCR7
CJNER7,#32H,T0IT1
MOVR7,#00H
STEBTIME1SOK
T0IT1:
POPPSW;
1s定时到标志
RETI
MAIN:
LCALLDISP1;
调用显示子程序
JNBTIME1SOK,MAIN
CLRTIME1SOK;
测温每1s一次
JNBTEMPONEOK,MAIN2;
上电时先温度转换一次
LCALLREADTEMP1;
读出温度值子程序
LCALLCONVTEMP;
温度BCD码计算处理子程序
LCALLDISPBCD;
显示区BCD码温度值刷新子程序
消闪烁,显示一次
MAIN2:
LCALLREADTEMP;
温度转换开始
SETBTEMPONEOK
INITDS1820:
SETBTEMPDIN
CLRTEMPDIN
MOVR6,0A0H
DJNZR6,$
MOVR6,#0A0H;
延时480us
MOVR6,#32H
MOVR6,#3CH
LOOP1820:
MOVC,TEMPDIN
JCINITDS1820OUT
DJNZR6,LOOP1820
MOVR6,#064H;
延时200us
SJMPINITDS1820
RET
READDS1820:
MOVR7,#08H
READDS1820LOOP:
MOVR6,#07H;
延时15us
RRCA
DJNZR7,READDS1820LOOP
MOVR6,#3CH;
延时120us
WRITEDS1820:
WRITEDS1820LOP:
MOVR6,#07H
MOVTEMPDIN,C
MOVR6,$
MOVR6,#34H;
延时104us
DJNZR7,WRITEDS1820LOP
READTEMP:
LCALLINITDS1820
MOVA,#0CCH
LCALLWRITEDS1820;
SkipROM
MOVR6,#34H
MOVA,#44H
开始转换
READTEMP1:
中间结果寄存器
MOVA,#0BEH
LCALLWRITEDS1820
MOVR5,#09H
MOVR0,#TEMPHEAD
MOVB,#00H
READTEMP2:
LCALLREADDS1820
MOV@R0,A
READTEMP21:
LCALLCRC8CAL
DJNZR5,READTEMP2
MOVA,B
JNZREADTEMPOUT
MOVA,TEMPHEAD+0
MOVTEMPL,A
MOVA,TEMPHEAD+1
MOVTEMPH,A
READTEMPOUT:
CONVTEMP:
MOVA,TEMPH
ANLA,#80H
JZTEMPC1
CLRC
MOVA,TEMPL
CPLA
ADDA,#01H
MOVTEMPL,A;
整数部分
MOVTEMPHC,#0BH
SJMPTEMPC11
TEMPC1:
MOVTEMPHC,#0AH
TEMPC11:
MOVA,TEMPHC
SWAPA
MOVTEMPHC,A
ANLA,#0FH
MOVDPTR,#TEMPDOTTAB
MOVCA,@A+DPTR
MOVTEMPLC,A
ANLA,#0F0H
ORLA,TEMPL;
十位数BCD
LCALLHEX2BCD1
SWAPA,
ORLA,TEMPHC
SWAPA;
个位数BCD
ORLA,TEMPLC
MOVA,R7
JZTEMPC12