STC15W 单片机及编程的一些问题

2019-07-15 16:59发布

       AD采样的公式为   getadv=2.5*adhl2/adhl1; (其中adhl2是单片机采样电位器的AD转换结果,adhl1是外接2.5V基准源AD转换的结果)
     1、用KEIL软件运行仿真了一下,为什么程序执行到getadv=2.5*adhl2/adhl1;语句后,getadv的值为-1,理论上应该是getadv=0的(因为此时AD转换器还没开始工作,adhl2/adhl1都该为0x0000),                                                                       当我根据 if(x<=getadv<y)判断调光函数里时,,程序不进入到if(0<=getadv<0.3){},而是进入到了if(0.3<=getadv<0.6){;;;;}及以后的所有if()函数语句。。。(定义如下:uint adhl1,adhl2;  float getadv;




    2、当定义uchar getadv时,软件运行仿真程序执行到getadv=2.5*adhl2/adhl1;语句后,getadv的值为255,,,,,
当我根据 if(x<=getadv<y)判断调光函数里时,,程序进入到了if(0.9<=getadv<1.2){;;;;}及以后的所有if()函数语句。。。

编译什么无错误 但是软件运行有点毛病,不知道那个地方出了点问题。。。求赐教!!!很怀疑是不是这些小数无法被系统识别。。。求帮忙!!!!!!先谢谢了。。程序如下:


  1. #ifndef        __STC15W_H
  2. #define        __STC15W_H

  3. #define ADC_POWER        0x80
  4. #define ADC_FLAG        0x10
  5. #define ADC_START        0x08
  6. #define ADC_SPEEDHH        0x60//90T

  7. sfr P1M1=0x91;
  8. sfr P1M0=0x92;
  9. sfr P1ASF=0x9d;
  10. sfr ADC_CONTR=0xbc;
  11. sfr ADC_RES=0xbd;
  12. sfr ADC_RESL=0xbe;

  13. sfr CMOD=0xD9;
  14. sfr CCON=0xD8;
  15. sfr PCA_PWM0=0xf2;
  16. sfr CCAPM0=0xDA;
  17. sfr CL=0xE9;
  18. sfr CH=0xF9;
  19. sfr CCAP0L=0xEA;
  20. sfr CCAP0H=0xFA;
  21. sbit CR=0xDE;
  22. sbit EADC=0xad;

  23. #endif



  24. /****内部时钟6MHZ  PWM的频率为6000/12/256=1.953125KHZ 周期512us ************/
  25. //注意:在更新重装值时,必须先写高两位PWMn_B9H,PWMn_B8H,后写低八位CCAPnH
  26. //所有与PWM相关的端口,在上电后均为高阻输入态,必须在程序中将这些口设置为双向口或强推挽模式才可正常输出波形
  27. #include<reg51.h>
  28. #include<STC15W.h>
  29. #include<intrins.h>
  30. #define uchar unsigned char
  31. #define uint unsigned int
  32. uchar ch=3;//AD转换通道3
  33. uint adhl1,adhl2;
  34. float getadv;//AD采样的最终电压值0-2.5V
  35. unsigned char code PWM[8]={0xff,0xe2,0xba,0x96,0x80,0x62,0x49,0x00};//设置PWM占空比数组; 当CCAP0H的值为255时,理论上占空比应该为0
  36. //占空比分别为0%、11.765%、27.45%、41.57%、50.20%、61.96%、71.75%、100%
  37. void delay1ms()                //@6.000MHz
  38. {
  39.         unsigned char i, j;
  40.         i = 6;
  41.     j = 211;
  42.         do
  43.         {
  44.                 while (--j);
  45.         } while (--i);
  46. }

  47. void InitADC()//定时10个毫秒或者5个毫秒做一次ADC,根本不影响!待确定******
  48. {
  49.         P1M1=0x18;
  50.     P1M0=0x00;//设置P1_3,P1_4仅为输入模式
  51.         P1ASF=0x18;//设置P1_3,P1_4为AD模拟口
  52.         EA=1; EADC=1;
  53.         ADC_RES=0;//清除结果寄存器
  54.         ADC_RESL=0;
  55.         ADC_CONTR=ADC_POWER|ADC_SPEEDHH|ADC_START|ch;
  56.         delay1ms();//延时,ADC上电稳定
  57. }
  58. void pwm_init()
  59. {        
  60.     CL=0x00;
  61.     CH=0x00;
  62.         //CR=1;//时才启动PCA定时器,CL与CCAP0L开始比较
  63. }

  64. void pwm_set(unsigned char a)
  65. {        
  66.         CCAP0L= a; //设置值直接写入CCAP0L
  67.     CCAP0H= a; //设置值直接写入CCAP0H
  68.         CR=1;//计数器阵列运行控制位
  69. }

  70. void adc_it() interrupt 5
  71. {
  72.         ADC_CONTR&=!ADC_FLAG;
  73.         if(ch==3)   adhl1=(ADC_RES*4+ADC_RESL);//读取10位通道3的AD转换结果
  74.         else
  75.         adhl2=(ADC_RES*4+ADC_RESL);//读取10位通道4的AD转换结果
  76.         ch++;
  77.         if(ch>=5) ch=3;
  78.         ADC_RES=0;ADC_RESL=0;
  79.         ADC_CONTR=ADC_POWER|ADC_SPEEDHH|ADC_START|ch;
  80. }
  81. void main()
  82. {
  83.         InitADC();
  84.         pwm_init();
  85.         P1M1&=0xfd;
  86.         P1M0|=0x02;//PWM的P1_1为推免输出
  87.         CMOD=0x00; //PCA计数脉冲源12分频,无中断使能
  88.         CCAPM0=0x42;//使能PCA的PWM模式,PWM0设置PCA工作方式为PWM方式,无PCA中断
  89.         PCA_PWM0=0x00;//PCA模块0的PWM工作于8位PWM, 与CCAP0L组成的EPC0L设置为0,EPC0H为0
  90.         //AUXR1=0x00; //CCP默认在P12,P11,P10,P37脚
  91.         //pwm_set(0xff);//设置PWM占空比为0,全低电平。。。NMOS管不导通
  92.         while(1)
  93.         {
  94.                 getadv=2.5*adhl2*0.5/adhl1;        //*0.5软件处理把采样电压减半为满电压时2.5V;仿真时上来就是getadv=0xffff????
  95.                 delay1ms();
  96.                 if(0<=getadv<0.3)//无法使用switch(ADget)
  97.                 {
  98.                         pwm_init();
  99.                         pwm_set(PWM[0]);//设置PWM占空比为0,全低电平,NMOS管不导通。或者这样设置PWM全低电平:pwm_set(PWM[0]);PCA_PWM0|=0x02;
  100.                         //需不需要delay();
  101.                 }
  102.                 if(0.3<=getadv<0.6)
  103.                 {
  104.                         pwm_init();
  105.                         pwm_set(PWM[1]);
  106.                         //需不需要delay();
  107.                 }
  108.                 if(0.6<=getadv<0.9)
  109.                 {
  110.                         pwm_init();
  111.                         pwm_set(PWM[2]);
  112.                 }
  113.                 if(0.9<=getadv<1.2)//仿真时上来就是getadv=0xff或者-1????
  114.                 {
  115.                         pwm_init();
  116.                         pwm_set(PWM[3]);
  117.                 }
  118.                 if(1.2<=getadv<1.5)
  119.                 {
  120.                         pwm_init();
  121.                         pwm_set(PWM[4]);
  122.                 }
  123.                 if(1.5<=getadv<1.8)
  124.                 {
  125.                         pwm_init();
  126.                         pwm_set(PWM[5]);
  127.                 }
  128.                 if(1.8<=getadv<2.1)
  129.                 {
  130.                         pwm_init();
  131.                         pwm_set(PWM[6]);
  132.                 }
  133.                 if(2.1<=getadv<=2.5)
  134.                 {
  135.                         pwm_init();
  136.                         pwm_set(PWM[7]);
  137.                 }         
  138.         }
  139. }
复制代码


            





友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。