Atmega32, UART sendet konstant bei zweitem Zeichen

OP #4965047
Lesenswert?

Hallo,

ich habe ein seltsames Problem mit UART und vielleicht sieht jemand 
meinen Fehler sofort.

Ich initialisiere UARt mit 9600 Baud, 8 bit, 1 Stop bit no parity. Ich 
moechte einen Buchstaben empfangen, einen Pin schalten und einen 
Buchstaben zuruecksenden.

Initialisierung:
1
 #define BAUD 9600                           // define baud
2
#define BAUDRATE ((F_CPU)/(BAUD*16UL)-1)    // set baudrate value for UBRR
3
                  // set the CPU clock
4

5
// function to initialize UART
6
void uart_init (void)
7
{
8
  UBRRH=(BAUDRATE>>8);
9
  UBRRL=BAUDRATE;                         //set baud rate
10
  UCSRB|=(1<<TXEN)|(1<<RXEN);             //enable receiver and transmitter
11
  UCSRC|=(1<<URSEL)|(1<<UCSZ0)|(1<<UCSZ1);// 8bit data format
12
}
Senden:
1
void uart_transmit (unsigned char data)
2
{
3
   if(UCSRA & (1<<UDRE))         /* Senden, wenn UDR frei ist                    */
4
   {    UDR = data;               /* schreibt das Zeichen x auf die Schnittstelle */
5
   }
6
}
Empfangen:
1
unsigned char uart_recieve (void)
2
{
3
  
4
  while(!(UCSRA) & (1<<RXC));           // wait while data is being received
5
  return UDR; 
6
                          // return 8-bit data
7
  
8
}
Main:
1
int main (void)
2
{
3
  unsigned char LED;
4
  uart_init();                            // initialize UART
5
  DDRA = 0xFF;
6
  while(1)
7
  {
8
    LED=uart_recieve();   // save the received data in a variable
9
    
10
      switch (LED)
11
      {
12
    case 'a':
13
      LED = '0';
14
      PORTA |= (1<<PA0);
15
      uart_transmit('a');
16
      
17
      break;
18
    
19
    case 'A':
20
      LED = '0';
21
      PORTA &= ~(1<<PA0);
22
      uart_transmit('A');
23
      
24
      break;
Das Problem ist nun, es funktioniert mit dem ersten Buchstaben perfekt. 
(Verbindung ueber HTerm), sobald ich den zweiten sende wird der 
vorhergehende Buchstabe in einer endlosschleife vom uC gesendet.
#4965356
Lesenswert?

Clemens K. schrieb:
> Senden:
1
void uart_transmit (unsigned char data)
2
 {
3
    if(UCSRA & (1<<UDRE))         /* Senden, wenn UDR frei ist */
4
    {    UDR = data;              /* schreibt das Zeichen x auf die  Schnittstelle */
5
    }
6
 }

Das hat zwar nichts mit dem Fehler "Dauersenden" zu tun, aber statt
1
    if(UCSRA & (1<<UDRE))         /* Senden, wenn UDR frei ist */
sollte da
1
    while (!(UCSRA & (1<<UDRE)))  /* warten bis UDR frei ist */
stehen.

In Deinen Fall können beim Senden Zeichen verloren gehen.
OP #4966292
Lesenswert?

Cyborg schrieb:
> Clemens K. schrieb:
>> Jup, das war es! Brilliant!
>
> Brillianter wäre den Debugger zu benutzen. Dann kann man Fehler
> selber finden. Wenn man trotzdem nicht weiter kommt, kann man
> immer noch andere fragen.

Das habe ich sogar getan, ich bin mit jtag und dem avr dragon Zeile fuer 
Zeile durchgegangen und habe Code eingefuegt wie flushen des Speichers 
usw. Er ist immer nach aufrufen der uart recieve Funktion in die switch 
case gegangen. Das ist sehr untypisch, daher war mir bewusst das es 
irgendwo eine Kleinigkeit ist die ich uebersehen habe. Natuerlich bin 
ich dann durch die Forumssuche gegangen, aber die haeufigsten Probleme 
dort waren nur das es gar keine Datenuebertragung gibt. Klar, es ist 
vll. etwas verfrueht das Forum zu fragen, aber manchmal sieht ein 
aussenstehender meinen Fehler sofort und ich lerne dadurch schneller.

So, vielen Dank!

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren