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.
大家好!
配置3个 ePWM 之间的相移以驱动3个升压功率级时遇到问题。
我希望每个 ePWM 具有120°相移(相位是输入用户)。 我将 EPWM1配置为主器件、将 EPWM2和 EPWM3配置为从器件。 但在我的示波器上、我看到每相60°、而不是120°。 请你解释一下。 为什么它不能正常工作?
谢谢。
void epwm_init(uint32_t base) { float PWM_TBPRD_1; float PWM_TBPRD_2; float PWM_TBPRD_3; float PWM_CMPA_1; float PWM_CMPA_2; float PWM_CMPA_3; EPWM_ClockDivider PWM_PARAM_PRESCALER; EPWM_HSClockDivider PWM_PARAM_HIGHSPEEDPRESCALER; float TBCLK; if(base == myEPWM1_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_1); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_B, (uint16_t)PWM_CMPA_1); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_enableSyncOutPulseSource(myEPWM1_BASE, EPWM_SYNC_OUT_PULSE_ON_CNTR_ZERO); } else if (base == myEPWM2_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_2); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_A, (uint16_t)PWM_CMPA_2); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_setSyncInPulseSource(base, EPWM_SYNC_IN_PULSE_SRC_SYNCOUT_EPWM1); set_phase(base, PHI); } else if(base == myEPWM3_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_3); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_A, (uint16_t)PWM_CMPA_3); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_setSyncInPulseSource(base, EPWM_SYNC_IN_PULSE_SRC_SYNCOUT_EPWM1); //EPWM_enableSyncOutPulseSource(myEPWM1_BASE, EPWM_SYNC_OUT_PULSE_ON_CNTR_ZERO); set_phase(base, PHI); } //EPWM_setTimeBaseCounter(base, 0U); EPWM_setTimeBaseCounterMode(base, EPWM_COUNTER_MODE_UP_DOWN); EPWM_setClockPrescaler(base, PWM_PARAM_PRESCALER, PWM_PARAM_HIGHSPEEDPRESCALER); // Set up shadowing EPWM_setCounterCompareShadowLoadMode(base, EPWM_COUNTER_COMPARE_A, EPWM_COMP_LOAD_ON_CNTR_ZERO); // Set actions EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_A, EPWM_AQ_OUTPUT_HIGH, EPWM_AQ_OUTPUT_ON_TIMEBASE_UP_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_A, EPWM_AQ_OUTPUT_LOW, EPWM_AQ_OUTPUT_ON_TIMEBASE_DOWN_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_B, EPWM_AQ_OUTPUT_HIGH, EPWM_AQ_OUTPUT_ON_TIMEBASE_UP_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_B, EPWM_AQ_OUTPUT_LOW, EPWM_AQ_OUTPUT_ON_TIMEBASE_DOWN_CMPA); // Trip zone // Configure ePWM1x to output low on TZx TRIP EPWM_setTripZoneAction(base, EPWM_TZ_ACTION_EVENT_TZA, EPWM_TZ_ACTION_LOW); EPWM_setTripZoneAction(base, EPWM_TZ_ACTION_EVENT_TZB, EPWM_TZ_ACTION_LOW); // Trigger event when DCBH is high EPWM_setTripZoneDigitalCompareEventCondition(base, EPWM_TZ_DC_OUTPUT_B1, EPWM_TZ_EVENT_DCXH_HIGH); // Configure DCBH to use TRIP4 as an input EPWM_enableDigitalCompareTripCombinationInput(base, EPWM_DC_COMBINATIONAL_TRIPIN4, EPWM_DC_TYPE_DCBH); // Enable DCB as OST EPWM_enableTripZoneSignals(base, EPWM_TZ_SIGNAL_DCBEVT1); // Configure the DCB path to be unfiltered and asynchronous EPWM_setDigitalCompareEventSource(base, EPWM_DC_MODULE_B, EPWM_DC_EVENT_1, EPWM_DC_EVENT_SOURCE_ORIG_SIGNAL); // Clear trip flags EPWM_clearTripZoneFlag(base, EPWM_TZ_INTERRUPT | EPWM_TZ_FLAG_OST); // Calculate delays get_delays_FED_RED(myEPWM1_BASE, &TBCLK); get_delays_FED_RED(myEPWM2_BASE, &TBCLK); get_delays_FED_RED(myEPWM3_BASE, &TBCLK); }
void set_phase(uint32_t base, uint16_t phi) { uint16_t phase; if(base == myEPWM2_BASE) { phase = ((float)phi * HWREGH(base + EPWM_O_TBPRD) / 360); } if(base == myEPWM3_BASE) { phase = ((float)phi * HWREGH(base + EPWM_O_TBPRD) * 2 / 360); } //EPWM_selectPeriodLoadEvent(base, EPWM_SHADOW_LOAD_MODE_SYNC); EPWM_enableSyncOutPulseSource(base, EPWM_SYNC_OUT_PULSE_ON_SOFTWARE); EPWM_forceSyncPulse(base); EPWM_setPhaseShift(base, phase); EPWM_setTimeBaseCounter(base, phase); EPWM_enablePhaseShiftLoad(base); }
Damien
您可以看到另一个函数、用于根据所需的频率和占空比计算 TBPRD 和 CMPA。 很抱歉我的英语水平! 如果我正确理解 TBPHS 最大值= TBPRD 最大值并且我确定这些值。 TBPRD 和 CMPA 正确。
例如、如果我希望 PWM1和 PWM2之间的相移为90°、PWM1和 PWM3之间的相移为180°
=> TBPHS (主器件 PWM1)= 0
=> TBPHS (从器件 PWM2)=((相位= 90°)* TBPRD)/ 360;在我的案例中 TBPRD = 156、因此 TBPHS = 39
=> TBPHS (从器件 PWM3)=((相位= 180°)* TBPRD)/360在我的案例中 TBPRD = 156、因此 TBPHS = 78
可以帮帮我吗? 我的错在哪里?
谢谢
Damien
void set_phase(uint32_t base, uint16_t phi) { uint16_t phase; if(base == myEPWM2_BASE) { phase = ((float)phi * HWREGH(base + EPWM_O_TBPRD) / 360); } if(base == myEPWM3_BASE) { phase = ((float)phi * HWREGH(base + EPWM_O_TBPRD) * 2 / 360); } //EPWM_selectPeriodLoadEvent(base, EPWM_SHADOW_LOAD_MODE_SYNC); EPWM_enableSyncOutPulseSource(base, EPWM_SYNC_OUT_PULSE_ON_SOFTWARE); EPWM_forceSyncPulse(base); EPWM_setPhaseShift(base, phase); EPWM_setTimeBaseCounter(base, phase); EPWM_enablePhaseShiftLoad(base); }
*TBPRD_boost_3 = PWM_Freq_TBCLK / (PWM_FREQ * 2); *CMPA_boost_3 = ((float) (100 - duty_boost_3) / 100) * (*TBPRD_boost_3);
void epwm_init(uint32_t base) { float PWM_TBPRD_1; float PWM_TBPRD_2; float PWM_TBPRD_3; float PWM_CMPA_1; float PWM_CMPA_2; float PWM_CMPA_3; EPWM_ClockDivider PWM_PARAM_PRESCALER; EPWM_HSClockDivider PWM_PARAM_HIGHSPEEDPRESCALER; float TBCLK; if(base == myEPWM1_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_1); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_B, (uint16_t)PWM_CMPA_1); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_enableSyncOutPulseSource(myEPWM1_BASE, EPWM_SYNC_OUT_PULSE_ON_CNTR_ZERO); } else if (base == myEPWM2_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_2); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_A, (uint16_t)PWM_CMPA_2); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_setSyncInPulseSource(base, EPWM_SYNC_IN_PULSE_SRC_SYNCOUT_EPWM1); set_phase(base, PHI); } else if(base == myEPWM3_BASE) { get_pwm_clock_from_freq(base , &PWM_TBPRD_1 , &PWM_TBPRD_2 , &PWM_TBPRD_3 , &PWM_CMPA_1 , &PWM_CMPA_2 , &PWM_CMPA_3 , &PWM_PARAM_PRESCALER , &PWM_PARAM_HIGHSPEEDPRESCALER, &TBCLK); // Parameters EPWM_setTimeBasePeriod(base, (uint16_t)PWM_TBPRD_3); EPWM_setCounterCompareValue(base, EPWM_COUNTER_COMPARE_A, (uint16_t)PWM_CMPA_3); EPWM_setPhaseShift(base, 0U); EPWM_disablePhaseShiftLoad(base); EPWM_setTimeBaseCounter(base, 0U); EPWM_setSyncInPulseSource(base, EPWM_SYNC_IN_PULSE_SRC_SYNCOUT_EPWM1); set_phase(base, PHI); } //EPWM_setTimeBaseCounter(base, 0U); EPWM_setTimeBaseCounterMode(base, EPWM_COUNTER_MODE_UP_DOWN); EPWM_setClockPrescaler(base, PWM_PARAM_PRESCALER, PWM_PARAM_HIGHSPEEDPRESCALER); // Set up shadowing EPWM_setCounterCompareShadowLoadMode(base, EPWM_COUNTER_COMPARE_A, EPWM_COMP_LOAD_ON_CNTR_ZERO); // Set actions EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_A, EPWM_AQ_OUTPUT_HIGH, EPWM_AQ_OUTPUT_ON_TIMEBASE_UP_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_A, EPWM_AQ_OUTPUT_LOW, EPWM_AQ_OUTPUT_ON_TIMEBASE_DOWN_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_B, EPWM_AQ_OUTPUT_HIGH, EPWM_AQ_OUTPUT_ON_TIMEBASE_UP_CMPA); EPWM_setActionQualifierAction(base, EPWM_AQ_OUTPUT_B, EPWM_AQ_OUTPUT_LOW, EPWM_AQ_OUTPUT_ON_TIMEBASE_DOWN_CMPA); // Trip zone // Configure ePWM1x to output low on TZx TRIP EPWM_setTripZoneAction(base, EPWM_TZ_ACTION_EVENT_TZA, EPWM_TZ_ACTION_LOW); EPWM_setTripZoneAction(base, EPWM_TZ_ACTION_EVENT_TZB, EPWM_TZ_ACTION_LOW); // Trigger event when DCBH is high EPWM_setTripZoneDigitalCompareEventCondition(base, EPWM_TZ_DC_OUTPUT_B1, EPWM_TZ_EVENT_DCXH_HIGH); // Configure DCBH to use TRIP4 as an input EPWM_enableDigitalCompareTripCombinationInput(base, EPWM_DC_COMBINATIONAL_TRIPIN4, EPWM_DC_TYPE_DCBH); // Enable DCB as OST EPWM_enableTripZoneSignals(base, EPWM_TZ_SIGNAL_DCBEVT1); // Configure the DCB path to be unfiltered and asynchronous EPWM_setDigitalCompareEventSource(base, EPWM_DC_MODULE_B, EPWM_DC_EVENT_1, EPWM_DC_EVENT_SOURCE_ORIG_SIGNAL); // Clear trip flags EPWM_clearTripZoneFlag(base, EPWM_TZ_INTERRUPT | EPWM_TZ_FLAG_OST); // Calculate delays get_delays_FED_RED(myEPWM1_BASE, &TBCLK); get_delays_FED_RED(myEPWM2_BASE, &TBCLK); get_delays_FED_RED(myEPWM3_BASE, &TBCLK); }
您好、如果您使用向上/向下计数模式、则 PWM 周期将是配置的周期值的两倍。 因此、您需要相应地调整相移。
请注意、您还可以在相位同步期间设置计数器方向(使用 PHSDIR 位)。
因此、对于需要240deg 的相位、您必须使用 PHSDIR 反转方向。
你好 ,苏布拉赫曼尼亚 ,
感谢您的回复。 如果我理解正确,我们必须反转方向,因为 TBPHS 的值将超过最大 TBPRD ? 是否可以通过 driverlib 函数来反转方向? 还是仅按位字段?
谢谢
Damien
您好!
您可以使用 driverlib 函数 PWM_setPhaseDir 来设置同步时的相位方向。
您好!
我找不到您的函数、但找到了该函数"ePWM_setCountModeAfterSync (myEPWM3_base、ePWM_COUNT_MODE_UP_After_SYNC)"。 当我希望 ePWM2°180°、而在 ePWM3上自然相位> 180°时、它不起作用
您能不能向我解释一下、在向上 和向下计数模式下、如何在 EPWM2和 EPWM3上实现更大的相位?
谢谢
Damien
您可以看到屏幕截图。 为什么当我设置相位= 120°时、ePWM2在 ePWM1和 ePWM3的正确相移情况下正常? 能不能更详细地解释一下?
谢谢
我的代码:
void set_phase(uint32_t base, uint16_t phi) { uint16_t phase; if(base == myEPWM2_BASE) { //EPWM_setCountModeAfterSync(base, EPWM_COUNT_MODE_UP_AFTER_SYNC); phase = ((float)phi * HWREGH(base + EPWM_O_TBPRD) * 2 / 360); // *2 to adapt scale on UP and DOWN Count mode } if(base == myEPWM3_BASE) { //EPWM_setCountModeAfterSync(base, EPWM_COUNT_MODE_UP_AFTER_SYNC); phase = ((float)phi * 2 * HWREGH(base + EPWM_O_TBPRD) * 2 / 360); } EPWM_enableSyncOutPulseSource(base, EPWM_SYNC_OUT_PULSE_ON_SOFTWARE); EPWM_forceSyncPulse(base); EPWM_setPhaseShift(base, phase); EPWM_setTimeBaseCounter(base, phase); EPWM_enablePhaseShiftLoad(base); }
您好!
对于 PWM3、您需要设置 PHSDIR。 该函数应该设置该位、但会将其注释掉。
//ePWM_setCountModeAfterSync (base、ePWM_COUNT_MODE_UP_After_SYNC);
这决定了计数器在 EPWM3的 SYNC 之后计数的方向。 请根据所需的相移设置所需的方向和相位。
你好 ,苏布拉赫曼尼亚 ,
很抱歉、我迟到了响应、最后我将 TBCTR 寄存器设置为向上计数模式、因为它在同步后不能在计数模式下工作。
我继续进行我的项目、稍后我将回到这个问题。
谢谢!
Damien
您好!
谢谢你。 我们现在将关闭此主题、如果您再次看到任何问题、您可以稍后启动新主题。