1. CURSO INTEGRAL SOBRE MICROCONTROLADORES
1
www.welgos.net
CURSO INTEGRAL
PIC
Las mejores cosas de la vida son
gratis!!!
Este curso es un obsequio de WELGOS
electrónica para todas las personas
interesadas en esta tecnología.
En uno de los capítulos se describe la
construcción de una tarjeta programadora “in
circuit”. Si le interesa sonstruirla, el software
del PIC y de la computadora puede solicitarlos
por medio de correo electrónico.
Disfrútenlo!!!!!
2. CURSO INTEGRAL SOBRE MICROCONTROLADORES
2
www.welgos.net
CURSO INTEGRAL
PIC
Capítulo 1
Introducción a los microcontroladores PIC
Los microcontroladores PIC son circuitos integrados producidos por la empresa
Microchip Technology Inc., que pertenecen a la categoría de microcontroladores,
debido a que en este componente se han integrado todos los circuitos necesarios
para realizar un completo sistema digital programable.
Como se puede ver en la figura,
el PIC (en este caso un PIC16F84A) posee una apariencia externa que no lo
diferencia de otro integrado TTL o CMOS, pero internamente dispone de todo lo
correspondiente a un sistema de microprocesadores:
* Una CPU (Central Processor Unit) la cual es la unidad central que esta en
capacidad de interpretar las instrucciones del programa.
* Una memoria FLASH en donde se memoriza de manera permanente las
instrucciones del programa a seguir.
* Una memoria RAM (Random Access Memory) utilizada para memorizar las
variables utilizadas en el programa.
* Una serie de líneas de I/O (Input/Output) que permite el ingreso y la lectura de
dispositivos externos o para recibir señales de sensores, pulsadores, etc.
* Una serie de dispositivos auxiliaries al funcionamiento como la generación de reloj,
buses, contadores, etc.
La presencia de todos estos dispositivos en un espacio tan supremamente reducido,
nos proporciona una gran ventaja frente a sistemas basados en microprocesadores.
Los microcontroladores PIC se encuentran disponibles en una amplia gama de
modelos, que se diferencian por el número de lِíneas I/O y los periféricos internos del
dispositivo.
Cada modelo posee su referencia, los más básicos se identifican por las siglas
PIC12C5xx y solo poseen 8 pines, y los más avanzados se identifican por la sigla
PIC18Cxx y está dotados de hasta 40 pines.
En la página web de la Microchip se encuentra una descripción completa de todos los
tipos de microcontroladores PIC, además de notas de aplicación y soporte.
3. CURSO INTEGRAL SOBRE MICROCONTROLADORES
3
www.welgos.net
Parta este curso vamos a trabajar con los PIC16F84A, los cuales están dotados de 18
pines.
Estos microcontroladores disponen de una memoria interna para almacenar el
programa que es de tipo FLASH, la cual puede reescribirse muchísimas veces, lo cual
los hace ideales para experimentos.
En la siguiente figura se muestra el diagrama de pines del PIC16F84A.
Los pines mostrados en azul corresponden a pines I/O diponibles para nuestra
aplicación, los pines en rojo y negro corresponden a los de alimentación y los verdes
son reservados para el funcionamiento del microcontrolador (MCLR para el reset, y
los OSC1-2 son para el reloj).
1.1 Realizando una sencilla activación de un
led
Pasemos de una vez a desarrollar una sencilla aplicación práctica con
microcontroladores PIC. Se trata de un circuito muy simple para activar un diodo
LED.
Veremos paso a paso, como se escribe un programa en assembler, como se compila
y como se transfiere a la memoria FLASH interna del microcontrolador PIC para
ponerlo a trabajar.
Monte en el entrenador el circuito que se muestra en la siguiente figura:
4. CURSO INTEGRAL SOBRE MICROCONTROLADORES
4
www.welgos.net
Para alimentar el circuito es necesario disponer de un voltaje DC constante de 5
voltios, la cual se aplica a el pin Vdd (pin 14) y la tierra se aplica al pin Vss (pin 5).
El pin MCLR (pin 4) sirve para efectuar el reset al PIC microcontrolador.
Normalmente viene mantenido a 5 voltios a través de una resistencia de pull up (R1)
y se lleva a cero voltios cuando se require aplicar un reset.
ATENCION
Gracias a la circuitería interna del reset interna del microcontrolador, no es necesario
colocar un pulsador para el reset o un circuito RC, pero nunca está demás.
El pin OSC1/CLKIN (pin 16) y el pin OSC2/CLKOUT (pin 15) se conectan con un
circuito interno que genera la frecuencia de reloj utilizada para temporizar todo el
ciclo de funcionamiento interno en el chip. De esta frecuencia depende casi todas las
operaciones internas del microcontrolador, especialmente la velocidad con que el PIC
ejecuta las instrucciones del programa.
En lo personal, cuando doy mis clases de microcontroladores, les digo a mis
estudiantes que hagan la analogía con una escalera eléctrica en la cual viajamos,
donde en cada peldaño que viajamos ejecutamos una instrucción. Cada
microcontrolador posee una capacidad maxima del cristal, si la escalera se mueve
demasiado rápido podríamos caernos. Pero también es possible que puede llegar otro
tipo con mayor fortaleza que puede permanecer allí.
Es decir, cada microcontrolador posee una cierta capacidad para manejar
determinada frecuencia.
5. CURSO INTEGRAL SOBRE MICROCONTROLADORES
5
www.welgos.net
En el caso del PIC16F84A-04/P teóricamente puede llegar a un máximo de 4Mhz,
aunque en realidad en la práctica es común superar apliamente esta frecuencia, lo
que recibe el nombre de overclocking, en lo personal le he aplicado un cristal de 10
MHz (ver convertidor RS-232/ RS-485 half-duplex, en www.wellgos.com) sin tener
ningún problema.
Como en el circuito se tiene un cristal de 4 Mhz y dos condensadores de 22 pF, se
obtiene una velocidad de ejecución de las instrucciones de 1 millón de instrucciones
por segundo.
El pin RB0 (pin 6) es la línea I/O que vamos a utilizar para este primer ejercicio. Allí
se encuentra conectada una resistencia para limitar la corriente y un LED.
1.2 Escritura y compilación de un programa
en ensamblador
Todo sistema microcontrolador necesita de un programa para hacerlo funcionar. Un
programa se constituye de una secuencia de instrucciones, cada una de las cuales
identifica unívocamente una function que el microcontrolador debe ejecutar.
Cada instrucción se representa por un código operative (en ingles operation code o
abreviadamente opcode) compuesto de 14 bits y que se memoriza en una posición
de la memoria donde se almacena el programa. En el PIC16F84A posee 1024
posiciones de memoria y el PIC16f877 posee 8K, cada una de las cuales puede
contener una sola instrucción o un dato.
Un ejemplo de un opcode en notació binaria, puede ser la siguiente:
00 0001 0000 0000
sin embargo es muy probable que el opcode lo vea en su representación
hexadecimal, así:
0x100
que es exactamente el mismo valor pero en una forma más breve. El 0x delante de
cualquier valor indica que se trata de una notación hexadecimal, aunque también se
puede representar con la notación: H'0100'. Este opcode, es completamente privado
para el entendimiento del ser humano, solo el PIC lo puede entender.
Afortunadamente existen algunas herramientas que facilitan trabajar con las
instruciones para su comprensibilidad. Por convención, se asocia a cada opcode, una
breve sigla. Denominada mnemonica, con la cual se puede recordar la función de
cada instrucción.
El opcode 0x100 del ejemplo anterior, efectúa el borrado del registro W (enseguida
veremos que significa esto) que en ingles viene indicado con la frase CLEAR W
REGISTER, o sea, borrar el registro W, o en su forma abreviada CLRW. Una
secuencia de estas siglas de acuerdo a ciertas reglas, forman un programa completo
en LENGUAJE ENSAMBLADOR.
6. CURSO INTEGRAL SOBRE MICROCONTROLADORES
6
www.welgos.net
Para escribir un programa en lenguaje ensamblador se debe conocer el conjunto de
instrucciones disponibles por el microcontrolador que va a usar (en este caso los
PIC), las reglas sintácticas para definer variables, parámetros, etc., y disponer de un
editor de texto en donde se digita el programa. El archivo de texto con el programa
se denomina fuente.
El paso siguiente consiste en traducer nuestro archive fuente en la secuencia de
instrucciones en formato binario que el PIC puede captar. Este programa se
denomina ensamblador compilado.
En la figura siguiente viene esquematizado el flujo de operaciones y los archivos
generados necesarios para obtener un PIC programado.
7. CURSO INTEGRAL SOBRE MICROCONTROLADORES
7
www.welgos.net
Como se dijo, la primera operación es la de efectuar la escritura de el programa
fuente en ensamblador y su grabado en un archivo de texto. La extension de este
archivo es .ASM.
Se puede usar un sencillo editor ASCII, como el NOTEPAD de Windows o el
Ultraedit32.
Es posible generar este archivo desde un programa sofisticado como WORD o Star
Office, pero no lo recomiendo mucho, debido a que el formato nativo de estos
programas es .DOC, lo cual puede traer algunos problemas en el formato de los
programas que el compilador puede entender.
8. CURSO INTEGRAL SOBRE MICROCONTROLADORES
8
www.welgos.net
En nuestro primer experimento práctico, utilizaremos el archivo LED.ASM.
El paso siguiente es la compilación del programa fuente, esto es, la trnasformación
en opcode del código mnemónico o instrucciones en ensamblador.
El compilador de ensamblador que utilizaremos el programa MPASM.EXE de la
Microchip.
Como se muestra en la figura anterior, además del archive .ASM, es necesario otro
archivo .INC, el cual es proporcionado por la Microchip. En el caso del PIC84 se
denomina P16F84.INC. Este archivo contiene las definiciones del chip utilizado.
Durante la compilación, el ensamblador genera una serie de archivos con el mismo
nombre al del archivo fuente pero con distitnas extensiones. Veamos cuales son y
que contiene cada uno de ellos:
.HEX es el archivo que contiene el opcode que se debe grabar en la memoria de
programa del microcontrolador PIC.
.LST es un archive de texto en donde viene reportado el archivo fuente complete y
la correspondiente traducción en opcode. Este no se utilize para programar el
microcontrolador, pero es extremadamente útil para verificar el proceso de
compilación que ha llevado a cabo el ensamblador.
.ERR contiene la lista errores de compilación encontrados y el número de línea del
archivo fuente donde se encontró.
Los archivos .LST y .ERR sirven para controlar lo hecho en la compilación. Solo el
.HEX se utilize para programar el microcontrolador.
El archivo .HEX no viene en formato binario, es un archivo codificado en un formato
inventado por la empresa norteamericana Intel para la descripción del archivo en
formato ASCII, con el cual se facilita la transferencia a la memoria del
microcontrolador PIC.
1.3 Analizando un archivo fuente
Analicemos línea por línea el contenido de nuestro archivo fuente LED.ASM.
Procedamos ahora a analizar el programa línea por línea.
Partamod de la primera línea del código:
PROCESSOR 16F84
PROCESSOR es una directiva del compilador que permite definir para que tipo de
microprocesador vamos a escribir nuestro programa.
Las directives no forman parte del conjunto de instrucciones del microcontrolador
que el compilador convierte en un OPCODE, simplemente son indicaciones de las
cuales se sirve el compilador para determiner el funcionamiento que va a seguir
durante la compilación.
En este caso le estamos diciendo al compilador que estamos escribiendo un
programa para el PIC16f84.
RADIX DEC
9. CURSO INTEGRAL SOBRE MICROCONTROLADORES
9
www.welgos.net
La directiva RADIX sirve para informar al compilador cual es la notación por defecto
que van a tener los diferentes números que se escriban dentro del programa. En este
caso, debido a la palabra DEC, establecemos que los valores numéricos se deben
entender como decimales.
Si vamos a especificar, por ejemplo, el número hexadecimal 10 (16 en decimal) no
podemos escribir simplemente 10 porque el compilador lo entendería como 10 en
decimal; debemos escribir 0x10 o H’10’.
ERRORLEVEL -302
Esta directiva sirve para excluir algunos mensajes de error resultantes de la
compilación. En este caso sirve para evitar que el compilador arroje estos dos tipos
de errores:
Message[302] C:EPICLED.ASM 37 :
Register in operand not in bank 0.
Ensure that bank bits are correct.
Message[302] C:EPICLED.ASM 40 :
Register in operand not in bank 0.
Ensure that bank bits are correct.
Los cuales se detectaron en las líneas 37 y 40 de nuestro código fuente, en donde no
estamos trabajando en el banco de memoria correcto. Más adelante veremos el
significado real de este error, por ahora sigamos adelante.
INCLUDE "P16F84.INC"
Esta es una directiva muy importante y que vamos a utilizar mucho en nuestros
programas.
Con esta directiva le manifestamos al compilador nuestra intención de incluir un
segundo archivo a nuestro código fuente denomiando P16F84.INC. El compilaador se
limitará a sustituir la línea que contiene la directiva INCLUDe con el contenido del
archivo especificado.
LED EQU 0
Otra directiva ! Cuando entraremos a las instrucciones ? Paciencia mi amigo,
paciencia.... ☺
La directiva EQU es muy importante, pues nos permite constantes simbólicas dentro
de nuestro programa. En este caso la palabra LED en cualquier punto del programa
será equivalente al valor 0.
El objetivo principal de la directiva EQU es facilitar la lectura y entendimiento de los
programas a un lector desprevenido. Es muy utilizada cuando manejemos banderas,
más adelante explicaremos este concepto.
Es importante resaltar que la palabra LED no es una variable más, simplemente es
un nombre simbólico válido durante la compilación. No es posible escribir una
instrucción donde se asigna a LED el número 3.
10. CURSO INTEGRAL SOBRE MICROCONTROLADORES
10
www.welgos.net
Cuando el PIC trabaja dentro de su aplicación final, solo puede manipular la
información suministrada por las instrucciones, no por las directivas.
Veamos ahora la siguiente línea:
ORG 0x0C
La directiva ORG permite definir una dirección donde el compilador va a ubicar los
datos o las instrucciones siguientes. En este caso vamos a definir un área de datos
dentro del PIC sobre la cual memorizar diversos datos dirante la ejecución de
nuestro programa. Esta área coincide con la RAM del PIC, definida por la Microchip
como el área de FILE REGISTER.
Esta área no es otra cosa que la localización de la RAM disponible para el usuario y
se encuentra a partir de la dirección 0x0C. Las direcciones de memoria anterioras a
esta no pueden ser utilizadas como casillas de memoria de propósito generalm pues
allí se han asignado previamente otros registros especializados para uso interno del
microcontrolador.
Count RES 2
En esta línea encontramos una etiqueta: Count y una directiva: RES.
La directiva RES le indica al compilador que queremos reservar un cierto número de
bytes en el interior del área de datos; en este caso 2 bytes.
La etiqueta Count, donde Count es un nombre, es una marcación que en el resto del
código fuente asumirá el valor de la dirección donde se ha insertado. Dado que
previamente habíamos definido como dirección de inicio la 0x0C (con la directiva
ORG), Count partirá desde 0x0C. Si por ejemplo, insertamos una etiqueta en la línea
inmediatamente sucesiva, esa variable se ubicará en 0x0C + 2, es decir 0x0E.
Una etiqueta se distingue de una constante simbólica porque su valor viene calculado
en la fase de compilación.
ORG 0x00
Esta segunda directiva nos permite señalar una dirección en el área de la memoria
de programa (FLASH). Desde allí se alamacenarán las instrucciones mnemonicas que
el compilador deberá convertir em opcodes para el PIC. El primer opcode que el
microcontrolador va a seguir después de un RESET se memoriza en la posición 0, por
eso es el valor 0x00 escrito en la ORG.
bsf STATUS,RP0
Al fin la primera instrucción mnemónica completa. El microcontrolador PIC posee una
CPU interna de tipo RISC, donde cada una de sus instrucciones ocupa una sola
posición de memoria, opcode e incluso parámetros.
En este caso la instrucción bsf (BIT SET FILE REGISTER) pone un uno (estado lógico
alto) el bit contenido en la posición de RAM especificada. El parámetro STATUS viene
definido en el archivo P16F84.INC a través de una directiva EQU.
En este archivo se a asignado la dirección 0x03, la cual corresponde a una casilla
reservada en la memoria ram del área de datos. El parámetro RP0 viene definido en
el archivo P16F84.INC con el valor 0x05h y corresponde al quinto bit del registro
11. CURSO INTEGRAL SOBRE MICROCONTROLADORES
11
www.welgos.net
STATUS. Si se pone un 1 en este bit para cambiar el banco de trabajo y poder
trbajar con los registros TRISA y TRISB, esto lo veremos más adelante.
movlw B'00011111'
Esta instrucción significa: MOVE LITERAL TO W REGISTER, es decir, mueva un valor
constante hacia el acumulador.
El acumulador es un registro particular utilizado por la CPU en todas las situaciones
donde se efectuen operaciones donde se necesite movimiento de valores de alguna
posición de memoria.
En la práctica es un registro de apoyo utilizado por la CPU para memorizar
temporalmente un byte.
El valor constante que vamos a memorizar en el acumulador es el 00011111 en
binario. El bit ubicado más a la derecha es el bit 0 o menos significativo.
En la instrucción siguiente:
movwf TRISA
el valor 00011111 se memoriza en el registro TRISA (al igual que el registro
STATUS, TRISA esta definido en el mismo archivo inc mediante otra directiva EQU)
el cual define el funcionamiento de cada una de las líneas I/O del puerto A.
En particular, cada bit en uno del registro TRISA configura como entrada la
respectiva línea del puerto A, mientras un 0 lo configura como salida.
En la siguiente tabla se muestra la configuración realizada en el PIC después de
ejecutada esta instrucción:
Como podemos ver, los bits 5, 6 y 7 no corresponde a ninguna línea I/O por lo tanto
el valor con que se configuren no importa.
12. CURSO INTEGRAL SOBRE MICROCONTROLADORES
12
www.welgos.net
Las dos instrucciones que siguen determinan el funcionamiento del puerto B del
microcontrolador:
movlw B'11111110'
movwf TRISB
En este caso la definición de las líneas será la siguiente:
Note como el valor 0 en el bit 0 del registro TRISB determina la configuración como
salida de la respectiva línea del PIC.
En nuestra aplicación esta línea se utiliza para manejar el LED.
Ya dijimos que la instrucción movwf TRISB trnasfiere el valor contenido en el
acumulador (inicializado previamente con la instrucción movlw B’11111110’) al
registro TRISB. El significado de movwf es (en inglés) MOVE W TO FILE REGISTER.
bcf STATUS,RP0
Esta instrucción es muy similar a la bsf vista en uno de los párrafos anteriores. La
diferencia es que en este caso el bit respectivo se pone en uno. La sigla en este caso
quiere decir (en inglés) BIT CLEAR FILE REGISTER.
Desde el punto de vista funcional de este programa, esta instrucción nos permite el
acceso a los registros internos del banco 0. Una descripción más detallada de este
proceso lo veremos más adelante.
bsf PORTB,LED
Con esta instrucción llevamos a cabo la primera operación en el entorno externo del
PIC, especificamente en la línea RB0 del integrado. PORTB es una constante definida
en el archivo P16F84.INC que nos permite referenciar el registros correspondiente a
las líneas I/O del puerto B. En cuanto a la palabra LED, recordemos que al inicio del
programa la definimos como 0, por lo que en esta línea nos estamos refiriendo a la
línea RB0.
13. CURSO INTEGRAL SOBRE MICROCONTROLADORES
13
www.welgos.net
MainLoop
Esta línea contiene una etiqueta esto es, una referencia simbólica hacia una posición
de memoria. EL valor de la etiqueta se calcula en la fase de compilación en base al
número de instrucción, a la directiva ORG y a la instrucción que hace reservar
espacio en la memoria del micro. En este caso, si contamos las instrucciones
insertadas a partir de la última directiva ORG podriamos calcular que el valor que se
asignará a MainLopp será 0x07.
El valor que asume la etiqueta es importante pues su objetivo real es el de conocer
la posición precisa su opcode en la memoria del PIC permitiendo referenciarla en una
determinada posición de memoria.
En este caso la etiqueta MainLoop se utiliza como punto de ingreso a un ciclo ( del
inglés loop) de encendido y apagado de un LED, es decir, una porción de código que
se repetirá cíclica e idefinidamente.
call Delay
Esta instrucción determina una llamada (de ingles call) a una subrutina que inicia en
correspondencia con la etiqueta Delay.
La subrutina es una parte del programa especializada en una función muy específica
que pueda necesitarse repetidamente dentro de un programa. Cada vez que
necesitemos ejecutar esta función basta invocar la función. En este caso la subrutina
inserta un retardo para darle tiempo al LED de prendido y apagado. Las instrucciones
que componen la subrutina Delay se encuentran más adelante en el código fuente.
btfsc PORTB,LED
El significado de esta instrucción es BIT TEST FLAG, SKIP IF CLEAR, es decir,
controla el estado de un bit interno de un registro y se salta la instrucción sucesiva si
el valor de dicho bit es cero. El bit que estamos controlando corresponde a la salida
en donde se encuentra conectado el LED. A través de este test podemos determinar
el estado del led para poder invertirlo, es decir, si se encuentra apagado se prende y
si se encuentra prendido se apaga.
goto SetToZero
Esta instrucción es un salto incondicional (del inglés GO TO, ir a) a la etiqueta
SetToZero donde tenemos las instrucciones para prender el led. Esta instrucción se
saltará las instrucciones sucesivas que sirven para apagar el led.
bsf PORTB,LED
goto MainLoop
Esta dos instrucciones activan el led y retorna el programa al ciclo de parpadeo.
SetToZero
bcf PORTB,LED
goto MainLoop
Esta dos instrucciones apagan el led y retorna el programa al ciclo de parpadeo.
La subrutina Delay
Como se dijo anteriormente, esta subrutina inserta un retardo de casi un segundo y
puede ser llamada desde nuestro código fuente mediante la instrucción call Delay.
Veamos como funciona:
14. CURSO INTEGRAL SOBRE MICROCONTROLADORES
14
www.welgos.net
Delay
clrf Count
clrf Count+1
DelayLoop
decfsz Count,1
goto DelayLoop
decfsz Count+1,1
goto DelayLoop
retlw 0
Delay y DelayLoop son dos etiquetas. Delay identifica la dirección de inicio de la
subrutina y se utiliza para llamar el cuerpo principal del programa. DelayLoop se
invoca internamente dentro de la subrutina y sirve como punto de entrada al ciclo (
del inglés loop) de retardo. En la práctica el retardo se obtiene ejecutando una serie
de instrucciones que no hacen absolutamente nada!
Este tipo de retardo se denomina retardo por software o retardo por programa. Es el
tipo de retardo mas sencillo de implementar y puede ser utilizado cuando podemos
darnos el lujo de que el PIC no tenga que ejecutar otras tareas mientras se
encuentra desarrollando el retardo.
Las instrucciones:
clrf Count
clrf Count+1
CLEAR FILE REGISTER, borran las dos posiciones de RAM que se han reservado
previamente mediante la instrucción:
Count RES 2
Estas dos posiciones son consecutivas y se ubican paratir de la dirección referenciada
por la etiqueta Count.
decfsz Count,1
Esta instrucción significa DECREMENT FILE REGISTER, SKIP IF ZERO, es decir,
decrementa el contenido de un registro (en este caso Count) y se salta la siguiente
instrucción si el valor obtenido es cero. Si el valor obtenido no es cero, se ejecuta la
instrucción consecutiva:
goto DelayLoop
Nos dirige hacia la ejecución de un ciclo de retardo. Una vez el contador Count ha
llegado a cero, se tienen las instrucciones:
decfsz Count+1,1
goto DelayLoop
que decremetan el registro siguiente hasta que este llegue a cero. El registro
Count+1 en particular se decrementerá en una unidad por cada 256 decrementos de
Count. Cuando Count+1 llegue a cero se ejecuta la instrucción:
return
el significado de esta instrucción es RETURN FROM SUBROUTINE, es decir, nos dará
la salida de la rutina de retardo y la posibilidad de continuar con la ejecución de la
instrucción consecutiva a la instrucción call Delay.
Para finalizar END es una directiva que indica al compilador el fin del código en
asembler.
1.4 Compilando un código en ensamblador
Veamos ahora como es posible efectuar en la práctica la compilación de un código en
lenguaje ensamblador. El primer paso es crear en el disco duro una carpeta donde
vamos a guardar todos los programas de este curso. Por ejemplo:
C:WEL
15. CURSO INTEGRAL SOBRE MICROCONTROLADORES
15
www.welgos.net
(Auqnue cualquier otro nombre es válido). Parsa trabajar adecuadamente es
necesario descargar de internet el compilador MPASM disponible gratuitamente en el
sitio de Microchip en la siguiente dirección:
http://www.microchip.com/1010/pline/tools/archive/other/61/index.htm
El archivo que se debe descargar se llama asm21500.zip (579K) y contiene el
ensamblador MPASM en su versión para Windows (MPASMWIN.EXE) o para
MS/DOS (MPASM.EXE) además de una serie de utilidades como todos los archivos
.INC los cuales necesitaremos para trabajar con los microcontroladores de Microchip.
Una vez expandido el contenido del archivo asm21500.zip en nuestro directorio de
trabajo podemos abrir el archivo MPASMWIN.EXE cuya presentación es la siguiente:
Oprimiendo el boton de “Browse..." podemos seleccionar de nuestra carpeta de
trabajo el archivo LED.ASM. Luego podemos oprimir el boton "Assemble". El
ensamblador iniciará la compilación. Al terminar la compilación obtendremos el
siguiente esquema:
16. CURSO INTEGRAL SOBRE MICROCONTROLADORES
16
www.welgos.net
Si vamos al directorio C:WEL podremos observar un nuevo archivo llamado
LED.HEX, el cual contiene el código objeto que utilizaremos para programar el PIC,
además de una serie de archivos auxiliares como LED.ERR y LED.LST. Ahora
podemos programar el PIC16F84A con el programa compilado.
1.5 Que programador utilizar?
Para programar los ejemplos presentados en este curso, hay dos opciones ha seguir.
Existen dos modalides para programar los microcontroladores: la serial y la paralela.
La empresa microEngineering Labs Inc. ha desarrollado un programa denominado
EPIC para la programación paralela y la segunda opción es utilizando el puerto serial
mediante nuestro programador WELPROG.
Recomendamos el uso de un programador serial (ya sea el WELPROG o el PICStart
PLUs de Microchip). Los usuarios del programador por el puerto paralelo han
manifestado daños en la estructura del puerto, lo que puede implicar no poder
utilizar el puerto paralelo para la impresora.
Las banderas de configuración del microcontrolador PIC
El microcontrolador PIC dispone de una serie de banderas de configuración
contenidos en la denominada configuration word. Estas bandera determinan
algunos aspectos del funcionamiento del microcontrolador cuando este sigue un
programa. La configuración de las banderas se puede establecer dentro del código
fuente mediante la directiva _CONFIG o establecerce en el momento de la
programación del microcontrolador.
Todos los ejercicios analizados en este curso a exepción del manejo del tiempo real,
utilizan la siguiente configuración:
17. CURSO INTEGRAL SOBRE MICROCONTROLADORES
17
www.welgos.net
* Oscilador en modalidad XT. En esta modalidad, el PIC funciona correctamente
con un cristal de cuarzo conectado a los pines OSC1 y OSC2 como se muestra en el
esquema del primer ejemplo.
* Watch Dog Timer Deshabilitado. La función del WATCH DOG se explica más
adelante en este curso. Cuando en alguno de los ejemplos de este curso se vaya a
habilitar, se especificará claramente esta acción.
1.6 Programando el PIC con EPICWIN
Una vez instalado correctamente la tarjeta de programación abrimos el programa
EPICWIN.EXE, seleccionamos el tipo de microcontrolador que vamos a programar
(PIC16F84A).
Insertamos el PIC en la base del programador teniendo cuidado en la orientación
como se instale, para lo cual puede guiarse por el screen de la tarjeta. Se carga el
archivo LED.HEX del directorio de trabajo C:WEL (En el EPICWin se selecciona
"Menu File" y luego "Open"). Por último nos aseguramos que los fusibles de
programación esten bien configurados.
18. CURSO INTEGRAL SOBRE MICROCONTROLADORES
18
www.welgos.net
Es importante seleccionar bien el tipo de oscilador con que vamos a trbaajr. Si
vamos a hacerlo con cristal se debe elegir XT y deshabilitar el watch dog timer. Si
metemos mal estos parámetros, los programas no nos funcionarán. Más adelante en
este curso veremos ejemplos de cual es la función de estos parámetros y cuando
modificarlos.
Finalmente podemos hacer la programación (Menu "Run" --> "Program"). Si no se
señalan errores en el sistema de programación tendremos el PIC listo para ser
insertado en el circuito de ejemplo.
Si alimentamos el circuito, podremos ver el LED parpadeando.
1.7 Programando el PIC con WELPROG
PROGRAMADOR “In – circuit” DE MICROCONTROLADORES PIC
El software del programador está escrito en C para DOS, y puede ejecutarse desde
un prompt o línea de comandos DOS en el ambiente Windows 3.1/95/98 y en
máquinas que poseen procesadores Intel de 286 en adelante.
Características del programador
• Interfaz interactiva
• Acepta la variedad de familias de microcontroladores PIC 16xxx
• Lectura y escritura de archivos en formato IN8HEX
• Chequeo de memoria vacía
19. CURSO INTEGRAL SOBRE MICROCONTROLADORES
19
www.welgos.net
• Lectura de la memoria de programa y de la palabra de configuración
• Programación “in circuit” o dentro de la aplicación.
TIPOS DE PIC SOPORTADOS POR LA TARJETA
12C508 12C509 16C554 16C556 16C558 16C61 16C62 16C62A 16C62B
16C620 16C620A 16C621 16C621A 16C622 16C622A 16C63 16C63A 16C64
16C64A 16C65 16C65A 16C65B 16C66 16C67 16C71 16C710 16C711
16C72 16C72A 16C73 16C73A 16C73B 16C74 16C74A 16C74B 16C76
16C77 16C84 16F83 16F84 16F84A 16C923 16C924 16CE623 16CE624
Instalación de la tarjeta
Un programador “in circuit” se caracteriza por enviar el programa directamente a la
memoria del PIC en cualquier sitio que este se encuentre ubicado.
Esa es la principal diferencia con respecto a los programadores “STAND ALONE” o
independientes, ellos cuentan con una base tipo ZIF en la cual se inserta el PIC en el
momento de programarlo, luego deben retirarlo del programador e insertarlo dentro
de la aplicación.
Para utilizar este programador se debe tener a disposición el prototipo montado, en
el cual se conecta la tarjeta programadora, tal como se muestra en la figura:
Para la conexión con el prototipo, la tarjeta cuenta con un conector de seis pines,
cada uno de los cuales deben ser conectados con el PIC objetivo así:
1. MCLR.
2. DATA. Por este pin van los datos de programación y debe conectarse al pin RB7
del PIC objetivo.
3. CLOCK. Es la señal de reloj, debe conectarse al pin RB6 del PIC a programar.
4. GND. Es la tierra del programador, debe conectarse a la tierra del prototipo.
5. KEY.
6. VCC. En este pin van los voltajes de programación. Debe conectarse a los pines
12,6 o 14,6 del PIC.
PC
Programador prototipo
20. CURSO INTEGRAL SOBRE MICROCONTROLADORES
20
www.welgos.net
Instalación del software y guía rápida de programación
Para instalar el programa debe crear una carpeta en el disco duro del computador
llamada WELGOS y copiar los archivos en esta carpeta, no altera ningún registro de
Windows y de la misma manera, para desinstalarlo solo basta borrar el archivo.
Para ejectar el programa debe ejecutar un prompt de DOS y abrir la carpeta
WELGOS:
Cd welgos
Luego ejecutar la siguiente sintaxis:
WELGOS> progra / com1 (o com2 según donde lo tenga conectado).
Si la tarjeta no se encuentra conectada al puerto serial, el software no establecerá
comunicación y el programa no se ejecutará.
Si la conexión con la tarjeta y el cable serial está bien instalado, se podrá entrar al
pantallazo inicial del programa:
En este pantallazo se indica el PIC actualmente seleccionado, el contenido del buffer
de memoria ( si este aún no se ha cargado aparecerá el aviso de no definido) , la
palabra de configuración y un menú de opciones. Para seleccionar cada una de las
posibilidades de este menú, basta con teclear la letra que se encuentra a la izquierda
de cada opción entre paréntesis, a continuación analicemos cada uno de los items de
este menú.
Seleccionar tipo de PIC
Este programador puede trabajar con toda la familia de microcontroladores PIC
16XXX. Con esta opción se selecciona el Pic en específico que se va a trabajar. Al
presionar la tecla T, sale un listado de todos los PICs que se pueden trabajar, para
esa selección se debe buscar el dispositivo correcot con las teclas de flecha hacia
arriba y flecha hacia abajo o las teclas Repág. y Avpág. En este pantallazo aparece a
la izquierda el tipo de PIC y a la derecha el tamnaño de la memoria de programa de
cada uno de ellos
Leer PIC
Al oprimir la tecla R, se puede leer el contenido de la memoria del micro. Este
proceso se demora unos cuantos segundos. Al cabo de ls cuales aparece un nuevo
menú, en el cual aparecen nuevas opciones. La lectura del programa del chip a
quedado almacenado en un espacio de memoria llamado la imagen de entrada.
Entre las nuevas opciones que aparecen se encuentran la de abrir un archivo de
disco, la de escribir en el PIC, establecer palabra de configuración.
40
21. CURSO INTEGRAL SOBRE MICROCONTROLADORES
21
www.welgos.net
Mostrar Buffer
En el buffer se encuentra almacenado un programa en hexadecimal, el cual puede
provenir de la lectura del PIC o de un archivo grabado en disco. Este buffer se puede
visualizar con esta opción, con la cual se muestran todas las direcciones de
memoria y su contenido.
Contenido del Buffer...........:IMAGEN DE LA MEMORIA DEL PIC
[1] MODO DEL OSCILADOR : XT
[2] WATCH DOG TIMER.: DESHABILITADO
[3] PROTECCION DEL CODIGO: DESHABILITADO
[4] POWER UP TIMER: DESHABILITADO
[D] Buffer dump
[R] LEER PIC
[W] ESCRIBIR EN EL PIC
[F] ESCRIBIR SOLO FUSIBLES
[L] CARGAR ARCHIVO IN8HEX
[V] VERIFICAR PIC
[T] SELECCIONAR TIPO DE PIC
[V] VERIFICAR PIC
[H] PANEL DE PRUEBAS DEL HARDWARE
[K] DESHABILITAR PROTECCION DEL CODIGO
Panel de pruebas del hardware
Con esta opción se realizan una serie de pruebas para comprobar que la tarjeta está
funcionando correctamente. Aquí se entra a un nuevo menú en el cual se permite
variar los voltajes del conector que va hasta el pic objetivo.
Se muestran cinco tipos de pruebas distintas las cuales modifican los voltajes en
cada uno de los pines del conector, de manera que si el aparato presenta alguna falla
en la programación, el usuario puede llevar a cabo estas pruebas con un multímetro.
Programación del microcontrolador
El primer paso para programar un microcontrolador es cargar el archivo hexadecimal
resultante de ensamblar el código fuente. Este archivo hexadecimal debe estar en
una de las unidades de la computadora; si pulsa la tecla L, el programa lle permitirá
cargar el archivo hexadecimal que desea programar, para lo cual le pide la ubicación
y el nombre del archivo.
22. CURSO INTEGRAL SOBRE MICROCONTROLADORES
22
www.welgos.net
DIGITE EL NOMBRE DEL ARCHIVO: c:welled.asm
Cuando el archivo ha sido leído, queda almacenado en un buffer de memoria, por lo
tanto podemos visualizarlo pulsando la letra D.
Después de que se ha cargado el archivo hexadecimal, se deben establecer los
fusibles de programación; ellos corresponden a las condiciones bajo las cuales va a
funcionar el sistema. Esos parámetros son: el tipo de oscilador que se va a instalar,
el estado del temporizador watchdog, la habilitación de la protección del código y el
PWRT. En el menú aparecen estas opciones para que las modifique de acuerdo a sus
necesidades; como se puede observar, a la izquierda de cada fusible aparece un
número ([1], [2], [3] y [4]), oprimiendo cada número se modificarán cada uno de
los fusibles. Por ejemplo, si el oscilador se encuentra en RC y oprime la tecla 1 este
fusible cambiará a XT, si lo oprime nuevamente cambiará a INTRC y así
sucesivamente para cada una de las opciones.
Una vez se ha seleccionado el microcontrolador, cargado el archivo hexadecimal y
configurado adecuadamente los fusibles, puede proceder a programar. Para llevar a
cabo este proceso hay que oprimir la tecla W, con la cual se inicia el almacenamiento
del programa en la memoria del PIC. En este momento podrá apreciar en la pantalla
como van apareciendo poco a poco las distintas posiciones de memoria llenándose
con los distitnos datos del archivo hexadecimal.
0000: 2813 ....... ....... ..... 306E 0080 306E 008E
0008: 0000 0000 0000 0000 088E 2080 4321 0000
0010: 0B8D 2806 3400 2134 OE40 3456 5639 0050
0018: 304F 34E0 1200 00A0 0789 2234 00B1 0090
0020:
El programa realiza un procedimiento de verificación para comprobar que en cada
posición se ha almacenado el dato correcto, para ello compara el dato actual
programado con el dato leído en el buffer. Al final de la programación se brinda un
pequeño reporte donde se especifica si han ocurrido errores o si la programación se
desarrolló correctamente.
Si ha ocurrido un error en la programación de alguna de las posiciones de memoria,
aparecerá un asterisco (*) enseguida de la posición donde se ha presentado la falla.
Finalmente es posible realizar una verificación total del programa grabado en el
microcontrolador, comparándo este último con el buffer de memoria que permanece
en el buffer de la PC.
23. CURSO INTEGRAL SOBRE MICROCONTROLADORES
23
www.welgos.net
;**************************************************
; Programa
; LED.ASM
;
;
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
ERRORLEVEL -302
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 0x3FF1
LED EQU 0
ORG 0x0C
Count RES 2
;Reset Vector
;Start point at CPU reset
ORG 0x00
bsf STATUS,RP0
movlw B'00011111'
movwf TRISA
movlw B'11111110'
movwf TRISB
bcf STATUS,RP0
bsf PORTB,LED
MainLoop
call Delay
btfsc PORTB,LED
goto SetToZero
bsf PORTB,LED
goto MainLoop
SetToZero
bcf PORTB,LED
goto MainLoop
;Subroutines
;Software delay
Delay
clrf Count
clrf Count+1
DelayLoop
decfsz Count,1
goto DelayLoop
decfsz Count+1,1
goto DelayLoop
return
END
24. CURSO INTEGRAL SOBRE MICROCONTROLADORES
24
www.welgos.net
LIST
; P16F84.INC Standard Header File, Version 2.00 Microchip Technology,
Inc.
NOLIST
; This header file defines configurations, registers, and other useful
bits of
; information for the PIC16F84 microcontroller. These names are taken to
match
; the data sheets as closely as possible.
; Note that the processor must be selected before this file is
; included. The processor may be selected the following ways:
; 1. Command line switch:
; C: MPASM MYFILE.ASM /PIC16F84
; 2. LIST directive in the source file
; LIST P=PIC16F84
; 3. Processor Type entry in the MPASM full-screen interface
;=======================================================================
===
;
; Revision History
;
;=======================================================================
===
;Rev: Date: Reason:
;2.00 07/24/96 Renamed to reflect the name change to PIC16F84.
;1.01 05/17/96 Corrected BADRAM map
;1.00 10/31/95 Initial Release
;=======================================================================
===
;
; Verify Processor
;
;=======================================================================
===
IFNDEF __16F84
MESSG "Processor-header file mismatch. Verify selected processor."
ENDIF
;=======================================================================
===
;
; Register Definitions
;
;=======================================================================
===
W EQU H'0000'
F EQU H'0001'
;----- Register Files---------------------------------------------------
---
INDF EQU H'0000'
TMR0 EQU H'0001'
PCL EQU H'0002'
STATUS EQU H'0003'
FSR EQU H'0004'
PORTA EQU H'0005'
PORTB EQU H'0006'
EEDATA EQU H'0008'
EEADR EQU H'0009'
PCLATH EQU H'000A'
INTCON EQU H'000B'
OPTION_REG EQU H'0081'
26. CURSO INTEGRAL SOBRE MICROCONTROLADORES
26
www.welgos.net
_WDT_OFF EQU H'3FFB'
_LP_OSC EQU H'3FFC'
_XT_OSC EQU H'3FFD'
_HS_OSC EQU H'3FFE'
_RC_OSC EQU H'3FFF'
LIST
CURSO INTEGRAL
PIC
Capítulo 2
Arquitectura interna del PIC16F84A
27. CURSO INTEGRAL SOBRE MICROCONTROLADORES
27
www.welgos.net
En la lección anterior vimos un poco de práctica, ahora pasemos a la teoría.
Empezemos estudiando como se estructura internamente un microcontrolador PIC.
En la figura siguiente se muestra un diagrama en bloques simplificado de la
arquitectura interna del PIC16F84A en el cual nos basaremos para las explicaciones
que siguen a continuación. Los bloques resaltados en amarillo son los que nos
referiremos en la explicación.
Iniciamos con la memoria de programa (PROGRAM MEMORY) y con la memoria de
datos (REGISTER FILE).
2.1 La Memoria de Programa
La PROGRAM MEMORY es una memoria especial de tipo FLASH, borrable
eléctricamente y se utiliza para almacenar el programa que el microcontrolador debe
seguir.
28. CURSO INTEGRAL SOBRE MICROCONTROLADORES
28
www.welgos.net
La capacidad de memoria en este caso es de 1024 posiciones, cada una de las cuales
puede contener un código operativo (opcode) de 14 bits, es decir, una instrucción del
microcontrolador, por lo tanto el microcontrolador puede almacenar un programa de
1024 instrucciones.
Las direcciones reservadas para la memoria de programa van desde la 0x000 hasta
la 0x3FF (0x3FF en hexadecimal equivale a 1023 en decimal).
El microcontrolador PIC solo puede seguir instrucciones memorizadas en estas
posiciones. No puede leer, escribir o cancelar posiciones que sobrepasen este rango.
Para escribir, leer o cancelar estas posiciones es necesario un dispositivo externo
denominado programador. Un ejemplo de este tipo de dispositivos es el EPIC Plus, el
PICSTART de la Microchip o el WELPROG (incluido en este curso).
La primera posición de memoria, debe contener la primera instrucción que el
microcontrolador debe seguir después del reset (reinicIo) y por esto se denomina
vector de reset.
Como podemos recordar, en el archivo LED.ASM presentado en la lección anterior, se
había insertado la directiva:
ORG 0x00
Para señalizar el inicio del programa. Esta directiva establece el hecho de que la
ejecución del programa después de un reset parte desde la dirección 0x000 del área
de memoria de programa. Después de la directiva ORG 0x00 se tiene:
bsf STATUS,RP0
que será la primera instrucción que se ejecuta enseguida.
2.2 Los registros (Register File)
El archivo de registros (REGISTER FILE) es un conjunto de posiciones de memoria
RAM sobre los cuales es posible modificar el contenido sin el auxilio de un
programador externo, simplemente se hace directamente desde el programa que se
está ejecutando en el microcontrolador.
Debido a que el archivo de registros se utiliza normalemente para almacenar las
variables del programa, su contenido es variables durante la ejecución del programa.
Contrariamente a lo que ocurre con la memoria de programa, el archivo de registros
pierden su contenido cuando el microcontrolador es reiniciado, por lo que es
recomendable inicializar las variables en el inicio del programa. Alguna posiciones
determinadas del archivo de registros vienen con funciones predeterminadas para el
control del hardware del microcontrolador como se muestra en la siguiente figura.
29. CURSO INTEGRAL SOBRE MICROCONTROLADORES
29
www.welgos.net
Las posiciones de memoria del
archivo de registros se pueden
direccionar directamente en un
espacio de memoria que va desde
0x00 hasta 0x2F para un total de 48
bytes, denominado página 0. Un
segundo espacio de direccionamiento
denominado página 1 va desde la
0x80 hasta la 0xAF. Para acceder a
este segundo espacio es necesario
recurrir a dos bits auxiliares
denominados RP0 y RP1
pertenecientes a un registro especial
denominado estado.
Las primera 12 posiciones de la
página 0 (0x00 hasta 0x0B) y de la
página 1 (desde la 0x80 hasta la
0x8B) son los reservados para
funciones especiales para el
funcionamiento del microcontrolador
y no se pueden utilizar para otras
funciones.
Las 36 posiciones en la página 0,
direccionadas desde la 0c0C hasta la
0x2F puede utilizarse libremente en
nuestro programa para memorizar
variables, contadores, etc. En
nuestro ejemplo LED.ASM, la
directiva:
ORG 0x0C
Indica la dirección de inicio del área
de datos de nuestro programa. La
directiva siguiente:
Count RES 2
Reserva un espacio de dos
posiciones, que el programa utilizará oara memoriza el contador de retardo de la
subrutina Delay.
Los registros especializados del PIC se utilizan de un modo diferente dentro del
programa.
Por ejemplo, se recurre a la copia del registro especializado TRISA (0x85) y TRISB
(0x86) para definir cuales de las líneas I/O son entradas y cuales serán salidas. El
estado lógico de las líneas I/O dependen del valor de los registros PORTA (0x05) y
PORTB (0x06). Algunos registros sirven para reportar el estado del funcionamiento
de los dispositivos internos del microcontrolador o el resultado de operaciones
aritméticas y lógicas. Es necesario conocer exactamente cual es la función de cada
uno de los registros especializados y cual es el efecto que se obtiene de manipular
sus contenidos. Para facilitar la manipulación de los registros especializados,
30. CURSO INTEGRAL SOBRE MICROCONTROLADORES
30
www.welgos.net
Microchip proporciona un listado de nombres que identifican cada uno de los
registros mediante un nombre único relacionados con la dirección correspondiente en
el archivo de registros, dicho listado se guarda en un archivo llamado P16F84.INC.
En nuestro programa LED.ASM el archivo de definiciones se ha insertado mediante la
directiva INCLUDE. Si por ejemplo, vamos a definir la configuración de las líneas del
puerto B del PIC como salidas, debemos utilizar el registro TRISB. Para ello debemos
referenciar directamente el registro mediante su dirección:
movlw B'00000000'
movwf 0x86
o podemos referenciarlo son su nombre simbólico:
movlw B'00000000'
movwf TRISB
lo que podemos hacer gracias a que insertamos la directiva INCLUDE "P16F84.INC"
en nuestro código fuente.
2.3 La ALU
La ALU (acrónimo de Arithmetic and Logic Unit: unidad lógico artimética) es el
componente más complejo del microcontrolador em cuanto contiene toda la
32. CURSO INTEGRAL SOBRE MICROCONTROLADORES
32
www.welgos.net
2.5 El Contador de Programa (PC)
Como habíamos mencionado anteriormente, el PIC16F84A inicia la ejecución del
programa a partir del vector de reset empezando por la instrucción memorizada
en la primera posición de memoria (dirección 0x000).
Después de ejecutada esta primera instrucción, pasa a la instrucción siguiente,
memorizada en la posición 0x001 y así sucesivamente. Si no existiera ninguna
instrucción que pueda influenciar o estar en capacidad este orden de ejecución, el
PIC seguiría ejecutando todas las instrucciones sucesivas hasta llegar a la última
posición de memoria disponible.
Casi todo microprocesador o lenguaje de programación brinda la posibilidad de
ejecutar instrucciones de salto, con lo que podemos modificar el flujo normal de la
ejecución del programa en base a las exigencias del programador.
33. CURSO INTEGRAL SOBRE MICROCONTROLADORES
33
www.welgos.net
Una de estas instrucciones es la GOTO (del inglés GO TO, ir a), la cual nos permite
cambiar la secuencia de la ejecución y “saltar” directamente a otro punto de la
memoria de programa y continuar la ejecución desde ese punto.
Miremos un ejemplo:
ORG 0x00
Point1
movlw 10
goto Point1
Una vez se reinicia el microcontrolador, se ejecutará la instrucción MOVLW 10,
memorizada en la posición de memoria 0x000, la cual cargará en el acumulador el
valor decimal 10, luego se pasa a la instrucción GOTO Point1.
Esta instrucción determina un salto incondicional a la posición de memoria apuntada
por la etiqueta Point1, la cual es de nuevo la 0x000. Este programa no hará otra
cosa más que ejecutar infinitamente estas dos intrucciones.
Durante este ciclo o lazo (loop) para determinar cual es la instrucción siguiente que
se debe ejcutar, el PIC utiliza un registro especial denominado el Contador de
Programa (PROGRAM COUNTER, PC) el cual posee la dirección de la próxima
instrucción que se debe ejecutar.
Este registro se incrementa automáticamente con cada instrucción, de esta manera
actualiza la dirección de la siguiente instrucción que se debe ejecutar. En el
momento de un reset, el contador de programa se borra, poniendose de nuevo en
0x000.
La instrucción GOTO permite modificar el contenido del contador de programa para
de esa manera ejecutar el salto hacia un punto en cualquier parte de la memoria de
programa.
2.6 El puntero a la pila (Stack Pointer)
Otra instrucción muy utilizada y que también puede modificar el valor del contador
de programa es la instrucción CALL (del inglés llamar) con la cual podemos hacer el
llamado a subrutinas.
Esta instrucción funciona de manera muy similar al GOTO. La diferencia consiste en
el hecho de que después del salto, el PIC memoriza en un registro especial
denominado la pila (stack) la dirección de la siguiente instrucción que se iba a
ejecutar antes de hacer el salto.
Veamos esto con un ejemplo:
ORG 0x00
Point1
movlw 10
call Point2
34. CURSO INTEGRAL SOBRE MICROCONTROLADORES
34
www.welgos.net
goto Point1
Point2
movlw 11
return
En este caso el PIC después de ejecutar MOVLW 10, pasa a la instrucción CALL
Point2. Antes de saltar memoriza en la pila la dirección 0x002, que es la dirección
que le sigue a la dirección donde se encuentra CALL. Luego se ejecuta la instrucción
MOVLW 11 y la instrucción RETURN (del inglés retorno). Esta instrucción, como su
nombre lo indica, permite “retornar” a la instrucción siguiente desde donde se invocó
a CALL, es decir, al punto exacto donde se abondó el flujo normal del programa,
acudiendo a la información almacenada en la pila.
Lo que acabamos de hace es lo que se denomina una llamada a subrutina. Es decir,
la interrupción momentanea del flujo normal del programa para invocar la ejecución
de otro conjunto de instrucciones agrupadas dentro de una unidad denominada
subrutina, y luego retornar al flujo normal de la ejecución.
La pila recibe ese nombre debido a que en realidad lo podemos asemejar a una
canasta donde apilamos, una sobre otra, distintas direcciones de retorno que se
deben recuperar en un programa, debido al uso de una o varias instrucciones CALL.
Este tipo de memorización se denomina LIFO (Last In First Out), en donde el último
elemento almacenado (last in) es necesariamente el primero en salir ( First Out).
Gracias a esta característica, es posible efectuar una serie de instrucciones CALL
anidadas sin perder el flujo normal en el momento en que se encuentre una
instrucción RETURN.
Veamos otro ejemplo:
ORG 0x00
Point1
movlw 10
call Point2
goto Point1
Point2
movlw 11
call Point3
return
Point3
movlw 12
return
En este caso, al efectuar la subrutina Point2, se encuentra otro CALL a la subrutina
Point3. En esta última sección del programa se encuentra un RETURN se entra a la
subrutina Point2 donde se ejecuta el segundo RETURN y de allí se retoma el flujo
normal del programa principal.
En este caso se han memorizado dos posiciones en la pila, ya que se ejecutan dos
CALL antes de encontrar un RETURN. El PIC 16F84A dispone de una pila de 8 niveles,
lo que permite 8 llamados anidados.
35. CURSO INTEGRAL SOBRE MICROCONTROLADORES
35
www.welgos.net
Es muy importante que en la escritura de un programa, que siempre haya una
instrucción RETURN por cada instrucción CALL. Esto evitará desalineamientos en la
pila que pueden traernos errores de compilación que pueden ser difíciles de detectar.
2.7 Realizando un secuenciador de luces
En este segundo ejercicio vamos a ampliar el primer ejercicio para hacer un
secuenciador de luces con cuatro diodos led. El nuevo programa se ha denominado
SEQ.ASM.
En la siguiente figura se muestra el diagrama esquemático del nuevo circuito, el cual
como se puede ver, es muy parecido al montaje anterior, con la diferencia que hay
cuatro LED en lugar de uno.
Las líneas utilizadas son RB0 para el primer LED, RB1 para el segundo, RB2 para el
tercero y RB3 para el cuarto. Estos pines debe ser configurados como salidas en el
inicio del programa cambiando las siguientes instrucciones:
movlw B'11111110'
movwf TRISB
por
movlw B'11110000'
movwf TRISB
36. CURSO INTEGRAL SOBRE MICROCONTROLADORES
36
www.welgos.net
en donde los cuatro bits menos significativos, corresponden a las líneas RB0, RB1,
RB2 y RB3. las cuales se configuran como salidas.
En el área de memoria del archivo de registros (en el código fuente inicia con la
directiva ORG 0x0C) de nuevo se tienen dos bytes reservados para la variable Count
y se reservan otros dos para la etiqueta Shift, la cual utioizaremos para determinar
la secuencia del movimiento del LED. La directiva adicionada es:
Shift RES 1
Antes de emnpezar el ciclo principal (etiqueta MainLoop) inicilizamos el nuevo
registro (Shift) con el valor 00000001B así:
movlw B'00000001'
movwf Shift
En este punto, dentro del ciclo principal de nuestro programa, nos ocuparemos de
transferir el contenido memorizado en el registro Shift sobre el puerto B, obteniendo
la iluminación del primer LED, así:
movf Shift,W
movwf PORTB
para efectuar el secuenciamiento de la iluminación de los LED necesitamos rotar el
contenido del registro Shift, con las siguientes instrucciones :
bcf STATUS,C
rlf Shift,F
la primera instrucción borra el bit CARRY del registro de estado, esto se analizará en
la siguiente lección. La instrucción RLF (Rotate Left F through Carry: rota el registro
a través del carry) se encarga de rotar hacia la izquierda el contenido del registro. Es
decir, el bit de la posición 7 pasa a la posición 6, el de la posición 6 pasa a la cinco y
así sucesivamente. El bit 0 pasa a ocupar el bit de carry (acarreo) que es un bit
pertenciente a un registro de la CPU denominado STATUS (estado) y el contenido del
carry pasa al bit 7. Es por esta razón que inicialmente borramos el contenido del
carry mediante la instrucción BCF STATUS,C.
En este punto el registro Shift tendrá el valor 00000010 y en la siguiente
transferencia al puerto B se activaráel LED 2 y se desactivará el LED 1.
Cuando el bit 4 de Shift valga 1, podemos deducir que ya se han activado los cuatro
LED, por lo tanto debemos repetir el ciclo para que se vuelva a ctivar el LED 1.
Miremos las siguientes instrucciones:
btfsc Shift,4
swapf Shift,F
La instrucción BTFSC Shift,4 detecta el momento en que el bit 4 del registro Shift
vale 1. Si detecta un cero se salta la instrucción siguiente que en este caso es
SWAPF Shift,F.
La instrucción SWAP (del inglés intercambiar) sirve para intercambiar el contenido de
los cuatro bits menos significativos con los cuatro bits más siginificativos. Cuando el
registro Shift toma el valor 00010000 debido a las rotaciones, la instrucción SWAP
convierte este valor en 00000001, para reiniciar la secuencia de encencido de los
diodos LED.
37. CURSO INTEGRAL SOBRE MICROCONTROLADORES
37
www.welgos.net
;**************************************************
; Curso integral de microcontroladores Pic
; SEQ.ASM
;
; (c) 2003, WELGOS electronica
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
ERRORLEVEL -302
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 0x3FF1
ORG 0x0C
Count RES 2
Shift RES 1
;Reset Vector
;Program start point at CPU reset
ORG 0x00
bsf STATUS,RP0
movlw B'00011111'
movwf TRISA
movlw B'11110000'
movwf TRISB
bcf STATUS,RP0
movlw B'00000001'
movwf Shift
MainLoop
movf Shift,W
movwf PORTB
bcf STATUS,C
rlf Shift,F
btfsc Shift,4
swapf Shift,F
call Delay
goto MainLoop
; Subroutines
Delay
clrf Count
clrf Count+1
DelayLoop
decfsz Count,1
goto DelayLoop
decfsz Count+1,1
goto DelayLoop
return
END
CURSO INTEGRAL
PIC
Capítulo 3
38. CURSO INTEGRAL SOBRE MICROCONTROLADORES
38
www.welgos.net
Introducción a los periféricos
3.1 Los puertos A y B
El PIC16F84A dispone de un total de 13 líneas I/O organizadas en dos puertos
denominados Puerto A y puerto B. El puerto A dispone de 5 líneas configurables
como entradas o como salidas, identificadas como RA0, RA1, RA2, RA3 y RA4.
El puerto B dispone de 8 líneas también configurables como entradas o como salidas,
ellas son RB0, RB1, RB2, RB3, RB4, RB5, RB6 y RB7.
Las líneas de cada uno de los puertos poseen una arquitectura interna determinada
dentro del microcontrolador. Para la gestión de la líneas I/O, el PIC dispone de dos
registros internos, uno para cada puerto. Ellos se denominan TRISA para determinar
el funcionamiento del puerto A y el registro TRISB para configurar el puerto B.
39. CURSO INTEGRAL SOBRE MICROCONTROLADORES
39
www.welgos.net
Cada uno de los bits contenidos en los registros anteriores tienen una
correspondencia unívoca con una de las líneas I/O. Por ejemplo, el bit 0 del registro
PORTA y del regsitro TRISA corresponde a la línea RA0, el bit 1 a la línea RA1 y así
sucesivamente.
Si el bit 0 del regsitro TRISA se pone en cero, la línea RA0 se configura como salida y
el valor que se ponga en el bit 0 de PORTA se verá reflejado en el estado lógico de
dicha línea (0= 0 voltios, 1 = 5 voltios).
Si en el bit 0 del registro TRISA se pone un uno, la línea RA0 se configurará como
entrada, en este caso, el estado lógico dependerá de la circuitería externa conectada
a la línea RA0 y dicha entrada externa se verá reflejasa en el estado del bit 0 del
registro PORTA.
Miremos un ejemplo práctico, instalemos un LED sobre la línea RB0 y un interruptor
en la línea RB4. Miremos el código siguiente:
movlw 00010000B
tris B
estamos poniendo un 0 en el bit 0 (RB0 como entrada) y un 1 en el bit 4 (línea RB4)
para que sea una entrada. Si recordamos la notación binaria del lenguaje
ensamblador, podremos recordar que el bit menos significativo corresponde al bit 0
(el que se encuentra en la primera posición de derecha a izquierda).
Para encender el LED podemos escribir lo siguiente:
bsf PORTB,0
y para apagarlo:
bcf PORTB,0
Para leer el estado del interruptor conectado a la línea RB4:
btfss PORTB,4
goto SwitchAMassa
goto SwitchAlPositivo
3.2 Estado de entrada de las líneas de I/O
Para entender la adaptabilidad del microcontrolador PIC para las diversas
configuraciones, la Microchip a implementado diversas topologías para las líneas I/O.
Cada grupo de pines posee un comportamiento distinto a los otros grupos.
Conociendo bien el funcionamieno de los diversos estados de las entradas podemos
disfrutar mejor de las características y optimizar su uso en nuestros proyectos.
Estado de las entradas de las líneas RA0, RA1, RA2 e RA3
Iniciemos con elgrupo de las líneas RA0, RA1, RA2 y RA3 el cual reproducimos en la
siguiente figura, el esquema del estado de las entradas se encuentra en las hojas de
datos de la Microchip:
40. CURSO INTEGRAL SOBRE MICROCONTROLADORES
40
www.welgos.net
Como se habiamos mencionado anteriormente, la configuración de una línea como
entrada o salida depende del estado del bit correspondiente en el registro TRIS
(TRISA para el puerto A y TRISB para el puerto B).Pongamos como ejemplo la línea
RA0 y analizemos su funcionamiento cuando actúa como entrada.
Funcionamiento como entrada
Para configurar la línea RA0 como entrada, debemos poner un 1 en el bit 0 del
registro TRISA, así:
bsf TRISA,0
Esto determina una conmutación a 1 del estado lógico del flip-flop tipo D indicado
con el bloque TRIS latch. Por cada línea de I/O existe un flip-flop de este tipo y su
estado lógico está ligado al estado lógico del bit correspondiente en el registro TRIS
(esto quiere decir que un bit en el registro TRIS se implementa físicamente con un
TRIS latch).
La salida Q del TRIS latch se conecta a la entrada de una compuerta lógica OR. Esto
significa que, independientemente del valor presente en la otra entrada, la salida de
la compuerta OR siempre será 1. En esta condición el transistor P se activa y
mantiene la línea RA0 conectada al positivo de la alimentación.
41. CURSO INTEGRAL SOBRE MICROCONTROLADORES
41
www.welgos.net
La salida negada del TRIS latch se conecta a la entrada de una compuerta AND, cuya
salida siempre valdrá cero debido a que una de sus entradas esta en cero. En esta
condición el transistor N no se activará y mantendrá la línea RA0 desconectada de la
tierra. El estado lógico de la línea RA0 dependerá exclusivamente de la circuitería
externa que se le conecte.
Ahora es posible leer el estado mediante la circuitería de entrada de los bloques
representados por el buffer de entrada TTL y el latch de entrada.
Funcionamento como salida
Para configurar la línea RA0 como salida, debemos poner en 0 el bit 0 del registro
TRISA mediante la instrucción:
bcf TRISA,0
Esto determina la conmutación a 0 de la salida Q del latch TRIS (y a 1 de la salida Q
negada). En este estado el valor en la salida de la compuerta OR y AND depende
exclusivamente del estado de la salida Q negada del latch de datos.
Así como en el latch TRIS, el latch de datos depende del estado de un bit de un
regsitro, en particular del registro PORTA.
La salida negada viene enviada a la entrada de las dos compuertas lógicas OR y AND
y de estas a la base de los transistores P y N. Si ponemos un 0 en el bit 0 del
registro PORTA con la instrucción:
bcf PORTA,0
obtenemos la conducción del transistor N con la consiguiente conexión a tierra de la
línea RA0. Si por el contrario ponemos un 1 en el bit 0 con la instrucción:
bsf PORTA,0
obtenemos la conducción del transistor P y la conexión de RA0 con los +5 voltios.
En esta condición siempre es posible leer nuevamente el valor enviado sobre la línea
a través de la circuitería de entrada.
Estado de salida de la línea RA4
Analicemos ahora el funcionamiento como salida de la línea RA4, la cual se diferencia
de las demás líneas de I/O en que comparte su función con la del contador interno
del microcontrolador (este tema lo abordaremos más adelante), por eso es común
encontrar diagramas donde este pin se encuentra con el nombre RA4/TOCKI.
En la siguiente figura se muestra el esquema en bloques del estado de salida RA4:
42. CURSO INTEGRAL SOBRE MICROCONTROLADORES
42
www.welgos.net
La lógica de conmutación es idéntica a la del grupo de líneas RA0-3 a excepción de
La carencia de la compuerta OR y del transistor P.
Esto significa, en términos prácticos, que cuando la línea RA4 viene programada
como salida y tiene un 1, no viene conectada al positivo.
Tal tipo de circuitería de salida se denomina en "colector abierto". Si necesitamos
sacar uu 1 por RA4 necesitamos poner externamente una resistencia de pull-up
conectada al positivo de la alimentación.
En cuanto a la utilización de la línea indicada en el esquema como entrada de TMR0,
ese tema lo veremos más adelante.
Estado de salida de las líneas RB0, RB1, RB2 y RB3
En este grupo de líneas disponemos de una circuitería de weak up que se activan
cuando la líneas se han programado como entradas.
El estado de la línea depende exclusivamente de la circuitería externa.
43. CURSO INTEGRAL SOBRE MICROCONTROLADORES
43
www.welgos.net
Si tal circuitería es de colector abierto puede constituirse simplemente con un
sencillo pulsador con una resistencia de pull-up conectada a 5 voltios, el cual en el
momento de pulsarse conecte a tierra la línea I/O.
La circuiteria de weak pull-up permite evitar el uso de resistencias de pull-up, para
activar o desactivar esta función se activa o desactiva el bit RBPU de un registro
interno del microcontrolador denominado OPTION.
En esta figura se muestra el esquema de bloques del estado de entrada de este
grupo de pines:
La línea RB0 presenta una característica muy particular. Cuando viene configurada
como entrada, puede generar, en correspondencia con un cambio de estado lógico,
una interrupción, esto es, como su nombre lo indica, una interrupción inmediata del
programa que se está ejecutando y una llamada a una subrutina especial
denominada servicio de interrupción. Hablaremos de este importante tema más
adelante.
Estado de salida de las líneas RB4, RB5, RB6 y RB7
La circuitería interna de conmutación de este grupo de líneas es idéntica a la del
grupo RB0-3. Estas líneas disponen de la circuitería de weak pull-up. En la siguiente
44. CURSO INTEGRAL SOBRE MICROCONTROLADORES
44
www.welgos.net
figura se reproduce el diagrama de bloques de las salidas tomada de las hojas de
datos de Microchip:
En la lección anterior, mostramos una secuenciador de luces utilizando las líneas
RB0-3 como líneas de salida, veamos ahora como realizar en entrada a tierra
configurando las líneas de RB4 a RB7 como entradas. Ampliemos el circuito
presentado en la lección 2 con cuatro pulsadores denominados SW1, SW2, SW3 y
SW4.
Esquema eléctrico
Cada uno de los pulsadores conecta a tierra las líneas de entrada, las cuales
normalmente se mantienen a +5 voltios mediante una resistencia (de R6 a R9). Por
ejemplo, el pin 10 del PIC16F84A se mantendrá en +5 voltios hasta que el pulsadro
SW1 no se active. Cuando esto ocurra el pin verá 0 voltios. Realizemos un programa
45. CURSO INTEGRAL SOBRE MICROCONTROLADORES
45
www.welgos.net
de ejemplo en donde se van iluminando los led D1, D2, D3 y D4 en correspondencia
a cuatro pulsadores SW1, SW2, SW3 y SW4.
El código fuente del ejemplo se muestra en el archivo INPUT.ASM .
En la parte inicial del programa se pueden apreciar las siguientes instrucciones:
movlw 11110000B
movwf TRISB
con las cuales se configuran las líneas de RB0 a RB3 como salidas para conectar allí
los LED y las líneas de RB4 a RB7 como entrada para conectar en ellas los cuatro
pulsadores. La instrucción:
bcf STATUS,RP0
Efectúa una conmutación del banco al registro 0 de manera que podemas acceder
directamente al estado de las líneas de I/O.
MainLoop
clrf PORT
Esta instrucción apaga todos los diodos led conectados al puerto B.
btfss PORTB,SW1
bsf PORTB,LED1
Este par de instrucciones se coloca por cada línea de entrada que posee un pulsador,
y con ella se verificar la activación de estos para activar el led correspondiente.
Si detecta un uno en SW1:
btfss PORTB,SW1
se salta la siguiente instrucción:
bsf PORTB,LED1
sólo si el pusador SW1 está oprimido se ejecuta la enterior instrucción. El mismo
proceso se repite para todos los pulsadores y al final se ejecuta todo el ciclo
neuvamente gracias a la instrucción:
goto MainLoop
46. CURSO INTEGRAL SOBRE MICROCONTROLADORES
46
www.welgos.net
;**************************************************
; Curso integral de microcontroladores Pic
; INPUT.ASM
;
; (c) 2003, WELGOS electrónica
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 3FF1H
LED1 EQU 0
LED2 EQU 1
LED3 EQU 2
LED4 EQU 3
SW1 EQU 4
SW2 EQU 5
SW3 EQU 6
SW4 EQU 7
ORG 0CH
47. CURSO INTEGRAL SOBRE MICROCONTROLADORES
47
www.welgos.net
;Reset Vector
;Punto di inizio del programma al reset della CPU
ORG 00H
;Commuta al segundo banco de registros para acceder al registro TRISA y
TRISB
bsf STATUS,RP0
;Definicion del las lineas de I/O (0=salida, 1=Entrada)
;Definicion del puerto A
movlw 00011111B
movwf TRISA & 7FH
;Definicion del puerto B
;Las lineas de RB0 a RB3 vienen programadas como salida para conectar
los cuatro led
;Las lineas de RB4 a RB7 viene programadas como entradas para conectar
los cuatro pulsadores
movlw 11110000B
movwf TRISB & 7FH
;Commuta el primer banco de registros
bcf STATUS,RP0
MainLoop
;apaga las led
clrf PORTB
;se se oprime SW1 se enciende el LED1
btfss PORTB,SW1
bsf PORTB,LED1
;se se oprime SW2 se enciende el LED2
btfss PORTB,SW2
bsf PORTB,LED2
;se se oprime SW3 se enciende el LED3
btfss PORTB,SW3
bsf PORTB,LED3
;se se oprime SW4 se enciende el LED4
btfss PORTB,SW4
bsf PORTB,LED4
goto MainLoop
END
CURSO INTEGRAL
PIC
Capítulo 4
48. CURSO INTEGRAL SOBRE MICROCONTROLADORES
48
www.welgos.net
El contador TMR0 y el PRESCALER
4.1 El registro contador TMR0
Veamos ahora como funciona el registro TMR0.
El registro TMR0 es un contador. Se trata de un tipo especial de registro cuyo
contenido se incrementa mediante los ciclos internos del reloj o mediante pulsos
externos al PIC. A diferencia de otros registros, el TRM0 puede alterar por si solo el
valor con que se memoriza inicialmente. Por ejemplo, escribamos en el TMR0 el valor
10:
movlw 10
movwf TMR0
49. CURSO INTEGRAL SOBRE MICROCONTROLADORES
49
www.welgos.net
a medida que las instrucciones del programa se van ejecutando, el contenido del
registro comienza a incrementarse 11, 12, 13 en pasos de a uno en directa
correspondencia con los ciclos de máquina empleados. Si por ejemplo, después de
haber cargado el TMR0 con algún valor, se plantea un ciclo infinito:
movlw 10
movwf TMR0
loop
goto loop
el registro TMR0 se incrementa de manera infinita a la para con el loop. Como el
TMR0 es un registro de 8 bits, solo puede incrementarse hasta 255. Cuando esto
ocurre y los ciclos de máquina siguen andando, el registro se reinicia y toma el valor
de 0.
La frecuencia con la cual se incrementa el TMR0 es directamente proporcional a la
frecuencia de reloj aplicada al circuito integrado, pero esta frecuencia puede
modificarse mediante unos bits de configuración.
En la siguiente figura se muestra el diagrama de bloques del funcionamiento interno
del registro TMR0.
Los bloques Fosc/4 y TOCKI (en azul) representan las dos posibilidades que se
tienen para incrementar el valor del TMR0. Fosc/4 es una seal generada
internamente en el PIC a partir del circuito de reloj y equivale a la frecuencia del
reloj dividio por cuatro (esto recibe el nombre de ciclo de máquina).
TOCKI es una señal generada desde un eventual circuito externo que se aplica sobre
el pin TOCKI, que en el caso del PIC16F84A corresponde al pin 3.
Los bloques TOCS y PSA (resaltados en verde) son dos conmutadores que
determinan las características de la señal que entra el TMR0. Estos conmutadores se
configuran en base a los valores de los bits TOCS y PSA del registro OPTION.
El bloque PRESCALER es un divisor programable cuyo funcionamiento se explicará en
la siguiente sección.
Veamos como funcionan estos bloques para obtener las distintas modalidades de
conteo por parte del TMR0.
50. CURSO INTEGRAL SOBRE MICROCONTROLADORES
50
www.welgos.net
Iniciamos programando los bits TOCS en 0 y el PSA en 1. La configuración de
funcionamineto que se obtiene se muestra en la siguiente figura:
En rojo se muestra la ruta que sigue la señal hasta llegar al TMR0. Como se habia
mencionado, la frecuencia Fosc/4 equivale a un cuarto de la frecuencia del reloj. Si
utilizamos un cristal de 4 Mhz obtendremos una frecuencia interna de 1 MHz. Tal
frecuencia se envia directamente al registro TMR0 sin ninguna modificación. El
incremento que se obtiene equivale a 1 millón de incrementos por segundo a partir
del valor presente en el TRM0.
Ahora comabiemos el estado del bit TOCS de 0 a 1, la configuración que obtenemos
es la siguiente:
En este caso la señal de entrada es la que se aplica externamente al pin TOCKI y esa
frecuencia es la que le entra al TMR0. Esta configuración nos brinda la posibilidad de
efectuar el conteo automátcio de un evento externo. Si por ejemplo aplicamos al pin
TOCKI una frecuencia de 100 Hz, obtendremos una frecuencia de conteo de 100 por
segundo.
La presencia de la compuerta lógica XOR (OR exclusiva) en la entrada TOCKI del PIC
tiene como función permitir que el bit TOSE del registro OPTION regule el
funcionamiento del TMR0 para determinar cual de las dos posibles entradas es la que
queremos habilitar. Si queremos que funciones con el ciclo interno del reloj
(T0SE=1) o mediante la señal externa (T0SE=0).
51. CURSO INTEGRAL SOBRE MICROCONTROLADORES
51
www.welgos.net
En la siguiente figura se representa la correspondencia de la señal externa y el valor
adjuntoi del contador TMR0:
4.2 El Prescaler
El último bloque que falta por analizar es el PRESCALER. Si configuramos el bit PSA
del registro OPTION en 0 enviamos al registro TMR0 una seَñal que primero pasa por
el PRESCALER come se muestra en la siguiente figura:
El PRESCALER consiste de un divisor programable de 8 bit que se utiliza para ajustar
la frecuencia de entrada al TMR0. En el caso anterior utilizamos un cristal de cuarzo
de 4 Mhz con el que obtenemos una frecuencia de 1 Mhz, la cual para muchas
aplicaciones puede resultar muy elevada.
Utilizando el PRESCALER podemos dividir la frecuencia Fosc/4 configurando
oportunamente los bits PS0, PS1 y PS2 en el registro OPTION, de acuerdo a la
siguiente tabla:
PS2 PS1 PS0 Divisor Frecuencia a la salida del PRESCALER
0 0 0 2 500.000
0 0 1 4 250.000
0 1 0 8 125.000
0 1 1 16 62.500
52. CURSO INTEGRAL SOBRE MICROCONTROLADORES
52
www.welgos.net
1 0 0 32 31.250
1 0 1 64 15.625
1 1 0 128 7.813
1 1 1 256 3.906
Podemos hacer un experimento para comprobar el funcionamiento del PRESCALER.
En la lección 2 habiamos realizado un ejercicio con el encendido de cuatro led en
donde la secuencia de encendido se dererminaba mediante un retardo por software,
basado en el tiempo de ejecución de un ciclo continuo de instrucciones.
Ahora vamos a re escribir esta subrutina pero introduciendo un retardo mediante el
registro TMR0. Las modificaciones se muestran en el archivo SEQTMR0.ASM.
Debemos programar el PRESCALER para obtener una frecuencia de conteo
conveniente, para ello se utilizan las siguientes instrucciones al inicio del programa:
movlw 00000100B
movwf OPTION_REG
En la práctica debemos programar los bits TOCS en 0 para seleccionar cual va a ser
la fuente del conteo para el PIC, el bit PSA se pone en 0 para asignar el PRESCALER
al registro TMR0 en lugar del temporizador Watch Dog (este tema lo trataremos más
adelante) y el bit de configuración del PRESCALER a 100 para obtener una frecuencia
de división de 1:32. La frecuencia de conteo que obtenemos con el TMR0 será:
Fosc = 1Mhz / 32 = 31.250 Hz
La subrutina Delay deberá utilizar oportunamente el registro TMR0 para obtener un
retardo de un segundo. Veamos como se hace esto.
La primera instrucción que viene enseguida del Delay es:
movlw 6
movwf TMR0
y
movlw 125
movwf Count
Las primeras dos instrucciones memorizan en TMR0 el valor 6, de manera que el
registro TMR0 vuelve a cero después de 250 conteo (256 – 6 = 250) obteniendo una
frecuencia de paso por cero del TMR0 de:
31.250 / 250 = 125 Hz
Las instrucciones siguientes memorizan en un registro de 8 bits (Count) el valor de
125 de modo tal que, decrementando este registro en una unidad por cada vez que
TMR0 para por cero, se obtiene una frecuencia de paso por cero del registro Count
de:
125/125 = 1Hz
Las instrucciones dentro del lazo DelayLoop se encargan de controlar si el TMR0 ha
llegado a cero, cada vez que se ha reiniciado seis vecesm se decrementa el valor
contenido en Count. Cuando Count llega a cero habrá transcurrido un segundo y la
subrutina podrá retornar al punto del programa desde donde se invocó.
;**************************************************
; Curso integral de microcontroladores Pic
; SEQTMR0.ASM
; Luces secuenciales con temporizacion via TIMER 0
;
; (c) 2003, WELGOS electronica
53. CURSO INTEGRAL SOBRE MICROCONTROLADORES
53
www.welgos.net
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 3FF1H
ORG 0CH
Count RES 1
Shift RES 1
;Reset Vector - Punto de inicio del programa al reset de la CPU
ORG 00H
;Conmuta al segundo banco de registros
bsf STATUS,RP0
;Definicion de la linea de I/O (0=salida, 1=entrada)
movlw 00011111B
movwf TRISA & 7FH
movlw 11110000B
movwf TRISB & 7FH
;Asigna el PRESCALER al TMR0 y lo configura a 1:32
;Ver la subroutina Delay
movlw 00000100B
movwf OPTION_REG & 0x7F
;Conmuta al primer banco de registros
bcf STATUS,RP0
;el registro Shift viene utilizado para representar internamente
;el estado de la linea de salida del puerto B donde se conectan los led
;el bit 0 del registro Shift viene inciado en 1 para iniciar el ciclo
;del primer led.
movlw 00000001B
movwf Shift
;Lazo de corrimiento
MainLoop
;envia sobre el puerto B el registro Shift de manera que cada bit en
;uno activará el led respectivo.
movf Shift,W
movwf PORTB
;Para rotar las luces se utiliza la instrucción rlf la cual hace
; rotar a la izquierda los bit contenidos en el registro e inserta en
;el bit 0 el estado del bit carry.Por este motivo primero se debe
;limpiar el carry con la instrucción: bcf STATUS,C.
bcf STATUS,C
rlf Shift,F
;Cuando con la rotacion el 1 llega al bit 4 se debe invertir los
;primeros cuatro bits con los segundos cuatro bits de modo que se pueda
;reiniciar el ciclo desde el bit 0.
;Esto sucede con los bits del registro Shift durante la ejecucion de
;este lazo:
;
; 00000001 <--- Valor inicial (primer led activado)
; 00000010 rlf
; 00000100 rlf
; 00001000 rlf
; 00010000 rlf en este punto se utiliza la instrucción swapf
;obteniendo:
; 00000001 ...
btfsc Shift,4
54. CURSO INTEGRAL SOBRE MICROCONTROLADORES
54
www.welgos.net
swapf Shift,F
;Insertar un retardo
call Delay
;Retorna a seguir nuevamente el lazo
goto MainLoop
;**************
; Subrutinas
;**************
; Retardo de un segundo
; utilizando el registro TMR0
;
; el ritardo viene obtenido de la frecuencia en la salida del PRESCALER
; por:
; 4Mhz / 4 / 32 = 31.250 Hz
; ... divide por 250 del TMR0 32.250 / 250 = 125 Hz
; ... y por 125 del contador Count 125 / 125 = 1Hz
Delay
; Inicializa el TMR0 para obtener 250 conteo antes de llegar a cero.
; El registro TMR0 es un registro de 8 bit que se incrementa
; nuevamentre cuando llega a 255 vuelve a cero.
; Si se inicializa en 6 debera llegar hasta 256 - 6 = 250
; incrementos antes de llegar a cero.
movlw 6
movwf TMR0
;el registro Count viene inicializado a 125
movlw 125
movwf Count
;Lazo de conteo
DelayLoop
;TMR0 vale 0 ?
movf TMR0,W
btfss STATUS,Z
goto DelayLoop ;No, espera...
movlw 6 ;Si, carga de nuevo TMR0 y controla si
movwf TMR0 ;ha pasado por 125
decfsz Count,1
goto DelayLoop
return
END
CURSO INTEGRAL
PIC
Capítulo 5
Las interrupciones
Las interrupciones es una característica muy especial en los microcontroladores PIC (
y de los microprocesadores en general) que permite la atención inmediata de un
evento externo, interrumpiendo momentaneamente el programa en curso para
55. CURSO INTEGRAL SOBRE MICROCONTROLADORES
55
www.welgos.net
ejecutar otra porción especializada del programa para el manejo de dicho evento y
una vez ejecutada esta se retorna al programa principal.
Podemos hacer un parangón con el mundo real, podemos hacer una analogía y decir
que las interrupciones son para el PIC lo que el timbre del teléfono para nosotros.
Para poder una llamada telefónica no necesitamos tomar el auricular
permanentemente, simplemente hacemos nuestras labores normales y solo las
interrumpimos si suena el timbre del teléfono. Cuando terminamos de hablar
volvemos de nuevo a nuestras actividades normales.
Miremos los elementos en esta analogía:
Nuestras actividades normales corresponden al programa en ejecución;
La llamada que alguien nos hace corresponde al evento a gestionar;
Cuando levanto el auricular corresponde a la respuesta a la interrupción;
Y la respuesta que le doy mediante el teléfono corresponde a la subrutina de gestión
de la interrupción.
Es mucho más eficiente manejar la atención a un evento externo mediante una
interrupción que mediante una verificación cíclica desde el programa principal.
Gracias al hardware interno del PIC la respuesta a un evento mediante una
interrupción es prácticamente inmediata.
5.1 Tipos de eventos y bits de habilitación
El PIC16F84A puede manejar interrupciones generadas por cuatro tipos de eventos:
1. El cambio de estado en la línea RB0 (Interrupción externa en el pin RB0/INT).
2. El fin del conteo del registro TMR0 (interrupción por sobreflujo del TMR0).
3. El cambio de estado sobre una de las líneas de RB4 a RB7 (interrupción por
cambio en el PORTB).
4. Fin de la escritura sobre una posición de la EEPROM (Interrupción por escritura
completa en la EEPROM).
La generación de la interrupción de cada uno de estos eventos puede habiliatrse o
deshabilitarse independientemente mediante un registro especial denominado
INTCON:
Si el bit INTE (bit 4) se pone en 1, se habilita la interrupción por cambio de estado
en la línea RB0. Si el bit T0IE (bit 5) se pone en 1 se habilita la interrupción por
desborde del TMR0. Si el bit RBIE (bit 3) se pone en 1, se habilita la interrupción por
cambio de estado en las líneas RB4-RB7. Si el bit EEIE (bit 6) se pone en 1, se
habilita ls interrupción por fin de escritura en la EEPROM.
Existe un bit que actúa como habilitador general de todas las interrupciones. Esto
quiere decir que para que cualquiera de las interrupciones se habilite debe estar este
bit activo. Se trata del bit GIE (Global Interrupt Enable bit) ubicado en el bit 7 del
registro INTCON.
5.2 Vector de interrupciones y el servicio de
interrupción
Cualquiera que sea la fuente de la interrupción, esta se manifiesta interrumpiendo la
ejecución del programa en curso, memoriza automáticamente en la pila, el valor
56. CURSO INTEGRAL SOBRE MICROCONTROLADORES
56
www.welgos.net
actual del contador de programa (POGRAM COUNTER) y salta a la instrucción
ubicada en la posición 0004H, la que recibe el nombre de vector de interrupción.
En este punto es donde debemos insertar la subrutina que maneja la interrupción
denominada servicio de interrupción.
Dentro de una aplicación es posible habilitar varias de las posibles fuentes de
interrupción, cuando se entra al servico de interrupción el primer paso de la
subrutina es verificar cual de las fuentes fué la que en realidad originó la
interrupción, para ellos se acude a la bandera de interrupción.
5.3 Bandera de interrupción
Dado que cualquier interrupción genera una llamada a la posición 04H, en el registro
INTCON se presentan una serie de banderas que nos indican cual evento ha
generado la interrupción, veamos:
INTF (bit 1) Si vale 1 la interrupción se ha generado por un cambio de estado sobre
la línea RB0.
T0IF (bit 2) Si vale 1 la interrupción se ha generado por el desborde del TRM0.
RBIF (bit 0) Si vale 1 la interrupción se ha generado por un cambio de estado en una
de las líneas de RB4 a RB7.
Importante: Una vez se ha detectado cual de las banderas originó la interrupción,
esta se debe borrar (y es responsabilidad del programador) de lo contrario la
interrupción correspondiente no se detectará nuevamente.
5.4 Retorno desde un servicio de interrupción
Cuando se ha generato una interrupción el PIC deshabilita automáticamente el bit
GIE (Global Interrupt Enable) del registro INTCON de modo que se deshabilitan
momentáneamente todas las interrupciones mientras se ejecuta el servicio de
interrupción. Para poder retornar al programa principal se debe reiniciar en 1 este bit
y utilizar la instrucción:
RETFIE
5.5 Ejemplo práctico del manejo de una
interrupción
Veamos ahora un ejemplo práctico del manejo de una interrupción y para ello
tomemos como base el programa LED.ASM de la lección 1; recordemos que se
trataba del ecendido del LED1 mediante un ciclo continuo utilizando un retardo por
software introducido mediante la subrutina Delay. Ahora modificaremos este
programa para activar el LED2 de acuerdo a la ejecución del programa principal.
El programa que estudiaremos ahora se denomina INTRB.ASM.
Si ejecutamos el programa dentro del circuito, podremos apreciar que el LED1 se
activa exactamente como lo hacía en el programa LED.ASM. Ahora funcionemos con
57. CURSO INTEGRAL SOBRE MICROCONTROLADORES
57
www.welgos.net
los pulsadores SW1..SW4, veremos que el LED2 se activa inmediatamente y
permanece así durante un tiempo 3 veces mayor que el tiempo del LED1.
En la práctica, mientras el lazo principal en LED.ASM continua encendiendo el LED 1
utilizando un retardo por software introducido por la subrutina Delay,el PIC por estar
pendiente de la presión del pulsador y señalarlo en el LED 2, verá notablemente
afectada la frecuencia de encendido del LED 1.
Antes de analizar el programa INTRB.ASM veamos la diferencia del comportamiento
con respecto a otro programa que efectúa estas mismas operaciones pero sin
recurrir al uso de interrupciones. Este programa se corresponde a NOINTRB.ASM.
Notemos que la activación del LED 2 en correspondencia al pulsador, se retarda un
poco debido a que la lectura del estado de las líneas RB4-7 no se hace mediante una
interrupción sino mediante el ciclo del lazo principal. Este ligero retardo se debe a la
presencia de la subrutina Delay en el interior de lazo principal.
5.6 Analizando el programa INTRB.ASM
Partamos de la directiva ORG 00H que como ya sabemos, ubica nuestro programa
después del reset, en la posición 0. Notemos que la primera instrucción que
encuentra el PIC es un salto incondicional a la etiqueta Start:
ORG 0x00
goto Start
seguido de otra directiva:
ORG 0x04
Que inidica la dirección de la subrutina que maneja la interrupción:
bsf PORTB,LED2
movlw 3
movwf nTick
bcf INTCON,RBIF
retfie
Como se había mencionado en la lección anterior, el manejador de la interrupción
debe necesariamente ubicarse a partir de la posición 0x04; para evitar que se
encuentre enseguida del reset debemos saltarlo mediante una instrucción de salto
incondicional.
El servicio de interrupción, en este caso, se limita a activar el LED 2, a cargar en el
registro nTick el número de veces que se activará el LED 2 y a borrar la bandera
RBIF para permitir que la circuitería interna de generación de interrupciones siga
funcionando. La instrucción RETFIE permite que el PIC pueda continuar en el punto
del programa donde se encontraba antes de la interrupción.
Como generar una interrupción cuando se active un pulsador ?
Después del reset ponemos los siguiente:
movlw 10001000B
movwf INTCON
58. CURSO INTEGRAL SOBRE MICROCONTROLADORES
58
www.welgos.net
donde ponemos un 1 en el bit GIE (bit 7) que corresponde al habilitador general de
los circuitos de generación de interrupciones. También ponemos en 1 el bit RBIE (bit
3) el cual habilita la interrupción por cambio de estado en las líneas RB4-7.
Si colocamos los pulsadores PU1, PU2, PU3 y PU4 sobre las correspondientes líneas
de I/O RB4, RB5, RB6 y RB7, solo con presionar uno de estos pulsadores obtenemos
un cambio de estado y por lo tanto una interrupción.
En el lazo principal, además de la operación de encendido de LED 1, se decrementa
el contatore nTick hasta que llega a cero. En correspondencia con esto se prende el
LED 2.
Ejemplo práctico de manejo de las interrupciones
Veamos como manejar las interrupciones. Sigamos utilizando el programa
INTRB.ASM pero ahora vamos a originar una interrupción con el desborde del TMR0
y de acuerdo a este evento activamos el LED 3. El código de este ejercicio lo vemos
en el archivo DBLNT.ASM.
Si compilamos el programa DBLINT.ASM y lo montamos sobre el circuito, veremos
como el LED 1 parpadea a una sola frecuencia y el LED 3 parpadea a una frecuencia
más elevada. Accionando el pulsador obtenemos la subida por tres ciclos del LED 2.
Analizando el programa DBLINT.ASM
En el momento de que se presenta una interrupción, en la subrutina del servicio de
la interrupción se verifica cual de las fuentes de interrupción generó la situación,
para ello consultamos las banderas TOIF (desborde del TMR0) y RBIF (cambio de
estado en RB4-RB7):
btfsc INTCON,T0IF
goto IntT0IF
btfsc INTCON,RBIF
goto IntRBIF
De acuerdo a la bandera activada saltamos a la etiqueta respectiva: IntT0IF ó
IntRBIF. Antes de salir del servicio de interrupción debemos recordar borrar las
banderas TOIF y RBIF, para poder funcionar nuevamente con dichas interrupciones.
;**************************************************
; Curso integral de microcontroladores Pic
; INTRB.ASM
;
; (c) 2003, WELGOs electrónica
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 3FF1H
LED1 EQU 0
LED2 EQU 1
59. CURSO INTEGRAL SOBRE MICROCONTROLADORES
59
www.welgos.net
LED3 EQU 2
LED4 EQU 3
ORG 0CH
Count RES 2
nTick RES 1 ;Registro utilizado para contar el numero de
;encendidas del LED 1
;Reset Vector
;Punto de inicio del programa al reset de la CPU
ORG 00H
;Salta al cuerpo principal del programa. Este salto es necesario
;para evitar toda la parte de codigo para el manejo de la
;interrupcion.
goto Start
;Interrupt vector
;Punto de inicio para toda la subrutina de manejo de la interrupcion
ORG 04H
;**********************************************************************
; Servicio de Interrupcion
;**********************************************************************
;Activa el led 2 para señalar que se ha dado una interrupcion
bsf PORTB,LED2
;Inicializa el contador del parpadeo del LED1
movlw 3
movwf nTick
;Borra la bandera RBIF para permitir nuevas interrupciones
bcf INTCON,RBIF
;Retorna al programa principal
retfie
;**********************************************************************
; Programa principal
;**********************************************************************
Start:
;Conmuta al segundo banco de registros para acceder al registro TRISA y
;TRISB
bsf STATUS,RP0
;Definicion de las lineas de I/O (0=salida, 1=Entrada)
;Definicion del puerto A
movlw 00011111B
movwf TRISA & 7FH
;Definicion del puerto B
;Las lineas de RB0 a RB3 viene programadas como salida para
;conectar los cuatro led
;Las lineas de RB4 a RB7 vienen programadas como entradas para
;conectar los cuatro pulsadores
movlw 11110000B
movwf TRISB & 7FH
;Conmuta al primer banco de registros
bcf STATUS,RP0
;apaga los led del puerto B
bcf PORTB,LED1
bcf PORTB,LED2
bcf PORTB,LED3
bcf PORTB,LED4
;Habilita la interupcion del cambio de estado en las lineas RB4,5,6,7
movlw 10001000B
movwf INTCON
;**********************************************************************
; Lazo principal
;**********************************************************************
MainLoop
call Delay ;Retardo por software
60. CURSO INTEGRAL SOBRE MICROCONTROLADORES
60
www.welgos.net
btfss PORTB,LED1 ;Led apagado ?
goto TurnOnLed1 ;No, lo prende
goto TurnOffLed1 ;Si, lo apaga
;Prende led y decremento el contatore de parapadeo
TurnOnLed1
bsf PORTB,LED1
;Controla si LED 2 de señalacion de la interrupcion esta prendido.
;Si esta prendido decrementa el contador nTick ad ogni lampeggio di
;LED1. Quando nTick vale 0 spegne LED 2
btfss PORTB,LED2 ;LED2 prendido ?
goto MainLoop ;No, continua a lampeggiare
decf nTick,1 ;Si, decrementa nTick
btfss STATUS,Z ;nTick = 0 ?
goto MainLoop ;No, continua a lampeggiare
bcf PORTB,LED2 ;Si, spegne LED2
goto MainLoop ;Continua a lampeggiare
;Spegnimento led
TurnOffLed1
bcf PORTB,LED1 ;Spegne LED 1
goto MainLoop ;Continua a lampeggiare
;**********************************************************************
; Subrutina
;**********************************************************************
;Subrutina de retardo por software
Delay
clrf Count
clrf Count+1
DelayLoop
decfsz Count,1
goto DelayLoop
decfsz Count+1,1
goto DelayLoop
return
END
;**************************************************
; Curso integral de microcontroladores Pic
; DBLINT.ASM
;
; (c) 2003, WELGOS electronica
; http://www.wellgos.com
;**************************************************
PROCESSOR 16F84
RADIX DEC
INCLUDE "P16F84.INC"
ERRORLEVEL -302
;Setup of PIC configuration flags
;XT oscillator
;Disable watch dog timer
;Enable power up timer
;Disable code protect
__CONFIG 3FF1H
LED1 EQU 0
LED2 EQU 1
LED3 EQU 2
LED4 EQU 3
ORG 0CH
Count RES 2
nTick RES 1
;Reset Vector
61. CURSO INTEGRAL SOBRE MICROCONTROLADORES
61
www.welgos.net
;Starting point at CPU reset
ORG 00H
;Jump to the main body of program to avoid the interrupt handler
;code.
goto Start
;Interrupt vector
;Starting point at CPU interrupts
ORG 04H
;**********************************************************************
; Interrupt handler
;**********************************************************************
;Check the interrupt event
btfsc INTCON,T0IF
goto IntT0IF
btfsc INTCON,RBIF
goto IntRBIF
;Reset the T0IF and RBIF flags to re-enable the interrupts
End_ih
bcf INTCON,T0IF
bcf INTCON,RBIF
;Go back to the main program
retfie
;**********************************************************************
; TMR0 Interrupt handler
;**********************************************************************
IntT0IF
;Turn on LED3 if it's off
btfsc PORTB,LED3
goto LED3_off
bsf PORTB,LED3
goto End_ih
LED3_off
bcf PORTB,LED3
goto End_ih
;**********************************************************************
; RB4-RB7 interrupt handler
;**********************************************************************
IntRBIF
;Turn on LED 2
bsf PORTB,LED2
;Starts the LED1 blink counter
movlw 3
movwf nTick
goto End_ih
;**********************************************************************
; Main body
;**********************************************************************
Start:
;Commuta sul secondo banco dei registri per accedere ai registri TRISA e
TRISB
bsf STATUS,RP0
;Definizione delle linee di I/O (0=Uscita, 1=Ingresso)
;Definizione della porta A
movlw 00011111B
movwf TRISA & 7FH
;Definizione della porta B
;Le linee da RB0 a RB3 vengono programmate in uscita per essere
collegate ai quattro
led
;Le linee da RB4 a RB7 vengono programmate in ingresso per essere
collegate ai quattro
pulsanti
62. CURSO INTEGRAL SOBRE MICROCONTROLADORES
62
www.welgos.net
movlw 11110000B
movwf TRISB & 7FH
;Assegna il PRESCALER a TMR0 e lo configura a 1:256
movlw 00000111B
movwf OPTION_REG & 7FH
;Commuta sul primo banco dei registri
bcf STATUS,RP0
;Spegne tutti i led collegati sulla porta B
bcf PORTB,LED1
bcf PORTB,LED2
bcf PORTB,LED3
bcf PORTB,LED4
;Abilita l'interrupt sul TMR0 e sul cambiamento di stato delle linee
RB4,5,6,7
movlw 10101000B
movwf INTCON
;**********************************************************************
; Loop principale
;**********************************************************************
MainLoop
call Delay ;Ritardo software
btfss PORTB,LED1 ;Led acceso ?
goto TurnOnLed1 ;No, lo accende
goto TurnOffLed1 ;Si, lo spegne
;Accensione led e decremento del contatore di lampeggi
TurnOnLed1
bsf PORTB,LED1
;Controlla se LED 2 di segnalazione dell'interrupt e' gia acceso.
;Se e' acceso decrementa il contatore nTick ad ogni lampeggio di
;LED1. Quando nTick vale 0 spegne LED 2
btfss PORTB,LED2 ;LED2 acceso ?
goto MainLoop ;No, continua a lampeggiare
decf nTick,1 ;Si, decrementa nTick
btfss STATUS,Z ;nTick = 0 ?
goto MainLoop ;No, continua a lampeggiare
bcf PORTB,LED2 ;Si, spegne LED2
goto MainLoop ;Continua a lampeggiare
;Spegnimento led
TurnOffLed1
bcf PORTB,LED1 ;Prende LED 1
goto MainLoop ;Continua el parpadeo
;**********************************************************************
; Subrutina
;**********************************************************************
;Subrutina de retardo por software
Delay
clrf Count
clrf Count+1
DelayLoop
decfsz Count,1
goto DelayLoop
decfsz Count+1,1
goto DelayLoop
return
END
63. CURSO INTEGRAL SOBRE MICROCONTROLADORES
63
www.welgos.net
CURSO INTEGRAL
PIC
Capítulo 6
El modo Power Down
El modo Power Down o modo Sleep es un estado muy particular del funcionamiento
del microcontrolador PIC utilizado para reducir el consumo de corriente en el
momento en que el microcontrolador no se está utilizando o solo esta a la espera de
que ocurra un evento externo.
Tomemos por ejemplo, el caso del control remoto del televisor. La mayor parte del
tiempo el microcontrolador interno no se encuentra desarrollando ninguna tarea, solo