搜索
bottom↓
回复: 2

关于红外遥控密码锁的问题

[复制链接]

出0入0汤圆

发表于 2013-5-1 00:49:34 | 显示全部楼层 |阅读模式
把程序下载到了单片机里面,但是接收部分毫无反应,希望各位指出代码那里出问题了!!!!!!!
发射模块代码
#include <stc89.h>
//13.37589
#define uchar unsigned char
#define uint unsigned int
sbit led=P3^7;
sbit out=P3^6;
#define port P2
//定义地址码
#define addr0  0x01
#define addr1  0x02
bit key_bit;  //按键重复标记
bit hw;
bit over;
bit ss;
uchar time;
void delay();
void InitTimer0(void);
void InitUART(void);
void send(uchar c);
uchar key();
void send_star();
void send_char(uchar c);
void send_hw(uchar c);
void delay1s(void)   //误差 -0.000000000003us
{
    unsigned char a,b,c;
    for(c=45;c>0;c--)
        for(b=132;b>0;b--)
            for(a=167;a>0;a--);
}
void delay()   //1ms 误差 -0.651041666667us
{
    unsigned char a,b;

    for(b=102;b>0;b--)
        for(a=3;a>0;a--);
}
void InitTimer0(void)
{
    TMOD = 0x22;
    TH0 = 0xe6;
    TL0 = 0xe6;
    EA = 1;
    ET0 = 1;
    TR0 = 1;
}                   //13us
void InitUART(void)        //4800
{
//    TMOD = 0x20;
    SCON = 0x50;  //采用串口工作方式1(8位异步收发,波特率可变);允许串行口接收数据
    TH1 = 0xF3;
    TL1 = TH1;
    PCON = 0x00;
    ES = 1;
        TR1 = 1;
}
void send(uchar c)
{
    SBUF = c;
    while(!TI);//一直发送数据,直至发送完毕
    TI = 0;
}
uchar key()
{
uchar a;
a=0;
port=0x0f;
a=port;

if(a==0x0f)
   {
     key_bit=1;  
         delay();
         return 0;
   }
if(!key_bit) return 0;
delay();
if(port==a)         
{       
  port=0xf0;
  a|=port;
  a=~a;
}
else return 0;
if(a)
{
  key_bit=0;
  switch(a)
  {
   case 0x11:  return 1;
   case 0x12:  return 2;
   case 0x14:  return 3;
   case 0x18:  return 4;
   case 0x21:  return 5;
   case 0x22:  return 6;
   case 0x24:  return 7;
   case 0x28:  return 8;
   case 0x41:  return 9;
   case 0x42:  return 10;
   case 0x44:  return 11;
   case 0x48:  return 12;
   case 0x81:  return 13;
   case 0x82:  return 14;
   case 0x84:  return 15;
   case 0x88:  return 16;
   default: return 0;
  }
}// if(a)
}

void main(void)
{
    uchar c;
        InitTimer0();
        InitUART();
        led=0;
        send(0xaa);        //为了测试串口是否正常工作
while(1)
{
c=key();
if(c)
  {
    send(c);
        send_hw(c);
  }


}
}
void send_star()
{
uchar i;
i=8;
/*9ms内发射38KHZ方波*/
while(i--)
{
  time=173;                 //9ms
  hw=1;                         //发射
  while(!over);
}
/*4.5ms内发射高电平*/
i=4;
while(i--)                 //4.5ms
{         
  time=173;
  hw=0;
  while(!over);         
}
}
void send_char(uchar c)
{
uchar i;
for(i=0;i<8;i++)
{
  time=45;
  hw=1;                   //0.565ms的38KHZ方波
  while(!over);
  
  if(c&0x80) time=126; //1.685ms的间隔
  else time=45;         //0.565ms的间隔
  hw=0;
  c=c<<1;
  while(!over);
  time=45;
  hw=1;
   
}
}
void send_hw(uchar c)
{
key_bit=0;
send_star();
send_char(addr0);
send_char(addr1);
send_char(c);
send_char(~c);

}
void Timer0Interrupt(void) interrupt 1
{
if(time) time--,over=0;
else over=1,hw=0;
if(hw) out=~out;
else out=1;
}
void UARTInterrupt(void) interrupt 4
{
uchar c;
    if(RI)
    {
        RI = 0;                //接收中断标志位;RI=1,表示数据接收完毕,并申请中断,要求CPU从接收SBUF提走数据,
    }
    else
        TI = 0; //发送中断标志位;TI=1,表示一帧数据发送结束;TI必须由软件清零
}


