# 18F4620 TMR1 Oshonsoft

#### camerart

Joined Feb 25, 2013
3,736
Hi,
Here is a TMR1 test program for 18F4620, which needs INTERRUPT time setting [ TMR1L = TMR1H ]

Here is a calculation, to assist the settings: (Thanks E)
(The OSC is from an 8MHz XTL with PLL enabled.)

[[ Prescaler for TMR1 look at T1CON = 0x30' = 8:1, so thats 1MHz/8= 125KHz or 8uSec

Then TMR1 if loaded with 0xFFFF =65536 division =1.97Hz or ~0.52Sec period.

So load TMR1 with 0x0BDC [ decimal 65536-62500=3036] , that will give 8uSec*62500 = 0.5Sec.
So it will have to count UP from 3036 decimal to 65536 then roll over to 0000 count and generate an Interrupt every 0.5sec

You MUST reload TMR1 every time its in the Interrupt subroutine with 0x0BDC ]]

EDIT: I've coloured the 8's RED. Are these two different, in other words OSC/8/8 ?

C.

#### Attachments

• 1.3 KB Views: 8
Last edited:

#### ericgibbs

Joined Jan 29, 2010
19,106
[[ Prescaler for TMR1 look at T1CON = 0x30' = 8:1, so thats 1MHz/8= 125KHz or 8uSec

hi C,

If the Xtal is 8MHz and the PLL is enabled the CPU clock is 32MHz

Without the PLL enabled the Internal Clock for a 8MHz xtal is 8MHz/4 = 2MHz == 0.5uSec.
So if the Prescaler is set to 8, thats 2MHz/8 = 250KHz == 4uSecs

If TMR1 is set for 16Bit Mode ie: 65535/6 counts , the shortest interval between Interrupts 4 uSec*65536 =0.262144Seconds
So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec]

REM: It is an UP counter that rolls over at 0xFFFF > 0x0000 to generate an Interrupt]

As this is only 0,25Sec, you need to have a counter in the Inrerrupt routine that counts to 2, in order get 0.5Second.
'
If the Internal clock is 32MHz, the above figures have to be recalculated to suit in order to get 0.5Sec

E

#### camerart

Joined Feb 25, 2013
3,736
[[ Prescaler for TMR1 look at T1CON = 0x30' = 8:1, so thats 1MHz/8= 125KHz or 8uSec

hi C,

If the Xtal is 8MHz and the PLL is enabled the CPU clock is 32MHz

Without the PLL enabled the Internal Clock for a 8MHz xtal is 8MHz/4 = 2MHz == 0.5uSec.
So if the Prescaler is set to 8, thats 2MHz/8 = 250KHz == 4uSecs

If TMR1 is set for 16Bit Mode ie: 65535/6 counts , the shortest interval between Interrupts 4 uSec*65536 =0.262144Seconds
So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec]

REM: It is an UP counter that rolls over at 0xFFFF > 0x0000 to generate an Interrupt]

As this is only 0,25Sec, you need to have a counter in the Inrerrupt routine that counts to 2, in order get 0.5Second.
'
If the Internal clock is 32MHz, the above figures have to be recalculated to suit in order to get 0.5Sec

E
Hi E,
My setup has an 8MHz XTL and PLL, so 32MHz clock. Does the prescaler and all of those calculations work with this set-up?

Is this correct
32MHz xtal is 32MHz/4 = 8MHz = 2.0uSec.
So if the Prescaler is set to 8, thats 8MHz/8 = 1MHHz == 16uSecs

C.

#### ericgibbs

Joined Jan 29, 2010
19,106
hi C,
Run this file in the sim.
Use IDE 'Real Time Duration' to measure the time.
There is a Break before the Intr subr and one in the Intr sub, it takes a while to reach 0.5Sec.
E
Note the Real time on the 1st Break, then restart using Ultimate, subtract the first time from the 2nd.
Takes about 2 -3 minutes to run

#### Attachments

• 12.2 KB Views: 2
• 1.7 KB Views: 4

#### camerart

Joined Feb 25, 2013
3,736
hi C,
Run this file in the sim.
Use IDE 'Real Time Duration' to measure the time.
There is a Break before the Intr subr and one in the Intr sub, it takes a while to reach 0.5Sec.
E
Note the Real time on the 1st Break, then restart using Ultimate, subtract the first time from the 2nd.
Takes about 2 -3 minutes to run
Hi E,
I removed the second set of configs!

It looks like it's going to take an hour on my computer even at ultimate RATE. I tried it live, by removing the BREAK and adding LEDS, still it didn't work properly.

There appears to be something wrong, I'll keep checking

C.

#### ericgibbs

Joined Jan 29, 2010
19,106
Its pointless removing the Breaks!
It takes only 5 minutes to run to 0.5Sec on my 4Giga PC

#### camerart

Joined Feb 25, 2013
3,736
Its pointless removing the Breaks!
It takes only 5 minutes to run to 0.5Sec on my 4Giga PC
Hi E,
I'm not sure how fast my computer is, but it's fairly new, and on this system, I started the simulator with your settings, 40 minutes ago, and INT_CNT hasn't counted to 1 yet.
I'll keep checking. Problems are normally at my end
C

#### ericgibbs

Joined Jan 29, 2010
19,106
Where do you expect a 1 to appear.?

#### Ian Rogers

