Getting started with PIC16F Architecture

Getting started with PIC architecture

Tags: Introduction of PIC16F,PIC16F Architecture ,Memory Organization of PIC16F877,
Overall rating

Introduction of PIC16F

The PIC16F family of devices is CMOS (Complementary Metal Oxide Semiconductor) microcontrollers consisting of the PIC16F83, PIC16C83, PIC16F84, PIC16C84, PIC16LCR8X and PIC16LF8X types.

CMOS technology offers a number of advantages over other technologies. For example, CMOS circuits consume very little power, operate over quite a wide voltage range and are quite forgiving of bad layout and electrical noise.

PIC is a family of modified Harvard architecture microcontrollers made by Microchip Technology, derived from the PIC1650 originally developed by General Instrument's Microelectronics Division.

The name PIC initially referred to"Peripheral Interface Controller".

PICs are popular with both industrial developers and hobbyists alike due to their low cost, wide availability, large user base, extensive collection of application notes, availability of low cost or free development tools, and serial programming (and re-programming with flash memory) capability.

Since 1998, Microchip Technology continuously developed new high performance microcontrollers with new complex architecture and enhanced in-built peripherals. PIC microcontroller is based on Harvard architecture.

At present PIC microcontrollers are widely used for industrial purpose due to its high performance ability at low power consumption.

It is also very famous among hobbyists due to moderate cost and easy availability of its supporting software and hardware tools like compilers, simulators, debuggers etc.

The 8-bit PIC microcontroller is divided into following four categories on the basis of internal architecture:

  • Base Line PIC
  • Mid-Range PIC
  • Enhanced Mid-Range PIC
  • PIC18

Base Line PIC

Base Line PICs are the least complex PIC microcontrollers. These microcontrollers work on 12-bit instruction architecture which means that the word size of instruction sets are of 12 bits for these controllers.

These are smallest and cheapest PICs, available with 6 to 40 pin packaging. The small size and low cost of Base Line PIC replaced the traditional ICs like 555, logic gates etc. in industries.

Mid-Range PIC

Mid-Range PICs are based on 14-bit instruction architecture and are able to work up to 20 MHz speed. These controllers are available with 8 to 64 pin packaging. These microcontrollers are available with different peripherals like ADC, PWM, Op-Amps and different communication protocols like USART, SPI, I2C (TWI), etc. which make them widely usable microcontrollers not only for industry but for hobbyists as well.

Enhanced Mid-Range PIC

These controllers are enhanced version of Mid-Range core. This range of controllers provides additional performance, greater flash memory and high speed at very low power consumption. This range of PIC also includes multiple peripherals and supports protocols like USART, SPI, and I2C and so on.


PIC18 range is based on 16-bit instruction architecture incorporating advanced RISC architecture which makes it highest performer among the all 8-bit PIC families.

The PIC18 range is integrated with new age communication protocols like USB, CAN, LIN, Ethernet (TCP/IP protocol) to communicate with local and/or internet based networks. This range also supports the connectivity of Human Interface Devices like touch panels etc.

Besides 8-bit microcontrollers, Microchip also manufactures 16-bit and 32-bit microcontrollers. Recently Microchip developed XLP (Extreme Low Power) series microcontrollers which are based on NanoWatt technology. These controllers draw current in order of nanoamperes (nA).

The following table compares the above four categories:


Base Line


Enhanced Mid-Range


No. of Pins





Program Memory

Up to 3 KB

Up to 14 KB

Up to 28 KB

Up to 128 KB

Data Memory

Up to 134 Bytes

Up to 368 Bytes

Up to 1.5 KB

Up to 4 KB

Instruction Length





No. of instruction set






 5 MIPS*



Up to 16 MIPS


• Comparator

• 8-bit ADC

• Data Memory

•Internal Oscillator

In addition of baseline

·   SPI

·   I2C

·   UART

·   PWM

·   10-bit ADC

·   OP-Amps

In addition of Mid-range

·   High Performance

·   Multiple communication peripherals


In addition of Enhanced Mid-range




• Ethernet

• 12-bit ADC


PIC10,PIC12, PIC16

PIC12, PIC16




Memory variations

The PIC microcontrollers are available with different memory options which are mask ROM, EPROM and flash memory. They are denoted with different symbols as given in the following table:


Memory Type






Mask ROM



Flash memory



PIC microcontrollers are also available with extended voltage ranges which reduce the frequency range. The operating voltage range of these PICs is 2.0-6.0 volts. The letter ‘L’ is included in controller’s name to denote extended voltage range controllers. For example, PIC16LFxxx (Operating voltage range is 2.0-6.0 volts).

Peripheral integration is key with communication and control peripherals like SPI, I2C™, UART, PWM, ADC and comparators as well as specialized peripherals for USB, m Touch™ Sensing, LCD, CAN and Ethernet. Customers have made PIC MCUs a worldwide standard, with over one million development systems shipped. PIC microcontrollers are quick and easy to design into a wide variety of applications with a long history of dependable product delivery.

Basic Characteristics of PIC16F

The main Features of PIC16F is,

High-performance RISC CPU

  • Lead-free : RoHS - compliant
  • Operating speed : 20Mhz, 200ns instruction cycle
  • Operating voltage : 4.0-5.5volts
  • Industrial temperature range(-40 to +85 degrees)
  • 15 Interrupt sources
  • 35 single word instructions
  • All single-cycle instructions except for program branches

Special Microcontroller Features

  • Flash memory : 14.3KB(8192 words)
  • Data SRAM : 368 bytes
  • Data EEPROM : 256 bytes
  • Self-reprogrammable under software control
  • In-circuit serial programming via two pins
  • Watchdog timer with on-chip RC oscillator
  • Programmable code protection
  • Power-saving code protection
  • Selectable oscillator options
  • In-circuit debug via two pins

