OpenVINOTM,给你看得见的未来!>>
电子产品世界 » 论坛首页 » 嵌入式开发 » MCU » 测周法测方波频率,数据测出来了就是结合串口发不出去,求大神放马过来

共7条 1/1 1 跳转至

测周法测方波频率,数据测出来了就是结合串口发不出去,求大神放马过来

菜鸟
2014-03-12 21:20:00    评分

测周法测方波频率,用AT89S52单片机的外部中断0输入待测信号,定时器T0产生标准信号,外部中断输入信号(即待测信号)两个下跳沿分别控制定时器TO的开和关,这样即测得待测信号包含多少个标准信号,乘以标准信号周期取倒数即待测频率。不过现在数据测量出来了,就是想用串口与上位机串口通信,数据发不过去,或者发过去一直是00 00 00 00 00 00 00 00(八组00)程序如下:

 

#include <reg52.h>
#define uint unsigned int
#define uchar unsigned char
#define ulong unsigned long int
//#define CHU 100 

sbit lcden=P3^1; //1602使能端
sbit lcdrs=P2^7;  //命令、数据端
sbit RW=P2^6;   //读写控制端

uchar i=0;  //外部中断0下调沿次数,定时功能
ulong t=0;  // T0定时模式软件计数
ulong num;  //暂存1S计数次数中间变量
uchar n;  //固定显示字符个数
ulong a,b,c,d; //个位,十位,百位
uint e,g;

uchar code table[]="maibo cishu :"; //第一排固定显示
uchar code table1[]=" ci/min"; //第二排固定单位显示
uchar code table2[]={0x30,0x31,0x32,0x33,0x34,0x35,0x36,0x37,0x38,0x39}; //1602调用0到9数字库


void delay(uint z)  // 1ms延时
{
 uint a;
 for(z;z>0;z--)
  for(a=110;a>0;a--); 
}
 
void write_com(uchar com) // 1602写命令
{
 lcdrs=0;
 P0=com;
 RW=0;
 delay(5);
 lcden=1;
 delay(5);
 lcden=0;
}
void write_data(uchar date)   // 1602写数据
{
 lcdrs=1;
 P0=date;
 RW=0;
 delay(5);
 lcden=1;
 delay(5);
 lcden=0;
}
void init()    // 1602初始化
{
 lcden=0;
 write_com(0x38);   //功能设定,4/8位数据等
 write_com(0x0e);   //显示状态开/关
 write_com(0x06); //设置光标
 write_com(0x01); //清屏
 write_com(0x80); //显示位址 第一行:80H-A7H  第二行:C0H-E7H
}

void display(ulong n)
 {
   a=n%10;     //个位
   b=n/10%10;    //十位
         c=n/100%10;    //百位
   d=n/1000%10;    //千位

       write_com(0xc6);    //第二行第六个显示块
    write_data(table2[d]);
    delay(2);
   
    write_com(0xc7);    //第二行第六个显示块
    write_data(table2[c]);
    delay(2);

//   if(c==0)    //百位为0不显示
//   {
//    write_com(0xc5);  //第二行第六个显示块
//    write_data(0x20);
//    delay(20); 
//   }

    write_com(0xc8);    //第二行第七个显示块
    write_data(table2[b]);
    delay(2);
   
//    if(c==0&&b==0)    //十位为0不显示
//   {
//    write_com(0xc6);  //第二行第七个显示块
//    write_data(0x20);
//    delay(20); 
//   }

     
       write_com(0xc9);  //第二行第八个显示块
    write_data(table2[a]);
    delay(2);
}

 

void main()
{
//   PS=1;
   SCON=0x50;      //串口模式1,允许接收;SM0 SM1 = 01;  REN=1;
   PCON=0x00;      //波特率不倍增 SMOD=0;

 TMOD=0x21; //定时器T0设置为定时模式1,服务程序为软件计时

 ET0=0;
 TR0=0;
 TI=1;          //TI 置1,以发送第一个字节 
    TR1=1;         //启动定时器 T1

 TH0=(65536-5000)/256;
 TL0=(65536-5000)%256;
    TL1=0xfd;
    TH1=0xfd;      //波特率9600

 EX0=1;//开外部中断0
 IT0=1;//下降沿触发

// ES=1;
 EA=1;

 init();  // 1602初始化
   
 while(1)
  {

 if(e==1)
 { 
  display(num);
  e=0;
  ES=0;
  SBUF=g;   //向上位机传数据(此时为返回上位机发送的数据)
  while(!TI);
  ES=1;
  TI=0;    //软件清零TI,以准备发送下一帧数据
 }  
  }
 
}
void exr0() interrupt 0

     i++;     //来一个外部脉冲计一次数 
   if(i==1)
    { 
   TH0=(65536-5000)/256;
   TL0=(65536-5000)%256; //定时满一次的时间T=CHU*t机器
   ET0=1;    //开定时器T0
   TR0=1;

    }
   if(i==2)       // 取i-1个周期来计数内部脉冲
  {
   ET0=0;     //关定时器T0
   TR0=0;
      num=200000/t;  //频率=num=1000/t 1为测了1次周期,为了显示小数点后3位再乘以1000 即1000000
//      num=(40000000/10/t)*60/1000;  //f=num=4000/t 4为测了4次周期,为了显示小数点后3位再乘以1000 即4000000
   g=num;

    //显示频率
   i=0;
   e=1;
   t=0;    //计数器清零
   
  } 

}

void timer0() interrupt 1
{
  TH0=(65536-5000)/256;
  TL0=(65536-5000)%256; //定时满一次的时间T=CHU*t机器
  t++;     //定时满一次t加一
}




关键词: 单片机     测周法     串口通信     中断    

院士
2014-03-13 08:49:50    评分
2楼
妈呀,不明白啊

高工
2014-03-13 08:55:32    评分
3楼
一看就知道跟郭天祥学的51编程风格,,,问题交给楼下大侠处理啦,,

专家
2014-03-13 08:56:52    评分
4楼

1、查看下波特率设置的是否一致;

2、构建一个详细的错误指令集,何种错误对应何种指令,这样便于检查错误。

你上面写的都是测量的,对于串口发送没有涉及到。


专家
2014-03-13 08:56:55    评分
5楼
从返回的数据来看,楼主你的串口波特率设置错误了

专家
2014-03-13 09:16:50    评分
6楼
你的串口可以单独工作不?波特率设置的对不?晶振用多大的? 2、可以用1602现实测得结果,如果不能,还请看看定时器和中断那边的配置。 分步调试,再联调。

高工
2014-03-13 10:55:49    评分
7楼

1、串口波特率

2、串口通信的函数没见啊,检查一下是不是缓存错了。

建议撸主中断里面还是不要有计算。


共7条 1/1 1 跳转至

回复

匿名不能发帖!请先 [ 登陆 注册 ]