From: Phil Hobbs on
Okay, so I'm trying to resurrect my long-deceased PIC skills. (I do a
lot of C++ programming, off and on, but my last significant firmware was
about 2000--the Footprints sensor, running on a PIC17C456.)

From last time, I remember that MCU programming is all about getting
the configuration bits right--once that's done, it's pretty simple.
Sooo, I'm trying something fairly simple to start with, namely
controlling an RC airplane servo.

The servo needs 0.8-2.4 ms pulses, at a rep rate between 50 and 100 Hz.
I'm using a PIC 18F46k20 demo board with a nice little OLED display,
running at a clock frequency of 64 MHz (16 MHz instruction clock). The
PWM is done with Timer 2 and capture/PWM module ECCP 1.

I started with demo program, which ran fine. Next I ported that to
Hi-Tech C, which I remember very fondly from back when--it was pretty
nearly bug-free, in stark contrast to Microchip's C17, which stank on
ice. So far, so good.

I got the PWM working OK, but with a 64 MHz clock, the slowest rate the
PWM can go is 4 kHz (10-bit resolution and 16x prescaler), which is too
quick for the servos. Sooo, I used the TMR2 interrupt handler to
implement a divide-by-64 counter. For N+M/1024 cycles, it turns ON the
RD5 output when the down-count reaches N, and then switches to the PWM
for cycle 0 only. That way, I could have N complete cycles and M/1024
partial cycles, yielding 15 bits resolution at a 61 Hz rep rate. Plenty
good for an RC servo.

However....

The 15 bits are made up of the number of full cycles (5 bits), bits 4
and 5 of the CCP1CON register, plus an 8-bit value in CCP1L. According
to the datasheet, any time I'm using x256 division in TMR2, I should be
getting 10 bits worth of resolution, but it's acting exactly as though I
were getting only 8--changing the programmed delay produces 4 times more
PWM duty cycle change than it should, and the two CCP1CON bits don't
seem to do anything, though I can read and write them correctly.

The setup values are:
T2CKPS0 = 0;
T2CKPS1 = 1; //prescale by 16
PR2 = 0xFF; // divide by 256
DC1B1:DC1B0:CCPR1L = many values

This is almost certainly pilot error, but the reason doesn't exactly
leap out of the 450-page datasheet.

C'mon, all you PIC guys--what gives?

Thanks

Phil Hobbs

--
Dr Philip C D Hobbs
Principal
ElectroOptical Innovations
55 Orchard Rd
Briarcliff Manor NY 10510
845-480-2058
hobbs at electrooptical dot net
http://electrooptical.net
From: David L. Jones on
Phil Hobbs wrote:
> Okay, so I'm trying to resurrect my long-deceased PIC skills. (I do a
> lot of C++ programming, off and on, but my last significant firmware
> was about 2000--the Footprints sensor, running on a PIC17C456.)
>
> From last time, I remember that MCU programming is all about getting
> the configuration bits right--once that's done, it's pretty simple.
> Sooo, I'm trying something fairly simple to start with, namely
> controlling an RC airplane servo.
>
> The servo needs 0.8-2.4 ms pulses, at a rep rate between 50 and 100
> Hz. I'm using a PIC 18F46k20 demo board with a nice little OLED
> display, running at a clock frequency of 64 MHz (16 MHz instruction
> clock). The PWM is done with Timer 2 and capture/PWM module ECCP 1.
>
> I started with demo program, which ran fine. Next I ported that to
> Hi-Tech C, which I remember very fondly from back when--it was pretty
> nearly bug-free, in stark contrast to Microchip's C17, which stank on
> ice. So far, so good.
>
> I got the PWM working OK, but with a 64 MHz clock, the slowest rate
> the PWM can go is 4 kHz (10-bit resolution and 16x prescaler), which
> is too quick for the servos. Sooo, I used the TMR2 interrupt handler
> to implement a divide-by-64 counter. For N+M/1024 cycles, it turns
> ON the RD5 output when the down-count reaches N, and then switches to
> the PWM for cycle 0 only. That way, I could have N complete cycles
> and M/1024 partial cycles, yielding 15 bits resolution at a 61 Hz rep
> rate. Plenty good for an RC servo.
>
> However....
>
> The 15 bits are made up of the number of full cycles (5 bits), bits 4
> and 5 of the CCP1CON register, plus an 8-bit value in CCP1L. According to
> the datasheet, any time I'm using x256 division in TMR2,
> I should be getting 10 bits worth of resolution, but it's acting
> exactly as though I were getting only 8--changing the programmed
> delay produces 4 times more PWM duty cycle change than it should, and
> the two CCP1CON bits don't seem to do anything, though I can read and
> write them correctly.
> The setup values are:
> T2CKPS0 = 0;
> T2CKPS1 = 1; //prescale by 16
> PR2 = 0xFF; // divide by 256
> DC1B1:DC1B0:CCPR1L = many values
>
> This is almost certainly pilot error, but the reason doesn't exactly
> leap out of the 450-page datasheet.
>
> C'mon, all you PIC guys--what gives?
>
> Thanks
>
> Phil Hobbs

