[LOOK] 关于PWM输出反向的LOOK应用

[复制链接]
 楼主| wang0225 发表于 2011-8-18 12:34 | 显示全部楼层 |阅读模式
本帖最后由 wang0225 于 2011-8-18 12:58 编辑
  1. /*
  2. 初始化设置:  时钟配置为 XTL12M_EN
  3.               CPU时钟频率为12MHz
  4.      外设时钟配置为PWM01_S : 外部 4~24MHz 晶振使能
  5.      外设时钟配置为PWM01_EN : 选上
  6.      GPIOB的多功能管教选择:PB.14 INT0,PB.15 INT1
  7.       端口模式:PB.10 输出 ,PB.14 输入,PB.15 输入
  8.       去抖使能:PB.14 和PB.15 选上
  9.         输出值:PB.10 低
  10.         PA.12选择多功能管脚选择PWM0
  11.             
  12. 主要完成功能:测试下新塘的的PWM的输出反向寄存器,刚开始按key2输出占空比位20%的1K的方波,按科key1输出占空比位80%的1K的方波。
  13.      按按键Key1可以通过示波器看到占空比位80%的1K的方波
  14.      按按键Key2可以通过示波器看到占空比位20%的1K的方波
  15.      为保证按键确实按下,添加一个蜂鸣器的任务。
  16. */
  17. #include "LOOK_Key_PWM.h"
  18. #define LOOK_H 0
  19. #if LOOK_H == 0
  20. #include "NUC1xx.h"
  21. #include "NUC1xxM051Seriescfg.h"
  22. #else
  23. #define __HAVE_GPIO
  24. #include <nuc120re3an.h>
  25. using namespace nuvoton;
  26. #endif
  27. flag_t Flag(0);
  28. class Keyboard_t : public interrupt_t {
  29. public:
  30. __INLINE__ Keyboard_t();
  31. protected:
  32. bool isr(int vector);
  33. void dsr(int vector, uintptr_t count);
  34. };
  35. // Keyboard_t 构造函数
  36. __INLINE__  Keyboard_t::Keyboard_t()
  37. {
  38. attach(EINT0_IRQn);
  39. attach(EINT1_IRQn);
  40. #if LOOK_H == 0
  41. GPIOBs.IEN.Regs = (1 << Pin15) | (1 << Pin14);   // 开启中断
  42. #else
  43. GPIOB.IEN(0)
  44.       .IF_EN15(1)
  45.    .IF_EN14(1); // 开启中断
  46. #endif
  47. vector_t::enable(EINT0_IRQn);
  48. vector_t::enable(EINT1_IRQn);
  49. }
  50. // Keyboard_t 中断服务例程
  51. bool Keyboard_t::isr(int vector)
  52. {
  53. #if LOOK_H == 0
  54. GPIOBs.ISRC.Regs = GPIOBs.ISRC.Regs;   // 清中断 flag
  55. #else
  56. //注意:下句被优化了
  57. // GPIOB.ISRC = GPIOB.ISRC;   // 清中断 flag
  58. //注意:下句不能被优化,特别注意()是建立缓存
  59. GPIOB.ISRC = GPIOB.ISRC();   // 清中断 flag
  60. #endif
  61. return true;
  62. }
  63. // Keyboard_t 中断滞后服务例程
  64. void Keyboard_t::dsr(int vector, uintptr_t count)
  65. {
  66. if (vector == EINT0_IRQn)//Key2
  67. {
  68.   Flag.do_set_bits(0b101);
  69. }
  70. else if (vector == EINT1_IRQn)//Key1
  71. {
  72.   Flag.do_set_bits(0b110);
  73. }
  74. }
  75. Keyboard_t Key;         // 创建Key对象
  76. // 任务类 task_LOOK_Key_PWM_t 的例程
  77. void task_LOOK_Key_PWM_t::routine()
  78. {
  79. // TODO: 在此编写 task_LOOK_PWM_t 例程的内容
  80. uint8_t PWM0_Duty_Cycle = 20;   //PWM初始化占空比为20
  81. //Enable PWM engine clock and reset PWM
  82.     #if LOOK_H == 0
  83.    SYSCLKs.CLKSEL1.Bits.TMR0_S = 0b000; //外部12M晶振
  84.    PWM0s.PPR.Bits.CP01 = 1;    //预分频  1
  85.    PWM0s.CSR.Bits.CSR0 = 0b100;   //分频系数 1
  86.    uint16_t u16Duty = 12000000/((1+1)*1*1000);//PWM 频率 1000HZ
  87.    PWM0s.CNR0.Regs = u16Duty-1;     //PWM 频率 = PWMxy_CLK/(prescale+1)*(clock divider)/(CNR+1);
  88.    PWM0s.CMR0.Regs = u16Duty*PWM0_Duty_Cycle/100-1; //占空比 = (CMR+1)/(CNR+1).
  89.    PWM0s.PCR.Bits.CH0MOD = 1;    //自动重载
  90.    PWM0s.POE.Bits.PWM0 = 1;    //PWM0输出使能
  91.   
  92.   #else
  93.   
  94.    SYSCLK.CLKSEL1().TMR0_S = tmrs_t::XTL12M; //外部12M晶振
  95.    PWMA.PPR().CP01 = 1;    //预分频  1
  96.    PWMA.CSR().CSR0 = 0b100;   //分频系数 1
  97.    uint16_t u16Duty = 12000000/((1+1)*1*1000);//PWM 频率 1000HZ
  98.    PWMA.CNR0 = u16Duty-1;     //PWM 频率 = PWMxy_CLK/(prescale+1)*(clock divider)/(CNR+1);
  99.    PWMA.CMR0 = u16Duty*PWM0_Duty_Cycle/100-1; //占空比 = (CMR+1)/(CNR+1).
  100.       PWMA.PCR()
  101.     .CH0MOD(1);    //自动重?
  102.    PWMA.POE().PWM0 = 1;    //PWM0输出使能
  103.    
  104.       
  105.   #endif
  106. while (true) {
  107.   // TODO: 在此编写 task_LOOK_PWM_t 例程的内容
  108.   int flag = Flag.wait(0b001, flag_t::ANY_CONSUME);
  109.      if(flag==0b001)
  110.     {
  111.   #if LOOK_H == 0
  112.    PWM0s.PCR.Bits.CH0INV = 0;    //反向关闭
  113.    PWM0s.PCR.Bits.CH0EN = 1;    // 使能PWM功能
  114.   #else
  115.   
  116.       PWMA.PCR()
  117.     .CH0INV(0)    //反向关闭
  118.    PWMA.PCR().CH0EN = 1;     // 使能PWM功能   
  119.   #endif
  120.     }
  121.     else{
  122.         #if LOOK_H == 0
  123.    PWM0s.PCR.Bits.CH0EN = 0;    // 禁止PWM功能
  124.   #else
  125.    PWMA.PCR().CH0EN = 0;     // 禁止PWM功能   
  126.   #endif
  127.    
  128.     }
  129. }
  130. }
  131. // 任务类 task_LOOK_Key_PWM1_t 的例程
  132. void task_LOOK_Key_PWM1_t::routine()
  133. {
  134. // TODO: 在此编写 task_LOOK_PWM_t 例程的内容
  135. uint8_t PWM0_Duty_Cycle = 20;   //PWM初始化占空比为20
  136.     #if LOOK_H == 0
  137.    SYSCLKs.CLKSEL1.Bits.TMR0_S = 0b000; //外部12M晶振
  138.    PWM0s.PPR.Bits.CP01 = 1;    //预分频  1
  139.    PWM0s.CSR.Bits.CSR0 = 0b100;   //分频系数 1
  140.    uint16_t u16Duty = 12000000/((1+1)*1*1000);//PWM 频率 1000HZ
  141.    PWM0s.CNR0.Regs = u16Duty-1;     //PWM 频率 = PWMxy_CLK/(prescale+1)*(clock divider)/(CNR+1);
  142.    PWM0s.CMR0.Regs = u16Duty*PWM0_Duty_Cycle/100-1; //占空比 = (CMR+1)/(CNR+1).
  143.    PWM0s.PCR.Bits.CH0MOD = 1;    //自动重载
  144.    PWM0s.POE.Bits.PWM0 = 1;    //PWM0输出使能
  145.   
  146.   #else
  147.   
  148.    SYSCLK.CLKSEL1().TMR0_S = tmrs_t::XTL12M; //外部12M晶振
  149.    PWMA.PPR().CP01 = 1;    //预分频  1
  150.    PWMA.CSR().CSR0 = 0b100;   //分频系数 1
  151.    uint16_t u16Duty = 12000000/((1+1)*1*1000);//PWM 频率 1000HZ
  152.    PWMA.CNR0 = u16Duty-1;     //PWM 频率 = PWMxy_CLK/(prescale+1)*(clock divider)/(CNR+1);
  153.    PWMA.CMR0 = u16Duty*PWM0_Duty_Cycle/100-1; //占空比 = (CMR+1)/(CNR+1).
  154.       PWMA.PCR()
  155.     .CH0MOD(1);    //自动重载
  156.    PWMA.POE().PWM0 = 1;    //PWM0输出使能
  157.       
  158.   #endif
  159. while (true) {
  160.   // TODO: 在此编写 task_LOOK_PWM_t 例程的内容
  161.   int flag = Flag.wait(0b010, flag_t::ANY_CONSUME);
  162.      if(flag==0b010)
  163.     {
  164.     #if LOOK_H == 0
  165.   PWM0s.PCR.Bits.CH0INV = 1;    //反向打开
  166.   PWM0s.PCR.Bits.CH0EN = 1;    // 使能PWM功能
  167. #else
  168.      PWMA.PCR()
  169.    .CH0INV(1)    //反向打开
  170.   PWMA.PCR().CH0EN = 1;     // 使能PWM功能   
  171. #endif
  172.     }
  173.     else{
  174.         #if LOOK_H == 0
  175.    PWM0s.PCR.Bits.CH0EN = 0;    // 禁止PWM功能
  176.   #else
  177.    PWMA.PCR().CH0EN = 0;     // 禁止PWM功能   
  178.   #endif
  179.    
  180.     }
  181. }
  182. }
  183. // 任务类 task_BEEP_t 的例程
  184. void task_BEEP_t::routine()
  185. {
  186. // TODO: 在此编写 task_BEEP_t 例程的内容
  187. while (true) {
  188.   // TODO: 在此编写 task_BEEP_t 例程的内容
  189.   int flag = Flag.wait(0b100, flag_t::ANY_CONSUME);
  190.   if (flag==4)
  191.   {   
  192.    for (uint32_t i = 0; i < 6; i ++){//蜂鸣器响三次
  193. #if LOOK_H == 0
  194.       GPIOBs.DOUT.Bits.Pin10 ^= 1;//蜂鸣器响PB10=1,不响PB10=0
  195. #else
  196.       GPIOB.DOUT().DOUT10 ^= 1;
  197. #endif
  198.            delay(LOOK_TICKS_PER_SEC / 20);//断续间隔
  199.    }
  200. #if LOOK_H == 0
  201.    GPIOBs.DOUT.Bits.Pin10 = 0;
  202. #else
  203.    GPIOB.DOUT().DOUT10(0);
  204. #endif
  205.   }
  206. }
  207. }
  208. #ifdef LOOK_SCHEDULING_PRIORITY
  209. instantiate::task<task_LOOK_Key_PWM_t, LOOK_STACK_SIZE> task_LOOK_Key_PWM(0);
  210. instantiate::task<task_LOOK_Key_PWM1_t, LOOK_STACK_SIZE> task_LOOK_Key_PWM1(1);
  211. instantiate::task<task_BEEP_t, LOOK_STACK_SIZE> task_BEEP(2);
  212. #else
  213. instantiate::task<task_LOOK_Key_PWM_t, LOOK_STACK_SIZE> task_LOOK_Key_PWM;
  214. instantiate::task<task_LOOK_Key_PWM1_t, LOOK_STACK_SIZE> task_LOOK_Key_PWM1;
  215. instantiate::task<task_BEEP_t, LOOK_STACK_SIZE> task_BEEP;
  216. #endif
照片晚点传上!:)

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册

×
hotpower 发表于 2011-8-18 12:41 | 显示全部楼层
非常好!!!
 楼主| wang0225 发表于 2011-8-19 11:33 | 显示全部楼层
地板啊;P
 楼主| wang0225 发表于 2011-8-19 20:26 | 显示全部楼层
再添一层!
您需要登录后才可以回帖 登录 | 注册

本版积分规则

0

主题

185

帖子

1

粉丝
快速回复 在线客服 返回列表 返回顶部

0

主题

185

帖子

1

粉丝
快速回复 在线客服 返回列表 返回顶部