Hola buenas tardes!
Llevo un tiempo siguiendo este foro para aprender lenguaje C pero pocas veces me he animado a escribir en el. Tengo un problema parecido al del creador de este tema pero mi sistema sigue sin funcionar aun utilizando las soluciones que se dijeron en el.
Estoy creando un sistema de alarma tambien. El programa funcionaba perfectamente, pero al añadirle la interrupcion externa no me funciona y la parte de la interrupcion por separado si. Es una cosa un poco rara porque si elimino el cable que une el pin del micro de la interrupcion del interruptor que la crea, el programa funciona correctamente excepto lo que es la interrupcion.
Aquí les dejo el programa para ver si me podeis ayudar. Tambien adjunto los diferentes archivos del programa con la libreria del teclado y el esquema del circuito electrico
#include "C:\Users\acer\Documents\Ruben\UNIVERSIDAD\PFC\Pruebas en C\Pruebas\prueba.h"
#fuses XT //Crystal osc <= 4mhz
#fuses NOWDT //deshabilita el Watch Dog Timer
#fuses NOPROTECT //deshabilita la proteccion del codigo del pic
#fuses PUT //habilita el reseteo de power up timer
#fuses NOLVP //No Low Voltage Programming on B3(PIC16) or B5(PIC18,no habilita la programacion en bajo voltaje)
#fuses NOBROWNOUT //No Reset when brownout detected
#use delay(clock = 4000000)
#use fast_io(A) //con esta instruccion evitamos que
#use fast_io(B) //se este configurando cada vez que usamos
#use fast_io(C) //alguna instruccion de entrada o salida
#BYTE TRISA = 0b10000101 //TRISA = 0x85
#BYTE PORTA = 0b00000101 //PORTA = 0x05
#BYTE TRISB = 0b10000110 //TRISB = 0x86
#BYTE PORTB = 0b00000110 //PORTB = 0x06
#BYTE TRISC = 0b10000111 //TRISC = 0x87
#BYTE PORTC = 0b00000111 //PORTC = 0x07
#include <kbd3x4_2.c> //libreria manejo keypad 3x4
#include <lcd3.c> //libreria manejo lcd 8 bits
#include <string.h> //libreria manejo cadenas
#rom 0x2100={0,0,0,0,0,0,0} //la EEPROM se carga con los valores 00h desde la direccion 00h hasta 06h
////////////////DEFINICION DE FUNCIONES////////////////////////////
void menu_principal(void); //funcion que muestra el menu principal
void escribir_clave(char clave[]); //funcion que escibre la clave tecleada
void cambia_clave_inicial(void); //funcion que cambia clave
void cambiar_clave(void); //funcion que cambia clave
int comparar_claves(int); //función que compara las claves
void nueva_clave_admin(void); //funcion que añade la nueva clave administrativa
void activar_alarma(void); //funcion que activa la alarma
void desactivar_alarma(void); //funcion que desactiva la alarma
void escribir_clave_en_eeprom(int); //función que escribe las claves en la memoria eeprom
void leer_clave_en_eeprom(int); //función que lee las claves y las guarda en su correspondiente variable
void alarma_general(void); //funcion que enciende la sirena
void conteo_intentos(void); //funcion que cuenta el numero de intentos de ingreso de contraseña
////////////////VARIABLES GLOBALES///////////////////////////
char clave_inicial[3]= {'1','2','3'}; //variable usada como clave de inicio
char clave_eeprom_admin[3]; //variable usada para comparar los datos de la eeprom contra los datos ingresados
char clave[3]; //variable usada para recoger la clave tecleada
char k; //variable usada para recoger las teclas pulsadas del teclado
signed char i; //variable usada para movernos por las posiciones de la memoria
char clave_introducida[3]={}; //variable usada para los datos ingresados
int alarm_cont=0; //variable global que cuenta los fallos
int flag;
//////////////////LLAMADA FUNCION INTERRUPCION//////////////
#INT_EXT
void intrb0(void)
{
flag=1;
}
////////////////////PROGRAMA PRINCIPAL//////////////////////
void main()
{
setup_adc_ports(NO_ANALOGS);
setup_adc(ADC_CLOCK_DIV_2);
setup_spi(SPI_SS_DISABLED);
setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
setup_timer_1(T1_DISABLED);
setup_timer_2(T2_DISABLED,0,1);
flag=0;
set_tris_b(0b11100001);
set_tris_c(0b11100000);
enable_interrupts(int_ext);
ext_int_edge(L_TO_H);
enable_interrupts(GLOBAL);
lcd_init(); //inicializa lcd
delay_ms(1000);
lcd_putc (" Bienvenido ");
delay_ms(1000);
for( ; ; )
{
cambia_clave_inicial();
menu_principal();
if(flag==1)
{
delay_ms(20); //antirrebote
flag=0;
alarma_general ();
}
do
{
cambia_clave_inicial();
menu_principal();
}while(flag==0);
}
}
//////////FUNCION CAMBIAR CLAVE INICIAL
void cambia_clave_inicial(void) //funcion que cambia clave administrativa
{
int p;
clave_introducida=0;
escribir_clave(clave_introducida);
p=strcmp(clave_introducida , clave_inicial);
if (p==0)
{lcd_putc("\fClave Correcta\n");
delay_ms(2000);
nueva_clave_admin();
}
if (p!=0)
{lcd_putc("\fClave Incorrecta\n");
delay_ms(2000);
clave_introducida=0;
//conteo_intentos();
alarma_general ();
}
}
//////////FUNCION ESCRIBIR NUEVA CLAVE
void escribir_clave(char clave[]) //funcion que escibre la clave tecleada
{
int i=0;
lcd_putc("\fEscribir clave:\n"); //presentacion
do{
do{ //espera hasta...
k=kbd_getc();
}while(k==0); //...pulsar una tecla
if(!(k=='*' || k=='#'))
{
lcd_putc("*");
clave=k;
}
i++;
}while( !(k=='*' || k=='#') ); //Si '*' o '#' señalamos que hemos terminado de introducir la contraseña
}
/////FUNCION MENU PRINCIPAL
void menu_principal (void) //funcion que muestra el menu principal
{
for( ; ; )
{
lcd_putc("\f0-Activa Alarma\n1-Cambia Clave");
do{ //espera hasta...
k=kbd_getc();
}while(k==0 || k==1); //...pulsar una tecla
switch (k)
{
case '0': //va a activar la alarma
activar_alarma();
break;
case '1': //va a comprobar clave para despues cambiar la clave
cambiar_clave();
break;
}
}
}
//////////FUNCION CAMBIAR CLAVE
void cambiar_clave(void) //funcion que cambia clave administrativa
{
int p;
escribir_clave(clave_introducida);
leer_clave_en_eeprom(i);
p=comparar_claves(i);
if (p==0)
{lcd_putc("\fClave Correcta\n");
delay_ms(2000);
nueva_clave_admin();
}
if (p!=0)
{lcd_putc("\fClave Incorrecta\n");
delay_ms(2000);
clave_introducida=0;
alarma_general ();
}
}
//////////FUNCION NUEVA CLAVE
void nueva_clave_admin(void) //funcion que añade la nueva clave administrativa
{
int i=0;
lcd_putc("\fNueva clave:\n"); //presentacion
do{
do{ //espera hasta...
k=kbd_getc();
}while(k==0); //...pulsar una tecla
if(k!='*' || k!='#')
{
lcd_putc("*");
clave=k;
}
escribir_clave_en_eeprom(i);
i++;
}while( !(k=='*' || k=='#') ); //Si '*' o '#' señalamos que hemos terminado de introducir la contraseña
}
//////////FUNCION COMPARAR CLAVES
int comparar_claves(int) //funcion que cambia clave administrativa
{
int i=0;
int s=0;
for (i=0;i<3;i++)
{
if (clave_introducida==clave_eeprom_admin)
s++;
else
{s=0;
lcd_putc("\fClave Incorrecta\n");
break;
}
}
if (s==3)
return 0;
}
//////////ACTIVAR ALARMA
void activar_alarma(void)
{
int i=0;
int p=0;
escribir_clave(clave_introducida);
leer_clave_en_eeprom(i);
p=comparar_claves(i);
if (p==0)
{lcd_putc("\fAlarma Activada");
delay_ms(2000);
desactivar_alarma();
}
if (p!=0)
{lcd_putc("\fClave Incorrecta\n");
delay_ms(2000);
clave_introducida=0;
alarma_general ();
}
}
//////////DESACTIVAR ALARMA
void desactivar_alarma(void)
{
int i=0;
int p=0;
lcd_putc("\fDesactivar alarma\n"); //presentacion
escribir_clave(clave_introducida);
leer_clave_en_eeprom(i);
p=comparar_claves(i);
if (p==0)
{lcd_putc("\fAlarma\nDesactivada");
delay_ms(2000);
break;
}
if (p!=0)
{lcd_putc("\fClave Incorrecta\n");
delay_ms(2000);
clave_introducida=0;
alarma_general ();
}
}
//////////ESCRIBIR_CLAVE_EN_EEPROM
void escribir_clave_en_eeprom(int i) //función que escribe las claves en la memoria eeprom
{
write_eeprom (i,k); //guardamos cada valor de la variable global correspondiente
delay_ms(20); //en la direccion i + 0 (para no pisar datos) de la eeprom
i++; //en una palabra escribe de la posicion 0 a la 4 (5 lugares)
}
//////////LEER_CLAVE_EN_EEPROM
void leer_clave_en_eeprom(int i) //función que lee las claves y las guarda en su correspondiente variable
{
for (i=0;i<3;i++)
{
clave_eeprom_admin = read_eeprom(i); //guardamos cada valor de la direccion i + 0 (para no pisar datos)
delay_ms(20); //de la eeprom en la variable global correspondiente
}
}
////////////FUNCION CONTEO INTENTOS
/*void conteo_intentos(void) //funcion que cuenta el numero de intentos de ingreso de contraseña
{
if (alarm_cont==3)
alarma_general();
else
alarm_cont++;
}*/
//////////FUNCION ALARMA GENERAL
void alarma_general (void)
{
set_tris_c(0b11100000); //pines C0 hasta C4 como salida
output_high(pin_C0); //enciende la sirena durante 10 seg y muestra mensaje
//lcd_putc("\fALARMA\n");
delay_ms(2000);
output_low(pin_C0); //apaga la sirena
alarm_cont = 0; //pongo a cero el contador de errores
break;
}
Muchas gracias por todo