微波EDA网,见证研发工程师的成长!
首页 > 研发问答 > 嵌入式设计讨论 > MCU和单片机设计讨论 > 遇到一个PWM波形问题,请教大神。

遇到一个PWM波形问题,请教大神。

时间:10-02 整理:3721RD 点击:

  1. ////////////////////////实现目标//////////////////////////////
  2. //单片机时钟频率12MHZ,T0做定时器使用,定时时长为0.1ms,要求用P1.0口输出周期为10ms,脉冲宽度按以下规律变化的信号:
  3. //第一个脉冲周期,P1.0引脚高电平持续时间为1*0.1ms;
  4. //第二个脉冲周期,P1.0引脚高电平持续时间为2*0.1ms;
  5. //第三个脉冲周期,P1.0引脚高电平持续时间为3*0.1ms;
  6. //第i个脉冲周期,P1.0引脚高电平持续时间为i*0.1ms(0=<i<=100).
  7. //即:占空比1%--100%  PWM
  8. ///////////////////////定时器初值/////////////////////////////////
  9. //单片机Fosc=12Mhz,T0的定时时长为0.1ms,        T0的计数次数为:
  10. //   n=(t*Fosc)/12=(0.1ms*12MHz)/12=100
  11. //
  12. //
  13. ////////////////////////////////////////////////////////////
  14. #include<reg52.h>
  15. #define uchar unsigned char
  16. #define out P1^0
  17. uchar PWM,count;
  18. void display(uchar);

  19. void init()
  20. {
  21.         TMOD=0X51;                         //T0:定时、方式1,
  22.         TH0=(65536-100)/256;
  23.         TL0=(65536-100)%256;
  24.         ET0=1;                             //开T0中断
  25.         EA=1;                              //开全局中断、
  26.         TR0=1;                             //启动定时器/计数器T0
  27. }

  28. void main()
  29. {   
  30.     //up=100-down;
  31.     //count=1;
  32.         init();                       
  33.         while(1)
  34.         {
  35. ?
  36.         }
  37. }
  38. void time0()  interrupt 1 using 1      //T0中断服务函数,中断型号为1
  39. {
  40.         TH0=(65536-100)/256;               //T0重置初值:0.1ms
  41.         TL0=(65536-100)%256;
  42.     count++;
  43.         if(count==101) count=1;
  44. }

  45. //一个周期分成100份,每份0.1ms;在一个周期中,高电平占有的分量不断增加。

复制代码


在程序中,写到如何循环一个周期卡壳了, 每个周期中有100次的10ms的波形,占空比1%——100%。  
在main()应如何写?

我觉得main不用写,直接用中断好了
每次增加1%占空比
unsingned char duty_cnt = 1;
unsingned char duty = 0;
void time0()  interrupt 1 using 1      //T0中断服务函数,中断型号为1
{
        TH0=(65536-100)/256;               //T0重置初值:0.1ms
        TL0=(65536-100)%256;

        duty++;
        if( duty == duty_cnt  )
        {
                //输出高电平
                duty = 0;
                duty_cnt ++;  //每次增加0.1ms
                if( duty_cnt ==101 )   
               {
                     duty_cnt =1;
                     duty = 0;
               }
        }
        else
        {
                //输出低电平
        }
}
以上代码随手写,可以实现,需要调试
另,用0.1ms的中断去做精度0.1ms的PWM,出来的波形可能有误差,用50us去做可能精度高一些
如果单片机带硬件PWM,使用硬件PWM会更好

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top