Вы находитесь на странице: 1из 10

E.P.S.

de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

Prctica 10 Microcontroladores PIC: Conversin A/D para Voltmetro Se trata del diseo del programa encargado de realizar la medida de dos tensiones analgicas comprendidas entre 0 y 5V y mostrar su valor (en V) en dos lneas distintas de un mdulo LCD. La medida se realizar mediante dos canales de entrada del mdulo A/D. El LCD se gestiona con las lneas de control procedentes del PORTC y las lneas de datos del PORTB. Las tensiones se introducen en las entradas analgicas 1 y 3 del PORTA (RA1 y RA3). E R/W RS

V1: 3,4567 V V3: 1,4589 V LCD HD44780

4MHz

RB7 RB6 ....................... RB0

RC0 RC1 RC2 +5V

PIC16C74B

RA3/AN3 RA1/AN1 +5V

Se emplea un microcontrolador PIC16C74B con un oscilador de 4MHz El esquema de la placa de circuito impreso con el LCD es similar al empleado en las prcticas 8 y 9.

E.P.S. de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

Planteamiento: Se utiliza el mdulo A/D para realizar de manera alternativa la conversin de la entrada de tensin del canal 1 y del canal 3. Se configura el mdulo A/D para que utilice el reloj basado en la red RC interna independiente del oscilador del microcontrolador (valor nominal de Tad de 4s y con variacin de 2 a 6s). Se lanza la conversin con el canal seleccionado y se activa la generacin de interrupciones por finalizacin de la conversin. En el programa de tratamiento de la interrupcin se recoge el valor resultante de la conversin en el registro ADRES de 8 bits y se convierte el valor a su equivalente de tensin en voltios. Como la tensin de referencia es de 5V, la resolucin del convertidor es de 5V/256 = 0,0195V (195E-4 V). Realizando el producto del valor resultante por 195 obtendremos un valor de tensin analgica comprendida entre 0 y 49804 diez milsimas de voltio que se puede almacenar en binario en dos bytes y que podemos descomponer en sus 5 dgitos BCD (con un subprograma ya conocido y utilizado) de cara a su representacin en el LCD. Una vez realizado el producto y su descomposicin en dgitos decimales los enviamos al LCD. Si se trata del canal 1 lo representamos en la lnea superior del LCD y si es el canal 3 en la lnea inferior. Para enviar los caracteres, colocamos el puntero de la DDRAM del LCD en el inicio de la lnea 0 de la lnea 1 segn corresponda. A continuacin, cambiamos la configuracin del conversor A/D para que cambie el canal de entrada al conversor. Nos aseguramos que haya transcurrido 2Tad (8s) antes de lanzar la nueva conversin (el propio programa de tratamiento lo asegura), ponemos a cero el flag de indicacin de fin de conversin (ADIF) y arrancamos una nueva conversin, retornando posteriormente del programa de tratamiento.

E.P.S. de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

Algoritmo utilizado: INICIALIZACIN Puertos: PORTB inicialmente de salida para enviar datos y comandos al LCD, pero sern de entrada en algunos intervalos para leer estado del LCD PORTC ser de salida en sus 3 bits ms bajos para lneas de control del LCD (RS,R/W y E) y son salidas permanentemente CONVERSOR A/D: Entradas RA0, RA1, RA2, RA3 y RA5 como analgicas y referencia de 5V, resto entradas digitales Reloj Tad basado en red RC interna (4s) Canal analgico de entrada: al principio canal 1 Activamos interrupciones por fin de conversin Inicializamos el LCD: tras esperar el arranque (15ms de temporizacin software) definimos interface de 8 bits y 2 lneas de pantalla, desactivamos la pantalla al principio Reseteamos el flag ADIF Activamos mscara global y de perifricos Lanzamos primera conversin

BUCLE PRINCIPAL Es una espera continua por la interrupcin del conversor A/D

