Autor Tema: PIC "se cuelga" al recibir datos por USART  (Leído 9143 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado Pelos

  • PIC10
  • *
  • Mensajes: 3
Re:PIC "se cuelga" al recibir datos por USART
« Respuesta #15 en: 20 de Agosto de 2020, 02:08:44 »
Hola a todos, estoy teniendo el mismo problema de sauron solo que no me ocurre un desbordamiento (o almenos eso creo).
Realizo la lectura de DNI´s y este mismo me da la orden de iniciar los otros procesos del micro, pero, si por accidente se lee la DNI mientras se empezó a ejecutar un proceso del micro este se bloquea.
(Los datos de la DNI llegan por usart)

He deshabilitado las interrupciones intentando que solo funcione la interrupción por serial mientras se solicita la DNI pero aun asi, sigue sin funcionar.

El código del programa completo es extenso asi que pondré una parte y si alguien puede ayudarme y considera necesario otra, estaré atento.

Gracias

Código: CSS
  1. #int_rda
  2. void serial(){
  3.  if(kbhit(hardw)){
  4.     for (k=0;k<80; k++){
  5.         trama[k]=getchar(hardw);
  6.         if(trama[k]==9){
  7.            nueve++;
  8.            if(nueve==5){
  9.               if(trama[k-1]==9){
  10.                  error=1;
  11.               }else{
  12.                 error=0;
  13.               }
  14.           }
  15.         }
  16.        if(trama[k]==10){
  17.           trama[k]=0;            
  18.           break;
  19.       }
  20.    }              
  21.  }
  22.  permiso=1;
  23. }

así es como ejecuto la lectura del puerto y lo almaceno en el buffer llamado "Trama".

Desconectado remi04

  • PIC24F
  • *****
  • Mensajes: 657
Re:PIC "se cuelga" al recibir datos por USART
« Respuesta #16 en: 20 de Agosto de 2020, 04:00:14 »
Hola a todos, estoy teniendo el mismo problema de sauron solo que no me ocurre un desbordamiento (o almenos eso creo).
Realizo la lectura de DNI´s y este mismo me da la orden de iniciar los otros procesos del micro, pero, si por accidente se lee la DNI mientras se empezó a ejecutar un proceso del micro este se bloquea.
(Los datos de la DNI llegan por usart)

He deshabilitado las interrupciones intentando que solo funcione la interrupción por serial mientras se solicita la DNI pero aun asi, sigue sin funcionar.

El código del programa completo es extenso asi que pondré una parte y si alguien puede ayudarme y considera necesario otra, estaré atento.

Gracias

Código: CSS
  1. #int_rda
  2. void serial(){
  3.  if(kbhit(hardw)){
  4.     for (k=0;k<80; k++){
  5.         trama[k]=getchar(hardw);
  6.         if(trama[k]==9){
  7.            nueve++;
  8.            if(nueve==5){
  9.               if(trama[k-1]==9){
  10.                  error=1;
  11.               }else{
  12.                 error=0;
  13.               }
  14.           }
  15.         }
  16.        if(trama[k]==10){
  17.           trama[k]=0;            
  18.           break;
  19.       }
  20.    }              
  21.  }
  22.  permiso=1;
  23. }

así es como ejecuto la lectura del puerto y lo almaceno en el buffer llamado "Trama".

 Seguramente sí que se desborda el fifo. Durante esos procesos basta que utilices un delay_ms() para que desborde. Sobre todo si son tramas lo que viene por el usart.

   Kbhit en la interrupción no parece tener sentido. Si entra en la interrupción es por que se ha recibido un carácter si o si.  Aunque esto no es problema tampoco que uses kbhit ahí, pero lo veo absurdo.

   Para evitar desbordamientos del fifo Lo que puedes hacer es instar el bit CREN con la macro #bit y la dirección del registro RCSTA de tu micro que no se cual es.  Si la dirección es por ejemplo 0x0a3 (es un ejemplo), y el bit CREN es el 4 tienes que instarlo en la cabecera de la siguiente forma:

   
Código: C
  1. #bit CREN=0x0a3.4

  También puedes instarla mediante variables de entorno usando getenv();

Código: C
  1. #bit CREN=getenv(“BIT:CREN”)

   Una vez que tienes esto lo que haces es deshabilitar CREN mientras están en los procesos y habilitarlo solamente cuando el programa esté en disposición de recibir.

 Es una forma de tener un control total del puerto si la interrupción no puede ser atendida con la suficiente rapidez.

  Al poner CREN a 0 prohíbes la recepción de datos y además reseteas el módulo de recepción y todas las banderas de los errores que haya activos.  Si había desbordado, esto reseteara todo y luego al volver a poner CREN a 1 volverá a recibir.

  Como usarlo depende de cómo sea el flujo del programa y la periodicidad con la que llegan las tramas.

  Saludos.