Joined Dec 12, 2012
1,136
You have to set OSCCON or it defaults to 500khz If it isn't set to 4 or 8 Mhz the PLL will not kick in either.

OSCCON = 0x70

If you are using the serial port at 32Mhz I suggest this line as well
OSCTUNE= 0x40

This sets it to center...

#### Ian Rogers

Joined Dec 12, 2012
1,136
Whoah!! Hold up Ian... You said ext crystal.... Shutting up now.. Just check your config OSC settings..

#### jjw

Joined Dec 24, 2013
823
Hi E,
My setup has an 8MHz XTL and PLL, so 32MHz clock. Does the prescaler and all of those calculations work with this set-up?

Is this correct
32MHz xtal is 32MHz/4 = 8MHz = 2.0uSec.
So if the Prescaler is set to 8, thats 8MHz/8 = 1MHHz == 16uSecs

C.
8Mhz = 0.125us
Prescaler 8 - > 1us

#### camerart

Joined Feb 25, 2013
3,736
Hi all,
E, Here's an image of where I expect '1' to appear.

I, I fully understand the OSCCON mistake, it took me a while to spot it

Can someone clarify, if the Prescaler and calculations work with 8MHz XTL+PLL, please. It's not clear to me.

C.

#### Attachments

• 252.8 KB Views: 3

#### jjw

Joined Dec 24, 2013
823
What is the problem?
Slow simulation?
I added intcnt to program in #1, changed TMR1H = 0xFF and it runs to first interrupt in a few seconds in the simulator.

You can't get 0.5 second interrupt with 32MHz oscillator and timer1. Maximum time is 65536 us or 0.065 s

#### camerart

Joined Feb 25, 2013
3,736
What is the problem?
Slow simulation?
I added intcnt to program in #1, changed TMR1H = 0xFF and it runs to first interrupt in a few seconds in the simulator.

You can't get 0.5 second interrupt with 32MHz oscillator and timer1. Maximum time is 65536 us or 0.065 s
Hi J,
I very rarely change CODE written for me, unless I'm feeling confident (I recall the telling off I had )

I now have done what you suggest and, of course it works.

Can you clarify, that your use of OSCILLATOR covers XTLs also please?.

When you say "Maximum time is 65536 us or 0.065" 'E' suggested adding a COUNT, which I assume to be approx x6. Is this correct?
C.

Last edited:

#### ericgibbs

Joined Jan 29, 2010
19,106
Hi C,
Use a count load of :
So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec] == 8 times 0.0625Seconds = 0.5Sec.

With a IntCntr > 7 you will get 0.5Seconds, as shown in my Basic program.
E

#### jjw

Joined Dec 24, 2013
823
Hi J,
I very rarely change CODE written for me, unless I'm feeling confident (I recall the telling off I had )

I now have done what you suggest and, of course it works.

Can you clarify, that your use of OSCILLATOR covers XTLs also please?.

When you say "Maximum time is 65536 us or 0.065" 'E' suggested adding a COUNT, which I assume to be approx x6. Is this correct?
C.
I don't think, that the simulator cares about oscillator settings. Just set the frequency you are using.

Btw why is the 0.5s interrupt important? Can't it be shorter?

#### camerart

Joined Feb 25, 2013
3,736
I don't think, that the simulator cares about oscillator settings. Just set the frequency you are using.

Btw why is the 0.5s interrupt important? Can't it be shorter?
Hi J,
I've just posted a thread 'How the simulator speed' mine's running much too slow.

Ok, regarding OSCILLATOR and XTL, thanks.

The actual time of the INTERRUPT DELAY is not important at this stage, I'm preparing for LIVE tests, and need to change it, 0.5S or 1S is a good starter.
C.

#### camerart

Joined Feb 25, 2013
3,736
Hi C,
Use a count load of :
So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec] == 8 times 0.0625Seconds = 0.5Sec.

With a IntCntr > 7 you will get 0.5Seconds, as shown in my Basic program.
E
Hi E,
Ok, once I get sensible results, I can play a bit. (I've done this exercise a number of times, but it doesn't stick)

At the moment, my simulator takes about 45 S, with TMR1 set to 0xFF, which doesn't seem right.
C.

#### camerart

Joined Feb 25, 2013
3,736
Hi C,
Use a count load of :
So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec] == 8 times 0.0625Seconds = 0.5Sec.

With a IntCntr > 7 you will get 0.5Seconds, as shown in my Basic program.
E
Hi E,

In your answer [[ So you need to load TMR1 with 65536- 62500 decimal ie 0xFFFF - 0xF424 = 0x0BDB== [ 3036 dec] == 8 times 0.0625Seconds = 0.5Sec. ]]

Why didn't you calculate a larger number (Marked in RED)?
C

#### ericgibbs

Joined Jan 29, 2010
19,106
hi,
As I said TMR1 is an UP counter , so if you load it with 3036 decimal, it will have to count up to 65536, at which time it will over flow to 0000o and generate an Interrupt.
So 65536-[with a pre load of 3036] = 62500 counts to an interrupt.
As the PLL clock is 32MHZ, divided by 4= 8MHz and you are using the pre-scaler at divide by 8, the TMR1 clock= 1MHz,,,, which is 1uSec period per clock pulse.

So an Interrupt occurs every 62500uSec ie: 0.0625Seconds.
If you want to get an action, like get_msg every 0.5Secs, you have to count the number of interrupts, in this case 8 * 0.0625s = 0.5Seconds

Do you follow.?
E