Tuesday, May 26, 2020

Using timer 0 module of PIC16F887 in timer mode

Timer 0 module could be implement as timer mode or counter mode. In this post, I configure this module to run in timer mode. Running timer 0 module in timer mode, it could be implemented as:
  • a delay timer
  • a frequency generator
  • a software controlled PWM
To make it run in timer mode, we must do a software configuration as follow:
  • clear T0CS
  • select a preferring prescaler, with the PSA and PS bits.
  • clear timer 0 interrupt flag (T0IF)
  • clear timer 0
An example program below I use timer to create a delay to blink an LED every one second. I assign the T0CS to work as timer mode. I clear the PSA bit to select the timer 0 prescaler rate. The PSA default values is 0x07, giving a 1:256 prescaler value.

The MCU clock is 4 MHz. With the pipe-lining technique of PIC architecture, the instruction clock is a quarter of the MCU clock. So,
Using timer 0 module of PIC16F887 in timer mode
The period the instruction clock is,
Using timer 0 module of PIC16F887 in timer mode
Timer 0 prescaler is 1:256, giving 256 x 1 micro second = 256 micro seconds. So TMR0 is increase at every 256 micro seconds. TMR0 overflows when it rolls from 0xFF to 0x00, setting a the interrupt flag T0IF. The period that interrupt occurs is 256 x 256 micro seconds = 65 milli seconds.

Using this 65 milli seconds period, I want to toggle an LED every 1 second. So,

every 15 timer 0 overflow make one second.
Using timer 0 module of PIC16F887 in timer mode
Schematic diagram. PIC16F887 clocks at 4 MHz. The instruction clock
is 1 MHz. RB7 toggles every 1 second.

The C source code is here.

#include "xc.h"
// PIC16F887 Configuration Bit Settings
// CONFIG1
#pragma config FOSC = XT
#pragma config WDTE = OFF
#pragma config PWRTE = OFF
#pragma config MCLRE = ON
#pragma config CP = OFF
#pragma config CPD = OFF
#pragma config BOREN = ON
#pragma config IESO = ON
#pragma config FCMEN = ON
#pragma config LVP = OFF
// CONFIG2
#pragma config BOR4V = BOR40V
#pragma config WRT = OFF


void main(){
    unsigned char cnt=0;
    PORTB=0x00;
    TRISB7=0;
    T0CS=0;
    PSA=0;
    T0IF=0;
    TMR0=0;
    while(1){
        if(T0IF){
            cnt+=1;
            T0IF=0;
        }
        if(cnt>=15){
            cnt=0;
            RB7^=1;
        }
    }
}





No comments:

Post a Comment

Search This Blog

Labels

25AA010A (1) 8051 (7) 93AA46B (1) ADC (30) Analog Comparator (1) Arduino (15) ARM (6) AT89C52 (7) ATMega32 (54) AVR (57) CCS PICC (28) DAC (1) DHT11 (2) Display (105) Distance Sensor (3) DS18B20 (3) dsPIC (2) dsPIC30F1010 (2) EEPROM (5) Environment Sensor (4) esp8266 (1) I2C (29) Input/Output (67) Interrupt (19) Keil (5) Keypad (10) LCD (46) Master/Slave (1) MAX7221 (1) MCP23017 (5) MCP23S17 (4) Meter (3) MikroC (2) Motor (15) MPLABX (66) Nokia 5110 LCD (3) OLED (2) One-Wire (6) Oscillator (8) PCB (6) PCD8544 (3) PCF8574 (5) PIC (107) PIC12F (2) PIC16F628A (2) PIC16F630 (1) PIC16F716 (3) PIC16F818 (10) PIC16F818/819 (2) PIC16F84A (15) PIC16F876A (1) PIC16F877A (9) PIC16F88 (1) PIC16F887 (60) PIC18 (19) PIC18F1220 (4) PIC18F2550 (3) PIC18F4550 (12) PWM (11) RTC (8) Sensor (10) SH1106 (1) Shift Register (11) Shift Registers (2) SPI (24) STM32 (6) STM32 Blue Pill (6) STM32CubeIDE (6) STM32F103C8T6 (6) SysTick (3) temperature sensor (11) Thermometer (21) Timer/Counter (30) TM1637 (2) UART (7) Ultrasonic (4) Voltmeter (7) WDT (1) XC16 (2) XC8 (94)