接收模块代码
#include <stc89.h>
#define uchar unsigned char
#define uint unsigned int
sbit rs=P2^0;//数据命令选择端
sbit rw=P2^1;//读写选择端
sbit e=P2^2;//使能端
#define port P0//lcd数据
sbit beep=P1^0;//蜂鸣器
sbit led=P1^1;//开锁指示灯
uchar buffer[4];
uchar n;
uchar dat;
uchar js;//解锁
bit ks; //开锁
uchar wrong;
uchar bp;  //蜂鸣器时间控制
uchar mima[17];                          //已设定密码
uchar mima_temp[17];          //当前输入密码
uchar mima1[17];                  //改密码用
uchar mmxg;   //密码修改控制
uchar asc[16]="01234567890ABCDEF";
void show(uchar c);
void lcd_wr(uchar a,uchar c);
void delay(uchar c);
void send(uchar c);
void IAP_Disable();
void eeprom_wr();
void eeprom_re();
void delay(uchar c)   //1ms  误差 -0.651041666667us          
{
    unsigned char a,b;
  while(c--)
  {
    for(b=102;b>0;b--)
        for(a=3;a>0;a--);
  }
}
void InitUART(void)         //9600串口初始化
{
    TMOD = 0x21;
    SCON = 0x50;
    TH1 = 0xFD;
    TL1 = TH1;
    PCON = 0x00;
    EA = 1;
    ES = 1;
    TR1 = 1;
}
uchar lcd_re(uchar a)
{
uchar c;
e=0;
rw=1;
rs=a;
;
;
e=1;
;
;
e=0;
c=port;
return c;
}
void busy()
{
uchar i;
i=1;
while((lcd_re(0)&0x80)&&i++);
}
void lcd_wr(uchar a,uchar c)
{
busy();
e=0;
rw=0;
rs=a;
port=c;
;
;
e=1;
;
;
e=0;
}
/**************初始化**************/
void lcd_int(void)
{
delay(15);
rs=0;
rw=0;
port=0x38;
e=1;
;
;
e=0;
delay(5);
port=0x38;
e=1;
;
;
e=0;
delay(5);
port=0x38;
e=1;
;
;
e=0;
rw=1;
rs=1;
lcd_wr(0,0x38); //显示模式设置
lcd_wr(0,0x08); //关闭显示
lcd_wr(0,0x01); //清屏
lcd_wr(0,0x02);
lcd_wr(0,0x06); //光标又移,整屏不移动
lcd_wr(0,0x0c); //开显示
}
//mm:ss:s
void show(uchar c)
{
uchar i;
lcd_wr(0,0x80);//地址为第一行第一个字符
lcd_wr(1,'E');
lcd_wr(1,'n');
lcd_wr(1,'t');
lcd_wr(1,'e');
lcd_wr(1,'r');
lcd_wr(1,' ');
lcd_wr(1,'P');
lcd_wr(1,'a');
lcd_wr(1,'s');
lcd_wr(1,'s');
lcd_wr(1,'W');
lcd_wr(1,'o');
lcd_wr(1,'r');
lcd_wr(1,'d');
lcd_wr(1,' ');
if(mmxg==1) lcd_wr(1,'1');
else if(mmxg==2) lcd_wr(1,'2');
else lcd_wr(1,' ');
lcd_wr(0,0xc0);//o代表指令,1代表数据//地址为第二行第一个字符
if(c<17)//c输入密码个数
{
  for(i=0;i<c;i++)
  lcd_wr(1,'*');
}
else
{
  if(c==110)                //show PassWord        Right
  {
  lcd_wr(1,'P');
  lcd_wr(1,'a');
  lcd_wr(1,'s');
  lcd_wr(1,'s');
  lcd_wr(1,'W');
  lcd_wr(1,'o');
  lcd_wr(1,'r');
  lcd_wr(1,'d');
  lcd_wr(1,' ');
  lcd_wr(1,'R');          //Ringht
  lcd_wr(1,'i');
  lcd_wr(1,'g');
  lcd_wr(1,'h');
  lcd_wr(1,'t');
  lcd_wr(1,'!');
  }
  if(c==119)
  {
  lcd_wr(1,'P');
  lcd_wr(1,'a');
  lcd_wr(1,'s');
  lcd_wr(1,'s');
  lcd_wr(1,'W');
  lcd_wr(1,'o');
  lcd_wr(1,'r');
  lcd_wr(1,'d');
  lcd_wr(1,' ');
  lcd_wr(1,'W');   //wrong
  lcd_wr(1,'r');
  lcd_wr(1,'o');
  lcd_wr(1,'n');
  lcd_wr(1,'g');
  lcd_wr(1,'!');
  }
}
for(i=0;i<16;i++)                 //写空格,防止显示重叠
  lcd_wr(1,' ');
lcd_wr(0,0x0c); //开显示

}
uchar mmyz()//密码验证
{
uchar j;
for(j=0;j<17;j++)
{
  send(mima_temp[j]);
  send(mima[j]);
}
if(mima_temp[16]==mima[16])
{
  for(j=0;j<mima[16];j++)
  if(mima_temp[j]!=mima[j])        return 2;  //密码错误退出
  wrong=0;
  return 1;
}
else return 2;
}
main()
{
uchar i,j;
uchar k,s;
eeprom_re();
if(mima[16]>16)
{
  for(j=0;j<17;j++)
  mima[j]=6;
}
lcd_int();
InitUART();   //串口初始化
ET0=1;
EX1=1;  //开外部中断1   
IT1=1;  //下隆沿中断
show(0);
while(1)
{
  if(js)
  {
   js=0;
   if(buffer[2]<13)
   {
    if(i<16)
        {
         mima_temp[i]=buffer[2];
         i++;
            show(i);
        }
   }
   else
   {
    if(buffer[2]==13&&i)  i--,show(i);       //退格
        if(buffer[2]==14)
        {
         if(ks) ks=0;
         i=0,show(i);                  //清屏
    }
        if(buffer[2]==15&&ks)          //修改密码
          {
            mmxg=1;
                i=0;
                show(i);
          }
        if(buffer[2]==16)                    //确定
        {
         i=0;
         if(mmxg)                  //密码修改
         {
          if(mmxg==2)
          {
           s=0;
           if(mima1[16]==mima_temp[16])
           {
            s++;
            for(j=0;j<mima_temp[16];j++)
                {
             if(mima1[j]==mima_temp[j])
                 {
                  s++;
                 }
            }
           }
           mmxg=0;
           if(s>mima1[16])
           {
                for(j=0;j<17;j++)
                {
                 mima[j]=mima1[j];
//                 send(mima[j]);
                }
                show(110);
                eeprom_wr();
           }
           else show(119);
          }
          if(mmxg==1)
          {  
            for(j=0;j<17;j++)
            mima1[j]=mima_temp[j];
                mmxg=2;
            show(i);
          }          
         }
         else  k=mmyz();
        }
   }
   mima_temp[16]=i;                                         //密码长度
//  send(buffer[2]);
//  send(mima_temp[16]);
  }
  if(k==1) ks=1,show(110);
  if(k==2) ks=0,show(119),wrong++;
  k=0;
  if(ks) led=0;
  else led=1;
  if(wrong>2) wrong=0,bp=100;
}
}                                               
/************外部中断1**********************/
void Int1(void) interrupt 2  using 1
{
uchar dh;
uchar k;
TR0=0;
dh=TH0;
TL0=0;
TH0=0;
TR0=1;
if(dh>25&&dh<100) n=33;
else if(dh>2&&dh<5) k=0;
else if(dh>6&&dh<12) k=1;
else n=0;
if(n)  
  {
   dat=dat<<1;
   dat+=k;
   if(n==25) buffer[0]=dat,dat=0;
   if(n==17) buffer[1]=dat,dat=0;
   if(n==9) buffer[2]=dat,dat=0;
   if(n==1) buffer[3]=dat,dat=0;
   n--;
        if(!n)
    {
          if(!(buffer[2]&buffer[3]))  //数据校验
            {
              js=1;  //接收完成
                  beep=0;
                 }
          else
            {
                  buffer[0]=0;
                  buffer[1]=0;
                 }
         }
  }
//  send(dh);
}
/************定时器0**********************/

