请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。
器件型号:TMS320F28379D 问题:如何为 CMPA 和 CMPB 事件生成中断? 没有选项可以同时选择 CMPA 和 CMPB 来为我的 ePWM 模块生成中断、这可以完成吗?
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
问题:如何为 CMPA 和 CMPB 事件生成中断? 没有选项可以同时选择 CMPA 和 CMPB 来为我的 ePWM 模块生成中断、这可以完成吗?
答案:
是的。 最有效的方法是使用两个 ePWM 模块、在这两个模块之间启用同步、并链接 CMPx 和 TBPRD 寄存器。
这允许两个 ePWM 模块生成相同的波形。 接下来、您可以设置第一个 EPWM 模块在 CMPA 上发生的中断、以及第二个 EPWM 模块在 CMPB 上发生的中断。
下面的示例展示了 ePWM1和 ePWM2实现这一目标。
// //包含的文件 // #include "driverlib.h" #include "device.h" #define ePWM_TIMER_TBPRD 1000 // 函数原型 // void initEPWM (uint32_t ePWM_base); __interrupt void epwm1ISR (void); __interrupt void epwm2ISR (void); // void Main (void)/ void / void / // //初始化设备时钟和外设 // device_init(); // //禁用引脚锁定并启用内部上拉。 // DEVICE_initGPIO(); // //初始化 PIE 并清除 PIE 寄存器。 禁用 CPU 中断。 // interrupt_initModule(); // //使用指向 shell 中断的指针初始化 PIE 矢量表 //服务例程(ISR)。 // interrupt_initVectorTable(); // //将中断服务例程分配给 ePWM 中断 // INTERRUPT_REGISTER (INT_EPWM1、epwm1ISR); INTERRUPT_REGISTER (INT_EPWM2、epwm2ISR); // //将 GPIO0/1、GPIO2/3配置为 ePWM1A/1B、ePWM2A/2B //引脚 // GPIO_setPadConfig (0、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_0_EPWM1A); GPIO_setPadConfig (1、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_1_EPWM1B); GPIO_setPadConfig (2、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_2_EPWM2A); GPIO_setPadConfig (3、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_3_EPWM2B); GPIO_setPadConfig (6、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_6_GPIO6); GPIO_setDirectionMode (6、GPIO_DIR_MODE_OUT); GPIO_setPadConfig (7、GPIO_PIN_TYPE_STD); GPIO_setPinConfig (GPIO_7_GPIO7); GPIO_setDirectionMode (7、GPIO_DIR_MODE_OUT); // //禁用同步(也冻结 PWM 的时钟) // SYSCTL_DisablePeripheral (SYSCTL_Periph_CLK_GTBCLKSYNC); SYSCTL_DisablePeripheral (SYSCTL_Periph_CLK_TBCLKSYNC); initEPWM (EPWM1_base); initEPWM (EPWM2_base); ePWM_setInterruptSource (EPWM1_base、ePWM_INT_TBCTR_U_CMPA); ePWM_setInterruptSource (EPWM2_base、ePWM_INT_TBCTR_U_CMPB); ePWM_setupEPWMLinks (EPWM2_base、ePWM_LINK_带有 ePWM_1、ePWM_LINK_COMP_A); ePWM_setupEPWMLinks (EPWM2_base、ePWM_LINK_带有 ePWM_1、ePWM_LINK_COMP_B); ePWM_setupEPWMLinks (EPWM2_base、ePWM_LINK_带有 ePWM_1、ePWM_LINK_TBPRD); ePWM_setSyncOutPulseMode (EPWM1_base、ePWM_SYNC_OUT_PULSE_ON_COUNTER_ZERO); ePWM_enablePhaseShiftLoad (EPWM2_base); // //启用到 PWM 的同步和时钟 // SYSCTL_enablePeripheral (SYSCTL_Periph_CLK_TBCLKSYNC); //启用 ePWM 中断 // INTERRUPT_ENABLE (INT_EPWM1); INTERRUPT_ENABLE (INT_EPWM2); // //启用全局中断(INTM)和实时中断(DBGM) // EINT; ERTM; // //空闲循环。 只需坐下来循环(可选): // for (;;) { ePWM_setCounterCompareValue (EPWM1_base、ePWM_COUNTER_COMPARE_A、400); ePWM_setCounterCompareValue (EPWM1_base、ePWM_COUNTER_COMPARE_B、800); SYSCTL_DELAY (20000); ePWM_setCounterCompareValue (EPWM1_base、ePWM_COUNTER_COMPARE_A、800); ePWM_setCounterCompareValue (EPWM1_base、ePWM_COUNTER_COMPARE_B、300); SYSCTL_DELAY (20000); } } // // epwm1ISR - ePWM 1 ISR // __interrupt void epwm1ISR (void) { GPIO_togglePin (6); // //清除此计时器的 INT 标志 // ePWM_clearEventTriggerInterruptFlag (EPWM1_BASE); // //确认中断组 // interrupt_clearACKGroup (interrupt_ACK_Group3); } // epwm2ISR - ePWM 2 ISR // _中断 void epwm2ISR (void) { GPIO_togglePin (7); // //清除此计时器的 INT 标志 // ePWM_clearEventTriggerInterruptFlag (EPWM2_base); // //确认中断组 // interrupt_clearACKGroup (interrupt_ACK_Group3); } void initEPWM (uint32_t ePWM_base) { // //设置 TBCLK // ePWM_setTimeBasePeriod (ePWM_base、ePWM_TIMER_TBPRD); ePWM_setPhaseShift (ePWM_base、0U); ePWM_setTimeBaseCounter (ePWM_base、0U); // //设置比较值 // ePWM_setCounterCompareValue (ePWM_base、 ePWM_COUNTER_COMPARE_A、 ePWM_TIMER_TBPRD/3); ePWM_setCounterCompareValue (ePWM_base、 ePWM_COUNTER_COMPARE_B、 ePWM_TIMER_TBPRD/2); // //设置计数器模式 // ePWM_setTimeBaseCounterMode (ePWM_base、ePWM_COUNTER_MODE_UP); ePWM_DisablePhaseShiftLoad (ePWM_base); ePWM_setClockPrescaler (ePWM_base、 ePWM_CLOCK 分频器_8、 ePWM_HSCLOCK_DEVIDER_1); // //设置隐藏 // ePWM_setCounterCompareShadowImage LoadMode (ePWM_base、 ePWM_COUNTER_COMPARE_A、 ePWM_COMP_LOAD_ON_CNTR_ZERO); ePWM_setCounterCompareShadowImage LoadMode (ePWM_base、 ePWM_COUNTER_COMPARE_B、 ePWM_COMP_LOAD_ON_CNTR_ZERO); // //设置操作 // ePWM_setActionQualifierAction (ePWM_base、 ePWM_AQ_OUTPUT A、 ePWM_AQ_OUTPUT 高电平、 ePWM_AQ_output_on_timebase_up_CMPA); ePWM_setActionQualifierAction (ePWM_base、 ePWM_AQ_OUTPUT A、 ePWM_AQ_OUTPUT 低电平、 ePWM_AQ_output_on_timebase_zero); ePWM_setActionQualifierAction (ePWM_base、 ePWM_AQ_OUTPUT _B、 ePWM_AQ_OUTPUT 高电平、 ePWM_AQ_output_on_timebase_up_CMPB); ePWM_setActionQualifierAction (ePWM_base、 ePWM_AQ_OUTPUT _B、 ePWM_AQ_OUTPUT 低电平、 ePWM_AQ_output_on_timebase_zero); // //中断,我们将在其中更改比较值 // ePWM_enableInterrupt (ePWM_base); ePWM_setInterruptEventCount (ePWM_base、1U); }
在 CMPx 的递增和递减计数时生成 EPWM 中断也可以执行同样的操作。 对代码进行少量更改、例如将 TB 模式更改为向上/向下、并且必须发生中断源事件。
上面的代码为 ePWM1和 ePWM2生成相同的波形。 两个模块的 TBPRD、CMPA 和 CMPB 被连接、因此、写入 ePWM1的 CMPA 也将对 ePWM2产生同样的影响。