View previous topic :: View next topic |
Author |
Message |
soonc
Joined: 03 Dec 2013 Posts: 215
|
Using Timer 0 with External Clock |
Posted: Sun Nov 26, 2017 5:07 pm |
|
|
PIC18F46K42
Compiler V5.075 Does not yet support the debugger for this chip.
I have a DS32KHz feeding Pin C1 which is the SOSCI pin.
I'm confused about how this works.
The header file has values from T0_DIV_1 to T0_DIV_32768
I expected this next line of code to interrupt once every second:
setup_timer_0( T0_SOSC | T0_DIV_32768 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
Nothing ever happens.
If I use this setting
setup_timer_0( T0_SOSC | T0_DIV_1 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
Interrupt happens every 2 seconds.
How can I make the interrupt happen once per second ?
What am I missing something here:
Update:
Using Timer_4 like this:
setup_timer_4( T4_CLK_SOSC | T4_DIV_BY_128 , 128, 2 ); // 1 second interrupt
Interrupt happens every 1 second.
I really want Timer_0 as I hope to use it when the CPU is in Sleep mode. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9229 Location: Greensville,Ontario
|
|
Posted: Sun Nov 26, 2017 6:19 pm |
|
|
It could be a compiler bug not setting the appropriate bits. Dump the listing and see what they are , compared to what the datasheet says they need to be.
I don't have that PIC but according to the datasheet it has 'pin selectable peripherals. It might be those have to be set/clrd as well ??
Jay |
|
|
soonc
Joined: 03 Dec 2013 Posts: 215
|
|
Posted: Sun Nov 26, 2017 7:38 pm |
|
|
temtronic wrote: | It could be a compiler bug not setting the appropriate bits. Dump the listing and see what they are , compared to what the datasheet says they need to be.
I don't have that PIC but according to the datasheet it has 'pin selectable peripherals. It might be those have to be set/clrd as well ??
Jay |
Yes I checked that already here is what I have for TMR0
setup_timer_0( T0_SOSC | T0_DIV_32768 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
Register addresses related to TMR0
T0CON = 3FB8h
T0CON1 = 3FB9h
TMR0H = 3FB7h
TMR0L = 3FB6h
PIE3 = 3993h
lst file
01B22: MOVLW 90
01B24: MOVWF 3FB8 // T0CON
01B26: MOVLW CF
01B28: MOVWF 3FB9 // T0CON1
Checked as followes:
T0CON 10010000 // 90h
EN = 1
MD16 = 1
OUT = 0 // I don't need to output TMR0
Post Scaler = 0 which is 1:1
T0CON1 11001111 // CFh
CS = SOSC
ASYNC = 1 Not Sync'ed
CKPS = 32768
PIE3 enable_interrupts(INT_TIMER0);
01B7C: BSF x93.7
TMR0 is listed in the .h Pin Select Input but as I'm using SOSC as the input clock source I should not have to use #pin_select I could be wrong about this.... ! There is mention of using External Clock... I'll look into that some more.
Also as the TMRO does work with this line of code
setup_timer_0( T0_SOSC | T0_DIV_1 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT. 1 );
but it interrupts every 2 seconds so I know the SOSC is being used.
These are early (bleeding edge) chips so who knows may be it's a silicon bug.
As I updated:
I can use TMR4 and produce a 1 second interrupt, but for future use when I want to put the cpu to sleep it has to be TMR0 !
Thanks for your suggestions. |
|
|
PCM programmer
Joined: 06 Sep 2003 Posts: 21708
|
|
Posted: Sun Nov 26, 2017 7:53 pm |
|
|
Quote: |
I have a DS32KHz feeding Pin C1 which is the SOSCI pin.
I expected this next line of code to interrupt once every second:
setup_timer_0( T0_SOSC | T0_DIV_32768 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
Nothing ever happens.
|
The parameter in bold is a prescaler. You have a 32768 Hz external
clock going into a "divide by 32768" prescaler. This means Timer0
is clocked at 1 Hz. You have Timer0 configured as 16 bits. These means
it takes 65536 clocks to roll over. That's 65536 seconds. That's why
nothing appears to ever happen. |
|
|
soonc
Joined: 03 Dec 2013 Posts: 215
|
|
Posted: Sun Nov 26, 2017 10:02 pm |
|
|
PCM programmer wrote: | Quote: |
I have a DS32KHz feeding Pin C1 which is the SOSCI pin.
I expected this next line of code to interrupt once every second:
setup_timer_0( T0_SOSC | T0_DIV_32768 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
Nothing ever happens.
|
The parameter in bold is a prescaler. You have a 32768 Hz external
clock going into a "divide by 32768" prescaler. This means Timer0
is clocked at 1 Hz. You have Timer0 configured as 16 bits. These means
it takes 65536 clocks to roll over. That's 65536 seconds. That's why
nothing appears to ever happen. |
I still don't get it... I'll leave this for later... Timer 2 and 4 make sense Timer 0 does not.
thanks |
|
|
Mike Walne
Joined: 19 Feb 2004 Posts: 1785 Location: Boston Spa UK
|
|
Posted: Mon Nov 27, 2017 6:04 am |
|
|
Quote: | Also as the TMRO does work with this line of code
setup_timer_0( T0_SOSC | T0_DIV_1 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT. 1 );
but it interrupts every 2 seconds so I know the SOSC is being used. |
I don't have your chip.
You say the code above interrupts once every 2 seconds.
The code is feeding your 32768 clock into a 16 bit counter.
(i.e. counts 0 to 65535).
I'd expect it to roll over once every 2 seconds!
Maybe running timer0 in 8 bit mode will yield desired 1 second roll over.
Mike |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9229 Location: Greensville,Ontario
|
|
Posted: Mon Nov 27, 2017 6:41 am |
|
|
I don't have it either but I'd like you to configure the post_scaler=0 ( /1). While the datasheet it will be 0, hence /1 = 1, I've learned it's best for YOU to tell the compiler and PIC exactly what you want.
If both pre and post scalers are 0, then you should get 32768 KHz, after that change one or the other and see what happens. A 2 channel scope will show what's going on.
Being a 'new' chip, it could have a bug or the compiler might.... |
|
|
soonc
Joined: 03 Dec 2013 Posts: 215
|
|
Posted: Mon Nov 27, 2017 8:12 am |
|
|
temtronic wrote: | I don't have it either but I'd like you to configure the post_scaler=0 ( /1). While the datasheet it will be 0, hence /1 = 1, I've learned it's best for YOU to tell the compiler and PIC exactly what you want.
If both pre and post scalers are 0, then you should get 32768 KHz, after that change one or the other and see what happens. A 2 channel scope will show what's going on.
Being a 'new' chip, it could have a bug or the compiler might.... |
I can make it interrupt once per second using 8 bit.
But that defeats the ultimate goal of what I was hoping to do.
I guess I'm more confused about how to make it a counter that interrupts at a preset count rather than a timer.... !
The clock is a DS32768 osc.
I need a counter that clocks every clock cycle and interrupts at 32768.
Then I need the ability to read the counter at any time and get a 1/32768 th resolution.
Running the thing in 8 bit mode does not allow me to do that, unless I'm just not understanding how to configure it.
Thanks for the help.
Update: I went back to the original code:
setup_timer_0( T0_EXT_L_TO_H | T0_SOSC | T0_DIV_1 | T0_INPUT_NOT_SYNCRONIZED | T0_16_BIT, 1 );
I added "T0_EXT_L_TO_H |" and I'll be able to get a 2 second counter interrupt with a a 1/32768 th resolution.
I can make that work for what I'm doing.
Thanks again for the help. |
|
|
temtronic
Joined: 01 Jul 2010 Posts: 9229 Location: Greensville,Ontario
|
|
Posted: Mon Nov 27, 2017 8:44 am |
|
|
You might like to look at the SW-RTC that's posted in the 'code library'. it use the PIC clock as the timing source.
For my PIC products I use an I2C RTC module using the DS1337. For $2 CDN I get the high accurate RTC, battery AND 2KB of EEPROM. It also has a 32KHz output pin..... The RTC also has 50+ bytes of battery backed up RAM.
Might be an option for you depending on application. |
|
|
|