Peripheral Features

  • 33 I/O pins : 5 I/O ports
  • Timer0 : 8-bit timer/counter with 8-bit pre-scaler
  • Timer1 : 16-bit timer/counter with pre-scaler
  • Timer2 : 8-bit timer/counter with 8-bit period register, pre-scaler and post-scaler
  • Two capture, compare, PWM modules
  • Synchronous serial port with two modes
  • USART/SCI with 9-bit address detection
  • Parallel slave port
  • Brown-out detection circuitry for brown-out reset

Analog Features

  • 10-bit, 8-channel A/D converter
  • Brown-out reset
  • Analog comparable module

Let us see the dynamic features of PIC which has made it a better choice than other microcontrollers,

code efficiency - The PIC 8 bit microcontroller is based on Harvard architecture, which means there are separate internal buses for memory and data. The throughput rate is therefore increased due to simultaneous access to both data and program memory. It would be easier if you have known about von Neumann architecture which has common bus for memory and data.

safety - All the instructions fit into a 12 or 14 bit program memory word. There is no likelihood of software jumping onto the DATA section of a program and trying to execute DATA as instructions.

Instruction set - There are 33 instructions you have to learn in order to write software for the 16C5x family. The lesser number of instructions eases our job while writing program in assembly language.

Speed - The PIC has an internal divide by 4 connected between the oscillator and the internal clock bus(note : we know there is a divide by 2 in a 8085 microprocessor where we connect a 6Mhz clock in order to operate the microprocessor at a speed of 3Mhz). The PIC is very fast to work with. The speed of PIC16F877A is 20 MHz but it can even operate at a speed of 30Mhz. some PIC in 18Fx family can be operated at 40 MHz.

Static Operation - The PIC is a fully static microcontroller, in other words, if you stop the clock, all the register contents are maintained. In practice you would not actually do this, you would place the PIC into a Sleep mode-this stops the lock and sets up various flags within the PIC to allow you to know what state it was in before the Sleep.

In sleep, the PIC takes only its standby current which can be less than 1uA. The need for sleep mode can be easily understood by considering the Fire alarm circuit, since the circuit has to be activated only when there is a fire, the rest of the time the PIC can be made to be in its sleep mode and wake up when there is fire thus saving the power required for the operation of PIC.

Drive Capability - The PIC has a high output drive capability and can directly drive LEDs and TRIACs etc. Any I/O pin can sink 25mA or 100mA for the whole device.

Options - A range of speed, temperature, package, I/O lines, timer functions, and serial communication, A/D and memory sizes is available from the PIC family to suit virtually all your requirements.

PIC microcontroller can be programmed using embedded C. some of the compilers which it has used are mikroC, CCS C compiler and Mplab. It is easier to program in embedded C rather than programming in assembly language.

The PIC16F and PIC18F microcontroller consists of following peripherals:

I/O Ports: PIC16F877A have 5 (PORTA, PORTB, PORTC, PORTD and PORTE) 8-bit input-output ports. PORTB, PORTC & PORTD have 8 I/O pins each. Although other two ports are 8-bit ports but they do not have eight I/O pins. In general, when a peripheral is enabled, that pin may not be used as a general purpose I/O pin.

Memory: PIC16F877A consists of three different memory sections:

Flash Memory: Flash memory is used to store the program downloaded by a user on to the microcontroller. Flash memory is non-volatile, i.e., it retains the program even after the power is cut-off. PIC16F877A has 8K X 14 words of Flash Memory.

EEPROM: This is also a nonvolatile memory which is used to store data like values of certain variables. PIC16F877A has 256 Bytes of EEPROM.

SRAM: Static Random Access Memory is the volatile memory of the microcontroller, i.e., it loses its data as soon as the power is cut off. PIC16F877A is equipped with 368 Bytes of internal SRAM.

Oscillator: The PIC16F series has flexible clock options. An external clock of up to 20 MHz can be applied to this series. These controllers also consist of an internal oscillator which provides eight selectable frequency options varying from 31 KHz to 4MHz.

8x8 Multiplier: The PIC18F4550 includes 8 x 8 multiplier hardware. This hardware performs the multiplications in single machine cycle. This gives higher computational throughput and reduces operation cycle & code length.

ADC Interface: PIC16F877A is equipped with 8 ADC (Analog to Digital Converter) channels of 10-bits resolution. ADC reads the analog input, for example, a sensor input and converts it into digital value that can be understood by the microcontroller.

Timers/Counters: PIC16F877A has three timer/counters. There is one 16-bit timer and the remaining timers have option to select 8 bit mode. Timers are useful for generating precision actions, for example, creating precise time delays between two operations.

Interrupts: PIC16F877A consists of only one external interrupts source. There are 14 internal interrupts which are associated with different peripherals like USART, ADC, Timers, and so on.

USART: The Universal Synchronous Asynchronous Receiver Transmitter (USART) module is one of the two serial I/O modules. The USART can be configured as a full duplex asynchronous system that can communicate with peripheral devices such as CRT terminals and personal computers, or it can be configured as a half duplex synchronous system that can communicate with peripheral devices such as A/D or D/A integrated circuits, serial EEPROMs etc.

ICSP and ICD: PIC16F series controllers have In Circuit Serial Programming facility to program the Flash Memory which can be programmed without removing the IC from the circuit. ICD (In Circuit Debugger) allows for hardware debugging of the controller while it is in the application circuit.

SPI: The SPI mode allows 8 bits of data to be synchronously transmitted and received simultaneously. All four modes of SPI are supported. PIC16F supports 4-wire SPI communication between two devices on a common clock source. The data rate of SPI is more than that of USART.

