mikrocontroller.net

Forum: Mikrocontroller und Digitale Elektronik Problem mit UART zwischen zwei ATmega8


Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hallo,

folgendes Problem tritt bei mir auf:

Zwei ATmega8 sollen über UART Daten austauschen -  das kleine 
Testprogramm funktioniert, solange ich nur selten ( einmal pro Sekunde) 
Daten sende - senden ich häufig kommt  -  sobald ich kurz das Sendekabel 
aus und wieder eingesteckt habe nur noch Datenmüll an  -  beim langsamen 
Senden geht das problemlos  -  bitte gebt mir einen Tipp:

Es wird einfach eine Zahl gezählt und gesendet  -  beim Empfänger am 
PortC ausgegeben  -  Port B zeigt Paritätsfehler an....

Sender:
# include <stdint.h>
# include <avr/io.h>

uint8_t temp,temp1,temp2,temp3;

int main(void)
{
DDRB=0b11111111;
//PORTB=0b0000000;
UBRRH=(uint8_t)(4000000/(2000*16L-1))>>8;
UBRRL=(uint8_t) (4000000/(2000*16L-1));
UCSRB =(1<<TXEN);
UCSRC =(1<<URSEL)|(1<<USBS)|(1<<UPM1)|(1<<UPM0)|(1<<UCSZ1)|(1<<UCSZ0);

//sendet binär 0 bis 63

temp=1;
while(1){
temp=temp+1;
if (temp==63) temp=0;
while(!(UCSRA & (1<<UDRE)));
UDR=temp; // hier geht es prima  

//Warten .....
temp1=0;
while(temp1<254){
temp1++;temp2=0;// if((UCSRA & (1<<UDRE))) UDR=temp;  // hier geht es nicht mehr sinnvoll
      while(temp2<254){
    temp2++;temp3=0;
              while(temp3<3){
           temp3++;
       //
      
                            }
                    }
                 }
        }
}




Empänger:
 
# include <stdint.h>
# include <avr/io.h>

uint8_t temp;

int main(void)
{
DDRC=0b11111111;
DDRB=0b11111111;


UBRRH=(uint8_t)(4000000/(2000*16L-1))>>8;
UBRRL=(uint8_t) (4000000/(2000*16L-1));
UCSRB =(1<<RXEN);
UCSRC =(1<<URSEL)|(1<<USBS)|(1<<UPM1)|(1<<UPM0)|(1<<UCSZ1)|(1<<UCSZ0);



while(1){
while(!(UCSRA &(1<<RXC)) | (UCSRA &(1<<PE)) ){ if(UCSRA &(1<<PE)) {temp=UDR;PORTB=255;} else PORTB=0; }
PORTC=UDR;
}
}


DANKE!!!!

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
es sieht so aus als würde der MC den anfang des bitpaketes nicht mehr 
finden  -  was mache ich falsch ????

Autor: holger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>was mache ich falsch ????

Du ziehst einfach den Stecker raus ? Lass ihn doch dran.
Oder mach eine Synchronisation mit irgendwelchen von dir
selbst gewählten Start/Stopbytes.

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Tommy (Gast)

>es sieht so aus als würde der MC den anfang des bitpaketes nicht mehr
>finden  -  was mache ich falsch ????

Hast du mal die Tutorials angeschaut?

AVR-Tutorial: UART

AVR Checkliste

MFG
Falk

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Letzlich soll die Strecke per Funk übertragen werden und da sollen 
Störungen vorkommen dürfen ....

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Falk  -  klar habe ich alles gelesen  -  nur es hilft ja nicht weiter 
-  es funktioniert ja prima  -  bis eine Störung kommt  -  dann wird der 
Anfang nicht mehr gefunden  -  außer man hat lange Pausen drin ...

Gruß

T.

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@holger

