Part Number: C2000WARE
Hi,
I am having an issue that my PWM outputs are constantly PWMA1 = 0 and PWMB1 = 1, because i'm using active complimentary high PWM and my CMPA and CMPAHR values are not updating in code, or even initialising. It seems they are stuck at 0. Code below for the bits that are of concern:
interrupt void MainCPU_ISR(void)
{
// Read sensor data across the ADCs
// Read all in CPU1 to make easier to distribute between cores
inputVolts_CLA1 = AdcbResultRegs.ADCRESULT5; // Read the ADC value placed into ADC register
inputVolts_CPU2 = inputVolts_CLA1; // Place a copy into CLA shared RAM
// May need to type-cast these values as floating point for the DCL CLA calculations to be accurate as possible
flyVolts = ((AdcaResultRegs.ADCRESULT1
+ AdcaResultRegs.ADCRESULT2
+ AdcaResultRegs.ADCRESULT3
+ AdcaResultRegs.ADCRESULT4
+ AdcaResultRegs.ADCRESULT5
+ AdcaResultRegs.ADCRESULT6
+ AdcaResultRegs.ADCRESULT7
+ AdcaResultRegs.ADCRESULT8)/8); // Compute the average reading on the over-sampled Cathode Output Voltage SOCs
// 8x over-sampling for cathode voltage
// Modulate the PWM register compare bit
EPwm1Regs.CMPA.bit.CMPAHR = MAX_DUTY_FLY;
// Return from interrupt
AdcaRegs.ADCINTFLGCLR.bit.ADCINT1 = 1; // Clear ADC INT1 flag
PieCtrlRegs.PIEACK.all = PIEACK_GROUP1; // Acknowledge PIE group 1 to enable further interrupts
Isr1Count++;
}
The ISR is triggering fine, even when I place a constant value in the CMPAHR register, nothing happens. Have also tried with CMPA. Here is my PWM initialisation code:
// Fly-back PWM Module
void InitEPwm1(void)
{
// Setup time-base
EPwm1Regs.TBCTL.bit.CTRMODE = 0; // Up count mode
EPwm1Regs.TBPRD = FLY_PERIOD; // Set timer period
// EPwm1Regs.TBPRDHR = FLY_PERIOD; // Set timer period, for HR bits
EPwm1Regs.TBCTL.bit.PHSEN = 0; // Disable phase loading
EPwm1Regs.TBPHS.bit.TBPHS = 0x0000; // Phase is 0
EPwm1Regs.TBCTR = 0x0000; // Clear counter
// Set TBCLK = EPWMCLK = 100MHz
// Although the system clock is 200MHz, maximum EPWM clock is 100MHz
EPwm1Regs.TBCTL.bit.HSPCLKDIV = 0; // Clock ratio to SYSCLKOUT
EPwm1Regs.TBCTL.bit.CLKDIV = 0;
EPwm1Regs.TBCTL.bit.SYNCOSEL = 1; // SYNC output on CTR = 0
// Set initial modulation in Counter Compare Module
EPwm1Regs.CMPA.bit.CMPAHR = 10; // Set compare A value initially to zero (we will want to soft-start)
// Set actions in the action qualifier module
EPwm1Regs.AQCTLA.bit.CAU = 1; // Action When TBCTR = CMPA on Up Count -> Force PWMA Output Low
EPwm1Regs.AQCTLA.bit.CAD = 2; // Action when TBCTR = CMPA on Down Count -> Force PWMA Output High
EPwm1Regs.DBCTL.bit.OUT_MODE = 3; // Fully enable dead-band for both falling and rising-edges
EPwm1Regs.DBCTL.bit.POLSEL = 2; // Active High Complimentary (AHC) Mode
EPwm1Regs.DBFEDHR.bit.DBFEDHR = FLY_DEADTIME; // Set dead-time for falling edge
EPwm1Regs.DBREDHR.bit.DBREDHR = FLY_DEADTIME; // Set dead-time for rising edge /* BEEN CHANGED BY JM HOLLAND */ TO HR BITS
EALLOW;
// Digital Compare (DC) Submodule
// Generate DCAH signal from Trip Combination Input
EPwm1Regs.DCTRIPSEL.bit.DCAHCOMPSEL = 15; // OR together all Trip combinations selected by DCALTRIPSEL Registers -> DCAH
EPwm1Regs.DCTRIPSEL.bit.DCBHCOMPSEL = 15; // OR together all Trip combinations selected by DCALTRIPSEL Registers -> DCBH
// DCAH/DCAEVT1/2 are used for one-shot trip faults
// DCBH/DCBEVT1/2 are used for cycle-by-cycle faults
// Individually select which trip signals are passed into the block to be ORed together
EPwm1Regs.DCAHTRIPSEL.bit.TRIPINPUT5 = 1; // Input Over Voltage Trip One-Shot Fault
EPwm1Regs.DCAHTRIPSEL.bit.TRIPINPUT7 = 1; // Cathode Over Voltage Trip One-Shot Fault
EPwm1Regs.DCBHTRIPSEL.bit.TRIPINPUT4 = 1; // Fly-back Over Current Trip Cycle-by-Cycle Fault
// Event A Action Qualifier block
// Generate DCAEVT1/DCBEVT1 trip events according to DCAH and DCBH
// Only EVT1 can be used for OST, and EVT2 for CBC
// Need to enable both A and B of these registers to trigger both the PWMx outputs
EPwm1Regs.TZDCSEL.bit.DCAEVT1 = 2; // DCAEVT1: DCAH = high, DCAL = don't care
EPwm1Regs.TZDCSEL.bit.DCAEVT2 = 2; // DCAEVT2: DCAH = high, DCAL = don't care
EPwm1Regs.TZDCSEL.bit.DCBEVT1 = 2; // DCBEVT1: DCBH = high, DCBL = don't care
EPwm1Regs.TZDCSEL.bit.DCBEVT2 = 2; // DCBEVT2: DCBH = high, DCBL = don't care
// Event Triggering block - Generate DCAEVT1.force and DCBEVT1.force signals (One Shot Source)
EPwm1Regs.DCACTL.bit.EVT1SRCSEL = 0; // Select DCAEVT1 as input signal
EPwm1Regs.DCACTL.bit.EVT1FRCSYNCSEL = 1; // Select Asynchronous
EPwm1Regs.TZFRC.bit.DCAEVT1 = 0; // Enable DCAEVT1.force output signal
EPwm1Regs.DCBCTL.bit.EVT1SRCSEL = 0; // Select DCBEVT1 as input signal
EPwm1Regs.DCBCTL.bit.EVT1FRCSYNCSEL = 1; // Select Asynchronous
EPwm1Regs.TZFRC.bit.DCBEVT1 = 0; // Enable DCBEVT1.force output signal
// Event Triggering block - Generated DCAEVT2.force and DCBEVT2.force signals (Cycle-by-Cycle Source)
EPwm1Regs.DCACTL.bit.EVT2SRCSEL = 0; // Select DCAEVT2 as input signal
EPwm1Regs.DCACTL.bit.EVT2FRCSYNCSEL = 1; // Select Asynchronous
EPwm1Regs.TZFRC.bit.DCAEVT2 = 0; // Enable DCAEVT2.force output signal
EPwm1Regs.DCBCTL.bit.EVT2SRCSEL = 0; // Select DCBEVT2 as input signal
EPwm1Regs.DCBCTL.bit.EVT2FRCSYNCSEL = 1; // Select Asynchronous
EPwm1Regs.TZFRC.bit.DCBEVT2 = 0; // Enable DCBEVT2.force output signal
// Trip Zone Submodule - Trip Logic block
// Using only TZCTL and EVT1
EPwm1Regs.TZCTL2.bit.ETZE = 0; // Use only TZCTL register, disable TSCTL2
EPwm1Regs.TZCTL.bit.DCAEVT1 = 0x10; // On trip, force EPWM1A to a LOW state
EPwm1Regs.TZCTL.bit.DCBEVT1 = 0x10; // On trip, force EPWM1B to a LOW state
EPwm1Regs.TZCTL.bit.DCAEVT2 = 0x10; // On trip, force EPWM1A to a LOW state
EPwm1Regs.TZCTL.bit.DCBEVT2 = 0x10; // On trip, force EPWM1B to a LOW state
EPwm1Regs.TZCTL.bit.TZA = 0x10; // On trip, force EPWM1A to a LOW state
EPwm1Regs.TZCTL.bit.TZB = 0x10; // On trip, force EPWM1B to a LOW state
// Trip-Zone Submodule - select OSHT and CBC sources
EPwm1Regs.TZSEL.bit.DCAEVT1 = 1; // Enable DCAEVT1 as one-shot-trip source for this ePWM module
EPwm1Regs.TZSEL.bit.DCBEVT1 = 1; // Enable DCBEVT1 as one-shot trip source for this ePWM module
EPwm1Regs.TZSEL.bit.DCAEVT2 = 1; // Enable DCAEVT2 as a CBC trip source for this ePWM module
EPwm1Regs.TZSEL.bit.DCBEVT2 = 1; // Enable DCBEVT2 as a CBC trip source for this ePWM module
//EPwm1Regs.TZFRC.bit.OST = 0x01; // Force trip to disable PWM outputs
//EPwm1Regs.TZFRC.bit.CBC = 0x01; // Force cycle-by-cycle trip to disable PWM outputs
// May insert code which either waits a delay time before clearing the one-shot fault, or something along those lines
// At the moment, I believe, this will turn OFF the PWM module until user-reset.
// High Resolution Pulse Width Modulator Definitions
// We may need more information here!
EPwm1Regs.HRCNFG.all = 0x0; // Clear all bits first within the HRCNFG register
EPwm1Regs.HRCNFG.bit.EDGMODE = 0x3; // Control both falling and rising edge delays with the MEP
EPwm1Regs.HRCNFG.bit.CTLMODE = 0x0; // CMPAHR controls the MEP
EPwm1Regs.HRCNFG.bit.HRLOAD = 0x0; // Shadow load on CTR=Zero for count-up mode
EDIS;
// Set up ADC trigger pulse to ADC SOCA (ADCAINT1)
EPwm1Regs.ETSEL.bit.SOCAEN = 0; // Disable SOCA on A group
EPwm1Regs.ETSEL.bit.SOCASEL = 2; // Select SOCA on period match
EPwm1Regs.ETSEL.bit.SOCAEN = 1; // Enable SOCA
EPwm1Regs.ETPS.bit.SOCAPRD = 1; // Generate pulse on 1st event
}
I have checked all the peripheral clocks and the TBPRD is counting correctly, but no modulation occurs because there is nothing in the CMPA nor CMPAHR bits. I have tried multiple combinations of CMPA and CMPAHR as you can see and no matter what, something is stopping the CMPA and CMPAHR register from actually being updated with the value I set.
Any ideas on what might be causing this bug from my code snippet?
Best wishes,
Joel
