EmbeddedRelated.com
Forums
Memfault Beyond the Launch

PWM glitch possible when setting new duty-cycle value?

Started by joconradt May 22, 2008
Hi LPC users,

I am programming LPC2103 in a motor control application using PWM on
timer0. I have set T0_MR3 to specify the cycle length (let's say 1000
timer ticks) and I am using T0_MR2 to specify the duty cycle for the
motor output on Mat0.2 (P0.16). That all works well Smile

I am concerned about the following scenario: the motor is set to a
duty cycle of 700, but I want to reduce the cycle to 600. When I
update the register T0_MR2, the current timer value (T0_TC) might be
in-between 600 and 700 - and thus the comparison with the match
register will not show a hit in this cycle --- hence the
rising/falling edge for this cycle only occurs during the next cycle,
leaving a single **very** long PWM signal...

I have verified this on an oscilloscope - it really does happen! Sad
Is there a trick to avoid that? I know having one extra long pulse
doesn't sound dramatic in motor PWM - but e.g. in servo control it
might be a more severe problem! So we should be able to avoid that,
shouldn't we?

Possible fixes:
- only change value when T0_TC is at zero (difficult to do for a fast
PWM cycle)
- only change T0_MR2 in tiny steps (well, doesn't solve the problem,
might still occur, only less likely)
- when updating T0_MR2 explicitly check T0_TC against the new setting,
and possibly change the PWM-output-pin by hand. How would I do that?
The output is configured as PWM pin, so GPIO_SET or GPIO_CLR don't
work (I checked that).

Any suggestions?

Thanks a lot!

Jorg

PS: Upon request I can send a (huge) source code and/or images that
demonstrate the problem...

An Engineer's Guide to the LPC2100 Series

Hi, one way to avoid this to enable the interrupts for the timer when
you want to change the duty cycle. Once you hit the IRQ you disable
the interrupt (not just clear it), check a variable that you've
preloaded with your new desired duty cycle and then load register MR2.
To be doubly sure you could then reset the timer from within the
interrupt after loading MR2. This loading of MR2 and resetting the
timer shouldn't delay the duty cycle by more than a few dozen
processor clock cycles.

We're doing this on a 2103 at about 20 kHz with negligible impact on
the system. If it's fairly critical thing you could stick it in the
FIQ which should give you an interrupt of less than a micro second or
two at most.

Hope that helps - or at least maybe gives you an idea to try something
different.

Also - NXP have an application note for PWM motor control on their
website. I don't remember the details but that might be worth checking.

Darcy

--- In l..., "joconradt" wrote:
>
> Hi LPC users,
>
> I am programming LPC2103 in a motor control application using PWM on
> timer0. I have set T0_MR3 to specify the cycle length (let's say 1000
> timer ticks) and I am using T0_MR2 to specify the duty cycle for the
> motor output on Mat0.2 (P0.16). That all works well Smile
>
> I am concerned about the following scenario: the motor is set to a
> duty cycle of 700, but I want to reduce the cycle to 600. When I
> update the register T0_MR2, the current timer value (T0_TC) might be
> in-between 600 and 700 - and thus the comparison with the match
> register will not show a hit in this cycle --- hence the
> rising/falling edge for this cycle only occurs during the next cycle,
> leaving a single **very** long PWM signal...
>
> I have verified this on an oscilloscope - it really does happen! Sad
> Is there a trick to avoid that? I know having one extra long pulse
> doesn't sound dramatic in motor PWM - but e.g. in servo control it
> might be a more severe problem! So we should be able to avoid that,
> shouldn't we?
>
> Possible fixes:
> - only change value when T0_TC is at zero (difficult to do for a fast
> PWM cycle)
> - only change T0_MR2 in tiny steps (well, doesn't solve the problem,
> might still occur, only less likely)
> - when updating T0_MR2 explicitly check T0_TC against the new setting,
> and possibly change the PWM-output-pin by hand. How would I do that?
> The output is configured as PWM pin, so GPIO_SET or GPIO_CLR don't
> work (I checked that).
>
> Any suggestions?
>
> Thanks a lot!
>
> Jorg
>
> PS: Upon request I can send a (huge) source code and/or images that
> demonstrate the problem...
>

hi jorg.
Soon i'll be starting to develop an application for motor control
(ACIM and Servo)..... i gad gone through documents.....
Dont u have PWM registers as such in ur controller instead of using
the timer 0 register..... If u've then its the best thing use it
otherwise v'll 've to take care of the timeing v update the
register... if it is the pWM register the updation of the register
at the rite time 'll be taken care by the peripheral itself..

I'll be able to get a better suggestion immediatelly after i get all
the required things. till then sorry.

But i wanna know which algorithm aare u following for the motor
control.... if so i would like u to fwd me the documents if not a
problem...

