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.

EPWM SYNCI and SYNCO timing across multiple processors

Other Parts Discussed in Thread: TMS320F28069, CONTROLSUITE

Hello,

We have a custom board that has 8 TMS320F28069 devices, each device controlling the voltage and current for a single channel.  We run a buck-boost circuit using PWM1 and PWM2.  To synchronize all 8 channels, we use the SYNCO from the first device, and feed it into the SYNCI of all 7 other devices.  Our clock is 90MHz, there is no dividing of the clock for the PWM module.  Our PWM frequency is 100kHz or 200kHz, depending on the situation.

We're observing a noticeable delay between the SYNC pulse and the rising edge of the PWMs on the other 7 devices.  TBPHS for all test cases is set to 0, GPIO qualification is also set to 0.

It appears that for device 1 (sending SYNCO), the PWM rising edge is aligned with the rising edge of the SYNCO pulse.  When measuring the rising edge of PWMs on other devices, it's almost perfectly aligned with the falling edge of the same SYNCO pulse (about 78ns after the rising edge).  Sending the same SYNC pulse through a single device shows that PWM1 and PWM2 are aligned based on the same pulse, with no measurable delay.

What could be causing this delay?  I can't seem to find anything in the documentation that discusses a delay this long (at most 2 clock cycles, maybe 6 if GPIO qual is used).  One forum post confirms that SYNCI is edge triggered, although not which edge (http://e2e.ti.com/support/microcontrollers/c2000/f/171/t/245400.aspx) and this post confirms there is no way to configure it FOR falling edge sync, so it's not some misconfiguration there (http://e2e.ti.com/support/microcontrollers/c2000/f/171/t/21119.aspx).

Thanks.

  • Additionally, is there any kind of recommended practice for using this PWM SYNC signal across multiple processors?

    Thanks again.

  • Hi James,

    Can you take a look at the following thread and see if it gives you any ideas:
    http://e2e.ti.com/support/microcontrollers/c2000/f/171/p/250995/882619.aspx#882619

    If this doesn't help (or you're already doing what's mentioned) can you provide the ePWM configuration for the master and one of the slaves?


    Thank you,
    Brett

  • Hi Brett,

    Thanks for the reply.  I saw this post and we have used offsets like that to line them up better.  The "2" offset makes sense for what's documented.

    What we're seeing is a much larger offset, so we were more trying to get to the bottom of this larger offset.  Can you tell me other possible sources for a delay like this?

    I have attached our configuration functions in a text file.  The first function is our default config for ALL PWMs, run once at startup.  The second is a stagger configuration that has to do with the sync and phase registers that is run after the default configuration, and then again each time the PWM frequency is changed.  The master is DspNum 0, the slaves are 1-7.

    Default config for all PWMs (run once at startup):
    
    void EPwmConfigDefault(int n, Uint16 period)
    {
    	EALLOW;
    	(*ePWM[n]).TBCTL.bit.PRDLD = TB_SHADOW;	        // set shadow load
    	(*ePWM[n]).TBPRD = period;		                // PWM frequency = 1 / period
    	(*ePWM[n]).CMPA.half.CMPA = 0;		// set duty to 0% initially
    	(*ePWM[n]).CMPA.half.CMPAHR = 0;	// initialize HRPWM extension
    	(*ePWM[n]).CMPB = 0;				// set duty to 0% initially
    	(*ePWM[n]).TBPHS.all = 0;
    	(*ePWM[n]).TBCTR = 0;
    
    	(*ePWM[n]).TBCTL.bit.CTRMODE = TB_COUNT_UP;
    	(*ePWM[n]).TBCTL.bit.PHSEN = TB_DISABLE;
    	(*ePWM[n]).TBCTL.bit.SYNCOSEL = TB_SYNC_DISABLE;
    	(*ePWM[n]).TBCTL.bit.HSPCLKDIV = TB_DIV1;
    	(*ePWM[n]).TBCTL.bit.CLKDIV = TB_DIV1;
    
    	(*ePWM[n]).CMPCTL.bit.LOADAMODE = CC_CTR_ZERO;
    	(*ePWM[n]).CMPCTL.bit.LOADBMODE = CC_CTR_ZERO;
    	(*ePWM[n]).CMPCTL.bit.SHDWAMODE = CC_SHADOW;
    	(*ePWM[n]).CMPCTL.bit.SHDWBMODE = CC_SHADOW;
    
    	(*ePWM[n]).AQCTLA.bit.ZRO = AQ_SET;          // PWM toggle low/high
    	(*ePWM[n]).AQCTLA.bit.CAU = AQ_CLEAR;
    	(*ePWM[n]).AQCTLB.bit.ZRO = AQ_SET;
    	(*ePWM[n]).AQCTLB.bit.CBU = AQ_CLEAR;
    
    	// enable phase sync so each PWM is 90 degrees out of phase with the last
    	(*ePWM[n]).TBCTL.bit.SYNCOSEL = 0x01;	// set sync output on CTR = zero
    	if(n > 1 && n != 8)
    	{
    		(*ePWM[n]).TBCTL.bit.PHSEN = 1;		// enable phase sync
    		(*ePWM[n]).TBPHS.half.TBPHS =  period / 4;
    	}
    
    	// configure HRPWM registers
    	if(n == 1 || n == 2)
    	{
    		(*ePWM[n]).HRCNFG.all = 0x0;
    		(*ePWM[n]).HRCNFG.bit.EDGMODE = HR_FEP;		//MEP control on falling edge
    		(*ePWM[n]).HRCNFG.bit.CTLMODE = HR_CMP;
    		(*ePWM[n]).HRCNFG.bit.HRLOAD  = HR_CTR_ZERO;
    	}
    }
    
    
    
    Stagger configuration (run each time frequency changes, and once on startup, after the default config above):
    void PwmStaggerConfig(Uint16 DspNum, Uint16 period)
    {
    	// see FB5141
    	if(0 == DspNum)
    	{
    		// DSP1 is the buck reference for the other DSP2-DSP8
    		EPwm1Regs.TBPHS.half.TBPHS = 0;
    		EPwm2Regs.TBPHS.half.TBPHS = EPwm2Regs.TBPRD - 25;
    		EPwm1Regs.TBCTL.bit.PHSEN = TB_DISABLE;
    		EPwm1Regs.TBCTL.bit.SYNCOSEL = 0x01;	// TBCTR = 0x0000
    	}
    	else
    	{
    		// ensure other buck PWM has phase of 1/2 difference
    		EPwm1Regs.TBCTL.bit.SYNCOSEL = 0;	// EPWMxSYNC
    		// 1/2 stagger
    		if(DspNum == 2 || DspNum == 4 || DspNum == 6)
    		{
    			EPwm1Regs.TBPHS.half.TBPHS = 0;
    			EPwm2Regs.TBPHS.half.TBPHS = EPwm2Regs.TBPRD - 25;
    		}
    		else if(DspNum == 1 || DspNum == 3 || DspNum == 5 || DspNum == 7)
    		{
    			EPwm1Regs.TBPHS.half.TBPHS =  (Uint16)((float)period / 2) - debugOffset;
    			// see FB5854
    			EPwm2Regs.TBPHS.half.TBPHS = (Uint16)((float)period / 2) - 25;
    		}
    
    		EPwm1Regs.TBCTL.bit.PHSEN = TB_ENABLE;
    		EPwm2Regs.TBCTL.bit.PHSEN = TB_ENABLE;
    	}
    }

  • James,

    Generally, delays will come from A) misconfiguration, B) trace length between master and slaves, and potentially C) crystal/oscillator jitter.

    Since you are using up-count mode, PWM_1ch_Cnf.c and/or PWM_1chHiRes_Cnf.c should be good references for you:
    \controlSUITE\libs\app_libs\digital_power\f2803x_v3.4\CNF\
    Based on a comparison, I might see a few unintentional math things that may lead to 1 or 2 clock cycles of delay between master and slave and then a few because you haven't directly compensated for the logic delay of 2.  At the moment, I don't see significantly more than this though.

    Comments:
    1) What in particular are you comparing when you describe your delay? 
    DspNum0.EPwm1A and DspNum2.EPwm1A is what I'd focus on getting synched first.
    2) Earlier you stated that you were seeing 78ns of delay which equals 7 SYSCLK cycles @ 90MHz.  Is this the delay that you are seeing?  While not unsubstantial, you keep using words like 'much larger'.  (I just want to make sure that I'm understanding the issue correctly)
    4) Is the delay constant or does it vary from synch pulse to synch pulse?


    Thank you,
    Brett

  • Brett, 

    Thank you for this information, I believe I checked those references out but I will look again and compare to what we now have implemented.

    For your comments:
    1) I am comparing DSP0 PWM1A and DSP2 PWM1A for that ~78ns delay.  I also compared DSP2 PWM1A and DSP2 PWM2A (debug setting 0 TBPHS), as well as comparing PWM1A of several devices to the SYNC pulse itself (measured coming out of DSP0, setting TBPHS to 0 on any PWMs measured that weren't already set to 0).
    2) Yes, the ~78ns delay is still what I'm seeing.  By "much larger" I just mean larger that documented, in that it is almost 4 times larger (and a larger percentage of a 5us period, 0.44% for 2 clocks, 1.56% for the 78ns).
    3) The delay is constant over time

    All  DSPs are clocked using the same crystal (distributed via a buffer with an output for each device), and I'd be surprised of trace lengths contributed that much delay on the SYNC signal.  I'll measure the SYNCO from device 0 and compare it to the SYNCI on the other 7 devices to see, though.

    It seems most likely it's some configuration we're missing (or have incorrect) in the PWM or GPIO, or possibly that it's some undocumented delay.  Any other places you suggest we look?

    Thanks again.

    - James

  • James,

    Thanks the setup is more clear to me at least :).  Based on what you say we're probably dealing with something in the configuration.

    Besides looking at the reference code I mentioned, my other recommendation might be (if possible) to do all the major configuration in EPwmConfigDefault().  Then you'd only change need to change all the TBPHS values in PwmStaggerConfig(). 

    I haven't seen your full code, but then you'd have the below for the PWM:
    1) Initialize system and PWM clocks
    2)
       EALLOW;
       SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 0;
       EDIS;
    3) Call EPwmConfigDefault() for each PWM
    4)
       EALLOW;
       SysCtrlRegs.PCLKCR0.bit.TBCLKSYNC = 1;
       EDIS;
    5) Call PwmStaggerConfig() when you wish.
    6) Call PwmStaggerConfig() when you wish.
    ...


    This would fall more in line with the configuration order recommended by the TRM.


    Thank you,
    Brett

  • Brett,

    Your recommendation has reduced this delay somewhat, although only ~10ns between DSP 0 and DSP 2.  This delay channel-to-channel varies on its own +/- a clock cycle or so from each other (e.g. DSP 4 and 6 by default have the 78ns delay from DSP 0, within a clock cycle, which is not necessarily surprising).  I imagine part of it is that even the TBCLKSYNC only works within a single chip, rather than across multiple (for obvious reasons)?  For the previous testing, the SYNC pulse from DSP 0 to DSP 2 has at most a 1-2ns difference on the rising edge, so it's not trace delays.

    We do actually have code later that freezes and unfreezes the TBCTR so we can change the frequency from 100kHz to 200kHz or the reverse (when necessary).  Could this be a potential source of error?  It doesn't seem like it since the SYNC pulse itself should take care of that, but I want to be sure.  Additionally, we enable and disable PHSEN at different times to prevent issues with the mixed PWM frequencies, mostly just using it to SYNC once in a while.  Is there some inherent delay in this?

    I'm kind of at a loss.  I don't mind working around something, but not until I know the source, at least.  Even if that's just some extra silicon delay or a GPIO configuration from another pin or something affecting the PWM pins.

    Thanks again.

    - James

  • Re-reading the SYNC section in the TRM on page 256, it appears that 2 clock SYNC delay might only apply from Internal master to slave modules?  At least when TBCLK = SYSCLKOUT, which is our situation.

    Is it possible that the logic delays of getting the SYNCI pulse from the input pin to the counter of EPwm1 is just larger than this?  

  • Changing GPAQSEL1 for GPIO6 to 3 (for async) has reduced this delay by ~24us.

  • James,

    I plan to try this on my side tomorrow or at least very soon.  I will let you know what I find.

    From my understanding, there may be another delay that needs to be compensated: one between when the PWMSYNCI pulse is received and when it actually is provided to the PWMs.

    ---

    To clarify for me:
    You started with 78ns of delay (7 SYSCLK cycles) between a PWM from the master C2000 and a PWM from an even slave C2000.
    -24ns better based on the logic delay from the master's PWM to the SYNCO pulse
    -11ns better based on the configuration suggestions I gave previously
    -24ns better based on changing to GPIOs to asynch mode

    If I understand correctly, this means that now you have 2 SYSCLK cycles of delay.  Is this correct? 


    Thank you,
    Brett

  • The best I've measured so far is ~50ns delay (combination of your suggestion and changing the GPIO input to async).  One thing that surprised me was that changing to async gained 2 SYSCLK cycles, instead of just 1 (at most).

    It does seem like there is just some other delay being unaccounted for, let me know what you find.

    Thanks!

    - James

  • James,

    I have used two F28069 controlCARDs to create a simple setup similar to yours.

    When running I see 6 cycles (~67ns) of delay between the rising edge of the PWMSYNCI pulse and the rising edge of my PWM (the PWM is configured to rise when it synchronizes).  For this experiment I set the GPIO input qualification to 'synchronize to SYSCLK')

    I also see jitter varying between 0 and 1 additional cycle due to the fact that the both devices are using different clock sources.

    ---

    From the documentation, we can expect 2 cycles of delay between a master synch pulse and a slave PWM.

    When I change the GPIO input qualification to asynchronous mode I also see about 2 cycles decrease in the delay.  As you are, I would expect only 1 cycle of delay when changing from one mode to the other.

    This leaves 2 cycles that are uncompensated for.

    ---

    I have started some internal conversations regarding the unknowns above.  I will report back when there is something to report.

    In general, I believe very strongly that all these delays are fixed and will not change under different conditions.  Because of this, you should be able to compensate for them by changing the PHS.


    Thank you,
    Brett

  • James,

    There has been some progress with regard to the above. 

    From timing analysis, TI's expectation is that there will be 6-7 clock cycles of delay between the PWMSYNCI rising edge and when a PWM will synchronize.  This falls directly in line with what I was observing.

    In addition, we recommend using synchronous GPIO qualification for PWMSYNCI (as opposed to asynchronous).  The design timing was closed around synchronous qualification and we can't guarantee functionality with asynch qualification.  As usual, you can account for the delay be adding extra delays via TBPHS.

    Hopefully this your question.  I now need to file a bug to get some of the above added to the datasheet/TRM.


    Thank you,
    Brett

  • Excellent, thank you very much for all your help, Brett.

    Now that we know it's just the expected delay, we can workaround it without worry, knowing that it's not something lingering in our configuration.

    Thanks again.

    - James