Microcontroladores PIC => Todo en microcontroladores PIC => Mensaje iniciado por: picipici en 15 de Agosto de 2016, 09:13:15
Título: Reinicio del programa
Publicado por: picipici en 15 de Agosto de 2016, 09:13:15
Buenos días: He confeccionado un sencillo programa para el 18F46J50 que solo hace encender un led una única vez y finaliza el programa. No tiene ningún bucle. Cuando compilo con CCS y grabo el fichero .hex en el pic con el ICD2 y el MPLAB IDE v8.92, funciona como se espera. Cuando compilo con XC8 (adaptando el programa al XC8) y grabo el fichero .hex en el pic con el ICD2 y el MPLAB IDE v8.92, el programa se reinicia continuamente. Alguien podría darme una explicación para evitar este reinicio.
Muchas gracias de antemano. Un saludo
Título: Re:Reinicio del programa
Publicado por: KILLERJC en 15 de Agosto de 2016, 11:38:10
Para empezar, SIEMPRE deberias tener un loop infinito.
Y lo que estas experimentando es como cada compilador posee su codigo de inicializacion. Antes de arrancar lo que es tu programa, existe un codigo el cual resetea varios registros e inicializa las variables en la RAM, ya que por default la RAM tiene valores 0x00 (pierde todo ante el reset). Luego de alli pueden optar por algunos modos de funcionamiento.
- Por ejemplo el de Arduino, si ves tienen 2 funciones al escribir un programa: setup y loop. En el cual el usuario no necesita poner el loop por que el codigo de inicializacion lo tiene incorporado. Es decir ademas de configurar inicialmente lo basico para el usuario y que arranque el microcontrolador, llama a una funcion llamada setup, y cuando vuelve luego llama a una funcion de nombre loop, aunque este esta en ASM, en C lo verias como algo asi:
Código: C
void inicializacion(void)
{
//... Inicializacion de variables / registros
setup();
while(1)
{
loop();
}
}
- El caso de CCS, tal ves lo que hace CCS es casi lo mismo, nomas que no se separa en setup y loop, solo llama a "main", tal ves no tenga incorporado un bucle infinito para que ejecute una y otra ves las cosas, pero a veces a la vuelta de la funcion (cuando llega al fin del main) se suele colocar un bucle infinito para que se quede ahi para siempre y no recorra toda la memoria y produzca el efecto de reset. Pensalo como que hace esto:
Código: C
void inicializacion(void)
{
//... Inicializacion de variables / registros
main();
while(1);
}
- En XC8 tal ves utiliza otro enfoque, en ves de hacer un llamada y esperar que vuelva, directamente realiza un salto ( ya voy a decir cual seria la ventaja ), Con lo cual si tu "main" se termina comienza a ejecutar toda la memoria que queda no programada, hasta que llega al final y por overflow del Contador de Programa ( PC ) vuelve al inicio, es decir direccion 0x00, como si fuera un reset.
Código: C
void inicializacion(void)
{
//... Inicializacion de variables / registros
goto main();// Aca no se guarda en el stack esta direccion.
}
- La otra opcion es que el mismo compilador agregue al final del main un while(1); sin hacer una llamada
Cual es la diferencia de una llamada o un salto ? Los PICs 8bits tienen una pila por hardware limitada, distinto a lo que es otras arquitecturas que usan la RAM (stack) para almacenar la direccion de retorno. Entonces si haces una llamada ya estas ocupando una direccion de la pila, mientras que si haces un salto NO. Creo que es la unica que se me ocurre.
Para ver exactametne cual es cual, uno deberia ver los codigos de inicializacion, que creo que ni XC8, ni CSS lo tienen a simple vista y habria que verlo en ASM o el hex.
Todo esto si es que los FUSES estan correctamente configurados de forma que sean iguales en ambos compiladores