regards
Rajeev
--- In l..., "joconradt" wrote:
>
> Hi LPC users,
>
> I am programming LPC2103 in a motor control application using PWM
on
> timer0. I have set T0_MR3 to specify the cycle length (let's say
1000
> timer ticks) and I am using T0_MR2 to specify the duty cycle for
the
> motor output on Mat0.2 (P0.16). That all works well Smile
>
> I am concerned about the following scenario: the motor is set to a
> duty cycle of 700, but I want to reduce the cycle to 600. When I
> update the register T0_MR2, the current timer value (T0_TC) might
be
> in-between 600 and 700 - and thus the comparison with the match
> register will not show a hit in this cycle --- hence the
> rising/falling edge for this cycle only occurs during the next
cycle,
> leaving a single **very** long PWM signal...
>
> I have verified this on an oscilloscope - it really does happen!
Sad
> Is there a trick to avoid that? I know having one extra long pulse
> doesn't sound dramatic in motor PWM - but e.g. in servo control it
> might be a more severe problem! So we should be able to avoid that,
> shouldn't we?
>
> Possible fixes:
> - only change value when T0_TC is at zero (difficult to do for a
fast
> PWM cycle)
> - only change T0_MR2 in tiny steps (well, doesn't solve the
problem,
> might still occur, only less likely)
> - when updating T0_MR2 explicitly check T0_TC against the new
setting,
> and possibly change the PWM-output-pin by hand. How would I do
that?
> The output is configured as PWM pin, so GPIO_SET or GPIO_CLR don't
> work (I checked that).
>
> Any suggestions?
>
> Thanks a lot!
>
> Jorg
>
> PS: Upon request I can send a (huge) source code and/or images that
> demonstrate the problem...
>

hi jorg wer u succefull in running the motor
rajeev

--- In l..., "urjust2oocool"
wrote:
>
> hi jorg.
> Soon i'll be starting to develop an application for motor control
> (ACIM and Servo)..... i gad gone through documents.....
> Dont u have PWM registers as such in ur controller instead of
using
> the timer 0 register..... If u've then its the best thing use it
> otherwise v'll 've to take care of the timeing v update the
> register... if it is the pWM register the updation of the register
> at the rite time 'll be taken care by the peripheral itself..
>
> I'll be able to get a better suggestion immediatelly after i get
all
> the required things. till then sorry.
>
> But i wanna know which algorithm aare u following for the motor
> control.... if so i would like u to fwd me the documents if not a
> problem...
>
> regards
> Rajeev
> --- In l..., "joconradt" wrote:
> >
> > Hi LPC users,
> >
> > I am programming LPC2103 in a motor control application using
PWM
> on
> > timer0. I have set T0_MR3 to specify the cycle length (let's say
> 1000
> > timer ticks) and I am using T0_MR2 to specify the duty cycle for
> the
> > motor output on Mat0.2 (P0.16). That all works well Smile
> >
> > I am concerned about the following scenario: the motor is set to
a
> > duty cycle of 700, but I want to reduce the cycle to 600. When I
> > update the register T0_MR2, the current timer value (T0_TC)
might
> be
> > in-between 600 and 700 - and thus the comparison with the match
> > register will not show a hit in this cycle --- hence the
> > rising/falling edge for this cycle only occurs during the next
> cycle,
> > leaving a single **very** long PWM signal...
> >
> > I have verified this on an oscilloscope - it really does happen!
> Sad
> >
> >
> > Is there a trick to avoid that? I know having one extra long
pulse
> > doesn't sound dramatic in motor PWM - but e.g. in servo control
it
> > might be a more severe problem! So we should be able to avoid
that,
> > shouldn't we?
> >
> > Possible fixes:
> > - only change value when T0_TC is at zero (difficult to do for a
> fast
> > PWM cycle)
> > - only change T0_MR2 in tiny steps (well, doesn't solve the
> problem,
> > might still occur, only less likely)
> > - when updating T0_MR2 explicitly check T0_TC against the new
> setting,
> > and possibly change the PWM-output-pin by hand. How would I do
> that?
> > The output is configured as PWM pin, so GPIO_SET or GPIO_CLR
don't
> > work (I checked that).
> >
> > Any suggestions?
> >
> > Thanks a lot!
> >
> > Jorg
> >
> > PS: Upon request I can send a (huge) source code and/or images
that
> > demonstrate the problem...
>
could i jus go through your motor control code

Raj

----- Original Message ----
From: joconradt
To: l...
Sent: Friday, May 23, 2008 1:53:38 AM
Subject: [lpc2000] PWM glitch possible when setting new duty-cycle value?
Hi LPC users,

I am programming LPC2103 in a motor control application using PWM on
timer0. I have set T0_MR3 to specify the cycle length (let's say 1000
timer ticks) and I am using T0_MR2 to specify the duty cycle for the
motor output on Mat0.2 (P0.16). That all works well Smile

I am concerned about the following scenario: the motor is set to a
duty cycle of 700, but I want to reduce the cycle to 600. When I
update the register T0_MR2, the current timer value (T0_TC) might be
in-between 600 and 700 - and thus the comparison with the match
register will not show a hit in this cycle --- hence the
rising/falling edge for this cycle only occurs during the next cycle,
leaving a single **very** long PWM signal...

I have verified this on an oscilloscope - it really does happen! Sad

Is there a trick to avoid that? I know having one extra long pulse
doesn't sound dramatic in motor PWM - but e.g. in servo control it
might be a more severe problem! So we should be able to avoid that,
shouldn't we?

Possible fixes:
- only change value when T0_TC is at zero (difficult to do for a fast
PWM cycle)
- only change T0_MR2 in tiny steps (well, doesn't solve the problem,
might still occur, only less likely)
- when updating T0_MR2 explicitly check T0_TC against the new setting,
and possibly change the PWM-output-pin by hand. How would I do that?
The output is configured as PWM pin, so GPIO_SET or GPIO_CLR don't
work (I checked that).

Any suggestions?

Thanks a lot!

Jorg

PS: Upon request I can send a (huge) source code and/or images that
demonstrate the problem...



Memfault Beyond the Launch