佚名通过本文主要向大家介绍了wlan驱动程序出现问题,显示驱动程序出现问题,程序遇到问题需要关闭,解析程序包时出现问题,解析程序包出现问题等相关知识,希望对您有所帮助,也希望大家支持linkedu.com www.linkedu.com
问题: 程序运行问题
描述:
解决方案1:
描述:
keil4 与proteus联合调试,全速运行与单步运行正常.但,proteus单独运行就不正常.
/******************************头文件加载与宏定义**************************************************/
#include <reg52.h>
/*用于声明特殊功能寄存器的名称.
如果没有这个头文件,特殊功能寄存器,只能用硬件的地址进行读写操作。*/
#include <binary.h>
typedef unsigned int uint;
typedef unsigned char uchar;
/******************************声明全局函数和变量*********************************************************/
/*此处增加其它全局声明*/
volatile uchar pulse_dly=0; //延时变量
void cominit(); //串口初始化
void init(); //1602初始化函数
void wcom(uchar com); //写指令
void wdat(uchar dat); //写数据
void delay(uint i); //延时函数
sbit rs=P1^0;
sbit rw=P1^1;
sbit e=P1^2;
volatile uchar a;
/**********************主函数*******************/
void main()
{
/*C51所有变量声明必须在代码段前*/
/*此处增加其它局部声明*/
cominit();
init ();
wcom(0x80);
wdat('a');
while(1);
}
/*串口初始化*/
void cominit()
{
/************************************定时器初始化***************************************************/
TMOD=0x21; /*0000 0001 TMOD 是计时器工作方式寄存器,有8位
高四位设置定时器1.低四位定时器0. 两者设置相同.
低四位0001
低两位01 代表方式1:16位寄存器
{00 代表方式0:13位寄存器(高8,低5).
10 代表方式3:8位自动重装定时:高8位溢出后,
低8位数值自动装入高8位做为初值.
11 代表方式4:分为两个单独的8位定时/计数器}.
最高位0代表:GATE位(0不受中断控制,1受中断控制),
第二位代表:CT位(选择0为定时器,选择1为计数器)*/
/*********************************定时器加载初值******************************************************/
/*********************************定时器加载初值******************************************************/
TH0=(65536-932)/256; /*定时器0是由两个8位寄存器TH0与TL0组成,
定时器初值计算方法为65536减去定时间隔除以256放入高8位,*/
TL0=(65536-932)%256; /*再用65536减去定时间隔取余256放入低8位*/
TH1=0xfd;
TL1=0xfd;
/**********************************开中断****************************************************/
ET0=1; //开定时器0中断
TR0=1; //启动定时器0
//ET1=1; //开定时器1中断,串口通信中,开启波特率的定时器不要打开定时器中断,如果打开中断,就要写对应的中断服务程序.
TR1=1; //启动定时器1
/***************************************************************************************/
//SCON= B01010000;
/*SCON有8位
SM0=SCON^7,
SM1=SCON^6
(SM0与SM1是串口工作方式选择共有四种模式
00:移位寄存器,波特率为晶振频率fosc/12,
01:10位异步收发器,8位数据,波特率可变 (比较常用)
10:11位异步收发器,9位数据,波特率为晶振频率fosc/64或32
11:11位异步收发器,9位数据,波特率可变).
SM2=CON^5,
多机通信控制位,SM2=1;时,利用收到的RB8来控制是否激活RI,SM2=0;时无论RB8收到何种数据,都会激活RI
REN=SCON^4,
允许串行接收位,REN=1;时,允许接收 0时禁止接收数据
TB8=SCON^3,
方式2-3中,通信数据的第9位.可做奇偶校验位.在多机通信中作为地址帧数据帧的标志位.
RB8=SCON^2;
方式2-3中,通信数据的第9位.SM2=1;时控制是否激活RI,方式1时,SM2=0时,接收到的是停止位.
TI=SCON^1;
发送中断标志位.方式0时,当第8位数据发送结束时,或在其它方式串行发送停止位开始时,向CPU发送中断申请,中断处理函数中必须对其清0,取消此中断申请.
RI=SCON^0;
接收中断标志位.方式0时,当第8位数据接收结束时,或在其它方式串行接收停止位中间时,向CPU发送中断申请,中断处理函数中必须对其清0,取消此中断申请.*/
SM0=0;
SM1=1;
REN=1;
ES=1; //打开串口中断
EA=1; //开总中断
/***************************************************************************************/
}
void serial() interrupt 4
{
a=SBUF;
RI=0;
wdat(a);
delay(1);
}
void delaytime() interrupt 1
{
TH0=(65536-1000)/256;
TL0=(65536-1000)%256;
pulse_dly++;
}
void delay(uint i)
{
pulse_dly=0;
while(i!=pulse_dly);
}
void init ()
{
delay(30);
wcom(0x38);
delay(10);
wcom(0x38);
delay(10);
wcom(0x38);
wcom(0x38);
wcom(0x08);
wcom(0x01);
wcom(0x06);
wcom(0x0c);
}
void wcom(uchar com)
{
e=0;
rs=0;
rw=0;
P0=com;
delay(1);
e=1;
delay(2);
e=0;
delay(1);
}
void wdat(uchar dat)
{
e=0;
rs=1;
rw=0;
P0=dat;
delay(1);
e=1;
delay(2);
e=0;
delay(1);
}
解决方案1:
void serial() interrupt 4
{
a=SBUF;
RI=0;
wdat(a);
delay(1);
}
void delaytime() interrupt 1
{
TH0=(65536-1000)/256;
TL0=(65536-1000)%256;
pulse_dly++;
}
void delay(uint i)
{
pulse_dly=0;
while(i!=pulse_dly);
}
第一点
delay(1);
这句是1至1000个机械周期都有可能,执行pulse_dly=0;后没有设定TH0及TL0,这是0至-----1000都有可能的。
delay(3);
便会延时2000至3000机械周期都有可能。
第二点
在中断void serial() interrupt 4内执行delay();这样wdat(a);内又有delay();中断内太长延时并没有离开interrupt,若在运行这interrupt内的delay 时有串口数入便死机,
中断不应有delay(),中断内尽量小东西时长要小。