PROGRAMA DE TRATAMIENTO DE LA INTERRUPCIN Comprobamos que el flag ADIF est activado Salvaguarda del contexto (W y STATUS) Tomamos el resultado de la conversin en ADRES Lo cargamos en la posicin FACTOR1 Cargamos 195 en FACTOR2 Llamamos a subprograma PRODUCTO para realizar la multiplicacin de FACTOR1 por FACTOR2 Se recoge el resultado en dos bytes (BIN_ALTO BIN_BAJO) y se descompone en sus 5 dgitos decimales con el subprograma BINBCD Si el canal que se convirti era el 1, cambiamos el canal de conversin A/D al 3 para la prxima conversin. A continuacin nos colocamos en la lnea superior del LCD y enviamos una cabecera de

E.P.S. de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

identificacin: V1: a la que siguen los dgitos BCD y ciertos caracteres: subprograma SACA_VALOR Se envan caracteres de unidades de voltio, una coma de separacin, dcimas de voltio, centsimas de voltio, milsimas de voltio y diez milsimas de voltio, espacio en blanco y carcter V (voltios) Si el canal era el 3, cambiamos al canal 1 para la siguiente conversin que se lance. Luego nos posicionamos en la lnea inferior del LCD y enviamos la cabecera: V3: seguido del conjunto de caracteres y dgitos BCD correspondientes mediante el subprograma SACA_VALOR Finalizamos el programa de tratamiento poniendo a 0 el flag ADIF Recuperamos el contexto Lanzamos una nueva conversin

Subprograma SACA_VALOR Se encarga de tomar los 5 valores almacenados en los nibbles de los bytes BCD2, BCD1 y BCD0 y se envan al LCD en formato ASCII. Se intercala la coma de separacin y se aaden las unidades de representacin V SUBPROGRAMA BINBCD Se encarga de tomar los 16 bits almacenados en las posiciones BIN_ALTO y BIN_BAJO y devuelve los 5 dgitos BCD correspondientes a la representacin decimal de ese valor SUBPROGRAMA PRODUCTO Realiza el producto de FACTOR1 por FACTOR2 y el resultado va a parar a dos posiciones: BIN_ALTO + BIN_BAJO FACTOR2 = b7 b6 b5 b4 b3 b2 b1 b0 FACTOR1 = a7 a6 a5 a4 a3 a2 a1 a0 Operacin a realizar: Resultado = FACTOR1 * FACTOR2 = b0 * FACTOR1 + b1 * (2 * FACTOR1) + + b2 * (2 * (2 * FACTOR1)) + ...+ b7 * (2*(2*(2*(2*(2*(2*(2*FACTOR1)))))))

E.P.S. de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

Cada multiplicacin por 2 en binario consiste en realizar un desplazamiento a la izquierda introduciendo un cero por la derecha, tras cada desplazamiento se realiza la suma o no en funcin del bit bi correspondiente a FACTOR2 Para facilitar estas operaciones utilizamos BIN_ALTO y BIN_BAJO en conjunto: BIN_ALTO BIN_BAJO operacin a realizar desde dentro hacia fuera: 0 FACTOR1 0000000 + 00 FACTOR1 000000 + 000 FACTOR1 00000 + 0000 FACTOR1 0000 + 00000 FACTOR1 000 + 000000 FACTOR1 00 + 0000000 FACTOR1 0 + 00000000 FACTOR1 * b7 * b6 * b5 * b4 * b3 * b2 * b1 * b0

E.P.S. de Ingeniera de Gijn Curso 2002-2003

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin

Cdigo Fuente de la Aplicacin


;************************************************************************** ; ; Programa de ejemplo de manejo del conversor A/D como voltmetro ; ; Ejemplo de realizacin de un programa para la medida en voltios, ; del nivel elctrico de dos seales analgicas comprendidas entre 0 y 5V ; ; La referencia del conversor ser de 5V, con lo que la resolucin resulta ; ser de 5V/256 = 0.0195 V, el resultado binario de la conversin se multiplica ; por 195 y se obtiene un valor en unidades de 1e-4 V, que mostramos en el LCD ; colocando la coma decimal adecuadamente ; ; Los valores medidos se muestran en dos lneas de un LCD ; ; Est en el fichero v_metro.asm ; Autor: Fernando Nuo Garca ; ;************************************************************************** list p=PIC16C74 ;Definimos MCU a utilizar include "p16c74b.inc" ;Incluimos fichero de etiquetas ;Definicin de lneas a utilizar para el manejo del LCD LCD_DATA LCD_DATA_TRIS LCD_CTRL LCD_CTRL_TRIS LCD_LINE0 LCD_LINE1 EQU EQU EQU EQU EQU EQU PORTB TRISB PORTC TRISC 0x000 0x040 ;DATOS se conecta a PORTB ;Registro de direccin de datos ;CONTROL se conecta a PORTC ;Registro de direccin de Control ;direccin comienzo lnea superior DDRAM ;direccin comienzo lnea inferior DDRAM

