单片机课程设计PC机与单片机通信.docx
《单片机课程设计PC机与单片机通信.docx》由会员分享,可在线阅读,更多相关《单片机课程设计PC机与单片机通信.docx(23页珍藏版)》请在冰点文库上搜索。
单片机课程设计PC机与单片机通信
信息科学与技术学院
《单片机原理》课程设计报告
PC机与单片机通信
目录
第一章设计任务及要求3
1.1设计任务3
1.2设计要求3
第二章设计设计思路与原理3
2.1设计思路3
2.2设计原理4
第三章系统功能模块5
3.1总原理图5
3.2温度测量电路5
3.3通信模块8
3.4发光二极管电路10
3.5复位电路及时钟电路11
第四章程序设计...............................................................................................................12
4.2软硬件功能16
第五章参考结论与体会13
第六章参考文献15
附录15
一、设计任务及要求
1.1设计任务
PC机与单片机通信
1.2设计要求
1、通过DS18B20采集当前温度
2、将当前温度发送至PC机,在PC机上设计接收温度界面,(并绘制接收温度曲线);
3、根据温度值向单片机传送不同字符,并点亮相应的二极管。
若温度值在20~26,传送字符A,点亮绿灯;温度值在27~30,传送B,点亮黄灯;温度值在31~40,传送C,点亮蓝灯。
二、设计思路与原理
2.1设计思路
在测控系统中,经常采用单片机在操作现场进行数据采集,但是单片机数据储存和数据处理能力较低,当需要处理较复杂数据或需要对多个采集数据进行综合处理以及需要进行集散控制时,单片机的算术运算和逻辑运算能力显的不足,这时往往需要借助计算机系统。
将单片机采集的数据通过串行口传给PC机,由PC机高级语言或数据库语言进行处理,或者实现PC机对远程单片机进行控制。
所以一般情况下单片机通过串行口与PC机的串行口相连,把采集到的数据传送到PC机上。
总体思路:
首先利用DS18b20采集温度数据,然后使用单片机串口将温度数据发送至PC机。
再判断温度值的范围控制发光二级管。
2.2设计原理
目前RS-232是PC与通信工业中应用最广泛的一种串行接口,其中EIA代表美国电子工业协会,RS代表推荐标准,232是标识号。
RS-232被定义为一种在低速率串行通信中增加通信距离的单端标准。
RS-232采取不平衡传输方式,即单端通信。
单片机之间的串口通信,基于RS-232电气特性的限制,只能实现一点对一点通信(既单机通信)。
本文要求设计一个51单片机与PC串口间通讯系统,实现单片机与PC机之间的远程通信。
设计分发送和接收两大模块,发送部分通过硬件电路的引用。
其中包括RS-232接口电路、MAX232接口电路,引用相应的管脚相连,并将相应的软件程序转入电路中,即可运行。
当电路是相对独立时,可直接调速电路参数值,其影响和干扰就小。
在满足发射和接收模块的要求后可单独对控制进行调整,程序的编入,接收部分相应的结果即以实现,因此实现了PC机对远端单片机的控制。
3、系统功能模块
3.1总原理图
整个系统由复位电路、时钟电路、发光二极管电路、温度测量电路、通信模块五部分组成。
(如图3.1.1)
图3-1总原理图
3.2温度测量电路
图3-2温度测量电路
3.2.1DS18b20简介
DS18b20测量范围为-55℃~+125℃。
在-10~+85℃范围内,精度为±0.5℃。
测量参数可配置DS18B20的测量分辨率可通过程序设定9~12位。
DS18B20采用单总线的接口方式与微处理器连接,即只有一根数据线,系统中的数据交换,控制都由这根线完成。
单总线通常要求外接一个约为4.7K—10K的上拉电阻,这样当总线闲置时其状态为高电平。
DS18B20存储的温度值是以补码的形式存储的,所以读出来的温度值是实际温度值的补码,要把的转换为原码。
3.2.2DS18b20初始化
主机首先发出一个480-960微秒的低电平脉冲,然后释放总线变为高电平,并在随后的480微秒时间内对总线进行检测,如果有低电平出现说明总线上有器件已做出应答。
若无低电平出现一直都是高电平说明总线上无器件应答。
做为从器件的DS18B20在一上电后就一直在检测总线上是否有480-960微秒的低电平出现,如果有,在总线转为高电平后等待15-60微秒后将总线电平拉低60-240微秒做出响应存在脉冲,告诉主机本器件已做好准备。
若没有检测到就一直在检测等待。
图3-3初始化时序图
3.2.3DS18b20读时序
主机发出各种操作命令都是向DS18B20写0和写1组成的命令字节,接收数据时也是从DS18B20读取0或1的过程。
因此首先要搞清主机是如何进行写0、写1、读0和读1的。
写周期最少为60微秒,最长不超过120微秒。
写周期一开始做为主机先把总线拉低1微秒表示写周期开始。
随后若主机想写0,则将总线置为低电平,若主机想写1,则将总线置为高电平,持续时间最少60微秒直至写周期结束,然后释放总线为高电平至少1微秒给总线恢复。
而DS18B20则在检测到总线被拉底后等待15微秒然后从15us到45us开始对总线采样,在采样期内总线为高电平则为1,若采样期内总线为低电平则为0。
图3-4读时序图
3.2.4DS18b20写时序
对于读数据操作时序也分为读0时序和读1时序两个过程。
读周期是从主机把单总线拉低1微秒之后就得释放单总线为高电平,以让DS18B20把数据传输到单总线上。
作为从机DS18B20在检测到总线被拉低1微秒后,便开始送出数据,若是要送出0就把总线拉为低电平直到读周期结束。
若要送出1则释放总线为高电平。
主机在一开始拉低总线1微秒后释放总线,然后在包括前面的拉低总线电平1微秒在内的15微秒时间内完成对总线进行采样检测,采样期内总线为低电平则确认为0。
采样期内总线为高电平则确认为1。
完成一个读时序过程,至少需要60微秒才能完成
图3-5写时序图
3.2.5DS18B20的操作步骤
DS18B20的一线工作协议流程是:
初始化→ROM操作指令→存储器操作指令→数据传输。
其工作时序包括:
a初始化时序b写时序c读时序
3.3通信模块
图3-6串口仿真图
图3-8
由于单片机输入输出都是RS-232标准串行接口,为9针D型连接器,其插头如图所示。
表3-1为PC机的RS-232接口信号。
由于两者的电平不匹配,因此必须对单片机输出的TTL电平转换为RS-232电平。
单片机与PC级接口方案如图3-9
3.3.1MAX232接口电路
图3-7MAX232引脚图
MAX232芯片是MAXIM公司生产的具有两路接收器和驱动器的IC芯片,其内部有一个电源电压变换器,可以将输入+5V的电压变换成RS-232C输出电平所需的+/-12V的电压。
在其内部同时也完成TTL信号电平和RS-232信号电平的转换。
所以,采用此芯片实现接口电路只需单一的+5V电源就可以。
MAX232芯片的引脚结构如图2-2所示。
其中管脚1-6(C1+,V+,C1-,C2+,C2-,V-)用于电源电压转
换,只要在其内部接入相应电解电容即可:
管脚7-10和管脚11-14.构成两组TTL信号电平与RS-232信号电平的转换电路,对应管脚可直接与单片机串行口的TTL电平引脚和PC机的RS-232电平引脚相连。
具体连接可参看图3-7
.
表3-1PC机接口信号
图3-9
3.4发光二极管电路
图3-10发光二极管电路
图3-11
P0口与P1、P2、P3口相比,P0口驱动能力较大,每位可驱动8个LSTTL输入,而P1、P2、P3口的每一位的驱动能力,只有P0口的一半。
当P0口的某位为高电平时,可提供400uA的电流。
而P1、P2、P3口内部有30KΩ上拉电阻,如果高电平输出,则强行从P1、P2、P3口输出电流会造成单片机端口的损坏。
因此想要获 得较大的驱动能力,只能用低电平输出。
3.5复位电路及时钟电路
4、程序设计
4.1软件简介
鉴于单片机技术比较成熟,且开发过程中可以利用的资源和工具丰富、价格便宜、成本低。
故设计用C语言对其编程并烧录到芯片内部,C语言表达和运算能力比较强,且具有很好的可移植性和硬件控制能力,程序可分为发射部分和接收部分。
在51系列单片机中,波特率由定时/计数器T1自动产生,但在使用前。
需对T1进行一些设置,才能得自己想要的波特率。
我们通常在有串行通信的系统中选用11.0592MHz的晶振,为了使用方便采用4800Kbps的波特率,所以T1的初值应设置为0Xfa。
4.2软件设计和硬件设计的关系
为了满足设计的功能和指标的要求,我们必须在开始设计时就应考虑到硬件和软件的协调;不然就是造成硬件资源的浪费,就是增加软件实现时的困难和复杂程度,甚至造成信号的断层,即使硬件和软件能单独使用,却不能使它们组成的系统工作,故在设计的过程中必须考虑软、硬件的处理能力以及它们的接口是否兼容,实现软、硬件的过渡,其次、设计时硬件之间应尽可能减小联系,只要把必要的信号线相连即可。
由于硬件的分离,在软件的调试时就可以单独针对控制模块。
5、结论与体会
5.1程序运行后的结果
DS18B20采集当前温度,能将当前温度值实时传送至PC机显示,根据温度值向单片机传送,并点亮了相应的二极管。
若温度值在20~26,点亮绿灯;温度值在27~30,点亮黄灯;温度值在31~40,点亮红灯。
5.2心得体会
经过一段时间的学习与研究,至此,本次课程设计已经全部完成,所设计的接口电路、单片机串行通信、传输模块基本达到预期的目的,顺利地完成了任务。
进行循环数据采集,并且误差范围非常小,数据采集速度高,能够满足一般多通道数据采集要。
在做课程设计之初,我查了很多关于单片机串行通信、单片机原理与接口技术的设计资料,我发现经了长时间的实践的检验,而我们几乎从零开始做,我们发现自己很难找到创新点,即使成功了也是对前人工作的一次重复,一度我们很茫然,前人的设计水2何在?
但是经过仔细思考,我们端正了自己的态度,同时我们也找到了姑且算作创新点的所在,作好了一切准备工作之后便开始了紧张的课程设计工作。
做课程设计的这段时间是紧张的一段时间,也是重新学习努力探索的一段时间,更是充满收获喜悦的一段时间。
经过这次课程设计,我们学会了许多新知识,学会了遇到问题先分析问题解决问题的能力,学会了如何充分的利用网络资源来提高自己的文化知识和专业知识,学会了单片机系统开发的一般流程;也明白了许多不曾明白的道理,明白了求学应当有严谨的作风,并且更应该有锲而不舍、坚强的韧劲。
本课程设计论文是在我们们的指导老师刘恩博老师的悉心指导下完成的,在课程设计过程中,刘老师倾注了大量的心血,他的悉心指导是本设计能够圆满完成的基础。
刘老师学识渊博,专业知识过硬,治学作风严谨,工作认真负责。
在这一段时间的课程设计过程中,刘老师言传身教,不仅在学习上耐心地给我们指点迷津,解惑答疑,在生活上也为我们提供方便,更使我们对人生的征途有了新的认识,有了新的目标。
刘老师的孜孜不倦的教诲和严谨的治学作风令我们终生难忘,也将使我们受益终生。
在此谨向刘老师表达一个学生最真挚的谢意!
6、参考文献
【1】张旭涛.曾现峰.单片机原理与应用.北京:
北京理工大学出版社.2006
【2】穆兰.单片微型计算机原理及接口技术.北京:
机械工业出版社.2002
【3】杨金岩.郑应强.51单片机数据传输接口扩展技术与应用实例.北京:
人民邮电出版社.2006
【4】胡伟.季晓衡.单片机C程序设计及应用实例.北京:
人民邮电出版社.2006
【5】黄智伟.全国大学生电子设计竞赛系统设计【M】.北京:
北京航空航天大学出版社.2006
【6】胡汉才组编.单片机原理及接口技术.北京:
清华大学出版社,1996
附录:
#include//包含相关的头文件
#defineucharunsignedchar//使用uchar代替unsignedchar
#defineuintunsignedint//使用uint代替unsignedint
sbitDQ=P3^7;//DS18B20的管脚
sbitled1=P1^0;//绿灯
sbitled2=P1^1;//黄灯
sbitled3=P1^2;//红灯
ucharSendBuff[]={"Temperature=."};
/*********************************************************/
//毫秒级的延时函数,time是要延时的毫秒数
/*********************************************************/
voidDelay1ms(uinttime)
{
uinti,j;
for(i=time;i>0;i--)
for(j=112;j>0;j--);
}
/*********************************************************/
//DS18B20初始化
/*********************************************************/
unsignedcharDs18b20Init()
{
unsignedinti;
DQ=0;//将总线拉低480us~960us
i=70;
while(i--);//延时642us
DQ=1;//然后拉高总线,若DS18B20做出反应会将在15us~60us后将总线拉低
i=0;
while(DQ)//等待DS18B20拉低总线
{
i++;
if(i>50000)//等待>50MS
return0;//初始化失败
}
return1;//初始化成功
}
/*********************************************************/
//读取DS18B20的一个字节
/*********************************************************/
unsignedcharDs18b20ReadByte()
{
unsignedcharbyte,bi;
unsignedinti,j;
for(j=8;j>0;j--)
{
DQ=0;//先将总线拉低1us
i++;
DQ=1;//然后释放总线
i++;
i++;//延时6us等待数据稳定
bi=DQ;//读取数据,从最低位开始读取
byte=(byte>>1)|(bi<<7);/*将byte左移一位,然后与上右移7位后的bi,注意移动之后移掉那位补0。
*/
i=4;//读取完之后等待48us再接着读取下一个数
while(i--);
}
returnbyte;
}
/*********************************************************/
//写数据的一个字节,满足写1和写0的时隙要求
/*********************************************************/
voidDs18b20WriteByte(unsignedchardat)
{
unsignedinti,j;
for(j=0;j<8;j++)
{
DQ=0;//每写入一位数据之前先把总线拉低1us
i++;
DQ=dat&0x01;//然后写入一个数据,从最低位开始
i=6;
while(i--);//延时68us,持续时间最少60us
DQ=1;//然后释放总线,至少1us给总线恢复时间才能接着写入第二个数值
dat>>=1;
}
}
/************************************************************
*函数名:
Ds18b20ChangTemp
*函数功能:
让18b20开始转换温度
************************************************************/
voidDs18b20ChangTemp()
{
Ds18b20Init();
Delay1ms
(1);
Ds18b20WriteByte(0xcc);//跳过ROM操作命令
Ds18b20WriteByte(0x44);//温度转换命令
Delay1ms(100);
}
/************************************************************/
*函数名:
Ds18b20ReadTempCom
*函数功能:
发送读取温度命令
************************************************************/
voidDs18b20ReadTempCom()
{
Ds18b20Init();
Delay1ms
(1);
Ds18b20WriteByte(0xcc);//跳过ROM操作命令
Ds18b20WriteByte(0xbe);//发送读取温度命令
}
/*********************************************************/
//读取温度值
/*********************************************************/
intDs18b20ReadTemp()
{
unsignedinttemp=0;
unsignedchartmh,tml;
floattt;
Ds18b20ChangTemp();//先写入转换命令
Ds18b20ReadTempCom();//然后等待转换完后发送读取温度命令
tml=Ds18b20ReadByte();//读取温度值共16位,先读低字节
tmh=Ds18b20ReadByte();//再读高字节
temp=tmh;
temp<<=8;
temp|=tml;
tt=temp*0.0625;
temp=tt*10+0.5;
return(temp);
}
/*********************************************************/
//串口初始化
/*********************************************************/
voidUartInit()
{
SCON=0X50;//设置为工作方式1
TMOD=0X20;//设置计数器工作方式2
PCON=0X80;//波特率加倍
TH1=0XF3;//计数器初始值设置,注意波特率是4800的
TL1=0XF3;
ES=1;//打开接收中断
EA=1;//打开总中断
TR1=1;
}
/*********************************************************/
//主函数
/*********************************************************/
voidmain()
{
uinttemp;//保存温度值
uchari;//临时变量
UartInit();//串口初始化
while
(1)
{
/*读取当前温度*/
temp=Ds18b20ReadTemp();
/*判断温度是否在20-26之间*/
if((temp>=200)&&(temp<270))
{
led1=0;//绿灯亮
led2=1;//黄灯灭
led3=1;//蓝灯灭
}
/*判断温度是否在27-30之间*/
elseif((temp>=270)&&(temp<310))
{
led1=1;//绿灯灭
led2=0;//黄灯亮
led3=1;//蓝灯灭
}
/*判断温度是否在31-40之间*/
elseif((temp>=310)&&(temp<=400))
{
led1=1;//绿灯灭
led2=1;//黄灯灭
led3=0;//蓝灯亮
}
/*如果不在上述的三个范围之内,则三盏灯都熄灭*/
else
{
led1=1;//绿灯灭
led2=1;//黄灯灭
led3=1;//蓝灯灭
}
/*通过串口把温度值发送出去*/
SendBuff[12]=temp/100+0x30;//获取十位
SendBuff[13]=temp%100/10+0x30;//获取个位
SendBuff[15]=temp%10+0x30;//获取小数后1位
for(i=0;i<16;i++)
{
SBUF=(SendBuff[i]);
while(!
TI);
TI=0;
}
SBUF=('\n');
while(!
TI);
TI=0;
/*延时200毫秒以后继续新一轮的采集*/
Delay1ms(200);
}
}