找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1559|回复: 2
收起左侧

12单片机实物运行成功但是仿真失败,如何排查错误?

[复制链接]
ID:797434 发表于 2021-5-30 15:23 | 显示全部楼层 |阅读模式
原理图.png

MQ5可以用按键模拟输入量,程序有的,提点建议,感谢各位大佬

为什么12单片机实物可以显示,但是用到51的仿真上温度也读取不了了啊

单片机源程序如下:
  1. #include "intrins.h"
  2. #include "temp.h"        
  3. #include "lcd.h"
  4. #define FOSC    11059200L

  5. typedef unsigned char BYTE;
  6. typedef unsigned int WORD;
  7. idata unsigned char str1[]="T:";
  8. idata unsigned char str2[]="CO:";
  9. BYTE code smgduan[17]={0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
  10.                                         0x80,0x90,0x88,0x83,0xc6,0xa1,0x86,0x8e};//显示0~F的值
  11. /*12单片机基础寄存器负责产生pwm */
  12. sfr CCON        =   0xD8;           //PCA control register
  13. sbit CCF0       =   CCON^0;         //PCA module-0 interrupt flag
  14. sbit CCF1       =   CCON^1;         //PCA module-1 interrupt flag
  15. sbit CR         =   CCON^6;         //PCA timer run control bit
  16. sbit CF         =   CCON^7;         //PCA timer overflow flag
  17. sfr CMOD        =   0xD9;           //PCA mode register
  18. sfr CL          =   0xE9;           //PCA base timer LOW
  19. sfr CH          =   0xF9;           //PCA base timer HIGH
  20. sfr CCAPM0      =   0xDA;           //PCA module-0 mode register
  21. sfr CCAP0L      =   0xEA;           //PCA module-0 capture register LOW
  22. sfr CCAP0H      =   0xFA;           //PCA module-0 capture register HIGH
  23. sfr CCAPM1      =   0xDB;           //PCA module-1 mode register
  24. sfr CCAP1L      =   0xEB;           //PCA module-1 capture register LOW
  25. sfr CCAP1H      =   0xFB;           //PCA module-1 capture register HIGH
  26. sfr PCAPWM0     =   0xf2;
  27. sfr PCAPWM1     =   0xf3;
  28. /*12单片机基础寄存器负责数模转换*/
  29. sfr ADC_CONTR   =   0xBC;           //ADC control register
  30. sfr ADC_RES     =   0xBD;           //ADC high 8-bit result register
  31. sfr ADC_LOW2    =   0xBE;           //ADC low 2-bit result register
  32. sfr P1ASF       =   0x9D;           //P1 secondary function control register
  33. #define ADC_POWER   0x80            //ADC power control bit
  34. #define ADC_FLAG    0x10            //ADC complete flag
  35. #define ADC_START   0x08            //ADC start control bit
  36. #define ADC_SPEEDLL 0x00            //420 clocks
  37. #define ADC_SPEEDL  0x20            //280 clocks
  38. #define ADC_SPEEDH  0x40            //140 clocks
  39. #define ADC_SPEEDHH 0x60            //70 clocks

  40. sbit key0=P3^0;
  41. sbit key1=P3^1;
  42. sbit key3=P3^2;
  43. sbit key4=P3^3;
  44. sbit key5=P3^4;
  45. sbit key6=P3^5;
  46. sbit beep=P3^6;

  47. BYTE flag=0,flag2=0,ppm=0,c=230,cw=0;//轮回扫描
  48. int pwm_pid,temp_1;
  49. WORD yus=150,baoj=190;



  50. void Delay(WORD n)
  51. {
  52.     WORD x;

  53.     while (n--)
  54.     {
  55.         x = 50;
  56.         while (x--);
  57.     }
  58. }


  59. void pwm_init()//初始化12C5A60单片机pwm寄存器
  60. {
  61.         
  62.     CCON = 0;                       //Initial PCA control register
  63.                                     //PCA timer stop running
  64.                                     //Clear CF flag
  65.                                     //Clear all module interrupt flag
  66.     CL = 0;                         //Reset PCA base timer
  67.     CH = 0;
  68.     CMOD = 0x02;                    //Set PCA timer clock source as Fosc/2
  69.                                     //Disable PCA timer overflow interrupt
  70.     CCAP0H = CCAP0L = 0xff;         //PWM0 port output 50% duty cycle square wave
  71.     CCAPM0 = 0x42;                  //PCA module-0 work in 8-bit PWM mode and no PCA interrupt



  72.     CR = 1;                         //PCA timer start run
  73. }

  74. void pwm_set(WORD x)//调节pwm占空比
  75. {

  76.         CCAP0H=x; //设置比较值
  77.         CCAP0L=x;

  78. }

  79. /*----------------------------
  80. 数模转换获取通道1
  81. ----------------------------*/
  82. BYTE GetADCResult(BYTE ch)//获取adc数值这里使用P1.1引脚GetADCResult(1)
  83. {
  84.     ADC_CONTR = ADC_POWER | ADC_SPEEDLL | ch | ADC_START;
  85.     _nop_();                        //Must wait before inquiry
  86.     _nop_();
  87.     _nop_();
  88.     _nop_();
  89.     while (!(ADC_CONTR & ADC_FLAG));//Wait complete flag
  90.     ADC_CONTR &= ~ADC_FLAG;         //Close ADC

  91.     return ADC_RES;                 //Return ADC result
  92. }


  93. /*----------------------------
  94. 数模转换初始化
  95. ----------------------------*/
  96. void InitADC()
  97. {
  98.     P1ASF = 0x02;                   //Open 8 channels ADC function
  99.     ADC_RES = 0;                    //Clear previous result
  100.     ADC_CONTR = ADC_POWER | ADC_SPEEDLL;
  101.     Delay(2);                       //ADC power-on and delay
  102. }
  103. /*pid高级处理*/

  104. int Position_PID (int Encoder,int Target)   //差速PID控制器//这里Encoder=实际CO浓度,Target=预期CO浓度;
  105. {         
  106.          float Position_KP=1.75,Position_KI=0.26,Position_KD=0.012;
  107. //Position_KI=c*0.01;
  108.          static float Bias,Pwm,Integral_bias,Last_Bias;
  109.         if(Encoder<=5)
  110.                 Integral_bias=0;
  111.          Bias=Encoder-Target;                                  //计算偏差
  112.          Integral_bias+=Bias;                                         //求出偏差的积分
  113.          Pwm=Position_KP*Bias+Position_KI*Integral_bias+Position_KD*(Bias-Last_Bias);       //位置式PID控制器
  114.          Last_Bias=Bias;                                       //保存上一次偏差
  115.          return Pwm;                                           //返回PWM值
  116. }


  117. int datapros(int temp) //温度的计算
  118. {
  119.            float tp;  
  120.         if(temp< 0)                                //当温度值为负数
  121.           {
  122.           //   -
  123.                 //因为读取的温度是实际温度的补码,所以减1,再取反求出原码
  124.                 temp=temp-1;
  125.                 temp=~temp;
  126.                 tp=temp;
  127.                 temp=tp*0.0625*100+0.5;        
  128.                 //留两个小数点就*100,+0.5是四舍五入,因为C语言浮点数转换为整型的时候把小数点
  129.                 //后面的数自动去掉,不管是否大于0.5,而+0.5之后大于0.5的就是进1了,小于0.5的就
  130.                 //算加上0.5,还是在小数点后面。

  131.           }
  132.          else
  133.           {                        

  134.                 tp=temp;//因为数据处理有小数点所以将温度赋给一个浮点型变量
  135.                 //如果温度是正的那么,那么正数的原码就是补码它本身
  136.                 temp=tp*0.0625*100+0.5;        
  137.                 //留两个小数点就*100,+0.5是四舍五入,因为C语言浮点数转换为整型的时候把小数点
  138.                 //后面的数自动去掉,不管是否大于0.5,而+0.5之后大于0.5的就是进1了,小于0.5的就
  139.                 //算加上0.5,还是在小数点后面。
  140.         }
  141. return temp;
  142. }


  143. void main()
  144. {
  145.                 pwm_init();//初始化pwm
  146.                 InitADC();  
  147.                 Init_DS18B20();
  148.                 LcdInit();
  149.         beep=0;//初始化关闭蜂鸣器
  150.         LcdShowStr(0,0,str1);
  151.         LcdShowStr(0,1,str2);
  152.         DisplayOneChar(7,0,'C');
  153.         DisplayOneChar(15,0,'C');
  154.         Display_Ref_T(350);//预设温度
  155.         P2=~smgduan[0];
  156.         while (1)
  157.     {
  158.                                 ppm=GetADCResult(1);
  159.                                 pwm_pid=Position_PID(ppm-135,yus-150);//传入pid变量
  160.                         
  161.                                                                 if(pwm_pid>235)//限幅
  162.                                                 pwm_pid=235;
  163.                                         if(pwm_pid<1)//限幅
  164.                                                 pwm_pid=1;
  165.                                         pwm_set(pwm_pid);
  166.                                        
  167.                                        
  168.                                        
  169.                                        
  170.                                        
  171.                                        
  172.                                                         if(!key0)
  173.                                         {
  174.                                         Delay(100);                                       
  175.                                                 if(!key0)
  176.                                                 {
  177.                                                         cw--;
  178.                                                         while(!key0);
  179.                                         if(cw<1)
  180.                                                 cw=0;
  181.                                                 }
  182.                                        
  183.                                         }
  184.                                                 if(!key1)
  185.                                         {
  186.                                         Delay(100);                                       
  187.                                                 if(!key1)
  188.                                                 {
  189.                                                         cw++;
  190.                                                         while(!key1);
  191.                                         if(cw>9)
  192.                                                 cw=9;
  193.                                                 }
  194.                                        
  195.                                         }
  196.                                        
  197.                                 P2=~smgduan[cw];
  198.                                        

  199.                                                         if(!key3)
  200.                                         {
  201.                                         Delay(100);                                       
  202.                                                 if(!key3)
  203.                                                 {
  204.                                                         yus--;
  205.                                                         while(!key3);
  206.                                         if(yus<1)
  207.                                                 yus=0;
  208.                                                 }
  209.                                        
  210.                                         }
  211.                                                 if(!key4)
  212.                                         {
  213.                                         Delay(100);                                       
  214.                                                 if(!key4)
  215.                                                 {
  216.                                                         yus++;
  217.                                                         while(!key4);

  218.                                                 }
  219.                                        
  220.                                         }
  221.         

  222.                                                         if(!key5)
  223.                                         {
  224.                                         Delay(100);                                       
  225.                                                 if(!key5)
  226.                                                 {
  227.                                                         baoj--;
  228.                                                         while(!key5);
  229.                                         if(baoj<1)
  230.                                                 baoj=0;
  231.                                                 }
  232.                                        
  233.                                         }
  234.                                                 if(!key6)
  235.                                         {
  236.                                         Delay(100);                                       
  237.                                                 if(!key6)
  238.                                                 {
  239.                                                         baoj++;
  240.                                                         while(!key6);

  241.                                                 }
  242.                                        
  243.                                         }                                       
  244.                                        
  245.                                        
  246.                                        
  247.                                 if(flag==10)
  248.                                 {
  249.                                         if(temp_1>350||ppm>baoj)
  250.                                         {
  251.                                         beep=1;
  252.                                         }else
  253.                                         {
  254.                                         beep=0;
  255.                                         }
  256.                                 }
  257.                                 if(flag==20)
  258.                                 {
  259.                                 temp_1=datapros(Ds18b20ReadTemp())*0.1;
  260.                                 ppm=GetADCResult(1);
  261.                                        
  262.                                 }
  263.                                 if(flag2==10)
  264.                                 {
  265.                                         Delay(100);
  266.                                 Display_T(temp_1);//实时温度
  267.                                 Display_Pre_CO(yus);
  268.                                 Display_Warn_CO(baoj);
  269.                                         Delay(100);
  270.                                         if(245<ppm)
  271.                                                 ppm=240;

  272.                                 Display_CO(ppm);
  273.                                 }
  274.                                 
  275.                                 flag++;
  276.                                 if(flag==21)
  277.                                 {
  278.                                         flag=0;
  279.                                         flag2++;
  280.                                         if(flag2==20)
  281.                                         {
  282.                                         flag2=0;
  283.                                         }
  284.                                 }
  285.                                 
  286.     }
  287. }

复制代码
回复

使用道具 举报

ID:57657 发表于 2021-5-30 17:10 | 显示全部楼层
sfr定义的寄存器,都不支持仿真。
回复

使用道具 举报

ID:96682 发表于 2021-5-30 17:14 来自手机 | 显示全部楼层
仿真软件本就没有的模型谈何失败?
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

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