TODOPIC
Microcontroladores PIC => Lenguaje Basic para microcontroladores PIC => Mensaje iniciado por: alan980 en 24 de Junio de 2017, 16:23:33
-
Hola, ando con un problemilla que no logro corregir, estoy trabajando con la interrupcion por TMR0 asi como con comunicacion serial con un modulo Bluetooth para un pic 18F4550, todo andaba bien con mi comunicacion serial pero al momento de agregarle la interrupcion por TMR, no anda como deberia, ya que mi intencion es que la comunicacion serial funcione al recibir caracteres y cada uno efectua diferentes tareas mientras tanto el timer debe ejecutarse cada 100mS aproximandamente para mandar un texto por serial, con mi codigo actual la comunicacion se realiza pero la interrupcion no ocurre hasta que no se recibe algun valor por HSERIN,
en resumen....el pic espera valores con HSERIN mientras deberia interrumpirse cada cierto tiempo y mandar texto por serial.....que ocurre realmente?.....el pic espera un valor y al recibirlo ejecuta las tareas y luego ejecuta la interrupcion, parece mas una interrpcion por cambio de estado que por timer
realmente en tiempo de interrupcion no me preocupa ya que con las formulas se puede modificar, al momento solo quisiera que se ejecutra la interrupcion correctamente, anexo codigo, gracias por su tiempo
_______________________________________________________________________________________
'----------------------FUSIBLES------------------------------
DEFINE OSC 48 'FRECUENCIA PARA LOS CALCULOS DE RETARDO
DEFINE HSER_RCSTA 90h
DEFINE HSER_TXSTA 20h 'ASINCRONO, PARA OSC 4 ES HIGH SPEED 24H, PARA OSC 48 ES LOW SPEED 20H
DEFINE HSER_BAUD 9600
'----------------------REGISTROS----------------------------------
ADCON1 = %00001111 'TODOS LOS PINES DIGITALES
BAUDCON.3 = 0 '8 BITS BAUD RATE GENERATOR
RCON.7 = 1 'SISTEMA DE PRIORIDAD EN LAS INTERRUPCIONES 1 ACTIVADO 0 DESACTIVADO
CMCON = 7
INTCON = %10100000 'CONFIGURANDO LA INTERRUPCION TMR0, BIT 2 FLAG TMR0
INTCON2.7 = 1 'DESACTIVAR LAS RESISTENCIAS EN PULL-UP DEL PUERTO B
INTCON2.1 = 1 'PRIORIDAD DE LA INTERRUPCION POR TMR0
T0CON = %10000111 'TIMER ACTIVO 16 BITS TEMPORIZADOR PRESCALER DE 1:256
TMR0H = $ED '%11101101 'VALORES DE INICIO DE CONTEO TIMER 16BITS
TMR0L = $A9 '%10101001
TRISC = %10000000 'PIN7 RECEPCION PIN 6 TRANSMISION
TRISD = 0 'PUERTO D PARA LOS MOTORES
'----------------------VARIABLES----------------------------------------
CR CON 13 'VALOR ASCII DEL 13 DECIMAL ES CR "RETORNO DE CARRO"
TIEMPO VAR BYTE
DISTANCIA VAR BYTE
CHAR VAR BYTE
'-----------------------ALIAS--------------------------------------------
CLEAR 'BORRA TODAS LAS VARIABLES
PORTC = 0
PORTD = 0
ON INTERRUPT GOTO SENSOR 'LECTURA CADA 100mS
HSEROUT [" INICIE",CR]
INICIO:
HSERIN [Char] 'ESPERA DE UN VALOR
SELECT CASE CHAR
CASE "A"
PORTD = %10011001
CASE "B"
PORTD = %01100110
CASE "C"
PORTD = %10010110
CASE "D"
PORTD = %01101001
CASE "E"
PORTD = 0
END SELECT
GOTO INICIO
DISABLE
SENSOR:
HSEROUT [" ME INTERRUMPI", CR]
TMR0H = $ED '%11101101
TMR0L = $A9 '%10101001
INTCON = %10100000 'BORRANDO BANDERA DE INTERRUPCION
RESUME
ENABLE
END
-
hola alan980.
esto es lo que uso para interrupción serial y timer, espero te sirva. que como tarea que la estudies y apliques.
incluir los siguientes archivos para que te facilite las cosas:
'http://web.archive.org/web/20141004065559/http://darreltaylor.com/DT_INTS-18/home.html
'aquí se trata este tema de las interrupciones
http://www.picbasic.co.uk/forum/showthread.php?t=3251&page=19&highlight=timer+interrup
saludos
desde aquí el programa:
'estas librerias deben existir en la carpeta donde tienes instalado el PBP3
include "alldigital.pbp" ' definiciones para todos los puertos como I/O digitales si hay entradas anlogas no usarlo.
INCLUDE "DT_INTS-18.bas" ' Base Interrupt System pic 18Fxx
INCLUDE "ReEnterPBP-18.bas" ' Include if using PBP interrupts pic 18Fxx
DEFINE OSC 8 ' Define clock freq. 8 MHz
'DECLARAS UN ARRAY DONDE VAS A METER LO QUE RECIBAS POR EL PUERTO SERIAL
'SI SON MUCHA LA INFORMACION, DE LO CONTRARIO DECLARAS UNA VARIABLE
MYBUFER VAR byte[100] 'AQUI VA TODO LO QUE LLEGUE
cuenta var byte ' ----> se incrementa cada vez que ocurre una interrupcion del timer
cuantos var byte
'//********************* Inicializo TXTSTA RXSTA *****************************
TXSTA = %00100100 ' abilitas el modo de transmision asincrono
RCSTA = %10010000 'preparas recepccion
'************************** INICIALIZO TIMER2 ES EL QUE USO**********************************
' PARA OBTENER ESTOS AJUSTES PUEDES USAR EL PROGRAMA FuseConfiguratorSetUp.exe
'LO BAJAS DE LA PAGINA https://forum.mikroe.com/viewtopic.php?f=215&t=68172
' COPIAS AQUI LOS VALORES QUE TE DA EL PROGRAMA SOLO LOS REGISTROS Y SUS
VALORES SELECCIONAS LA OPCION MILCROBASIC
' Prescaler=1:16; TMR2 PostScaler=1:1; PR2=208 - Freq = 1.495,21531Hz - Period = 0,6688 ms
T2CON = %00000110
PR2 = 208 ' PR2 (Timer2 Match value) (1 cycle adjusted)
TMR2 = 0 'TMR2 Holding register = 0
'********************* PREPARO INTERRUPCIONES ******************************
ASM
INT_LIST macro ; IntSource, Label, Type, ResetFlag?
INT_Handler RX_INT , _MI_INTERRUPCION, PBP, yes
INT_Handler TMR2_INT , _MI_INTERRUPCION, PBP, yes
endm
INT_CREATE ; Creates the interrupt processor
INT_ENABLE RX_INT ; enable external (INT) interrupts
INT_ENABLE TMR2_INT ; enable external (INT) interrupts
ENDASM
'********************* PROGRAMA PRINCIPAL ******************************
Main:
'AQUI TU PROGRAMA CON LO QUE VAS HACER
'manipulas en este ejemplo la variable cuenta
'usas los datos del bufer
'etc.....
GOTO MAIN
'*****************************************************************************
'!!!! Desabilito interrupcion no colocar ningun codigo del user !!!!
Disable
' ********************* OCURRIO INTERRUPCION LEO TRAMA ***********************
'AQUI LA INTERRUPCION SERIAL Y LA DEL TIMER LE DAS EL NOMBRE QUE QUIERAS
MI_INTERRUPCION:
If RCSTA.1 OR RCSTA.2 then ' SI OCURRE OVERRUN Y/O ERROR EN LA TRAMA LO BORRAS DE LO CONTRARIO DEJAS DE RECIBIR DATOS
RCSTA.4=0 ' // BORRO el error
RCSTA.4=1 ' // abilito la recepccion de nuevo
EndIf
if (PIR1.5 = 1) then ' OCURRIO INTERRUPCION DEL USART
while (PIR1.5 = 1) 'recibo los datos y los guardo en el bufer
MYBUFER [cuantos] = RCREG
cuantos= cuantos + 1
If cuantos>= 100 Then '---> para evitar se desborde el bufer
cuantos = 0
EndIf
Wend
EndIf
'********** ocurrio interrupcion del timer en mi caso el timer2 *************
if (PIR1.1 = 1) then
PIR1.1 = 0 ' lo reconozco
T2CON.2 = 0 ' desabilito el Timer2
CUENTA=CUENTA+1 '----> esta lleva las vece que ocurre la interrupción del timer
T2CON.2 = 1 'abilito el timer2
EndIf
@ INT_RETURN
End
-
Mis disculpa por entrometerme en tema de BASIC ya que no se el lenguaje. Pero:
ON INTERRUPT GOTO SENSOR 'LECTURA CADA 100mS
.........
SENSOR:
HSEROUT [" ME INTERRUMPI", CR]
Si yo no me equivoco al leer el programa hace que al momento de la interrupcion, es decir EN LA interrupcion se pone a enviar por la UART. El mayor problema de esto es que si uno queda encerrado en una interrupcion ( debido a que todavia no envio todo el mensaje) no va a poder entrar a otra interrupcion, Por eso mismo no vas a tener interrupciones del Timer entre otros hasta que no termine de enviar todo por la UART.
-
Hola gracias a todos por su tiempo, me permito comentarles lo siguiente,
En el programa principal tengo una instruccion que es HSERIN [CHAR] que es recibir un valor por el puerto serial, mientras no se recibe datos el programa pareciera estar en pause, al recibir algo, hace la funcion y luego se interrumpe por TMR
pero si borro esa instruccio, la interrupcion por TMR se ejecuta sin problema y recibo en el monitor serial el menaje "Me Interrumpi" cada 100mS , lo que yo quisiera es q se ejecute la interrupcion ppr TMR sin importar si se recibio algun dato o no,
Gracias nuevamente por sus comentarios