I2C: PIC16F supports Two Wire Interface (TWI) of I2C communication between two devices. It can work as both Master and Slave device. The MSSP module in I2C mode fully implements all master and slave functions and provides interrupts on START and STOP bits in hardware, to determine a free bus (multi-master function). The MSSP module implements the standard mode specifications, as well as 7-bit and 10-bit addressing.

USB: PIC18F supports full-speed USB with different clock options.


PIC microcontrollers are based on advanced RISC architecture.RISC stands for Reduced Instruction Set Computing. In this architecture, the instruction set of hardware gets reduced which increases the execution rate (speed) of system.

PIC microcontrollers follow Harvard architecture for internal data transfer. In Harvard architecture there are two separate memories for program and data. These two memories are accessed through different buses for data communication between memories and CPU core. This architecture improves the speed of system over Von Neumann architecture in which program and data are fetched from the same memory using the same bus. PIC16 series controllers are 8-bit instruction set. PIC18 series controllers are based on 16-bit instruction set.

In addition, the PIC family is based on a Reduced Instruction Set Computer (RISC) configuration which it use fewer instructions than a Complex Instruction Set Computer (CISC). All the PIC devices use less than 60 instructions.

In general, the PIC16XXX devices have only 35 instructions, whereas the PIC17XXX devices have only 58 instructions. There is a substantial amount of program code compatibility amongst 9 different devices in the PIC family. A program written for one PIC device can easily be assembled and used in another device type with a minimum number of modifications.

The PIC family is fully static devices, meaning that they preserve the contents of their registers when the clock frequency is reduced to zero. In PIC microcontrollers, each instruction takes four clock periods to execute. If a 1MHz clock frequency is used, the corresponding clock period is 1µsec, so each instruction will take 4µsec–this time is called the instruction cycle time.

The fastest devices in the PIC family can operate at clock frequencies up to 33MHz, with corresponding instruction cycle times of 121nsec. Most instructions execute in one instruction cycle, but some require two cycles because they need to branch to some destination other than the next address in the PC.

Microchip characterizes PIC microcontrollers according to their instruction word lengths. The low-end PICs, such as the eight pin 12C5XX series, have 12 bit word length instructions. The midrange PICs, such as the PIC16XXX, have 14 bit instructions and the high-end 17XXX PICs have 16 bit instructions. All PIC microcontrollers are, however, classified as eight bit microcontrollers as they all manipulate data in byte units on an eight bit wide data bus.

A detailed knowledge or understanding of these concepts is not essential to actually use PIC microcontrollers; all that is needed is practice in writing programs and some experimentation with microcontroller circuits to gain experience.


The question may arise that if PIC18 are called 8-bit microcontrollers, then what about them being based on 16-bit instructions set. ‘PIC18 is an 8-bit microcontroller’ this statement means that the CPU core can receive/transmit or process a maximum of 8-bit data at a time. On the other hand the statement ‘PIC18 microcontrollers are based on 16-bit instruction set’ means that the assembly instruction sets are of 16-bit.

The data memory is interfaced with 8-bit bus and program memory is interfaced with 16-bit bus as depicted in the following figure.


The high performance of the PICmicro™ devices can be attributed to a number of architectural features commonly found in RISC microprocessors. These include:

  • Harvard architecture
  • Long Word Instructions
  • Single Word Instructions
  • Single Cycle Instructions
  • Instruction Pipelining
  • Reduced Instruction Set
  • Register File Architecture
  • Orthogonal (Symmetric) Instructions

Harvard Architecture

Harvard architecture has the program memory and data memory as separate memories and is accessed from separate buses.


This improves bandwidth over traditional von Neumann architecture in which program and data are fetched from the same memory using the same bus. To execute an instruction, a von Neumann machine must make one or more (generally more) accesses across the 8-bit bus to fetch the instruction.

Then data may need to be fetched, operated on, and possibly written. As can be seen from this description, that bus can be extremely contested. While with a Harvard architecture, the instruction is fetched in a single instruction cycle (all 14-bits).

While the program memory is being accessed, the data memory is on an independent bus and can be read and written. These separated buses allow one instruction to execute while the next instruction is fetched.

Long Word Instructions

Long word instructions have a wider (more bits) instruction bus than the 8-bit Data Memory Bus.

This is possible because the two buses are separate. This further allows instructions to be sized differently than the 8-bit wide data word which allows a more efficient use of the program memory, since the program memory width is optimized to the architectural requirements.

Single Word Instructions

Single Word instruction opcodes are 14-bits wide making it possible to have all single word instructions. A 14-bit wide program memory access bus fetches a 14-bit instruction in a single cycle. With single word instructions, the number of words of program memory locations equals the number of instructions for the device. This means that all locations are valid instructions.

Typically in the von Neumann architecture, most instructions are multi-byte. In general, a device with 4-KBytes of program memory would allow approximately 2K of instructions. This 2:1 ratio is generalized and dependent on the application code.

Instruction Pipeline

The instruction pipeline is a two-stage pipeline which overlaps the fetch and execution of instructions.

The fetch of the instruction takes one TCY, while the execution takes another TCY. However, due to the overlap of the fetch of current instruction and execution of previous instruction, an instruction is fetched and another instruction is executed every single TCY.

Single Cycle Instructions

With the Program Memory bus being 14-bits wide, the entire instruction is fetched in a single machine cycle (TCY). The instruction contains all the information required and is executed in a single cycle.

There may be a one cycle delay in execution if the result of the instruction modified the contents of the Program Counter. This requires the pipeline to be flushed and a new instruction to be fetched.

Reduced Instruction Set

When an instruction set is well designed and highly orthogonal (symmetric), fewer instructions are required to perform all needed tasks. With fewer instructions, the whole set can be more rapidly learned.

Register File Architecture