"Oder mach eine Synchronisation mit irgendwelchen von dir
selbst gewählten Start/Stopbytes."  -  es kommen ja keine definierten 
Bytes mehr rein ! -  also kann ich das ja auch nicht machen ...

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Tommy (Gast)

>-  es funktioniert ja prima  -  bis eine Störung kommt  -  dann wird der
>Anfang nicht mehr gefunden  -  außer man hat lange Pausen drin ...

Genauso ist es. Du musst dem UART schon Zeit geben sich neu zu 
synchronisieren. Dazu musst du in regelmässigen Abständen eben KEINE 
Daten senden, für mindestens die Zeit eines Zeichens (10Bit), besser 
zwei oder drei. Dann fängt sich der Empfänger wieder.

Etwa so.

while (1) {
X Zeichen senden
1..3 Zeichen Pause
}

MfG
Falk

P.S. Deine Formatierung ist grausam!

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Wenn Störungen vorkommen können, dann musst du immer wieder
Pausen in die Übertragung einlegen, um dem Empfänger Zeit
zu geben sich irgendwann wieder mal auf ein Startbit
synchronisieren zu können.

Schau dir das Prinzip der RS232 Übertragung an, dann wird
es klarer. Der Empfänger erkennt den Anfang eines Bytes,
das Startbit nur aus dem Grundzustand heraus. Er kann nicht
wissen, welche von vielen Absenkungen die regelmässig daher-
kommen nun ein Startbit sein soll. Also muss man ihm eine
Chance dazu geben. Den Idle Zustand über eine längere Zeit
beibehalten, damit der Empfänger die Chance hat, ein fehlerhaft
synchronisiertes Byte abzuschliessen und auf das nächste Startbit
zu warten, dass dann auch vom Sender kommt. Erst dann sind
beide wieder synchronisiert.

Im Chaos-Sende-programm da oben schau ich mir noch nicht
mal an, wie das Zeitverhalten sein könnte :-)

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hi -  das hilft mir mal weiter  -  danke !

will einen billigen AM-Empfänger nutzten  -  aber das wird dann klar so 
nicht gehen --> FM


@ alle   - man lernt ja nur dadurch das anderen einem zeigen wie es 
besser geht  - daher würde mich freuen, wenn jemand die Schleifen so 
formatiert, dass es "ideal" ist

Gruß

T.

Autor: Karl Heinz (kbuchegg) (Moderator)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Tommy wrote:
> Hi -  das hilft mir mal weiter  -  danke !
>
> will einen billigen AM-Empfänger nutzten  -  aber das wird dann klar so
> nicht gehen --> FM
>
>
> @ alle   - man lernt ja nur dadurch das anderen einem zeigen wie es
> besser geht  - daher würde mich freuen, wenn jemand die Schleifen so
> formatiert, dass es "ideal" ist

Das macht man prgmatisch:
  Bei jeder { wird in der nachfolgenden Zeile zb um 2 Zeichen
  eingerückt. Die zu diesem { gehörende  } wird dann wieder
  um 2 Zeichen ausgerückt.

Wenn die erste {, also die Funktionsklammer, am linken Rand ist,
dann muss sich mit all den Einrückungen und Ausrückungen ergeben,
dass die schliessende Funktions-} wieder am linken Rand ankommt.
Ansonsten hast du einen Fehler in der Struktur.

Vorteil: man sieht sofort, welche Teile gemeinsam in einer
Struktur (sei es Schleifen- oder Abfragestruktur sind)

Ein paar Leerzeichen an strategischen Stellen haben auch noch nie
geschadet, die Lesbarkeit aber schon oft drastisch erhöht. Man muss
dann nicht mehr lange in einer Zeile nach dem = suchen :-)