void Timer0Interrupt(void) interrupt 1
{
TR0=1;
n=0;
if(bp) bp--,beep=0;
else beep=1;
}
/************串口**********************/
void send(uchar c)
{
   EA=0;
    SBUF = c;
    while(!TI);
    TI = 0;   
   EA=1;
}
void delay1s(void)   //误差 -0.000000000285us
{
    unsigned char a,b,c;
    for(c=13;c>0;c--)
        for(b=247;b>0;b--)
            for(a=142;a>0;a--);

}
void UARTInterrupt(void) interrupt 4
{
uchar c;
    if(RI)
    {
        RI = 0;
        c=SBUF;
                if(c==0xaa)
                {
                 delay1s();
                 ISP_CONTR=0x60;
                }
    }
    else
        TI = 0;
}
//******************************EEPROM***********************************//
void IAP_Disable()
{
    //关闭IAP 功能, 清相关的特殊功能寄存器,使CPU 处于安全状态,
    //一次连续的IAP 操作完成之后建议关闭IAP 功能,不需要每次都关
    ISP_CONTR = 0;      //关闭IAP 功能
    ISP_CMD   = 0;      //清命令寄存器,使命令寄存器无命令,此句可不用
    ISP_TRIG  = 0;      //清命令触发寄存器,使命令触发寄存器无触发,此句可不用
    ISP_ADDRH = 0;
    ISP_ADDRL = 0;
}
void eeprom_wr()
{
uchar  *p;
uchar i;
p=mima;
ISP_CONTR=0x82;  //启动IAP
ISP_CMD=0x03; //        擦除
ISP_ADDRH=0x20;  //地址
ISP_ADDRL=1;
EA=0;
ISP_TRIG=0x46;   //命令生效
ISP_TRIG=0xb9;
;
EA=1;
ISP_CMD=0x02;           //命令写
for(i=0;i<17;i++)
{
  ISP_DATA=*p;   //数据
  p++;
  ISP_ADDRH=0x20;  //地址
  ISP_ADDRL=i;
  EA=0;
  ISP_TRIG=0x46;   //命令生效
  ISP_TRIG=0xb9;
  ;
  EA=1;   
}
IAP_Disable();
}
void eeprom_re()
{
uchar *p;
uchar i;
p=mima;
ISP_CONTR=0x82;  //启动IAP
ISP_CMD=0x01;           //命令读
for(i=0;i<17;i++)
{
  ISP_ADDRH=0x20;  //地址
  ISP_ADDRL=i;

  ISP_TRIG=0x46;   //命令生效
  ISP_TRIG=0xb9;
  ;
  *p=ISP_DATA;
  p++;
  }
  IAP_Disable();
}

阿莫论坛20周年了!感谢大家的支持与爱护!!

知道什么是神吗?其实神本来也是人,只不过神做了人做不到的事情 所以才成了神。 (头文字D, 杜汶泽)

出0入0汤圆

发表于 2013-5-1 14:02:59 | 显示全部楼层
你对应的硬件正确吗?

出0入0汤圆

 楼主| 发表于 2013-5-1 14:56:39 | 显示全部楼层
lxa0 发表于 2013-5-1 14:02
你对应的硬件正确吗?

我是照着原理图焊的,应该是没有问题。
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片。注意:要连续压缩2次才能满足要求!!】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-7-23 16:14

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表