; Tambin se deben definir los Bits de control: LCD_E LCD_RW LCD_RS INDIR Banco_0_RAM EQU EQU EQU EQU EQU 2 1 0 0 0x20 ; Enable ser el bit 2 del PORTC ; Read/Write bit 1 del PORTC ; RS ser el bit 0 del PORTC ; Etiqueta para referirnos al registro fuente ; cuando utilizamos direccionamiento indirecto ; comienzo de la RAM de propsito general en Banco 0

; Bloque de variables en RAM cblock Banco_0_RAM W_TEMP ST_TEMP ;almacn temporal para el registro W ;almacn temporal para el registro STATUS

; Almacenamos los dgitos a mostrar en: BCD0 ;(DECENAS:UNIDADES) BCD1 ;(MILLARES:CENTENAS) BCD2 ;(0:DECENAS DE MIL) FACTOR1 FACTOR2 ;Uno de los factores del producto ;Otro de los factores del subprograma producto

;Resultado del producto: BIN_ALTO ;Parte alta del valor medido en binario BIN_BAJO ;Parte baja del periodo en binario LCD_TEMP AUX TMP CONTADOR DELAY X_DELAY endc ;variable temporal de uso interno en las subrutinas ;del LCD ;variable auxiliar ;otra variable auxiliar ;Para el subprograma de multiplicacin ;Para temporizacin software ;para temporizacin software ;Fin del bloque de variables de usuario

E.P.S. de Ingeniera de Gijn Curso 2002-2003


org goto org goto 0 INICIO 0x04 PTI

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin


;Salto a posicin de inicio ;Salto a Programa de Tratamiento de Interrupcin

include "S_LCD8B.ASM" ;Incluimos fichero de subprogramas de manejo ;del LCD INICIO bsf clrf movlw movwf movlw movwf bsf bcf movlw movwf call call bcf movlw movwf bsf LAZO goto STATUS,RP0 LCD_DATA_TRIS b'11111000' LCD_CTRL_TRIS b'00000010' ADCON1 PIE1,ADIE STATUS,RP0 b'11001001' ADCON0 LCDINIT LCDCLEAR PIR1,ADIF b'11000000' INTCON ADCON0,GO LAZO ;Paso al banco 1 ;Defino PORTB de salidas ;En el PORTC las 3 menos significativas ;como salidas para E, RS y R/W ;PORTA analgico, resto digitales PORTE ;y referencia de 5V ;Activamos mscara particular del conversor A/D ;Volvemos al banco 0 ;Configuramos entrada por canal 1 (RA1) ;y reloj RC interno de conversin TAD=4us tpico ;Inicializamos el LCD para definir funcionamiento ;interface de 8 bits y 2 lneas visibles ;Limpiamos pantalla al principio ;Pongo a 0 el flag de fin de conversin ;Activamos mscara global y de perifricos ;para interrupciones ;Lanzamos la primera conversin ;Bucle continuo de ejecucin en programa principal

;Programa de Tratamiento de Interrupcin PTI btfss PIR1,ADIF retfie movwf swapf movwf movf movwf movlw movwf call W_TEMP STATUS,W ST_TEMP ADRES,W FACTOR1 d'195' FACTOR2 PRODUCTO ;Comprobamos que es por fin de conversin ;si no, salimos ;Salvamos el contexto

;Cargamos el resultado en W ;y se lo pasamos a uno de los factores ;Cargamos 195 en el otro factor ;constante de multiplicacin ;Llamamos al subprograma de multiplicacin ;volvemos trayendo en BIN_ALTO - BIN_BAJO ;el valor en binario del producto ;Llamamos al subprograma de paso a BCD

