La comunicación en serie de Uart no se pudo devolver Atmega16a

1

Soy nuevo en avr (8bit uc) y recientemente tuve un problema con la comunicación en serie (uart) con la PC. El microcontrolador no responde en el terminal de masilla, donde debería devolver lo que haya enviado.

Gracias por su respuesta a todos.

Lo siento por el código corrupto, no tenía idea de lo que estaba haciendo ya que soy un novato en este código de intercambio en el intercambio de pila.

El nuevo código se adjunta a continuación, por favor sugiérelo

#define F_CPU 16000000UL
#include <avr/io.h>
#include <avr/interrupt.h>

volatile char data;

void USARTInit(uint16_t ubrr_value) {
    UBRRL = ubrr_value;
    UBRRH = (ubrr_value >> 8);
    UCSRC = (1 << URSEL) | (1 << UCSZ0) | (1 << UCSZ1);
    UCSRB = (1 << RXEN) | (1 << TXEN);
}

void USARTWriteChar(char data) {
    while (!(UCSRA & (1 << UDRE)))
        { }

    //Now write the data to USART buffer
    UDR = data;                                                               
}                                                                             

void main() {                                                                 
    sei();                                                                    
    UCSRB |= (1 << RXCIE);                                                    
    USARTInit(51);                                                            

    while (1) {                                                               
        if (data == 'a') {                                                    
            USARTWriteChar(data);
        }
    }
}

ISR(USARTRXC_vect) {
    data = UDR;
}

así que aquí foo solo representa mis datos = 'a', desafortunadamente avr no responde a mis entradas. cuando escribo "a".

    
pregunta arun crazz

1 respuesta

2

En primer lugar, ese código no se compilará. La última parte (el ISR) parece corrupto, es posible que desee volver a publicar ese bit.

En segundo lugar, no es sorprendente que al escribir "FOO" no responda, ya que el código está esperando a que presione "a", en cuyo punto respondería con "[a] [a] [a] [a] [a] [a] .... "hasta que presiones otra cosa.

En tercer lugar, deberías aprender a formatear tu código correctamente, o al menos usar uno de los buenos auto-formateadores, como Artistic Style.

Lamentablemente no tengo un ATMega16A aquí para probar su código, y no estoy al tanto de las interrupciones de Atmel, así que todo lo que puedo hacer es sugerir algunas cosas para probar:

  1. Asegúrese de que su código se esté ejecutando realmente y que la serie en sí esté funcionando: haga que imprima un mensaje de "Hola" al inicio de su main() después de configurar el UART.
  2. Asegúrese de que la interrupción se esté disparando realmente; haga que se encienda un LED cuando se active la interrupción.
  3. Haz que parpadee otro LED como un "latido" en tu bucle principal while(1) para asegurarte de que no se atasque.

Editar: Después de un poco de investigación y lectura (encuentro que las hojas de datos de Atmel están terriblemente mal escritas) encontré que su vector de interrupción se llama incorrecto.

Esta página los enumera todos: enlace

Allí, después de algunos recorridos, puedes encontrar que para el ATMega16 el vector RX debería llamarse:

    USART_RXC_vect 

Después de cambiar el nombre que puedo ver en una descompilación, el ISR se instala correctamente en la tabla de vectores:

00000000 <__vectors>:
   0:   0c 94 2a 00     jmp 0x54    ; 0x54 <__ctors_end>
   4:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
   8:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
   c:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  10:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  14:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  18:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  1c:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  20:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  24:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  28:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  2c:   0c 94 5c 00     jmp 0xb8    ; 0xb8 <__vector_11>   // <-- ISR
  30:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  34:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  38:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  3c:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  40:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  44:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  48:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  4c:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>
  50:   0c 94 47 00     jmp 0x8e    ; 0x8e <__bad_interrupt>

... que no lo hizo antes.

    
respondido por el Majenko

Lea otras preguntas en las etiquetas