Vergleich mal deinen Kauderwelsch mit
int main(void)
{

  DDRB = 0b11111111;
//PORTB=0b0000000;
  UBRRH = (uint8_t)( 4000000 / (2000*16L-1) ) >> 8;
  UBRRL = (uint8_t)( 4000000 / (2000*16L-1) );
  UCSRB = (1<<TXEN);
  UCSRC = (1<<URSEL) | (1<<USBS) | (1<<UPM1) |
          (1<<UPM0) | (1<<UCSZ1) | (1<<UCSZ0);

//sendet binär 0 bis 63

  temp = 1;
  while( 1 ) {

    temp = temp+1;
    if( temp == 63 )
      temp = 0;

    while( !( UCSRA & (1<<UDRE)) )
      ;

    UDR = temp; // hier geht es prima  

    // Warten .....

    temp1 = 0;
    while( temp1 < 254 ) {
      temp1++;

      temp2 = 0;
      // if( (UCSRA & (1<<UDRE)) )
      //   UDR = temp;  // hier geht es nicht mehr sinnvoll
      while( temp2 < 254 ) {
        temp2++;

        temp3 = 0;
        while( temp3 < 3 ) {
          temp3++;
        }
      }
    }
  }
}

Autor: Falk Brunner (falk)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
@ Tommy (Gast)

>will einen billigen AM-Empfänger nutzten  -  aber das wird dann klar so
>nicht gehen --> FM

Unsinn, das hat damit gar nichts zu tun.

MFG
Falk

Autor: Tommy (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
Hey Danke !

Autor: holger (Gast)
Datum:

Bewertung
0 lesenswert
nicht lesenswert
>will einen billigen AM-Empfänger nutzten  -  aber das wird dann klar so
>nicht gehen --> FM

Ach, das hast du vor.

>"Oder mach eine Synchronisation mit irgendwelchen von dir
>selbst gewählten Start/Stopbytes."  -  es kommen ja keine definierten
>Bytes mehr rein ! -  also kann ich das ja auch nicht machen ...

Wenn du bei der gestörten Kabelverbindung schon Probleme hast,
dann freu dich mal auf das was aus deinem Empfänger kommt
wenn kein Sendesignal da ist. Der rauscht eventuell wie verrückt.
Da bekommst du jede Menge undefinierter Bytes. Du wirst
nicht drumherum kommen mit einem Vorspann von ein paar
Bytes Sender und Empfänger zu synchronisieren. Noch ein Tip:
Lange Pausen zwischen den Bytes können dazu führen das der Empfänger
wieder rauscht. Und auch ein Dauerträger kann dazu führen das der
Empfänger rauscht ! Gleichspannungssignale wollen die billigen
Empfänger auch nicht haben.

Antwort schreiben

Die Angabe einer E-Mail-Adresse ist freiwillig. Wenn Sie automatisch per E-Mail über Antworten auf Ihren Beitrag informiert werden möchten, melden Sie sich bitte an.

Wichtige Regeln - erst lesen, dann posten!

  • Groß- und Kleinschreibung verwenden
  • Längeren Sourcecode nicht im Text einfügen, sondern als Dateianhang

Formatierung (mehr Informationen...)

  • [c]C-Code[/c]
  • [avrasm]AVR-Assembler-Code[/avrasm]
  • [code]Code in anderen Sprachen, ASCII-Zeichnungen[/code]
  • [math]Formel in LaTeX-Syntax[/math]
  • [[Titel]] - Link zu Artikel
  • Verweis auf anderen Beitrag einfügen: Rechtsklick auf Beitragstitel,
    "Adresse kopieren", und in den Text einfügen




Bild automatisch verkleinern, falls nötig
Bitte das JPG-Format nur für Fotos und Scans verwenden!
Zeichnungen und Screenshots im PNG- oder
GIF-Format hochladen. Siehe Bildformate.
Hinweis: der ursprüngliche Beitrag ist mehr als 6 Monate alt.
Bitte hier nur auf die ursprüngliche Frage antworten,
für neue Fragen einen neuen Beitrag erstellen.

Mit dem Abschicken bestätigst du, die Nutzungsbedingungen anzuerkennen.