call

BINBCD

;Tenemos que ver a qu canal corresponde la conversin btfsc goto ADCON0,4 CANAL3 ;Si el bit 4 de ADCON est a cero era el canal 1 ;el que se convirti ;si estaba a 1 era el canal 3

;Si llega hasta aqu es que era el canal 1 bsf movlw call movlw call movlw call ADCON0,4 LCD_LINE0 LCDSDDA ' ' LCDPUTCHAR 'V' LCDPUTCHAR ;Cambio al canal 3 para prxima conversin ;Cargo en W la direccin de la lnea 0 ;y coloco el puntero de la DDRAM del LCD ah ;Enviamos espacio en blanco ;Ahora una V

E.P.S. de Ingeniera de Gijn Curso 2002-2003


movlw call movlw call movlw call call goto '1' LCDPUTCHAR ':' LCDPUTCHAR ' ' LCDPUTCHAR SACA_VALOR FIN_PTI

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin


;Identificador de canal, el 1 ;Dos puntos ;Espacio en blanco ;Llamamos a subprograma que enva al LCD ;los dgitos BCD ;Vamos al final del programa de tratamiento

;Si llega hasta aqu es que era el canal 3 CANAL3 bcf movlw call movlw call movlw call movlw call movlw call movlw call call FIN_PTI bcf swapf movwf swapf swapf bsf retfie PIR1,ADIF ST_TEMP,W STATUS W_TEMP,F W_TEMP,W ADCON0,GO ;Ponemos a 0 el flag de fin de conversin ;Recuperamos STATUS con swapf ;Y W con doble swap ;Lanzamos nueva conversin ;Salimos del programa de tratamiento ADCON0,4 LCD_LINE1 LCDSDDA ' ' LCDPUTCHAR 'V' LCDPUTCHAR '3' LCDPUTCHAR ':' LCDPUTCHAR ' ' LCDPUTCHAR SACA_VALOR ;Cambio al canal 1 para prxima conversin ;Cargo en W la direccin de la lnea 1 ;y coloco el puntero de la DDRAM del LCD ah ;Enviamos espacio en blanco ;Ahora una V ;Identificador de canal, el 3 ;Dos puntos ;Espacio en blanco ;Llamamos a subprograma que enva al LCD ;los dgitos BCD

;*************************************************************************** ; Subprograma de conversin Binario a BCD ; ; Recibe el valor a convertir en 16 bits: BIN_ALTO & BIN_BAJO ; y devuelve los dgitos BCD asociados en: BCD2, BCD1 y BCD0 ; -------------------------; BCD2:| 0 | Decenas Mil | ; BCD1:| Unidad Mil | Centenas | ; BCD0:| Decenas | Unidades | ; -------------------------; BINBCD BCF MOVLW MOVWF CLRF CLRF CLRF STATUS,C 0x10 CONTADOR BCD2 BCD1 BCD0 BIN_BAJO BIN_ALTO BCD0 BCD1 BCD2 ;Puesta a cero del carry ;Cargamos 16 en el contador ;Puesta a cero ;inicial de las posiciones ;finales ;Rotacin total ;desde el byte bajo ;hasta el byte ms alto ;de los datos finales ;en BCD

DESPLAZ RLF RLF RLF RLF RLF

E.P.S. de Ingeniera de Gijn Curso 2002-2003


DECFSZ GOTO RETLW AJUSTE MOVLW MOVWF CALL MOVLW MOVWF CALL MOVLW MOVWF CALL GOTO CONTADOR AJUSTE 0 BCD0 FSR AJBCD BCD1 FSR AJBCD BCD2 FSR AJBCD DESPLAZ

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin


;Si el contador es cero ;ya van 16 desplazamientos ;y retornamos ;Empleamos direccionamiento indirecto ;para llamar al subprograma de ajuste ;decimal de cada byte, primero con BCD0 ;Lo mismo con BCD1

;Y lo mismo con BCD2

;Volvemos a las rotaciones