The register files/data memory can be directly or indirectly addressed. All special function registers, including the program counter, are mapped in the data memory.

Orthogonal (Symmetric) Instructions

Orthogonal instructions make it possible to carry out any operation on any register using any addressing mode. This symmetrical nature and lack of “special instructions” make programming simple yet efficient. In addition, the learning curve is reduced significantly.

The mid-range instruction set uses only two non-register oriented instructions, which are used for two of the cores features.

One is the SLEEP instruction which places the device into the lowest power use mode. The other is the CLRWDT instruction which verifies the chip is operating properly by preventing the on-chip Watchdog Timer (WDT) from overflowing and resetting the device.

Instruction Flow/Pipelining

An “Instruction Cycle” consists of four Q cycles (Q1, Q2, Q3, and Q4). Fetch takes one instruction cycle while decode and execute takes another instruction cycle. However, due to Pipelining, each instruction effectively executes in one cycle. If an instruction causes the program counter to change (e.g. GOTO) then an extra cycle is required to complete the instruction.

The instruction fetch begins with the program counter incrementing in Q1.

In the execution cycle, the fetched instruction is latched into the “Instruction Register (IR)” in cycle Q1. This instruction is then decoded and executed during the Q2, Q3, and Q4 cycles. Data memory is read during Q2 (operand read) and written during Q4 (destination writes).

The above process occurs in a single machine cycle. In PIC microcontroller, a single machine cycle consists of 4 oscillation periods. Thus an instruction needs 4 clock periods to be executed. This makes it faster than other 8051 microcontrollers.

Early processors and controllers could fetch or execute a single instruction in a unit of time. The PIC microcontrollers are able to fetch and execute the instructions in the same unit of time thus increasing their instruction throughput.

This technique is known as instruction pipelining where the processing of instructions is split into a number of independent steps.



There are two memory blocks in the Memory Organization; program memory and data memory. Each block has its own bus, so that access to each block can occur during the same oscillator cycle. The data memory can further be broken down into General Purpose RAM and the Special Function Registers (SFRs).

The operations of the SFRs that control the “core” are described here. The SFRs used to control the peripheral modules are described in the section discussing each individual peripheral module.

The memory of a PIC 16F877 chip is divided into 3 sections. They are,

  • Program memory
  • Data memory and
  • Data EEPROM

Program memory

Program memory contains the programs that are written by the user. The program counter (PC) executes these stored commands one by one. Usually PIC16F877 devices have a 13 bit wide program counter that is capable of addressing 8K×14 bit program memory space. This memory is primarily used for storing the programs that are written (burned) to be used by the PIC.

These devices also have 8K*14 bits of flash memory that can be electrically erasable /reprogrammed. Each time we write a new program to the controller, we must delete the old one at that time. The figure below shows the program memory map and stack.

Reset Vector

On any device, a reset forces the Program Counter (PC) to address 0h. We call this address the “Reset Vector Address” since this is the address that program execution will branch to when a device reset occurs. Any reset will also clear the contents of the PCLATH register. This means that any branch at the Reset Vector Address (0h) will jump to that location in PAGE0 of the program memory.

Interrupt Vector

When an interrupt is acknowledged the PC is forced to address 0004h. We call this the “Interrupt Vector Address”.

When the PC is forced to the interrupt vector, the PCLATH register is not modified. Once in the service interrupt routine (ISR), this means that before any write to the PC, the PCLATH register should be written with the value that will specify the desired location in program memory. Before the PCLATH register is modified by the Interrupt Service Routine (ISR) the contents of the PCLATH may need to be saved, so it can be restored before returning from the ISR.

Calibration Information

Some devices have calibration information stored in their program memory. This information is programmed by Microchip when the device is under final test. The use of these values allows the application to achieve better results. The calibration information is typically at the end of program memory, and is implemented as a RETLW instruction with the literal value being the specified calibration information.

Program Counter (PC)

The program counter (PC) specifies the address of the instruction to fetch for execution. The PC is 13-bits wide. The low byte is called the PCL register. This register is readable and writable. The high byte is called the PCH register. This register contains the PC<12:8> bits and is not directly readable or writable. All updates to the PCH register go through the PCLATH register.


The stack allows a combination of up to 8 program calls and interrupts to occur. The stack contains the return address from this branch in program execution. Mid-Range MCU devices have an 8-level deep x 13-bit wide hardware stack. The stack space is not part of either program or data space and the stack pointer are not readable or writable. The PC is pushed onto the stack when a CALL instruction is executed or an interrupt causes a branch.

The stack is popped in the event of a RETURN, RETLW or a RETFIE instruction execution. PCLATH is not modified when the stack is Pushed or Popped.

After the stack has been pushed eight times, the ninth push overwrites the value that was stored from the first push. The tenth push overwrites the second push.

Note 1:

There are no status bits to indicate stack overflow or stack underflow conditions. There are no instructions/mnemonics called PUSH or POP. These are actions that occur from the execution of the CALL, RETURN, RETLW, and RETFIE instructions, or the vectoring to an interrupt address.

Program Memory Paging

Some devices have program memory sizes greater then 2K words, but the CALL and GOTO instructions only have a 11-bit address range. This 11-bit address range allows a branch within a 2K program memory page size.

To allow CALL and GOTO instructions to address the entire 1K program memory address range, there must be other two bits to specify the program memory page. These paging bits come from the PCLATH<4:3> bits. When doing a CALL or GOTO instruction, the user must ensure that page bits (PCLATH<4:3>) are programmed so that the desired program memory page is addressed. When one of the return instructions is executed, the entire 13-bit PC is popped from the stack. Therefore, manipulation of the PCLATH<4:3> is not required for the return instructions.

Data Memory Organization

