Hey there,
I have a TWRK21 board and PWM output enabled using FTM3 on Pin E6.
I am using KSDK v1.3 with HAL and DRIVERS of FTM.
Basically everything works just fine, I am able to start and stop PWM, set a new duty cycle and alter the switching frequency.
My observation though is, that everytime I change the duty cycle and sync per software trigger the PWM output has some kind of hicup or glitch.
The instantanious activation of the new setting seems to break the cycle run of the actual counting.
Is it therefore easily possible to not use software triggered register sync but to automatically sync the FTM config register after the actual running PWM cycle has completed, say i.e. on overflow interrupt?
Thanks for the help, I really appreciate it.
I've added a screenhot indicating the glitches in PWM cycle (shortening) every 10.8 ms, placed timing markers just as visual indicator of glitch position.
Normal PWM cycle takes 0.73ms = 1.37kHz, glitched one takes 0.64ms = 1.56kHz. The switching pwm frequency gets sweeped, that's why at the time of measurement the awkwards switching frequencies result.
Also the code is added here. Hopefully this will make it easier to narrow down the issue.
Thanks in advance!
Code |
---|
#include "stdlib.h" #include "Pwm.h" #include "board.h" #include "Logging.h" #include "fsl_os_abstraction.h" bool brightnessUp = true; // Indicate LED is brighter or dimmer uint16_t sweepCount = 0; uint16_t freqTemp = 0; void sweepSwitchingFrequency(ClassPwm* pwm, uint16_t delta){ freqTemp = Pwm_getSwitchingFrequency(pwm); Pwm_setSwitchingFrequency(pwm, freqTemp - delta); sweepCount = 0; } void main(void){ uint32_t returnCode; returnCode = SysTick_Config(SystemCoreClock / 1000); // Configure SysTick to generate an interrupt every millisecond uint16_t gDutyCycle = 0; hardware_init(); OSA_Init(); ClassPwm* pwm = Pwm_NewClass(); Pwm_init(pwm, BOARD_FTM_INSTANCE, BOARD_FTM_CHANNEL); Pwm_setDutyCycle(pwm, 75); while(1){ Pwm_setDutyCycle(pwm, gDutyCycle); OSA_TimeDelay(10u); if(brightnessUp) { if (++gDutyCycle == 100) { // Increase duty cycle until it reaches limited value brightnessUp = false; sweepSwitchingFrequency(pwm, 1000u); } } else { if (--gDutyCycle == 0) { // Decrease duty cycle until it reaches limited value. brightnessUp = true; sweepSwitchingFrequency(pwm, 1000u); } } } } |
Hello Stefan,
In Section 40.4.10 Registers updated from write buffers from MCU's Reference Manual, you can find information about updating registers from their writing buffers, in this case, these registers will be updated in different ways according current configuration, you can give a look to these synchronization ways and that way you can try to avoid these glitches.
I hope this can help you!
Best regards,
Isaac Avila
Hey Isaac,
thanks so much for your reply. After a while of working on other stuff, we decided to leave this issue unsolved for now and treat it as technichal depth for later reengineering. I will most likely get back to this post after this depth is solved.
So many thanks for now.
Cheers
Stefan