mediaclassic 发表于 2014-6-21 21:46:27

求助:请各位大侠帮新新手看看这段小程序问题出在哪里?

求助:请各位大侠帮新新手看看这段小程序问题出在哪里。程序写的不好,各位大侠手下留情。
    我的想法是设定的时间到达后,定时器中断都关闭,然后控制继电器停止。现在的问题是时间到定时器停止,继电器不能自动停止,需要手动按停止才能停止,问题出在哪里,帮我看看,谢谢!


/********************************************************
*说明:48V潜水泵遥控控制器
*时间:2014-05-26
*接口参数:
*      四位共阳数码管:段位:P0.0-P0.7    位选:S1-P2.0,S2-P2.1,S3-P2.2,S4-P2.3
*      继电器:
*      遥控按键:解锁标志:P1.0;上锁标志:P1.3;铃声标志:P1.2;闪电标志:P1.1
**********************************************************/
#include        "AT89X52.h"
#include "intrins.h"//nop
#include <stdio.h>

#define RELOADVALH 0x3C
#define RELOADVALL 0xB0

#define uchar unsigned char
#define uint unsigned int

//定义按键
#define key1 P1_0   //遥控器上的解锁标志
#define key2 P1_1   //遥控器上的闪电标志
#define key3 P1_2   //遥控器上的铃声标志
#define key4 P1_3   //遥控器上的上锁标志
#define key5 P1_4   //如果48V的保险完好,通电就可以在P1.4上检测到高电平


uchar code code0[]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,0x80, 0x90};//将数码管0-9的段码定义到程序存储区里
uchar code code1[]={0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00, 0x10};//将数码管0-9带小数点的段码定义到程序存储区里

unsigned char minute = 00;
unsigned char second = 20;
unsigned char j=0;
static bit PowerTF=0;      //定义一个为变量,保存开启键是否按下
static bit StartoffTF=0;   //定义一个为变量,用于控制水泵的开启与停止
static bit KeyTF=0;      //定义一个位变量,用于防止按键一次按下多次响应

//函数声明
void delay_nms( uchar n );
unsigned char key_scan_duli(void);

void main()
{
        unsigned char i;
       
        //上电自检显示,4个带小数点显示的8,闪烁两次
        for (i=0;i<100;i++)
        {
                P0=code1; //带小数点的8字
                P2=0xFE;//P2.0选通
                delay_nms(5);
                P2=0xFD;//P2.1选通
                delay_nms(5);
                P2=0xFB;//P2.2选通
                delay_nms(5);
                P2=0xF7;//P2.3选通
                delay_nms(5);       
        }
       
        for (i=0;i<100;i++)                //消隐
        {
                P0= 0xFF;
                P2=0x00;//P2.0选通,不影响其它位
                delay_nms(10);
               
        }
       
        for (i=0;i<=100;i++)
        {
                P0=code1; //带小数点的8字
                P2=0xFE;//P2.0选通,
                delay_nms(5);
                P2=0xFD;//P2.1选通
                delay_nms(5);
                P2=0xFb;//P2.2选通
                delay_nms(5);
                P2=0xF7;//P2.3选通
                delay_nms(5);
        }
       
        for (i=0;i<=100;i++)                //消隐
        {
                P0=0XFF;
                P2=0x00;//P2.0选通,不影响其它位
                delay_nms(10);
               
        }
       
        IE=0;                //关闭所有中断
        TR0=0;                //停止定时器0
        TMOD= 0X01;                                //定时器0工作方式1,,16位定时器
        TH0= RELOADVALH;        //装定时器初值,定时50ms
        TH1= RELOADVALL;//
        //EA = 1;            //中断总控制位,允许中断
        //TR0=1;            //开启定时器0
        //ET0=1;            //允许T0中断
        P1=0xff;
       
        while(1)
        {
               
                P2=0xFE;//P2.0选通
                P0=code0[(second%10)];    //求余运算,秒个位显示
                delay_nms(3);
                P2=0xFD;//P2.1选通
                P0=code0[(second/10)];    //除法运算,秒十位显示
                delay_nms(3);
                P2=0xFB;//P2.2选通
                P0=code1[(minute%10)];    //求余运算,分钟个位显示
                delay_nms(3);
                P2=0xF7;//P2.3选通
                P0=code0[(minute/10)];    //除法运算,分钟十位显示
                delay_nms(3);       
                                               
    if(key2&!KeyTF)//遥控器上的闪电标志
               { delay_nms(10);   
                       if(key2)
                       {
                               KeyTF=1;                //用于防止按键一次按下多次响应
                           if(!PowerTF) PowerTF=1;
       }
                        }
   if(key4&!KeyTF)//遥控器上的上锁标志,用于启动与暂停
               { delay_nms(10);   
                       if(key4)
                       {
                               KeyTF=1;                //用于防止按键一次按下多次响应
                           if(PowerTF)
                                        StartoffTF=~StartoffTF;
       }
                        }

      if(!key2&!key4) KeyTF=0;                //都没有按下,按键标志清零
                       

      if(StartoffTF)//允许开启并且时间不为零
                                  {
                                                if ((second!=0)||(minute!=0))
                                                {
                                                        P3_4=0;    //开启水泵继电器
                                                  EA =1;    //中断总控制位,允许中断
                    TR0=1;   //开启定时器0
                    ET0=1;   //允许T0中断
                                          }
          }
                        if(!StartoffTF)
                                        {
                                                P3_4=1;    //关闭水泵继电器
                                                EA = 0;    //中断总控制位,禁止中断
                TR0=0;   //关闭定时器0
                ET0=0;   //不允许T0中断
          }       
   }//while
}//main