; Subprograma para ajuste BCD de cada byte AJBCD MOVLW ADDWF MOVWF BTFSC MOVWF MOVLW ADDWF MOVWF BTFSC MOVWF 3 INDIR,W TMP TMP,3 INDIR 0x30 INDIR,W TMP TMP,7 INDIR ;Sumamos 3 a la posicin a la que apunta FSR ;el contenido queda en W ;Exploramos si en el primer dgito el ;resultado es mayor que 7 ;si es as corregimos almacenando ese valor ;Hacemos lo mismo con el dgito BCD superior ;Exploramos sumando 30 al byte completo ;y si el dgito superios es mayor que 7 ;lo almacenamos para corregir

RETLW 0 ;Retorno desde el subprograma AJBCD ;********************************************************************** ; Subprograma que se encarga de sacar en el LCD el tiempo transcurrido ; Sacar en el LCD: u-unidades; d-decimas; c-centsimas; m-milsimas; n-diezmilsimas ; ; u,dcmn V ;********************************************************************** SACA_VALOR movf andlw addlw call movlw call movf andlw movwf swapf addlw call movf andlw addlw call movf andlw movwf swapf addlw call movf andlw addlw call BCD2,W 0x0F A'0' LCDPUTCHAR ',' LCDPUTCHAR BCD1,W 0xF0 AUX AUX,W A'0' LCDPUTCHAR BCD1,W 0x0F A'0' LCDPUTCHAR BCD0,W 0xF0 AUX AUX,W A'0' LCDPUTCHAR BCD0,W 0x0F A'0' LCDPUTCHAR ;Tomo las unidades de voltio ;y las extraigo ;le sumo el ASCII del 0 ;y lo envo al LCD ;coloco la coma decimal ;y la envo ;Tomo las dcimas y centsimas ;y extraigo las dcimas ;se las paso a la variable AUX ;y las coloco en la parte baja de W ;le sumo el ASCII del 0 ;y llamo a enviar caracter ;Tomo las centsimas ;de la parte baja de BCD1 ;le sumo el ASCII del 0 ;y lo envo al LCD ;Tomo ahora milsimas y diezmilsimas ;Extraigo las milsimas ;se las paso a la variable AUX ;y las coloco en la parte baja de W ;le sumo el ASCII del 0 ;y llamo a enviar caracter ;Tomo las ;diezmilsimas ;le sumo el ASCII del 0 ;y lo envo al LCD

E.P.S. de Ingeniera de Gijn Curso 2002-2003


movlw call movlw call return ' ' LCDPUTCHAR 'V' LCDPUTCHAR

Prcticas de Sistemas Electrnicos Digitales Curso 3 Ingeniera de Telecomunicacin


;coloco un espacio en blanco ;y lo envo al LCD ;envo las unidades (V) finalmente ;y lo envo al LCD ;salimos del subprograma

;*************************************************************************** ; Subprograma de multiplicacin de dos bytes ; ; Recibe los valores en posiciones FACTOR1 y FACTOR2 ; y entrega el resultado en dos bytes: BIN_ALTO & BIN_BAJO ; PRODUCTO clrf clrf movlw movwf movf bcf BUCLE rrf btfsc addwf BIN_ALTO BIN_BAJO 0x8 CONTADOR FACTOR1,W STATUS,C FACTOR2 STATUS,C BIN_ALTO,F ;Limpio el byte alto ;y el byte bajo tambin ;Cargamos 8 en CONTADOR ;Paso FACTOR1 a W para ir haciendo sumas ;Pongo a 0 el carry para empezar rotaciones ;Roto a dcha FACTOR2 para ver bit a la dcha ;Si era 1 el bit le sumo FACTOR1 a parte alta ;es FACTOR1 00000000

;Al llegar aqu el carry tendr el acarreo de la operacin anterior suma o cero si salt suma rrf rrf BIN_ALTO BIN_BAJO ;Roto en conjunto BIN_ALTO y BIN_BAJO ;Carry -> BIN_ALTO -> BIN_BAJO ;Decrementamos el contador ;si no llegamos a 0 repetimos ;si ya llegamos a cero salimos

decfsz CONTADOR goto BUCLE return END

Вам также может понравиться