The data memory of PIC16F877 is separated into multiple banks which contain the general purpose registers (GPR) and special function registers (SPR). According to the type of the microcontroller, these banks may vary. The PIC16F877 chip only has four banks (BANK 0, BANK 1, BANK 2, and BANK4). Each bank holds 128 bytes of addressable memory.

Data memory is made up of the Special Function Registers (SFR) area, and the General Purpose Registers (GPR) area. The SFRs control the operation of the device, while GPRs are the general area for data storage and scratch pad operations.

The data memory is banked for both the GPR and SFR areas. The GPR area is banked to allow greater than 96 bytes of general purpose RAM to be addressed. SFRs are for the registers that control the peripheral and core functions. Banking requires the use of control bits for bank selection.

These control bits are located in the STATUS Register (STATUS<7:5>). To move values from one register to another register, the value must pass through the W register. This means that for all register-to-register moves, two instruction cycles are required. The entire data memory can be accessed either directly or indirectly. Direct addressing may require the use of the RP1:RP0 bits. Indirect addressing requires the use of the File Select Register (FSR).

Indirect addressing uses the Indirect Register Pointer (IRP) bit of the STATUS register for accesses into the Bank0 / Bank1 or the Bank2 / Bank3 areas of data memory.

General Purpose Registers (GPR)

Some Mid-Range MCU devices have banked memory in the GPR area. GPRs are not initialized by a Power-on Reset and are unchanged on all other resets. The register file can be accessed either directly, or using the File Select Register FSR, indirectly. Some devices have areas that are shared across the data memory banks, so a read / write to that area will appear as the same location (value) regardless of the current bank.

Special Function Registers (SFR)

The SFRs are used by the CPU and Peripheral Modules for controlling the desired operation of the device. These registers are implemented as static RAM.

The SFRs can be classified into two sets, those associated with the “core” function and those related to the peripheral functions. All Mid-Range MCU devices have banked memory in the SFR area. Switching between these banks requires the RP0 and RP1 bits in the STATUS register to be configured for the desired bank. Some SFRs are initialized by a Power-on Reset and other resets, while other SFRs are unaffected. The register file can be accessed either directly, or using the File Select Register FSR, indirectly.

Note: The Special Function Register (SFR) Area may have General Purpose Registers (GPRs) mapped in these locations.


The data memory is partitioned into four banks. Each bank contains General Purpose Registers and Special Function Registers.

Switching between these banks requires the RP0 and RP1 bits in the STATUS register to be configured for the desired bank when using direct addressing. The IRP bit in the STATUS register is used for indirect addressing.

Each Bank extends up to 7Fh (128 bytes). The lower locations of each bank are reserved for the Special Function Registers. Above the Special Function Registers are General Purpose Registers.

All data memory is implemented as static RAM. All Banks may contain special function registers. Some “high use” special function registers from Bank0 are mirrored in the other banks for code reduction and quicker access.

STATUS Register

The STATUS register contains the arithmetic status of the ALU, the RESET status and the bank select bits for data memory. The STATUS register can be the destination for any instruction, as with any other register.

If the STATUS register is the destination for an instruction that affects the Z, DC or C bits, then the write to these three bits is disabled. These bits are set or cleared according to the device logic. Furthermore, the TO and PD bits are not writable, therefore, the result of an instruction with the STATUS register as destination may be different than intended.


The OPTION_REG Register is a readable and writable register, which contains various control bits to configure the TMR0 pre-scaler/WDT post-scaler, the External INT Interrupt, TMR0 and the weak pull-ups on PORTB.

INTCON Register

The INTCON Register is a readable and writable register, which contains various enable and flag bits for the TMR0 register overflow, RB Port change and External RB0/INT pin interrupts.


Interrupt flag bits are set when an interrupt condition occurs, regardless of the state of its corresponding enable bit or the global enable bit, GIE (INTCON<7>). User software should ensure the appropriate interrupt flag bits are clear prior to enabling an interrupt.

PIE1 Register

The PIE1 register contains the individual enable bits for the peripheral interrupts.

PIR1 Register

The PIR1 register contains the individual flag bits for the peripheral interrupts.


Interrupt flag bits are set when an interrupt condition occurs, regardless of the state of its corresponding enable bit or the global enable bit, GIE (INTCON<7>). User software should ensure the appropriate interrupt bits are clear prior to enabling an interrupt.

PIE2 Register

The PIE2 register contains the individual enable bits for the CCP2 peripheral interrupt, the SSP bus collision interrupt, and the EEPROM write operation interrupt.

PIR2 Register

The PIR2 register contains the flag bits for the CCP2 interrupt, the SSP bus collision interrupt and the EEPROM write operation interrupt.


Interrupt flag bits are set when an interrupt condition occurs, regardless of the state of its corresponding enable bit or the global enable bit, GIE (INTCON<7>).

User software should ensure the appropriate interrupt flag bits are clear prior to enabling an interrupt.

PCON Register

The Power Control (PCON) Register contains flag bits to allow differentiation between a Power-on Reset (POR), a Brown-out Reset (BOR), a Watchdog Reset (WDT), and an external MCLR Reset.


BOR is unknown on POR. It must be set by the user and checked on subsequent RESETS to see if BOR is clear, indicating a brown-out has occurred. The BOR status bit is a “don’t care” and is not predictable if the brown-out circuit is disabled (by clearing the BODEN bit in the configuration word).

Indirect Addressing, INDF, and FSR Registers

Indirect addressing is a mode of addressing data memory where the data memory address in the instruction is not fixed. An SFR register is used as a pointer to the data memory location that is to be read or written.

Since this pointer is in RAM, the contents can be modified by the program. This can be useful for data tables in the data memory. Indirect addressing is possible by using the INDF register. Any instruction using the INDF register actually accesses the register pointed to by the File Select Register, FSR.

