单片机和PC机串口通讯试验 | |
作者: 时间:2007-08-31 来源: | |
51单片机有一个全双工的串行通讯口,所以单片机和电脑之间可以方便地进行串口通讯。进行串行通讯时要满足一定的条件,比如电脑的串口是rs232电平的,而单片机的串口是ttl电平的,两者之间必须有一个电平转换电路,我们采用了专用芯片max232进行转换,虽然也可以用几个三极管进行模拟转换,但是还是用专用芯片更简单可靠。我们采用了三线制连接串口,也就是说和电脑的9针串口只连接其中的3根线:第5脚的gnd、第2脚的rxd、第3脚的txd。这是最简单的连接方法,但是对我们来说已经足够使用了,电路如下图所示,max232的第10脚和单片机的11脚连接,第9脚和单片机的10脚连接,第15脚和单片机的20脚连接。 串口通讯的硬件电路如上图所示 在制作电路前我们先来看看要用的max232,这里我们不去具体讨论它,只要知道它是ttl和rs232电平相互转换的芯片和基本的引脚接线功能就行了。通常我会用两个小功率晶体管加少量的电路去替换max232,可以省一点,效果也不错(如有兴趣可以查看http://www.cdle.net网站中的相关资料)。下图就是max232的基本接线图。 按图7-3加上max232就可以了。这大热天的拿烙铁焊焊,还真的是热气迫人来呀:p串口座用db9的母头,这样就可以用买来的pc串口延长线进行和电脑相连接,也可以直接接到电脑com口上。 为了能够在电脑端看到单片机发出的数据,我们必须借助一个windows软件进行观察,这里我们利用一个免费的电脑串口调试软件。 点击这里可以下载并运行这个串口调试软件,这是一个绿色的软件,无需安装,可以直接在当前位置运行这个软件。软件界面如上图,我们先要设置一下串口通讯的参数,将波特率调整为4800,勾选十六进制显示。串口选择为com1,当然将网站提供的51单片机实验板的串口也要和电脑的com1连接,将烧写有以下程序的单片机插入单片机实验板的万能插座中,并接通51单片机实验板的电源。 串口实验的源程序如下所示: ;这是一个s51单片机实验开发板向pc机的串口单向发送数据af的演示程序 ;采用max232专用芯片作rs232/ttl电平转换. ;通讯波特率为4800kbps,只要按下一次k1(就是p3.6引脚变成低电平) ;就发送一个16进制的af字符 org 0000h mov scon,#50h;设置成串口1方式 mov tmod,#20h;波特率发生器t1工作在模式2上 mov pcon,#80h;波特率翻倍为2400x2=4800bps mov th1,#0f3h;预置初值(按照波特率2400bps预置初值) mov tl1,#0f3h;预置初值(按照波特率2400bps预置初值) setb tr1;启动定时器t1 ;以上完成通讯初始化设置 writ:jb p3.6,$;判断k1是否按下,如果没有按下就等待 acall delay10;延时10毫秒消触点抖动 jb p3.6,writ;去除干扰信号 jnb p3.6,$;等待按键松开 mov a,#0afh;将16进制的字符af发送到串口去 mov sbuf,a;将af通过串口发送出去 ajmp writ ;10毫秒延时子程序 delay10:mov r4,#20 d2:mov r5,#248 djnz r5,$ djnz r4,d2 ret end ;=============两机串口通讯程序(主机)===================== ; ; 功 能: 使用串行中断,接收数据并显示 ; 硬件环境: 自制单片机实验板 ; 软件环境: 伟福 v3.20 ; create date: 2004_07_26 ; first modify: 2004_07_26 ; second modify: ; last modify: 2004_07_26 ; author: sujiande ; ;===========预定义=================== led0 equ 40h ;预定义数码管 led1 equ 41h ;预定义数码管 led2 equ 42h ;预定义数码管 led3 equ 43h ;预定义数码管 led4 equ 44h ;预定义数码管 led5 equ 45h ;预定义数码管 led6 equ 46h ;预定义数码管 led7 equ 47h ;预定义数码管 sda bit p0.1 ; 定义数据线引脚定义 scl bit p0.0 ; 定义时钟线引脚定义 ;--------------------------- org 0000h ;主程序入口 ajmp main ;跳转到主程序 org 0100h ;主程序在rom中存放位置 ;===============主程序===================== main: mov led0,#00h ;赋初值 mov led1,#00h mov led2,#16 ;赋初值为16, 数码管显示代码为: 灭 mov led3,#16 mov led4,#16 mov led5,#16 mov led6,#16 mov led7,#16 ;-------------------- ;mov dptr,#table ; 赋显示代码首地址 mov r1,#00h ; 给r1赋初值00h acall display ; 调显示子程序 mov sp, #30h ; 给堆栈指针赋初值 ;-------------------------- ; 使用定时器1,作为波特率发生器,设定波特率=9600, ; 定时器初值为:fah ; 串行控制器设置:sm0=0,sm1=1,sm2=0,ren=1,tb8=0, ; rb8=0,ti=0,ri=0 即0101 0000b ; 波特率加倍 ;----------------------------- mov tmod,#20h ;设置定时器1,工作方式2 mov th1,#0fah ;赋初值: fa mov tl1,#0fah ;赋初值: fa mov scon, #50h ;设置串行口控制寄存器 mov pcon, #80h ;设置电源控制寄存器, 让波特率加倍(2x) setb tr1 ;启动定时 ;*****************主程序结束************************ lp8: mov a,r1 ;将r1的数据装到a中 ;----------------------- mov sbuf,a ;将a的数据送到缓冲区 jnb ti,$ ;等待数据发送完毕 clr ti ;清发送中断标志 ;----------------------- inc r1 cjne r1,#99,lp3 mov r1,#00h lp3: acall seperate ;调拆分程序 acall display ;调显示子程序 acall delay_1s ;调延时子程序 ajmp lp8 ;=================拆分程序===================== seperate: anl a,#0fh ;与操作得到个位数据 mov led0,a ;个位送led0 mov a,r1 anl a,#0f0h ;与操作得到十位数据 swap a mov led1,a ;十位送led1 ret ;===============显示子程序====================== display: mov dptr,#table ; 赋显示代码首地址 mov a,led0 ;查表数据送a movc a,@a+dptr ;查表,得到显示代码 acall shift ;调移位子程序 mov a,led1 movc a,@a+dptr acall shift mov a,led2 movc a,@a+dptr acall shift mov a,led3 movc a,@a+dptr acall shift mov a,led4 movc a,@a+dptr acall shift mov a,led5 movc a,@a+dptr acall shift mov a,led6 movc a,@a+dptr acall shift mov a,led7 movc a,@a+dptr acall shift ret ;---------显示代码表--------- table: db 11h,0d7h,32h,92h,0d4h,98h,18h,0d3h,10h,90h ;0,1,2,3,4,5,6,7,8,9, db 50h,1ch,39h,16h,38h,78h, 0ffh,0feh,0efh ;10,11,12,13,14,15,灭,- ;================移位子程序============================ shift: push a ; 进栈暂存a值 mov r0,#8 ; 循环8次 clr c ;清进位标志 clr scl ;时钟线,先钳位为0 lp2: rlc a mov sda,c nop nop setb scl nop nop clr scl nop nop djnz r0,lp2 pop a ; 出栈恢复a值 ret ;=============延时子程序=============== delay_1s: mov r7,#0ffh loop7: mov r6,#0ffh loop6: nop nop nop nop nop nop djnz r6,loop6 djnz r7,loop7 ret ;------------------------------ end ;=============两机串口通讯程序(从机)===================== ; ; 功 能: 使用串行中断,接收数据并显示 ; 硬件环境: 自制单片机实验板 ; 软件环境: 伟福 v3.20 ; create date: 2004_07_26 ; first modify: 2004_07_26 ; second modify: ; last modify: 2004_07_26 ; author: sujiande ; ;===========预定义=================== led0 equ 40h ;预定义数码管 led1 equ 41h ;预定义数码管 led2 equ 42h ;预定义数码管 led3 equ 43h ;预定义数码管 led4 equ 44h ;预定义数码管 led5 equ 45h ;预定义数码管 led6 equ 46h ;预定义数码管 led7 equ 47h ;预定义数码管 sda bit p0.1 ; 定义数据线引脚定义 scl bit p0.0 ; 定义时钟线引脚定义 ;--------------------------- org 0000h ;主程序入口 ajmp main ;跳转到主程序 org 0023h ;中断入口地址 ajmp s_int ;跳转到中断程序 org 0100h ;主程序在rom中存放位置 ;==============主程序======================== main: mov led0,#00h ;赋初值 mov led1,#00h mov led2,#16 ;赋初值为16, 数码管显示代码为: 灭 mov led3,#16 mov led4,#16 mov led5,#16 mov led6,#16 mov led7,#16 ;------------------------------ mov dptr,#table ; 赋显示代码首地址 acall display ; 调显示子程序 mov sp, #30h ; 给堆栈指针赋初值 ;-------------------------------------------- ; 使用定时器1,作为波特率发生器,设定波特率=9600, ; 定时器初值为:fah ; 串行控制器设置:sm0=0,sm1=1,sm2=0,ren=1,tb8=0, ; rb8=0,ti=0,ri=0 即0101 0000b ; 波特率加倍 ;--------------------------------------------- mov tmod,#20h ;设置定时器1,工作方式2 mov th1,#0fah ;赋初值: fa mov tl1,#0fah ;赋初值: fa mov scon, #50h ;设置串行口控制寄存器 mov pcon, #80h ;设置电源控制寄存器, 让波特率加倍(2x) ;--------------------------------------- setb ea ; 启动总中断 setb es ; 启动串行中断 setb tr1 ;启动定时 ajmp $ ; 等待中断 ;*****************主程序结束************************ ;===============中断服务程序============================= s_int: mov r1, sbuf ;将缓冲区的数据送到r1 acall seperate ;调拆分程序 acall display ;调显示子程序 clr ri ;清接收中断标志 reti ;中断返回 ;=================拆分程序===================== seperate: mov a,r1 anl a,#0fh ;与操作得到个位数据 mov led0,a ;个位送led0 mov a,r1 anl a,#0f0h ;与操作得到十位数据 swap a ; mov led1,a ;十位送led1 ret ;===============显示子程序====================== display: mov a,led0 ;查表数据送a movc a,@a+dptr ;查表,得到显示代码 acall shift ;调移位子程序 mov a,led1 movc a,@a+dptr acall shift mov a,led2 movc a,@a+dptr acall shift mov a,led3 movc a,@a+dptr acall shift mov a,led4 movc a,@a+dptr acall shift mov a,led5 movc a,@a+dptr acall shift mov a,led6 movc a,@a+dptr acall shift mov a,led7 movc a,@a+dptr acall shift ret ;---------显示代码表--------- table: db 11h,0d7h,32h,92h,0d4h,98h,18h,0d3h,10h,90h ;0,1,2,3,4,5,6,7,8,9, db 50h,1ch,39h,16h,38h,78h, 0ffh,0feh,0efh ;10,11,12,13,14,15,灭,- ;================移位子程序============================ shift: push a ; 进栈暂存a值 mov r0,#8 ; 循环8次 clr c ;清进位标志 clr scl ;时钟线,先钳位为0 lp2: rlc a mov sda,c nop nop setb scl nop nop clr scl nop nop djnz r0,lp2 pop a ; 出栈恢复a值 ret ;=============延时子程序=============== delay_1s: mov r7,#0ffh loop7: mov r6,#0ffh loop6: nop nop nop nop nop nop djnz r6,loop6 djnz r7,loop7 ret ;------------------------------ |
文章评论(0条评论)
登录后参与讨论