PIC16F877A – Timer/Counter Tutorial

Now we will see the PIC16F877A Timer Tutorial. If you read this tutorial, you could generate this precise delay for your applications. Let’s start.

PIC16F877A Timer Tutorial

As the name suggests these are used to measure the time or generate the accurate time delay. The microcontroller can also generate/measure the required time delays by running loops, but the timer relieves the CPU from that redundant and repetitive task, allowing it to allocate maximum processing time for other tasks.

Timer is nothing but a simple binary counter that can be configured to count clock pulses(Internal/External). Once it reaches the Max value, it will roll back to zero setting up an OverFlow flag and generates the interrupt if enabled.

PIC16F877a has three timers.

  • Timer0 (8-bit timer)
  • Timer1 (16-bit timer)
  • Timer2 (8-bit timer)

All Timers can act as a timer or counter or PWM Generation. now we will see one by one.

To start using a timer we should understand some of the fancy terms like 8-bit/16-bit timer, Prescaler, Timer interrupts and Focs. Now, let us see what each one really means. As said earlier there are both the 8-bit and 16-bit Timers in our PIC16F877A. The main difference between them is that the 16-bit Timer has much better Resolution that the 8-bit Timer.

Prescaler is a name for the part of a microcontroller which divides oscillator clock before it will reach logic that increases timer status.  The range of the prescaler id is from 1 to 256 and the value of the Prescaler can be set using the OPTION Register (we will see this register later).

As the timer increments and when it reaches to its maximum value of 255 (for 8-bit timers) or 65536 (for 16-bit timers), it will trigger an interrupt and initialize itself to 0 back again. This interrupt is called as the Timer Interrupt. This interrupt informs the MCU that this particular time has lapped.

The Fosc stands for Frequency of the Oscillator, it is the frequency of the Crystal used. The time taken for the Timer register depends on the value of Prescaler and the value of the Fosc.

Timer 0

  • The Timer0 module timer/counter has the following features:
  • 8-bit timer/counter
  • Readable and writable
  • 8-bit software programmable prescaler
  • Internal or external clock select
  • Interrupt on overflow from FFh to 00h
  • Edge select for external clock

Registers used for Timer0

  • OPTION_REG
  • TMR0
  • INTCON

OPTION_REG

We perform all the necessary settings with OPTION_REG Register. The size of the register is 8 bits.

option-register-pic16f877a PIC16F877A - Timer/Counter TutorialR = Readable bit  W = Writable bit  U = Unimplemented bit, read as ‘0’  -n = Value at POR  ‘1’ = Bit is set  ‘0’ = Bit is cleared  x = Bit is unknown  

RBPU: PORTB Pull-up Enable bit (This bit is not used for timers)

1 = PORTB pull-ups are disabled
0 = PORTB pull-ups are enabled by individual port latch values

INTEDG  (This bit is not used for timers)

T0CS: TMR0 Clock Source Select bit

1 = Transition on T0CKI pin
0 = Internal instruction cycle clock (CLKO)

T0SE: TMR0 Source Edge Select bit

1 = Increment on high-to-low transition on T0CKI pin
0 = Increment on low-to-high transition on T0CKI pin

PSA: Prescaler Assignment bit

1 = Prescaler is assigned to the WDT
0 = Prescaler is assigned to the Timer0 module

PS2:PS0: Prescaler Rate Select bits

Timer0Prescalar PIC16F877A - Timer/Counter TutorialNote:There is only one prescaler available which is mutually exclusively shared between the Timer0 module and the Watchdog Timer. A prescaler assignment for the Timer0 module means that there is no prescaler for the Watchdog Timer and vice versa. This prescaler is not accessible but can be configured using PS2:PS0 bits of OPTION_REG.

INTCON Register

intcon-register-pic16f877a PIC16F877A - Timer/Counter Tutorial

GIE: Global Interrupt Enable bit

1-Enables all unmasked interrupts
0-Disables all interrupts

PIE: Peripheral Interrupt Enable bit

1-Enables all unmasked peripheral interrupts
0-Disables all peripheral interrupts

TMR0IE: TMR0 Overflow Interrupt Enable bit

1-Enables the TMR0 interrupt
0-Disables the TMR0 interrupt

INTE: Not for Timers

RBIE: Not for Timers

TMR0IF: TMR0 Overflow Interrupt Flag bit

1-TMR0 register has overflowed (must be cleared in software)
0-TMR0 register did not overflow

INTF: Not for Timers

RBIF: Not for Timers

TMR0 Register

This is the 8-bit register which holds the timer values. For example initially it will be 0. It will increment by one per one clock cycle. When it reaches 255, it will trigger the TMR0IF bit in INTCON Register. Then again starts from 0.

Delay Calculation for 1 second

TIMER0_CRYSTAL PIC16F877A - Timer/Counter Tutorial

Here, My fclk = 11.0592MHz (You can put your board’s fclk)

Prescaler = 256 (It is based on PS0 – PS2 bits in OPTION_REG)

TMR0 = 0. (My TMR0’s value will be 0)

Desire Delay (Tout = 1 second) So Fout = 1  (Tout = 1/Fout)

Apply this values to that above formula.