Reading the INDF register itself indirectly (FSR = '0') will read 00h. Writing to the INDF register indirectly results in a no-operation (although status bits may be affected). An effective 9-bit address is generated by the concatenation of the IRP bit (STATUS<7>) with the 8-bit FSR register.

Data EEPROM and FLASH Memory

The data EEPROM and Flash program memory is readable and writable during normal operation (over the full VDD range). This memory is not directly mapped in the register file space. Instead, it is indirectly addressed through the Special Function Registers.

The EEPROM data memory allows single-byte read and writes. The Flash program memory allows single-word reads and four-word block writes. Program memory write operations automatically perform an erase-before write on blocks of four words. A byte write in data EEPROM memory automatically erases the location and writes the new data (erase-before-write). The write time is controlled by an on-chip timer. The write/erase voltages are generated by an on-chip charge pump, rated to operate over the voltage range of the device for byte or word operations.

The EEPROM Data memory is rated for high erase/ writes cycles. The FLASH program memory is rated much lower, because EEPROM data memory can be used to store frequently updated values. An on-chip timer controls the right time and it will vary with voltage and temperature, as well as from chip to chip.

A byte or word write automatically erases the location and writes the new value. Writing to EEPROM data memory does not impact the operation of the device.

Writing to program memory will cease the execution of instructions until the write is complete. The program memory cannot be accessed during the write. During the write operation, the oscillator continues to run, the peripherals continue to function and interrupt events will be detected and essentially “queued” until the write is complete. When the write completes, the next instruction in the pipeline is executed and the branch to the interrupt vector will take place, if the interrupt is enabled and occurred during the write.

Read and write access to both memories take place indirectly through a set of Special Function Registers (SFR). The six SFRs used are:

  • EECON1
  • EECON2

The EEPROM data memory allows byte read and writes operations without interfering with the normal operation of the microcontroller.

When interfacing to EEPROM data memory, the EEADR register holds the address to be accessed. Depending on the operation, the EEDATA register holds the data to be written, or the data read, at the address in EEADR.

The PIC16F873/874 devices have 128 bytes of EEPROM data memory and therefore, require that the MSB of EEADR remain clear. The EEPROM data memory on these devices does not wrap around to 0, i.e., 0x80 in the EEADR does not map to 0x00. The PIC16F876/877 device has 256 bytes of EEPROM data memory and therefore, uses all 8-bits of the EEADR.

The FLASH program memories allows non-intrusive read access, but write operations cause the device to stop executing instructions, until the write completes.

When interfacing to the program memory, the EEADRH: EEADR registers form a two-byte word, which holds the 13-bit address of the memory location being accessed. The register combination of EEDATH: EEDATA holds the 14-bit data for writes, or reflects the value of program memory after a read operation.

Just as in EEPROM data memory accesses, the value of the EEADRH: EEADR registers must be within the valid range of program memory, depending on the device: 0000h to 1FFFh for the PIC16F873/874, or 0000h to 3FFFh for the PIC16F876/877. Addresses outside of this range do not wrap around to 0000h.

EECON1 and EECON2 Registers

The EECON1 register is the control register for configuring and initiating the access. The EECON2 register is not a physically implemented register, but is used exclusively in the memory write sequence to prevent inadvertent writes.

There are many bits used to control the read and write operations to EEPROM data and FLASH program memory. The EEPGD bit determines if the access will be a program or data memory access. When clear, any subsequent operations will work on the EEPROM data memory. When set, all subsequent operations will operate in the program memory.

Read operations only use one additional bit, RD, which initiates the read operation from the desired memory location. Once this bit is set, the value of the desired memory location will be available in the data registers.

This bit cannot be cleared by firmware. It is automatically cleared at the end of the read operation. For EEPROM data memory reads, the data will be available in the EEDATA register in the very next instruction cycle after the RD bit is set. For program memory reads, the data will be loaded into the EEDATH: EEDATA registers; following the second instruction after the RD bit is set.

Write operations have two control bits, WR and WREN, and two status bits, WRERR and EEIF. The WREN bit is used to enable or disable the write operation. When WREN is clear, the write operation will be disabled.

Therefore, the WREN bit must be set before executing a write operation. The WR bit is used to initiate the write operation. It also is automatically cleared at the end of the write operation. The interrupt flag EEIF is used to determine when the memory write completes. This flag must be cleared in software before setting the WR bit.

For EEPROM data memory, once the WREN bit and the WR bit have been set, the desired memory address in EEADR will be erased, followed by a write of the data in EEDATA. This operation takes place in parallel with the microcontroller continuing to execute normally.

When the write is complete, the EEIF flag bit will be set. For program memory, once the WREN bit and the WR bit have been set, the microcontroller will cease to execute instructions.

The desired memory location pointed to by EEADRH: EEADR will be erased. Then, the data value in EEDATH: EEDATA will be programmed. When complete, the EEIF flag bit will be set and the microcontroller will continue to execute code.

The WRERR bit is used to indicate when the PIC16F87X device has been reset during a write operation. WRERR should be cleared after Power-on Reset. Thereafter, it should be checked on any other RESET.

The WRERR bit is set when a write operation is interrupted by a MCLR Reset, or a WDT Time-out Reset, during normal operation. In these situations, following a RESET, the user should check the WRERR bit and rewrite the memory location, if set.

The contents of the data registers, address registers and EEPGD bit are not affected by either MCLR Reset, or WDT Timeout Reset, during normal operation.

Reading the EEPROM Data Memory

Reading EEPROM data memory only requires that the desired address to access be written to the EEADR register and clear the EEPGD bit. After the RD bit is set, data will be available in the EEDATA register on the very next instruction cycle.

EEDATA will hold this value until another read operation is initiated or until it is written by firmware.

