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.

Digital Compare Event Filter / Blanking Window (28035)

We are using a Comparator to generate a sync event and force the PWM counter to start at zero on an F28035.

The PWM is forced high at zero and forced low at compareA upcounting (pwm counter is upcounting).

To avoid additional sync events after the first one, we added the Digital Compare Event Filter / Blanking Window.

The filter starts at counter=zero, without offset.

The problem is that "sometimes", the filter does not seem to work. In that case, the sync event is generated permanently as long as the comparator is active, so the PWM counter is kept at zero and the pwm pulse is longer by the length of the comparator.

To verify this, we generated a PWM interrupt at zero which toggles a GPIO.

red: current
green: comparator output
blue: PWM zero interrupt GPIO

It seems as if the DCEVT filter has no effect - we get pwm zero interrupts as long as the comparator is active.

The filter blanking window DCFWINDOW is set to 100 (= 1.666 usec @ 60MHz), so the "Blanking Windows can NOT overlap" problem

( https://e2e.ti.com/support/microcontrollers/c2000/f/171/t/450130 ) should not occur here.

In a second image, you see that the PWM on time is suddenly longer by the amount of the comparator on time (compare value identical), obviously caused be the sync event(s) during comparator high: 

green: comparator
yellow: PWM

Any help on how to get the Digital Compare Event Filter / Blanking Window to work correctly is appreciated.

Stephan

  •   // Init PWM2:
      EPwm2Regs.TBCTL.bit.CTRMODE     = PWMCOUNTER_COUNT_UP;      // Count up
      EPwm2Regs.TBCTL.bit.PHSEN       = 1;                        // Enable phase loading
      EPwm2Regs.TBCTL.bit.PHSDIR      = PHASE_DIR_UP;             // Count up after sync event
      EPwm2Regs.TBCTL.bit.SYNCOSEL    = PWMSYNC_SYNC;             // Sync output = Sync input
      EPwm2Regs.TBCTL.bit.HSPCLKDIV   = PWMCLK_SYSCLOCKOUT;       // Clock ratio to SYSCLKOUT: div by 1
      EPwm2Regs.TBCTL.bit.CLKDIV      = PWMCLK_SYSCLOCKOUT;
    
      EPwm2Regs.TBPRD                 = 4000;                     // 4000 --> max. 15kHz
      EPwm2Regs.TBPHS.bit.TBPHS       = 0;                        // Phase is 0
      EPwm2Regs.TBCTR                 = 0;                        // Clear counter
    
      EPwm2Regs.CMPCTL.bit.SHDWAMODE  = PWM_COMPARE_LOAD_SHADOW;      // Load registers every ZERO, shadowed
      EPwm2Regs.CMPCTL.bit.SHDWBMODE  = PWM_COMPARE_LOAD_SHADOW;
      EPwm2Regs.CMPCTL.bit.LOADAMODE  = PWM_COMPARE_LOAD_ON_CTR_ZERO;
      EPwm2Regs.CMPCTL.bit.LOADBMODE  = PWM_COMPARE_LOAD_ON_CTR_ZERO;
    
      // Setup compare
      EPwm2Regs.CMPA.bit.CMPA     = 5;   // Set compare A value, 0% duty
      EPwm2Regs.CMPB              = 2;   // Set compare B value, in case zero event is missed
    
      // Set actions
      EPwm2Regs.AQCTLA.bit.ZRO    = PWM_ACTION_FORCE_HIGH;      // Set PWMA on zero event
      EPwm2Regs.AQCTLA.bit.CBU    = PWM_ACTION_FORCE_HIGH;      // Set PWMA on CompareB (upcount), in case zero event is missed
      EPwm2Regs.AQCTLA.bit.CAU    = PWM_ACTION_FORCE_LOW;       // Clear PWMA on CompareA (upcount)
    
      // Active Low PWMs - Setup Deadband
      EPwm2Regs.DBCTL.bit.OUT_MODE  = PWM_DB_BOTH;
      EPwm2Regs.DBCTL.bit.POLSEL    = PWM_DB_ACTIVE_LOW_PWMB;     // complementary: A high, B low active
      EPwm2Regs.DBCTL.bit.IN_MODE   = PWM_DB_SOURCE_PWMA_BOTH;
      EPwm2Regs.DBRED               = HF_PWM_RED;                 // db in cycles: 22*16.667=367nsec
      EPwm2Regs.DBFED               = HF_PWM_FED;
    
    
      
      // Trip Zone for PWM2 (comparator 1 as period sync event, TZ1/OSHT via Force as enable/disable PWM)
      // Define an event
      EPwm2Regs.DCTRIPSEL.bit.DCAHCOMPSEL    = DCTRIP_COMPSEL_COMP1OUT;  // DCAH = Comparator 1 output
      EPwm2Regs.TZDCSEL.bit.DCAEVT1          = TZ_DCAH_HI;               // DCEVT1 =  DCAH high (will become active as Comparator output goes high)
      EPwm2Regs.DCACTL.bit.EVT1SRCSEL        = EVTSRCSEL_DCEVTFILT;    // DCEVT1 source is DCEVTFILT, filtered
      EPwm2Regs.DCACTL.bit.EVT1FRCSYNCSEL    = 1;                        // Take async path for TZFRC
      EPwm2Regs.DCACTL.bit.EVT1SYNCE         = 1;                        // DCEVT1 Sync Enable
    
      EPwm2Regs.TZCTL.bit.TZA      = PWM_TZ_ACTION_FORCE_LOW;  // EPWMA will be forced low on a trip event (for switching PWM OFF)
      EPwm2Regs.TZCTL.bit.TZB      = PWM_TZ_ACTION_FORCE_LOW;  // EPWMB will be forced low on a trip event (for switching PWM OFF)
      EPwm2Regs.TZCTL.bit.DCAEVT1  = PWM_TZ_ACTION_NONE;
      EPwm2Regs.TZCTL.bit.DCAEVT2  = PWM_TZ_ACTION_NONE;
      EPwm2Regs.TZCTL.bit.DCBEVT1  = PWM_TZ_ACTION_NONE;
      EPwm2Regs.TZCTL.bit.DCBEVT2  = PWM_TZ_ACTION_NONE;
    
      // Setup Event Filtering / Blanking Window for DCAEVT
      EPwm2Regs.DCFCTL.bit.BLANKE            = 1;                        // Blanking Window enable
      EPwm2Regs.DCFCTL.bit.PULSESEL          = DCFCTL_PULSESEL_ZERO;     // Start blanking window on timer equal zero
      EPwm2Regs.DCFCTL.bit.SRCSEL            = DCFCTL_SRCSEL_DCAEVT1;    // Source for blanking window is DCAEVT1 (OST)
      EPwm2Regs.DCFOFFSET                    = 0;                        // start blanking window without offset/delay
      EPwm2Regs.DCFWINDOW                    = 100;                      // blanking window width in TBCycles
    
      EPwm2Regs.TZSEL.bit.OSHT1     = 1;                        // Enable TZ1 as OST trip event (will only be set via EPwm2Regs.TripZoneForce.bit.OST = 1, no TZ1 on pins)
                                                                // For switching PWM OFF
    
      EPwm2Regs.TZSEL.bit.OSHT2     = 1;                        // Overcurrent disables PWM
    
      EPwm2Regs.TZCLR.all           = 0xFFFF;
      EPwm2Regs.TZFRC.bit.OST       = 1;                        // start with disabled Switches
    
      
      // Comparator:
      Comp1Regs.COMPCTL.all            = 0;
      Comp1Regs.COMPCTL.bit.COMPDACEN  = 1;                      // Comparator/DAC logic is powered up
      Comp1Regs.COMPCTL.bit.COMPSOURCE = COMP_SOURCE_DAC_VAL;    // Input Pin A is compared to DAC output, not to Pin B
      Comp1Regs.COMPCTL.bit.CMPINV     = 0;                      // no NOT logic
      Comp1Regs.COMPCTL.bit.SYNCSEL    = 1;                      // Synchronous version of comparator output - possibility to qualify input
      Comp1Regs.COMPCTL.bit.QUALSEL    = 10;
      Comp1Regs.DACVAL.all             = 512;                    // set COMP DAC to half of max (DAC max is 1023, 10 bit)
    

  • Okay, I think I found part of the problem:
    Datasheet says "During the blanking window, all events are ignored."
    Our understanding was that all edges are ignored because only edges lead to new event triggers.
    In reality, during the blanking window, the DCEVTFILT output is forced to be zero (instead of keeping it as it is). So if the Blanking Window input event (the compare1 in our case) is still active after the window ends, it generates a new trigger event (a new pwm2 sync in our case).
    Very bad.
    The Digital Compare Event Filter / Blanking Window part in the datasheet really needs some rework.
  • Hi Stephan,

    Yes, your understanding is correct. Also I suggest keeping the blanking window offset of 1 and not 0. That has worked well for me in the past to make sure all actions associated with the CTR = 0 event occur as expected. You will have to keep a blanking window length longer than the longest time a comparator event may stay active.

    We are trying to fix these things in the documentation and your feedback is very valuable. We have a lot of features and configuration possibilities on these devices that sometimes make it difficult to describe everything in the TRM while still keeping it fairly easy to read. 

    Hrishi