Count = 11059200 / (4*256*256*1)

Count = 42.1875 (approximately 42).

Timer0 Code

In this code LED is connected to Port B. That LEDs are blinking at every 1 second.

Timer 1

The timer TMR1 module is an 16-bit timer/counter with the following features:

  • 16-bit timer/counter with two 8-Bit register TMR1H/TMR1L
  • Readable and writable
  • software programmable prescaler upto 1:8
  • Internal or external clock select
  • Interrupt on overflow from FFFFh to 00h
  • Edge select for external clock

Registers used for Timer1

  • T1CON
  • TMR1 (TMRIH, TMRIL)
  • PIR1

T1CON Register

t1con-register-pic16f877a PIC16F877A - Timer/Counter Tutorial

T1CKPS1:T1CKPS0:Timer1 Input Clock Prescale Select bits

11 = 1:8 prescale value
10 = 1:4 prescale value
01 = 1:2 prescale value
00 = 1:1 prescale value

T1OSCEN: Timer1 Oscillator Enable Control bit

1-Oscillator is enabled
0-Oscillator is shut-off

T1SYNC: Timer1 External Clock Input Synchronization Control bit

1-Do not synchronize external clock input
0-Synchronize external clock input

TMR1CS: Timer1 Clock Source Select bit

1-External clock from pin RC0/T1OSO/T1CKI (on the rising edge)
0-Internal clock (FOSC/4)

TMR1ON: Timer1 On bit

1-Enables Timer1
0-Stops Timer1

TMR1 Register

Timer1 has a register called TMR1 register, which is 16 bits of size.  Actually, the TMR1 consists of two 8-bits registers:

  • TMR1H
  • TMR1L

It increments from 0000h to the maximum value of 0xFFFFh (or  65,535 decimal). The TMR1 interrupt, if enabled, is generated on overflow which is latched in interrupt flag bit, TMR1IF (PIR1<0>). This interrupt can be enabled/disabled by setting/clearing TMR1 interrupt enable bit, TMR1IE (PIE1<0>). You can initialize the value of this register to what ever you want (not necessarily “0”).

PIR1 Register

This register contains the Timer1 overflow flag.(TMR1IF).

TMR1IF – TMR1 overflow Interrupt Flag bit.
This flag marks the end of ONE cycle count. The flag need to be reset in the software if you want to do another cycle count. We can read the value of the register TMR1 and write into. We can reset its value at any given moment (write) or we can check if there is a certain numeric value that we need (read).

Delay Calculation for 1 second

TIMER1_CRYSTAL PIC16F877A - Timer/Counter Tutorial

Here, My fclk = 11.0592MHz (You can put your board’s fclk)

Prescaler = 1 (It is based on T1CKPS1 – T1CKPS0 bits in T1CON Register)

TMR1 = 0. (My TMR1’s value will be 0)

Desire Delay (Tout = 1 second) So Fout = 1  (Tout = 1/Fout)

Apply this values to that above formula.

Count = 11059200 / (4*1*65536*1)

Count = 42.1875 (approximately 42).

Timer1 Code

In this code LED is connected to Port B. That LEDs are blinking at every 1 second.

Timer 2

The TImer2 module is an 8-bit timer/counter with the following features:

  • 8-bit timer/counter
  • Readable and writable
  • Software programmable prescaler/PostScaler upto 1:16
  • Interrupt on overflow from FFh to 00h

Registers used for Timer2

  • T2CON
  • TMR2
  • PIR1
  • PR2

T2CON Register

t2con-register-pic16f877a PIC16F877A - Timer/Counter Tutorial

TOUTPS3:TOUTPS0: Timer2 Output Postscale Select bits

0000 = 1:1 postscale
0001 = 1:2 postscale
0010 = 1:3 postscale



1111 = 1:16 postscale

TMR2ON: Timer2 On bit

1-Timer2 is on
0-Timer2 is off

T2CKPS1:T2CKPS0: Timer2 Clock Prescale Select bits

00 = Prescaler is 1
01 = Prescaler is 4
1x = Prescaler is 16

TMR2 & PR2 Register

  • TMR2 – The register in which the “initial” count value is written.
  • PR2 – The register in which the final or the maximum count value is written.

PIR1 Register

This register contains the Timer2 overflow flag(TMR2IF).

Delay Calculation for 1 second

TIMER2_fout PIC16F877A - Timer/Counter Tutorial

Here, My fclk = 11.0592MHz (You can put your board’s fclk)

Prescaler = 1 (It is based on T2CKPS1:T2CKPS0 bits in T2CON)

Postscaler = 16 (It is based on TOUTPS3:TOUTPS0 bits in T2CON)

TMR2 = 0. (My TMR2’s value will be 0)

PR2 = 255 (My PR2’s value will be 255)

Desire Delay (Tout = 1 second) So Fout = 1  (Tout = 1/Fout)

Apply this values to that above formula.

Count = 11059200 / (4*1*(256-0)*16*1)

Count = 675.

Timer2 Code

In this code LED is connected to Port B. That LEDs are blinking at every 1 second.

 

Download our new Android app. You can learn all Embedded Tutorials from your Android Phone easily.

Click Here to Download App!