The steps to reading the EEPROM data memory are:

  • Write the address to EEDATA. Make sure that the address is not larger than the memory size of the PIC16F87X device.
  • Clear the EEPGD bit to point to EEPROM data memory.
  • Set the RD bit to start the read operation.
  • Read the data from the EEDATA register.

Writing to the EEPROM Data Memory

There are many steps in writing to the EEPROM data memory. Both address and data values must be written to the SFRs. The EEPGD bit must be cleared, and the WREN bit must be set, to enable writes. The WREN bit should be kept clear at all times, except when writing to the EEPROM data.

The WR bit can only be set if the WREN bit was set in a previous operation, i.e., they both cannot be set in the same operation. The WREN bit should then be cleared by firmware after the write. Clearing the WREN bit before the write actually completes will not terminate the write in progress.

Writes to EEPROM data memory must also be prefaced with a special sequence of instructions that prevent inadvertent write operations. This is a sequence of five instructions that must be executed without interruptions.

The firmware should verify that a write is not in progress, before starting another cycle.

The steps to write to EEPROM data memory are:

  • If step 10 is not implemented, check the WR bit to see if a write is in progress.
  • Write the address to EEADR. Make sure that the address is not larger than the memory size of the PIC16F87X device.
  • Write the 8-bit data value to be programmed in the EEDATA register.
  • Clear the EEPGD bit to point to EEPROM data memory.
  • Set the WREN bit to enable program operations.
  • Disable interrupts (if enabled).
  • Execute the special five instruction sequence:
        -  Write 55h to EECON2 in two steps (first to W,then to EECON2)
        -  Write AA to EECON2 in two steps (first to W, then to EECON2)
        -  Set the WR bit
  • Enable interrupts (if using interrupts).
  • Clear the WREN bit to disable program operations.
  • At the completion of the write cycle, the WR bit is cleared and the EEIF interrupt flag bit is set.

Reading the FLASH Program Memory

Reading FLASH program memory is much like that of EEPROM data memory, only two NOP instructions must be inserted after the RD bit is set.

These two instruction cycles that the NOP instructions execute, will be used by the microcontroller to read the data out of program memory and insert the value into the EEDATH: EEDATA registers. Data will be available following the second NOP instruction. EEDATH and EEDATA will hold their value until another read operation is initiated, or until they are written by firmware.

The steps to reading the FLASH program memory are:

  • Write the address to EEADRH: EEADR. Make sure that the address is not larger than the memory size of the PIC16F87X device.
  • Set the EEPGD bit to point to FLASH program memory.
  • Set the RD bit to start the read operation.
  • Execute two NOP instructions to allow the microcontroller to read out of program memory.
  • Read the data from the EEDATH: EEDATA registers.

Writing to the FLASH Program Memory

Writing to FLASH program memory is unique, in that the microcontroller does not execute instructions while programming is taking place. The oscillator continues to run and all peripherals continue to operate and queue interrupts, if enabled. Once the write operation completes, the processor begins executing code from where it left off. Just like EEPROM data memory, there are many steps in writing to the FLASH program memory.

Both address and data values must be written to the SFRs. The EEPGD bit must be set, and the WREN bit must be set to enable writes. The WREN bit should be kept clear at all times, except when writing to the FLASH Program memory. The WR bit can only be set if the WREN bit was set in a previous operation, i.e., they both cannot be set in the same operation. The WREN bit should then be cleared by firmware after the write. Clearing the WREN bit before the write actually completes will not terminate the write in progress.

Writes to program memory must also be prefaced with a special sequence of instructions that prevent inadvertent write operations. This is a sequence of five instructions that must be executed without interruption for each byte written. These instructions must then be followed by two NOP instructions to allow the microcontroller to setup for the write operation. Once the write is complete, the execution of instructions starts with the instruction after the second NOP.

The steps to write to program memory are:

  • Write the address to EEADRH: EEADR. Make sure that the address is not larger than the memory size of the PIC16F87X device.
  • Write the 14-bit data value to be programmed in the EEDATH: EEDATA registers.
  • Set the EEPGD bit to point to FLASH memory.
  • Set the WREN bit to enable program operations.
  • Disable interrupts (if enabled).
  • Execute the special five instruction sequence:
        -  Write 55h to EECON2 in two steps (first to W, then to EECON2)
        -  Write AA to EECON2 in two steps (first to W, then to EECON2)
        -  Set the WR bit
  • Execute two NOP instructions to allow the microcontroller to setup for write operation.
  • Enable interrupts (if using interrupts).
  • Clear the WREN bit to disable program operations.

I/O Registers

These registers are used for the I/O control. Every I/O port in the PIC microcontroller has two registers: port data register and port direction control register.

Port data register has the same name as the port it controls. For example, the PIC16F877A microcontroller has five port data registers, PORTA, PORTB, PORTC, PORTD and PORTE. Eight bits of data can be sent to any port, or 8 bits of data can be read from the ports. It is also possible to read or write to individual port pins. For example, any bit of a given port can be set or cleared, or data can be read from one or more port pins at the same time.

Ports in a PIC microcontroller are bidirectional. Thus, each pin of a port can be used as an input or an output pin. Port direction control register configures the port pins as either inputs or outputs. This register is called the TRIS register and every port has a TRIS register named after its port name.

For example, TRISA is the direction control register for PORTA. Similarly, TRISB is the direction control register for PORTB and so on.

Setting a bit in the TRIS register makes the corresponding port register pin as input. Clearing a bit in the TRIS register makes the corresponding port pin an output. For example, to make bits 0 and 1 of PORTB input and the other bits output; we have to load the TRISB register with the bit pattern.


Timer Registers