Have you looked at the silicon errata?
http://ww1.microchip.com/downloads/en/DeviceDoc/80379A.pdf
and
http://ww1.microchip.com/downloads/en/DeviceDoc/80404C.pdf

There is an issue with Timer 1

Dave.

--
================================================
Check out my Electronics Engineering Video Blog & Podcast:
http://www.eevblog.com


From: Phil Hobbs on
On 2/5/2010 12:31 AM, David L. Jones wrote:
> Phil Hobbs wrote:
>> Okay, so I'm trying to resurrect my long-deceased PIC skills. (I do a
>> lot of C++ programming, off and on, but my last significant firmware
>> was about 2000--the Footprints sensor, running on a PIC17C456.)
>>
>> From last time, I remember that MCU programming is all about getting
>> the configuration bits right--once that's done, it's pretty simple.
>> Sooo, I'm trying something fairly simple to start with, namely
>> controlling an RC airplane servo.
>>
>> The servo needs 0.8-2.4 ms pulses, at a rep rate between 50 and 100
>> Hz. I'm using a PIC 18F46k20 demo board with a nice little OLED
>> display, running at a clock frequency of 64 MHz (16 MHz instruction
>> clock). The PWM is done with Timer 2 and capture/PWM module ECCP 1.
>>
>> I started with demo program, which ran fine. Next I ported that to
>> Hi-Tech C, which I remember very fondly from back when--it was pretty
>> nearly bug-free, in stark contrast to Microchip's C17, which stank on
>> ice. So far, so good.
>>
>> I got the PWM working OK, but with a 64 MHz clock, the slowest rate
>> the PWM can go is 4 kHz (10-bit resolution and 16x prescaler), which
>> is too quick for the servos. Sooo, I used the TMR2 interrupt handler
>> to implement a divide-by-64 counter. For N+M/1024 cycles, it turns
>> ON the RD5 output when the down-count reaches N, and then switches to
>> the PWM for cycle 0 only. That way, I could have N complete cycles
>> and M/1024 partial cycles, yielding 15 bits resolution at a 61 Hz rep
>> rate. Plenty good for an RC servo.
>>
>> However....
>>
>> The 15 bits are made up of the number of full cycles (5 bits), bits 4
>> and 5 of the CCP1CON register, plus an 8-bit value in CCP1L. According to
>> the datasheet, any time I'm using x256 division in TMR2,
>> I should be getting 10 bits worth of resolution, but it's acting
>> exactly as though I were getting only 8--changing the programmed
>> delay produces 4 times more PWM duty cycle change than it should, and
>> the two CCP1CON bits don't seem to do anything, though I can read and
>> write them correctly.
>> The setup values are:
>> T2CKPS0 = 0;
>> T2CKPS1 = 1; //prescale by 16
>> PR2 = 0xFF; // divide by 256
>> DC1B1:DC1B0:CCPR1L = many values
>>
>> This is almost certainly pilot error, but the reason doesn't exactly
>> leap out of the 450-page datasheet.
>>
>> C'mon, all you PIC guys--what gives?
>>
>> Thanks
>>
>> Phil Hobbs
>
> Have you looked at the silicon errata?
> http://ww1.microchip.com/downloads/en/DeviceDoc/80379A.pdf
> and
> http://ww1.microchip.com/downloads/en/DeviceDoc/80404C.pdf
>
> There is an issue with Timer 1
>
> Dave.
>

Thanks--I saw your video about silicon errata, so I did check before
starting. The chip I'm using is revision code 0x09 (B2). In the B
series errata, there are no apparent issues with Timer 2 or ECCP 1
except in full-bridge mode, whereas I'm using single mode.

Cheers

Phil Hobbs

--
Dr Philip C D Hobbs
Principal
ElectroOptical Innovations
55 Orchard Rd
Briarcliff Manor NY 10510
845-480-2058
hobbs at electrooptical dot net
http://electrooptical.net
From: Jon Slaughter on
Why not use the postscalar to further divide it by 16? Are you also stopping
the timer when the interrupt triggers?


From: Phil Hobbs on
On 2/5/2010 6:38 PM, Jon Slaughter wrote:
> Why not use the postscalar to further divide it by 16? Are you also
> stopping the timer when the interrupt triggers?
>
>

The postscaler doesn't work with PWM, and anyway I want the resolution.

Cheers

Phil Hobbs

--
Dr Philip C D Hobbs
Principal
ElectroOptical Innovations
55 Orchard Rd
Briarcliff Manor NY 10510
845-480-2058
hobbs at electrooptical dot net
http://electrooptical.net