Hallöchen, mir ist aufgefallen das es ziemlich viele dieser Anfragen gibt bezügl. des USART/UART. Ich habe ein Problem mit dem Kabel. Habe mir aus Flachbandkabel und zwei Steckern. Der erste ist ein COM-Stecker(weibl.), der andere ein 10-Pin-Stecker(der Name fällt mir gerade nicht ein). Ich habe den TXD Pin (über MAX232) an den COM-Pin2, den RXD-Pin an den COM-Pin3 und den GND-Pin an den COM-Pin5 angeschlossen. Habe ich da schon einen fehler gemacht? Des weiteren sieht mein Quellcode wie folgt aus: UCSRA |= (1<<U2X); UCSRB |= (1<<TXEN)|(1<<UCSZ2); UCSRC |= (1<<URSEL)|(0<<UMSEL)|(1<<UPM1)|(0<<UPM0)|(1<<USBS)|(1<<UCSZ1)|(1<<UCSZ0 )|(0<<UCPOL); UBRRH = UBRR_VAL>>8; //UBRR Wird vorher bestimmt UBRRL = UBRR_VAL; while(1){ while (!(UCSRA & (1<<UDRE))) {} UDR = 'x'; //SENDEN eines einfachen x } im Hyperterminal von Windows habe ich folgende Einstellungen: BAUD:9600 Datenbits:8 (UCSZ2:1:0 auf 1 gesetzt ==> 9-Bit gibts hier einen Konflikt??) Parität:Gerade (UPM1:0 auf EVEN gestellt) Stoppbits:2 (USBS auf 1) Flusssteuerung: kein (was hat es damit auf sich??) Mit freundlichem Gruß Frank O
Frank O wrote: > Hallöchen, > mir ist aufgefallen das es ziemlich viele dieser Anfragen gibt bezügl. > des USART/UART. Entsprechend viele Hilfe/Information bei Problemen mit UART und RS232 müsste unterwegs sein ;-) > Ich habe ein Problem mit dem Kabel. > Habe mir aus Flachbandkabel und zwei Steckern. Der erste ist ein > COM-Stecker(weibl.), der andere ein 10-Pin-Stecker(der Name fällt mir > gerade nicht ein). > Ich habe den TXD Pin (über MAX232) an den COM-Pin2, den RXD-Pin an den > COM-Pin3 und den GND-Pin an den COM-Pin5 angeschlossen. > Habe ich da schon einen fehler gemacht? Erstes Bild bei http://www.mikrocontroller.net/articles/AVR-Tutorial:_UART so sollte es aussehen. Deine Beschreibung passt in etwa dazu, ausser, dass man nicht sieht, wie du den MAX232 in deiner Schaltung hast. > Des weiteren sieht mein Quellcode wie folgt aus: > > UCSRA |= (1<<U2X); > UCSRB |= (1<<TXEN)|(1<<UCSZ2); > UCSRC |= > (1<<URSEL)|(0<<UMSEL)|(1<<UPM1)|(0<<UPM0)|(1<<USBS)|(1<<UCSZ1)|(1<<UCSZ0 )|(0<<UCPOL); > UBRRH = UBRR_VAL>>8; //UBRR Wird vorher bestimmt > UBRRL = UBRR_VAL; > > while(1){ > while (!(UCSRA & (1<<UDRE))) {} > > UDR = 'x'; //SENDEN eines einfachen x > } Also das ist ein Codefetzen und kein eigenständiger Quellcode. Man kann es nicht testen, sondern nur die kryptischen Werte im Datenblatt nachlesen. U.a. sieht man im Codefetzen nicht, wie dein UBRR_VAL definiert bzw. vorher bestimmt wird. Ein Setzen von U2X ("Doublespeed UART an") muss bei der Berechnung von UBRR_VAL berücksichtigt werden. Nützlich wären auch Infos darüber, wie du 9600 Baud bei welcher Taktrate (Taktquelle?, Fuses?, F_CPU?) eigentlich setzen willst. Näheres dazu in der http://www.mikrocontroller.net/articles/AVR_Checkliste#UART.2FUSART > im Hyperterminal von Windows habe ich folgende Einstellungen: > BAUD:9600 > Datenbits:8 (UCSZ2:1:0 auf 1 gesetzt ==> 9-Bit gibts hier einen > Konflikt??) Ja, gibt einen Konflikt. Wenn du auf dem PC 8 Datenbits hast und auf dem Atmega32 9, kann es nicht funktionieren. Ok wäre 8-Bits UCSRB = (1<<TXEN)|(0<<UCSZ2); > Parität:Gerade (UPM1:0 auf EVEN gestellt) > Stoppbits:2 (USBS auf 1) Kann gehen, wenn es auf beiden Seiten (AVR und PC) hleich ist. Obige Bits sehen OK aus. > Flusssteuerung: kein (was hat es damit auf sich??) S. Grundlagen im RS232 Artikel und bei Wikipedia http://de.wikipedia.org/wiki/RS232
Hallo, du brauchst einen Pegelwandler zwischen Mikrocontroller und PC! z.B. Max232, wenn du mit 5 Volt versorgst. Die Ein/Ausgänge am MC haben 5 Volt-Pegel, die RS-232 vom PC +/- 15 Volt. Flusssteuerung bedeutet, dass einer dem anderen verbieten kann, zu senden, wenn er gerade beschäftigt ist und keine Daten entgegennehmen kann. Der ATMEGA32 hat keine Hardwareflussteuerung und du hast sie auch nicht angeschlossen (RTS/CTS), du stellst also "keine" ein. Lass für die ersten Versuche die Parity weg, also 8 bit am MC und am Terminal einstellen. Also Parity: "keine". Nimm, nach korrektur der Schaltung mit Max232 vorsichtshalber einen neuen Atmega, der könnte durch die 15 Volt zerstört worden sein. Wenns dann geht kannst du ja den alten ausprobieren. Ich hoffe, das hilft etwas. Grüße, Peter
Hey Danke, das klappt jetzt, außerdem verwende ich das Bray-Terminal irgendwie ist das funktionaler. Jetzt nur nochmal eine Frage zum Verständnis. Ich möchte ja den korrekten Wert/Buchstaben/String wie auch immer empfangen. Zum Testen sende ich immer ein großes X und bekomme aber mal ein B, H, oder ein Kästchen. Bei BrayTerminal steht zusätzlich, Frame Error da, das heißt ich weiß das irgendetwas Falsch läuft. mfg Frank
Hallo, ein Frame-error bedeutet, dass entweder nicht die richtige Anzahl Bits empfangen worden ist, oder dass irgendeine andere Signalfoge (Start, Stopp) nicht stimmt. Das passiert üblicherweise, wenn man sich bei der Baudrate verrechnet hat. Es wäre hilfreich, wenn du deine Schaltung zur Pegelwandlung kurz beschreiben oder posten könntest. Hier sollte man nicht sparen, dass die Pegel mit entsprechend starken und schnellen Treibern gesendet werden ist wichtig. Grüße, Peter
Hallo, ich verwende das RN-Control v1.4, aus dem "Roboternetz"(siehe Anhang Schaltplan). Der MAX232 wandelt das automatisch, um die Schaltung musste ich mich also nicht kümmern. Der Wert für das UBRR-Register beläuft sich laut Datenblatt auf 103:BAUD9600 bei 16MHz und einfacher Übertragungsrate. Ich hab nochmal "rumgeschraubt" am Quelltext, die Parity auf EVEN gestellt(gibt es da einen Vorteil ob EVEN oder ODD oder KEINE??), 2STOPPBITS. Fazit die Fehler der Übertragung werden weniger. Ich möchte aber nochmal kurz den Fehler erläutern. Wenn ich auf EMPFANGEN bzw. CONNECT klicke gibt es bei mir zwei Möglichkeiten, (a) nur FRAME ERRORS (b) das RICHTIGE ZEICHEN... und je nachdem wie oft ich das CONNECT/DISCONNECT anklicke funktionierts oder nicht. Hier nochmal der Quelltext: //---------------------------------------------------------------------- --- //---------------------------------------------------------------------- --- #include <avr/io.h> int UBRR_XX = 207; //baud 9600 DOPPELTE ÜBERTRAGUNGSRATE //---------------------------------------------------------------------- --- //*** Testprogramm für den USART des ATMega32 ***// //---------------------------------------------------------------------- --- int main(void){ UCSRA |= (1<<U2X); UCSRB |= (1<<TXEN); UCSRC |= (1<<URSEL)|(0<<UMSEL)|(1<<UPM1)|(0<<UPM0)|(1<<USBS)|(1<<UCSZ1)|(1<<UCSZ0 )|(0<<UCPOL); UBRRH = UBRR_XX>>8; UBRRL = UBRR_XX; while(1){ while (!(UCSRA & (1<<UDRE))) {} //Warten bis Senden möglich UDR = 'X'; //Senden eines X ! } return 0; } //---------------------------------------------------------------------- --- //---------------------------------------------------------------------- --- Grüße Frank
Hallo, mit 16 MHz Quarz an einem ATmega32 kann man keine RS-232 mit genormter Baudrate betrieben. Du brauchst dafür ein Baudratenquarz. z.B. 14,7456 MHz Und setz U2X nicht, das reduziert die Präzision im Empfänger. Dann wird die Quarzfrequenz mit einem 16er Prescaler runtergeteilt, dann musst du nur noch z.B. 47 in UBRRL reinschreiben und bekommst 19200 Baud. Wie rechnet man das? (QuarzFrequenz/16/Baudrate) - 1 = UBRR, Was kommt da bei deinem Quarz raus (9600 Baud, 16 MHz): 16MHz/16/9600 = 104,1666666.... Dadurch kann man nicht ganzzahlig teilen! Du hast also einen Baudratenfehler. Jetzt rechnen wir das für U2X gesetzt: 16MHz/8/9600 = 208,333333..... Du hast korrekt 1 weniger eingestellt, das ändert aber nichts daran, dass die Baudrate nicht 9600 ist, sondern: 16MHz/8/208 = 9615,38 Baud Ob das funktiniert ist ein Zufallsexperiment. So würde ich das einstellen: UCSRA nicht anfassen. UCSRB |= (1<<TXEN); UCSRC |= (1<<URSEL)| muss gesetzt sein (0<<UMSEL)| Asynchrone Schnittstelle (0<<UPM1)| no parity (0<<UPM0)| no parity (0<<USBS)| one stop bit only (1<<UCSZ1)| 8-bit mode (1<<UCSZ0)| 8-bit mode (0<<UCPOL); Write this to zero in asynchronous mode oder kürzer: UCSRC = 0b10000110; dann weiter: UBRRH = 0; UBRRL = 47; Quarz 14,7456MHz einbauen, im Terminal 19200 Baud, 8 bit, no parity, one stop bit, no flow control einstellen und es muss funktionieren. Viel Erfolg damit, Peter
@Peter: so genau muss die Baudrate auch wieder nicht stimmen, auf S.154 des ATmega32 Datasheet ist eine Tabelle des tolerierbaren Fehlers, in diesem Fall sind +/- 2% zulässig. @Frank: >Ich möchte aber nochmal kurz den Fehler erläutern. >Wenn ich auf EMPFANGEN bzw. CONNECT klicke gibt es bei mir zwei >Möglichkeiten, (a) nur FRAME ERRORS (b) das RICHTIGE ZEICHEN... > >und je nachdem wie oft ich das CONNECT/DISCONNECT anklicke funktionierts >oder nicht. Wunderbar, eine Fehlerbeschreibung (sieht man selten ...)! (b) deutet darauf hin, dass Du gar kein Problem hast! Du lässt den ATmega rennen, und drückst dann CONNECT, richtig? In diesem Fall versucht sich die PC-Schnittstelle auf die bereits laufende Datenübertragung des Atmel zu synchronisieren. Und das klappt nur manchmal. Beide UARTs müssen synchron zueinander laufen, und dazu brauchen sie (beim Start) eine kurze Pause. Die einfachste Lösung ist, in die Übertragung des ATmega ab und an ein kurzes Delay (länger als ein Frame, bei 9600 baud also > 1ms) einzubauen. Viele Grüße, Stefan
Hallo, mhh die Idee einen genauen Quarz zu nehmen find ich nicht schlecht, passt mir aber leider nicht, weil ich die 16MHz schon brauche, für zeitkritische Messungen. Das mit dem Connect und ATMega32 läuft bereits dachte ich mir auch schon, habs auch verändert. 1.Frage: Was bringt mir das EVEN/ODD Parity-Bit?(Datenblatt werde ich gleich nochmal genauer Lesen!) 2.Frage: Warum empfiehlt sich ein einzelnes Stoppbit? Grüße Frank
Hallo, es ist schon richtig, dass die Baudrate einen leichten Fehler haben darf. Wenn aber Fehler auftreten, sollte man es mal mit der korrekten versuchen. Das Parity Bit ist ein Prüfbit, das jedem Byte hinzugefügt wird, wenn Parity benutzt wird. Even Parity bedeutet, dass mit dem Prüfbit die Anzahl "Einser" des Bytes und des Prüfbits zusammen auf eine gerade (even) Anzahl ergänzt wird. Odd ist entsprechend ungerade. Daran kann ein Übertragungsfehler erkannt werden, er muss aber nicht zwingend erkannt werden, es kann auch sein, dass Fehler nicht erkannt werden, wenn z.B. zwei Bits falsch sind. Beispiel: übertrage 0b10001010 Das hat drei Einser. Wenn die Parity even ist, wird ein weiterer Einser als Parity angehängt. Wenn sie odd ist, wird eine Null angehängt. Der Empfänger weiß dann, dass die Anzahl an Einsern im Nutzbyte ungerade war. Wenn das nicht stimmt, liegt auf jeden Fall ein Fehler vor. Für deine Versuche ist es wichtig, dass die Übertragung an sich funktioniert, lass deshalb die Fehlererkennung über parity abgeschaltet, sonst siehst du deine Fehler nicht, sie werden einfach ignoriert. Ich würde zudem eine Pause von einer Sekunde zwischen dem Senden der Bytes einbauen, das Hilft dem PC bei der Synchronisation und dir hilft es, zu erkennen, ob bytes verloren gehen. Das Verwenden von zwei Stoppbits ist unüblich, eine gängige Betriebsart zur Inbetriebnahme von seriellen Schnittstellen ist 8N1: 8 bits, no parity, 1 stop bit. Viele Grüße, Peter
Bray-Terminal //---------------------------------------------------------------------- --- http://braypp.googlepages.com/terminal
Hallo, wenn dir das Quarz mit 14,7456MHz zu langsam ist, kannst du auch eins mit 15,9744MHz verwenden. UBRRL ist dann auf 51 zu setzen für 19200 Baud. Als reines Bedienterminal eignet sich auch Putty hervorragend. Hat aber keine zusätliche Anzeige von Statussignalen oder HEX-Übersetzer... ist nur für ASCII gedacht. Wenn du was gescheites suchst, probier Realterm: http://realterm.sourceforge.net/ Viel Erfolg, Peter
Hallöchen, habe keinen Überblick über sämtliche Mikrocontroller. Dazu muss ich sagen, ich benutze den ATmega32 als Ereigniszähler, über den ICP-Pin (TIMER/COUNTER1 16-Bit zähler), genauer gesagt ich Messe Pulsbreiten. Nun die Frage, was ist derzeit das Maximum an Geschwindigkeit(in MHz :)) ?? Und um welchen Controller würde es sich dann handeln, da mir 16MHz eine Genauigkeit von etwa 4us geben, ich brauchs genauer. Nanosekunden oder kleiner wäre super genial!! Grüße Frank PS: Danke für die bisher sehr ausführlichen Tips!
Hallo, Nonosekunden sind natürlich ein Wort. Was willst du damit machen? Also eine konventionelle Technologie hat eine Auflösung von 1/Taktfrequenz. 1 Nanosekunde entspricht dann einer Frequenz von 1 GHz. Ich glaube die schnellsten AVR Mikrocontroller haben 24 MHz. Mit einem ARM kommst du vielleicht auf 80 MHz, darüber sind dann eigentlich alle in nicht mehr handhabbaren Gehäuseformen (BGA). Ich würde aber eher versuchen, es irgendwie zu umgehen, eine Pulsbreite auf 1 Nanosekunde genau messen zu müssen. Ansonsten gibt es schon Ansätze, die das können. Es gibt Phase-locked-loops, die mit mehreren phasenverschobenen Takten und Zählern auch mit niedrigerer Taktfrequenz eine so hohe Auflösung erreichen können. So was setzt man z.B. in Laserabstandsmessgeräten ein. Einige der TMS320C2000 DSPs von TI können Pulsweiten mit einer Auflösung von 150 ps(!) ausgeben, vielleicht sind da welche dabei, die auch Pulse messen können, müsstest du nachschauen. Oder viellecht kann man mit einem so generierten Referenzpuls die eingehenden Pulse abschätzen. Wenn es nur ein Versuchsaufbau ist, würde ich einfach ein Speicheroszi verwenden. Tektronix hat dafür die praktische Trigger hold off Funktion, damit kann man auch von sehr langen Pulsen sehr ganau die Länge bestimmen (auf wenige Nanosekunden genau). Viele Grüße, Peter
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.