|
|
View previous topic :: View next topic |
Author |
Message |
dluu13
Joined: 28 Sep 2018 Posts: 395 Location: Toronto, ON
|
Output compare not working when timer prescaler not 1 |
Posted: Tue Feb 05, 2019 10:20 am |
|
|
Hi, I am having a problem with the output compare module on a
PIC24FJ128GA308 with compiler version 5.082.
When the timer source of the OC module has a prescaler of anything
other than 1, the OC pin does not pulse as I expect it to.
Here is my code:
Code: | #include <24FJ128GA308.h>
#DEVICE ADC=12
#case
#FUSES ICSP1, NOJTAG, NODEBUG, NOWRT, NOPROTECT, WPDIS, NOWPCFG
#FUSES NOBROWNOUT, NODSBOR, NOVBATBOR
#FUSES NOLVR, NOIOL1WAY, VREFNORM_CVREFNORM, NOIESO
#FUSES NOWDT
#FUSES FRC_PLL, NOOSCIO
#use delay(clock=32MHz)
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#pin_select OC1=PIN_G6
#pin_select T4CK=PIN_E8
#word CLKDIV=getenv("SFR:CLKDIV")
struct
{
unsigned : 8;
unsigned RCDIV : 3;
unsigned DOZEN : 1;
unsigned DOZE : 3;
unsigned ROI : 1;
} CLKDIVbits;
#word CLKDIVbits=CLKDIV
int main(void)
{
CLKDIVbits.RCDIV = 0; // sets oscillator divider to 0
setup_timer4(TMR_EXTERNAL | TMR_DIV_BY_1, 1);
/****************** PROBLEM IS HERE ******************/
// setup_timer5(TMR_INTERNAL | TMR_DIV_BY_1); // works
setup_timer5(TMR_INTERNAL | TMR_DIV_BY_8); // does not work
setup_compare(1, COMPARE_SINGLE_PULSE | COMPARE_TIMER5 | COMPARE_TRIGGER | COMPARE_TRIG_SYNC_TIMER4);
set_compare_time(1, 200, 400);
enable_interrupts(INTR_GLOBAL);
enable_interrupts(INT_OC1);
enable_interrupts(INTR_CN_PIN | PIN_E1);
output_high(PIN_E2); // LED
while(1)
{
}
return 0;
}
#INT_OC1
void oc1_isr()
{
setup_compare(1, COMPARE_SINGLE_PULSE | COMPARE_TIMER5 | COMPARE_TRIGGER | COMPARE_TRIG_SYNC_TIMER4);
output_toggle(PIN_E2); // toggle my LED to show ISR is ran
}
#INT_CNI
void cni_isr() // gets triggered every time there is a change. this is the clock source to output into TMRCLK
{
output_high(PIN_E7); // connect timer pulse to timer clk in
output_low(PIN_E7);
output_high(PIN_E7);
output_low(PIN_E7);
} |
What I am doing is using Timer 4 as a trigger source to the OC module,
by using a button hooked up as the clock source to Timer 4. Note that in
my circuit, I have shorted PIN_E7 to PIN_E8. I don't see anything wrong
in the errata of the chip. When I look at the LST file, the only difference in
setting for the timer 5 control register between prescaler 1 and 8 setting is
at the TCKPS bits, as expected.
I can set Timer 4 to run from an internal source, and it will behave the
same way. I have also tried to use different timers and OC modules, with
the same result.
Do you guys have any idea? Let me know if you want me to try anything.
I have done this exact configuration on the PIC24FJ128GA204 Curiosity
Dev board from Microchip with no problems.
Thanks in advance!
Last edited by dluu13 on Tue Feb 05, 2019 1:16 pm; edited 1 time in total |
|
|
PrinceNai
Joined: 31 Oct 2016 Posts: 480 Location: Montenegro
|
|
Posted: Tue Feb 05, 2019 11:19 am |
|
|
Dear dluu,
for the price of being really stupid, I really don't have any experience with those chips. I don't get it exactly where are you pulsing the OC1 pin in your code? If you have anything on E7, isn't this a bit too fast to be visible at 32MHz?
Quote: |
{
output_high(PIN_E7); // connect timer pulse to timer clk in
output_low(PIN_E7);
output_high(PIN_E7);
output_low(PIN_E7);
} |
Not an answer, I know. I just ask for an explanation.
Regards,
Samo |
|
|
dluu13
Joined: 28 Sep 2018 Posts: 395 Location: Toronto, ON
|
|
Posted: Tue Feb 05, 2019 11:22 am |
|
|
PrinceNai wrote: | Dear dluu,
for the price of being really stupid, I really don't have any experience with those chips. I don't get it exactly where are you pulsing the OC1 pin in your code? If you have anything on E7, isn't this a bit too fast to be visible at 32MHz?
Quote: |
{
output_high(PIN_E7); // connect timer pulse to timer clk in
output_low(PIN_E7);
output_high(PIN_E7);
output_low(PIN_E7);
} |
Not an answer, I know. I just ask for an explanation.
Regards,
Samo |
No problem, this is really a very convoluted workaround... Unfortunately,
the OC module on this chip doesn't have a dedicated trigger pin, but I can
trigger from timer. Basically what I am doing is when I receive CN
interrupt from my button, I pulse PIN_E7 as a clock source to Timer4
which will cause it to overflow and trigger the CCP module.
The OC1 pulsing comes from the set_compare_time earlier on in the
setup. |
|
|
PrinceNai
Joined: 31 Oct 2016 Posts: 480 Location: Montenegro
|
|
Posted: Tue Feb 05, 2019 11:33 am |
|
|
Thanks for the explanation. Is it possible that the speed with which you change E7 makes a problem? |
|
|
dluu13
Joined: 28 Sep 2018 Posts: 395 Location: Toronto, ON
|
|
Posted: Tue Feb 05, 2019 11:46 am |
|
|
PrinceNai wrote: | Thanks for the explanation. Is it possible that the speed with which you change E7 makes a problem? |
I doubt that is the case, since I have the same problem even if I set the
Timer4 to run from internal clock. Once I change the prescaler for Timer5 to
anything other than 1, then OC1 no longer pulses.
Besides, I feel that even if the E7 pulsing is too quick, I should be able to
simply press my button a couple more times and Timer4 should overflow from that anyway. |
|
|
dluu13
Joined: 28 Sep 2018 Posts: 395 Location: Toronto, ON
|
|
Posted: Tue Feb 05, 2019 12:19 pm |
|
|
UPDATE - I've made a discovery:
It appears that indeed there is a pulse when I use another prescaler value.
The difference is that for some reason, when I use a prescaler value other
than 1 for Timer5, my OC1 ISR does not get triggered.
I am still confused but this gives me direction at least.
EDIT: correction: it appears that the ISR is running, but only once. However,
it appears that this line does not have the intended effect after running in the
ISR:
Code: | setup_compare(1, COMPARE_SINGLE_PULSE | COMPARE_TIMER5 | COMPARE_TRIGGER | COMPARE_TRIG_SYNC_TIMER4); |
I expected it to reset the OC module to prepare for another single pulse but it appears not to have reset. Or maybe it has, but somehow the Timer 5 prescaler not being 1 is messing it up. |
|
|
Ttelmah
Joined: 11 Mar 2010 Posts: 19535
|
|
Posted: Tue Feb 05, 2019 1:50 pm |
|
|
I think the extra time involved with a prescaler, and whatever the clock rate
actually is on your timer4, means that the syncronisation does not occur
in time. This is listed as one of the special circumstances in this mode,
which results in the module not resetting. |
|
|
dluu13
Joined: 28 Sep 2018 Posts: 395 Location: Toronto, ON
|
|
Posted: Tue Feb 05, 2019 2:10 pm |
|
|
Ttelmah wrote: | I think the extra time involved with a prescaler, and whatever the clock rate
actually is on your timer4, means that the syncronisation does not occur
in time. This is listed as one of the special circumstances in this mode,
which results in the module not resetting. |
But if it misses the current synchronisation, shouldn't it catch the next one?
Other than that, I still don't think it's the case that my trigger source is
running too fast for my timer5. If I run timer 4 like this:
Code: | setup_timer4(TMR_INTERNAL | TMR_DIV_BY_256, 65535); |
I get around a 1Hz trigger. It is still the case that giving a prescaler to timer 5
will prevent it from triggering.
Let me know if you think my logic is flawed.
Right now, I am setting OCxR and OCxR to 5 and 20, and 20 counts in the
OC timer register, which I am understanding comes from Timer 5, lasts
only 1.25 us, for a prescaler of 1, and 10 us for a prescaler of 8. There
should be plenty of time for the module to reset itself.
EDIT: If by the "special condition", you mean this one, I actually get
something different. My OC module does drive the pin back down and fire
the interrupt. (Click on thumbnails of images to see full size)
For some extra info, here are a couple of oscilloscope traces of my
pulses:
With Timer5 prescaler 1 (works properly)
With Timer5 prescaler 8 (only pulses once, and does not reset)
|
|
|
|
|
You cannot post new topics in this forum You cannot reply to topics in this forum You cannot edit your posts in this forum You cannot delete your posts in this forum You cannot vote in polls in this forum
|
Powered by phpBB © 2001, 2005 phpBB Group
|