Depending on the model used, some PIC microcontrollers have only one timer, and some may have up to three timers. In this section we shall look at the PIC16F84 microcontroller, which has only one timer. The extension to several timers is similar and we shall see in the projects section how to use more than one timer.

The timer in the PIC16F84 microcontroller is an 8-bit register (called TMR0), which can be used as a timer or a counter. When used as a counter, the register increments each time a clock pulse is applied to pin T0CK1 of the microcontroller.

When used as a timer, the register increments at a rate determined by the system clock frequency and a pre-scaler selected by register OPTION_REG. Prescaler rates vary from 1:2 to 1:256. For example, when using a 4-MHz clock, the basic instruction cycle is 1 _s (the clock is internally divided by four). If we select a pre-scaler rate of 1:16, the counter will be incremented at every 16 _s. The TMR0 register has address 01 in the RAM.

A timer interrupt is generated when the timer overflows from 255 to 0. This interrupt can be enabled or disabled by our program. Thus, for example, if we need to generate interrupts at intervals of 200 _s using a 4-MHz clock, we can select a pre-scaler value of 1:4 and enable timer interrupts.

The timer clock rate is then 4 _s. For a time-out of 200 _s, we have to send 50 clocks to the timer. Thus, the TMR0 register should be loaded with 256 – 50 _ 206—i.e., a count of 50 before an overflow occurs. The watchdog timer’s oscillator is independent from the CPU clock and the time-out is 18 ms.

To prevent a time-out condition the watchdog must be reset periodically via software. If the watchdog timer is not reset before it times out, the microprocessor will be forced to jump to the reset address. The pre-scaler can be used to extend the time-out period and valid rates are 1, 2, 4, 8, 16, 32, 64, and 128. For example, when set to 128, the time-out period is about 2 s (18 _ 128 _ 2304 ms). The watchdog timer can be disabled during programming of the device if it is not used.

A/D Converter Registers

The A/D converter is used to interface analog signals to the microcontroller.

The A/D converts analog signals (e.g., voltage) into digital form so that they can be connected to a computer. A/D converter registers are used to control the A/D converter ports. On most PIC microcontrollers equipped with A/D, PORTA pins are used for analog input and these port pins are shared between digital and analog functions.

PIC16F876 includes five A/D converters. Similarly, PIC16F877 includes eight A/D converters. The width of the A/D converter can be 8 bits or 10 bits. Both PIC16F876 and PIC16F877 have 10-bit converters. PIC16F73 has 8-bit converters. The A/D converter requires a reference voltage to operate.


Interrupts are an important feature of all microcontrollers. An interrupt can either occur asynchronously or synchronously. Asynchronous interrupts are usually external events which interrupt the microcontroller and request service.

For example, pin INT (RB0) of a PIC16F84 microcontroller is the external interrupt pin and this pin can be used to interrupt the microcontroller asynchronously; i.e., the interrupt can occur at any time independent of the program being executed inside the microcontroller. Synchronous interrupts are usually timer interrupts, such as the timer overflow generating an interrupt. Depending on the model used, different PIC microcontrollers may have a different number of interrupt sources. For example, the PIC16F84 microcontroller has the following four sources of interrupts:

  • External interrupts from INT (RB0) pin
  • TMR0 interrupt caused by timer overflow
  • External interrupts when the state of RB4, RB5, RB6,or RB7 pins change
  • Termination of writing data to the EEPROM.

Interrupts are enabled and disabled by the INTCON register. Each interrupt source has two bits to control it.

One enables interrupts, and the other one detects when an interrupt occurs. There is a common bit called GIE which can be used to disable all sources of interrupts.


The Central Processing Unit is responsible for using the information in the program memory (instructions) to control the operation of the device. Many of these instructions operate on data memory. To operate on data memory, the Arithmetic Logical Unit is required. In addition to performing arithmetical and logical operations, the ALU controls status bits. The result of some instructions forces status bits to a value depending on the state of the result.

Central Processing Unit (CPU)

The CPU can be thought of as the “brains” of the device. It is responsible for fetching the correct instruction for execution, decoding that instruction, and then executing that instruction.

The CPU sometimes works in conjunction with the ALU to complete the execution of the instruction (in arithmetic and logical operations). The CPU controls the program memory address bus, the data memory address bus, and accesses to the stack.

Instruction Clock

Each instruction cycle (TCY) is comprised of four Q cycles (Q1-Q4). The Q cycle time is the same as the device oscillator cycle time (TOSC). The Q cycles provide the timing/designation for the Decode, Read, Process Data, Write, etc., of each instruction cycle. The following diagram shows the relationship of the Q cycles to the instruction cycle.

The four Q cycles that make up an instruction cycle (TCY) can be generalized as:

Q1: Instruction Decode Cycle or forced No operation

Q2: Instruction Read Data Cycle or No operation

Q3: Process the Data

Q4: Instruction Write Data Cycle or No operation

Each instruction will show a detailed Q cycle operation for the instruction.

Arithmetic Logical Unit (ALU)

PICmicro MCUs contain an 8-bit ALU and an 8-bit working register. The ALU is a general purpose arithmetic and logical unit. It performs arithmetic and Boolean functions between the data in the working register and any register file.

The ALU is 8-bits wide and is capable of addition, subtraction, shift and logical operations. Unless otherwise mentioned, arithmetic operations are two's complement in nature. In two-operand instructions, typically one operand is the working register. The other operand is a file register or an immediate constant. In single operand instructions, the operand is either the W register or a file register.

The W register is an 8-bit working register used for ALU operations. It is not an addressable register.

Depending on the instruction executed, the ALU may affect the values of the Carry (C), Digit Carry (DC), and Zero (Z) bits in the STATUS register. The C and DC bits operate as a borrow bit and a digit borrow out bit, respectively, in subtraction.

Join the World's Largest Technical Community

we respect your privacy.