/********************************************************************
** 函数名:void delay_nms( uchar n )
** 说明:延时n 0 < n < 256,
** ??:??????????????, ????
**
********************************************************************/
void delay_nms( uchar n )
{
uchar i;
uchar j;
uchar t;
for( t = 0; t < n; t++ )
{
for( j = 0; j < 15; j ++ )
{
   for( i = 0; i < 21; i++ )
    {;}
}
}
}

/********************************************************************
** 函数名:void timer0(void) interrupt 1
** 说明:定时器T0的中断服务函数
** ??:??????????????, ????
**
********************************************************************/

void timer0_int(void) interrupt 1//
{
        ET0=0;    //T0中断控制位,禁止中断
        TR0=0;    //关闭T0
        TH0= RELOADVALH;        //装定时器初值,定时50ms
        TH1= RELOADVALL;
        TR0=1;   //开启T0
        //P3_0=~P3_0;
        j=j+1;
        if (j>3)    //如果不够20次跳出中断函数,50ms×20=1000ms
             {
          j=0;    //重新赋初值
                                  if (second>0) second=second-1;    //减一秒
                                  else
                                                  {
                                                                //second=59;
                                                                if (minute>0)
                                                                        {       
                                                                                second=59;
                                                                                minute=minute-1;    //减一分
                                                                        }
                                                                else
                                                                        {
                     minute =0;
                                                                               if(second>0)
                                                                                       {ET0=1;}
                                                                               else
                                                                                       {
                                                                                               second=0; //
                                                                                               P3_4=1;    //关闭水泵继电器
                                                                                               EA = 0;    //中断总控制位,禁止中断
                               TR0=0;   //关闭定时器0
                               ET0=0;   //不允许T0中断
                                                                                                //StartoffTF = 0;//关闭水泵
                                                                                               
                      }
                                                                                       
                  }
            }
   
       }
       
}

devcang 发表于 2014-6-22 09:15:55

直接驱动继电器的吗。。。。。。没电路,很难判断问题。。。。。timer中断里面代码太多了。

mediaclassic 发表于 2014-6-22 10:12:40

继电器的驱动部分

mediaclassic 发表于 2014-6-24 15:19:58

怎么没人知道吗?
页: [1]
查看完整版本: 求助:请各位大侠帮新新手看看这段小程序问题出在哪里?