rpi <--> avr uart Übertragungsfehler bei Quarzbetrieb

OP #7741288
Lesenswert?

Liebe Leute,

ich versuche mich an einer Motorsteuerung, bestehend u.a aus einem avr m328pb und einem SBC, derzeit ein rpi02W. Sie sollen über uart miteinander kommunizieren: Status und Kommandos sind in beide Richtungen austauschen, zudem sollen vom avr debug - Meldungen zum rpi versendet werden. Das ganze muss recht fix passieren, darum habe ich als baudrate > 300000 anvisiert.

Der avr sitzt auf einer Platine die auch den SBC huckepack über die 40poligen Pfostenleiste hält. Die Stromversorgung des SBC erfolgt mittels eines 5V - Abwärtsregler. Der avr wird mit den 3V3 des rpi gespeist. Seine Peripherie besteht nur aus zwei Tastern und zwei LED.

Das Problem ist nun: Betreibe ich den avr mit dem 14.7456 MHz - Quarz, so ist die höchstmögliche Baudrate für zuverlässige Übertragung 115200. Bei >= 234000 ist die Fehlerrate extrem hoch, es kippt regelmäßig nach ca 12 kB erfolgreicher Übertragung ein bit. Keine Aussetzer gibt es jedoch wenn der avr mit dem internen RC - Oszillator betrieben wird. Mit dem kann ich mit 500000 baud fehlerfrei mehrere Megabytes hin und her schieben.

Derzeit habe ich kein Scope zur Hand und ich bin ratlos. Hat jemand so was schon mal gehabt?

Schönen Gruß, H.

#7741295
Lesenswert?

Harald schrieb:

Der avr wird mit den 3V3 des rpi gespeist.

Harald schrieb:

Betreibe ich den avr mit dem 14.7456 MHz - Quarz

Datenblatt Auszug: 0 - 20MHz @ 4.5 - 5.5V

Harald schrieb:

Bei >= 234000 ist die Fehlerrate extrem hoch

http://www.gjlay.de/helferlein/avr-uart-rechner.html

Deine Zahlen kurz eingesetzt kommen da teilweise 8% Fehler raus.

Harald schrieb:

Keine Aussetzer gibt es jedoch wenn der avr mit dem internen RC - Oszillator betrieben wird. Mit dem kann ich mit 500000 baud fehlerfrei mehrere Megabytes hin und her schieben.

Vermutlich Glückssache. Verändere Mal die Versorgungsspannung oder Fön in mal auf 60°C.

#7741301
Lesenswert?

Mit 14,7456MHz und 3,3V betreibst du den AVR schon mal außerhalb der Spezifikationen...

Speed Grade:

– 0 - 4 MHz @ 1.8 - 5.5V

– 0 - 10 MHz @ 2.7 - 5.5V

– 0 - 20 MHz @ 4.5 - 5.5V

Abgesehen davon hilft ein Blick ins DB

Bei einer Baud Rate von 0.5M und 8MHz hast du 0% Fehler

Bei einer Baud Rate von 0.5M und 14.7456MHz hast du 7,80% Fehler

Also alles ganz normal...

Angehängte Dateien:
#7741318
Lesenswert?

Peter Z. schrieb:

Bei einer Baud Rate von 0.5M und 8MHz hast du 0% Fehler Bei einer Baud Rate von 0.5M und 14.7456MHz hast du 7,80% Fehler

Genau!

Zusätzlich sollte man die Abweichung auf beiden Seiten betrachten. Die nominelle Baudrate ist ziemlich wurst, wichtig ist, dass die tatsächliche Baudrate zwischen beiden Seiten zusammenpasst wenn unterschiedliche Chips mit unterschiedlichen Formeln und Quarzen verwendet werden.

Ich hatte das mal hier beschrieben: https://github.com/nospam2000/ch341-baudrate-calculation?tab=readme-ov-file#problem-b-the-calculated-baudrate-is-now-nearer-to-nominal-rate-but-farer-from-the-baud-rate-of-communication-partner

Michael

OP #7741319
Lesenswert?

Sorry, ich habe unklar geschrieben. Die Baudratenfehler sind immer 0, da ich mit Quarz 115200, 230400 und auch 921600 probiert habe. Nur mit 115200 klappt's mit Quarz fehlerfrei. Die 500000 funktionieren mit 8 MHz Takt aus dem internen RC - Oszillator.

Allerdings: Ein Blick ins richtige Datenblatt zeigt tasächlich dass 3.3V maximal für 13 MHz erlaubt sind... Wie man sich doch täuschen kann. Ich werde auf 11 MHz runtergehen und 460800 baud probieren.

Danke für euere Aufmerksamkeit!

#7741332
Lesenswert?

Chris S. schrieb:

Probiere 921.6K Mit normalem 16mhz Quarz sind 2mb möglich, internem osc 1mb. Rpi geht bis 4mbit.

Millibit wären kein Problem - alles eine Frage der Zeit, Darum geht es hier aber nicht. Quarzfrequenzen liegen eher einen Faktor 10^9 über dem von dir angegebenen Wert.

In deinem Beitrag offenbaren sich eklatante Defizite bei dem Umgang mit Maßeinheiten und ihren Vielfachen.

https://de.wikipedia.org/wiki/Vors%C3%A4tze_f%C3%BCr_Ma%C3%9Feinheiten

#7741337
Lesenswert?

Derzeit habe ich kein Scope zur Hand und ich bin ratlos.

Verwende entweder Controller die einen fraktionalen Teiler haben, oder aber achte darauf Bitclocks zu verwenden die man aus dem Quarz auch runterteilen kann.

Und ja, es schadet wirklich nichts bei den ersten Bytes mal ein Oszi zur Hand zu haben. .-)

Was mich aber wundert, wenn man sowas programmiert und sich die Registerwerte ausrechnet, dann sollte man das eigentlich merken. Wenn man faul ist und nur anderer Leute Libaries verwendet dann sollte man Rueckgabewerte abfragen. Wenn eine Libarie solche grobfalschen Werte setzt ohne einen Fehler zurueckzumelden oder man zu faul ist sowas in seinem Programm abzufragen dann sollte man daraus auch etwas lernen...

Vanye

Gast #7741390
Lesenswert?

Eventuell schwingt der Quarz nicht stabil. Das kann an den angeschlossenen Kondensatoren oder sonstigen Leitungskapazitäten liegen. Kommt auch vor, wenn man den Abblock-Kondensator an der Stromversorgung weg lässt.

Gast #7741391
Lesenswert?

Bruno V. schrieb:

Wenn Du mehr willst, nimm 115.2kBaud * 2 (230.4), *4 (460.8) oder * 8 (921.6)

So weit war er doch schon. Du bist nicht der Einzige, der das überlesen hat.

Die rein rechnerische Abweichung von der Baudrate durch den Takt-Teiler ist nicht sein Problem. Das muss noch etwas anderes im Argen sein.

Ich glaube auch nicht, dass die geringe Versorgungsspannung hier der Knackpunkt ist. Denn genau diese Kombination (3,3 Volt und 14.7456 MHz) habe ich schon öfters bei meinen Basteleien angewendet. Hat bisher noch nie Probleme gemacht.

#7741438
Lesenswert?

Monk schrieb:

Die rein rechnerische Abweichung von der Baudrate durch den Takt-Teiler ist nicht sein Problem. Das muss noch etwas anderes im Argen sein.

Wo hat er denn von der Gegenstelle geschrieben? Wenn es mit 500k klappt, dann auch mit 230.4.

Es gibt 2 typische Fehlermöglichkeiten:

  • Die Gegenstelle hat keinen Sio-Quartz
  • in einer der beiden Seiten hat sich ein off-by one-Fehler eingeschlichen.

Ich würde auf off-by one tippen. Teilerregister 16 statt 15.

OP #7741589
Lesenswert?

Upload von Dateien scheint grad nicht zu klappen:

An internal Error has occured. If this problem persists, please contact the administrator of this website (webmaster@embdev.net).

Ein interner Fehler ist aufgetreten. Falls dieses Problem erneut auftritt, wende dich bitte an den Administrator (webmaster@mikrocontroller.net).

Angehängte Dateien:
OP #7741612
Lesenswert?

Verluste an mehreren Stellen. Mein Text zu den pdf ist auch verloren gegangen. Er war in etwa so:

Softwareseitig gibt's keinen Grund zum Zweifeln. Avr und rpi sprechen die gleiche Sprache. Die rechnerische Fehlerrate ist immer 0. Die Kommunikation klappt bei niedrigen Baudraten. Über 115200 stottert der avr bei Quarzbetrieb. Der wackelige RC - Takt jedoch schafft 500k ohne Probleme.

Ich habe einige Quarze bestellt um zurück in den spezifizierten Bereich zu kommen. Ich glaube auch nicht dass 1.3MHz Übertaktung schlimm sind, aber man weiß ja nie.

Beim Lesen des DBs fällt auf dass der 328pb nicht mehr den "full swing oscillator" hat. Es ist nur noch die störanfällige low power - Variante vorhanden. Nun ist der rpi räumlich nicht weit vom avr entfernt. Da er headless betrieben wird ist sein wifi ist immer eingeschaltet und eine potentielle Störquelle(?)

Allerdings hört sich der Quarztakt gut an - Frequenzen im Hörbereich sind sauber und konstant. Der RC - Oszillator klingt deutlich schlechter, kraziger, mit gar nicht seidigen Höhen und spürbar unschwarzen Bass!

Gast #7741630
Lesenswert?

Harald schrieb:

Es ist ein IQD LFXTAL012313 von Reichelt. Die Bürdekapazitäten sind 15p.

Im Shop steht, dass der Quarz 30 pF Lastkapazität braucht. Abzüglich geschätzter 10pF für die Leitungen und den AVR komme ich auf den Bedarf von 2 Kondensatoren mit jeweils 50pF.

Deine 15 pF sind davon weit entfernt.

Gast #7741668
Lesenswert?

Monk schrieb:

Im Shop steht, dass der Quarz 30 pF Lastkapazität braucht

Ich dachte, ich zeige mal wo ich die 30 pF her habe.

Nachtrag: Sorry, ich hatte den Screenshot von RS zu weit beschnitten. Jetzt korrigiert.

Thomas Z. schrieb:

Lastkapazität 16 pF steht im Shop

Das wäre mir ehrlich gesagt auch lieber gewesen, weil 30 pF ungewöhnlich viel sind. Wo hast du denn die 16 pF gesehen?

Angehängte Dateien:
#7741694
Lesenswert?

Harald schrieb:

Die Stromversorgung des SBC erfolgt mittels eines 5V - Abwärtsregler. Der avr wird mit den 3V3 des rpi gespeist. Seine Peripherie besteht nur aus zwei Tastern und zwei LED.

Wenn du sowieso 5V zur Verfügung hast, warum dann den AVR mit 3,3V versorgen? Versorge ihn auch mit 5V und du kannst jeden Quarztakt bis 16/20MHz verwenden. Du kannst alle Baudraten verwenden die vom Quarztakt abgeleitet Ganzzahlig teilbar sind.

Bspw. 16MHz Quarz, kannste bspw. 250k oder 500k Baudrate einstellen - 0,0% Abweichung.

Auf der Seite vom RPI kann ich nichts dazu sagen, wie fein dieser konfigurierbar ist, er sollte dann auch 0% abweichen. Du suchst also den Größten gemeinsamen Nenner. ;-)

OP #7741715
Lesenswert?

S. L. schrieb:

Was spricht gegen die 500 kBd mit den internen 8 MHz?

Letztendlich nur die Temperaturdrift. Selbst wenn die Langzeitdrift nur +- 1% ist, so könnte unter ungünstigen Umständen (Geschlossenes Gehäuse, Sommersonne etc) der Temperaturgang zum Problem werden.

Die Idee war halt, nimm 'nen Quarz und alles wird gut. Spart Frickelei. Der avr hat ja einen Temperatursensor eingebaut, den könnte man zur Kompensation, also zum Nachtrimmen des RC - Oszillators nutzen...

Spaßeshalber werde ich mal den Kühlschranktest machen (Kältespray hab ich gerade nicht).

#7741822
Lesenswert?

Monk schrieb:

Harald schrieb:

Es ist ein IQD LFXTAL012313 von Reichelt. Die Bürdekapazitäten sind 15p.

Im Shop steht, dass der Quarz 30 pF Lastkapazität braucht. Abzüglich geschätzter 10pF für die Leitungen und den AVR komme ich auf den Bedarf von 2 Kondensatoren mit jeweils 50pF.

Deine 15 pF sind davon weit entfernt.

Das ist doch albern. Selbst wenn er ein paar pF neben der optimalem Lastkapazität läge, wäre der Einfluß derselben auf die Schwingfrequenz des Quarzes doch eher marginal. Damit RS-232 wegen Timingproblemen aussteigt, braucht man Abweichungen in der Größenordnung von 10%. Nicht 100ppm.

OK, der Quarz könnte mit der falschen Lastkapazität gar nicht anschwingen. Das würde er dann aber sofort merken.

#7741827
Lesenswert?

Harald schrieb:

Avr und rpi sprechen die gleiche Sprache. Die rechnerische Fehlerrate ist immer 0.

Kannst Du das mit einem Oszi verifizieren?

Die Kommunikation klappt bei niedrigen Baudraten.

Auch wenn es sich komisch anhört: die Baudrate ist fast egal. Da es offensichtlich keine Signal-Probleme gibt (es funktioniert ja mit 500kBaud).

Es ist also eher Wahrscheinlich, dass Du einen Fehler bei den Teilern hast. Du kannst die Werte posten oder messen.

OP #7742178
Lesenswert?

Bruno V. schrieb:

Es ist also eher Wahrscheinlich

Das ist eher unwahrscheinlich. Ich programmiere den avr in C++. Mittels consteval errechnet der compiler den ubrr (ich schätze das meinst du mit Teiler) und stellt mittels static_assert sicher dass die gewünschte Baudrate zur Taktfrequenz passt. Ist eine Abweichung vorhanden, so scheitert bereits die Kompilierung.

(Firma: 1984now) #7742197
Lesenswert?

Axel S. schrieb:

Lastkapazität läge, wäre der Einfluß derselben auf die Schwingfrequenz des Quarzes doch eher marginal.

Kommt drauf an, wieviel neben dem Optimum er liegt.

Damit RS-232 wegen Timingproblemen aussteigt, braucht man Abweichungen in der Größenordnung von 10%.

Nein. Eher 6%. Und das gilt auch nur dann, wenn der Peer auf ein paar ppm die exakte Baudrate hat. Haben beide Teilnehmer Fehler, kann auch schonmal bei drei Prozent Abweichung auf einer Seite der Kuchen gegessen sein. Wenn halt die andere Seite auch 3% hat, nur in die andere Richtung.

OK, der Quarz könnte mit der falschen Lastkapazität gar nicht anschwingen. Das würde er dann aber sofort merken.

Zwischen diesem Fall und dem Fall "läuft mit ein paar ppm Abweichung" existiert aber noch eine gewisse Bandbreite, in der der Quarz quasi "stottert". Das ist der eigentlich gefährliche Bereich, denn hier bemerkt man den Fehler des Taktgebers u.U. eben nur durch solche Effekte wie: UART funktioniert nicht richtig.

Gast #7742200
Lesenswert?

Thomas Z. schrieb:

Ich dachte, ich zeige mal wo ich die 30 pF her habe.

ich diesen hier: https://www.reichelt.de/standardquarz-grundton-14-7456-mhz-iqd-lfxtal012313-p245415.html?CCOUNTRY=445&LANGUAGE=de

Oh, jetzt sehe ich, dass Reichelt mir einen ganz anderen gezeigt hat, obwohl ich die richtige Artikelbezeichnung eingegeben habe. Das habe ich nicht erwartet.

Wenn die Lastkapazität 16 pF sein soll, dann komme ich auf 22 pF Kondensatoren. Ich schätze mal, dass in diesem Fall die vorhandenen 15 pF auch noch akzeptabel sind.

Axel S. schrieb:

Das ist doch albern. Selbst wenn er ein paar pF neben der optimalem Lastkapazität läge, wäre der Einfluß derselben auf die Schwingfrequenz des Quarzes doch eher marginal.

Das sehe ich auch so. Allerdings sind 50 pF versus 15 pF mehr als "ein paar pF". Wie dem auch sei, das hat sich ja inzwischen geklärt.

Ob S. schrieb:

Zwischen diesem Fall und dem Fall "läuft mit ein paar ppm Abweichung" existiert aber noch eine gewisse Bandbreite, in der der Quarz quasi "stottert". Das ist der eigentlich gefährliche Bereich, denn hier bemerkt man den Fehler des Taktgebers u.U. eben nur durch solche Effekte wie: UART funktioniert nicht richtig.

Deswegen hatte ich die Kondensatoren in Frage gestellt.

Harald schrieb:

Allerdings hört sich der Quarztakt gut an - Frequenzen im Hörbereich sind sauber und konstant

Interessante Idee, das so (ohne Oszilloskop) zu verifizieren. 👍

OP #7742207
Lesenswert?

S. L. schrieb:

Der 'Teiler' ist ja sehr klein

Genau. Die uart - Initialierung ist bei 460800

720: 88 e1 ldi r24, 0x18 ; 24 722: 80 93 c1 00 sts 0x00C1, r24 ; 0x8000c1 <TEXT_REGION_LENGTH+0x7e00c1> 726: 81 e0 ldi r24, 0x01 ; 1 728: 90 e0 ldi r25, 0x00 ; 0 72a: 90 93 c5 00 sts 0x00C5, r25 ; 0x8000c5 <TEXT_REGION_LENGTH+0x7e00c5> 72e: 80 93 c4 00 sts 0x00C4, r24 ; 0x8000c4 <TEXT_REGION_LENGTH+0x7e00c4>

Für 921600 ist 0xC4 gleich 0. Im code fallen die letzten vier Befehle weg. Gcc ist schlau genug um zu wissen dass die Register nach dem Reset ohnehin 0 sind.

#7742210
Lesenswert?

Monk schrieb:

Wenn die Lastkapazität 16 pF sein soll, dann komme ich auf 22 pF Kondensatoren. Ich schätze mal, dass in diesem Fall die vorhandenen 15 pF auch noch akzeptabel sind.

Die 15pf sind zwar etwas klein. Ich hätte da auch 22pf gewählt aber das passt soweit. Allerdings sagt Digikey für diesen Quarz auch 30pf und die haben dort auch ein einzelnes Datenblatt bereit gestellt. Nicht so ein generisches wie Reichelt

OP #7742381
Lesenswert?

Ob S. schrieb:

Zwischen diesem Fall und dem Fall "läuft mit ein paar ppm Abweichung" existiert aber noch eine gewisse Bandbreite, in der der Quarz quasi "stottert"

Der Meinung war ich bis gerade eben auch. Jetzt sehe ich das etwas anders. Tatsache ist, am Quarz steht ein stabiler Sinus mit 2V pp an, gemessen mit 1:10 Teiler am Tastkopf. CPU und uart stört das Andocken der Tastkopfspitze am Quarz nicht, sie laufen weiter. Jedoch kommt der uart ins Schleudern wenn ich den Anschluß mit dem Finger berühre. Die CPU läuft jedoch ungestört weiter. Das untermauert OB S.' These des anspruchsvolleren uart, spricht aber auch gegen Oszillations - Probleme.

Ich habe eher den rpi im Verdacht: Mit geloopten tx/rx zeigt der rpi bereits ohne involviertern avr seltsames Verhalten. Die bislang nur mit meiner eigenen software festgestellten Übertragungsfehler zeigen sich auch mit anderen Programmen die die serielle Schnittstelle schreiben UND lesen. Ich habe https://github.com/cbrake/linux-serial-test.git probiert. Es schickt einfach Daten an rx, liest von tx und vergleicht sie. Das klappt bis 115200 immer, darüber hinaus treten bei 5% der Versuche Fehler auf.

#7742437
Lesenswert?

Ob S. schrieb:

Nein. Eher 6%.

Bei 8 Datenbit + Parity, typischer Abtastrate 16-fach, Abtastung bei 7,8 und 9 16tel und perfekter Leitung wird das Stop-Bit nach 10 + 7,8 und 9 /16 Bitdauern abgetastet, wovon 2 "OK" sein müssen.

Es bleibt also eine Reserve von 6/16 Bit auf 168/16 bit. Damit sind es 3,6%. Wenn beide falsch laufen, 1,8%. (Ich glaube, es kommt prinzipbedingt noch 1/2 16tel Bit dazu, das wären dann 3,3% bzw. 1,6%)

Wohlgemerkt, wenn die physikalischen Signal perfekt sind, 0 Jitter etc.

Bei 8-facher Abtastung und check bei 3,4,5 8tel kommt man rechnerisch auf 2/84 also 2,4 bzw. 1.2%.

Harald schrieb:

Mittels consteval errechnet der compiler den ubrr (ich schätze das meinst du mit Teiler) und stellt mittels static_assert sicher dass die gewünschte Baudrate zur Taktfrequenz passt.

Es geht ja immer um beide Seiten. Für den RPI sind die 961k "krum". Miss einfach per Oszi beide Seiten nach, wenn Du die Möglichkeit hast.

#7742443
Lesenswert?

Ob S. schrieb:

Axel S. schrieb:

Lastkapazität läge, wäre der Einfluß derselben auf die Schwingfrequenz des Quarzes doch eher marginal.

Kommt drauf an, wieviel neben dem Optimum er liegt.

Wenn die Schaltung derart auf Kante genäht ist, daß eine Änderung der Taktfrequenz um ein paar ppm den Unterschied zwischen "funktioniert" und "funktioniert nicht" ausmacht, dann ist sie ohnehin kaputt.

Damit RS-232 wegen Timingproblemen aussteigt, braucht man Abweichungen in der Größenordnung von 10%.

Nein. Eher 6%.

Ja toll. Das ist ja so viel besser! 10% zu 100ppm (und 100ppm sind schon unrealistisch hoch gegriffen) ist Faktor 1000. Und du willst mir jetzt damit kommen, daß es ja nur Faktor 600 ist?

Nein. Wenn trotz quarzstabilem Takt der UART spinnt, dann liegt das Problem woanders. Dann stimmt entweder der Realität nicht mit den Annahmen überein (Quarz falsch bedruckt?) oder in der Teilerberechnung stimmt was nicht. Ein beliebter Fehler ist /off-by-one/, das wurde ja schon gesagt. Auch auf den ersten Blick triviale Probleme, etwa GND Bounce sind möglich.

OP #7742467
Lesenswert?

Bruno V. schrieb:

Für den RPI sind die 961k "krum"

Du meinst die 921.6k, die sind gerade für ihn, und er kann sie. Das zeigt

  • Meine SW. Sie macht im realen Einsatz sehr wenig Gebrauch des uart. Es werden selten Nachrichten ausgetauscht, aber wenn es passiert soll es schnell, sicher und nachvollziehbar vonstatten gehen. Beim Senden stellt der rpi sicher dass das letzte byte der Meldung rausgegangen ist.

  • Andere Programme, wie das oben verlinkte. Das arbeitet etwas anders, es schreibt und liest 1K - Blöcke und wartet bis die Blöcke komplett über rx reinkommen.

Beide Programme zeigen mit steigender Baudrate steigende Fehlerraten. Unterstellen wir mal dass meine hw und sw mangelhaft sind, wir lassen sie außen vor und machen den Idiotentest.

Ich nehme also den originalen rpi zero 2W, getrennt vom board, bestromt über USB, setze einen jumper über rx/tx, und sende 5 Sekunden lang mit 921k Daten zu mir selbst.

Das klappt

/linux-serial-test -f -e -S -p /dev/ttyAMA0 -b 921600 -i5 -o5 Linux serial test app Flush RX buffer. Stopped transmitting. Stopped receiving. Terminating ... /dev/ttyAMA0: count for this session: rx=425994, tx=430115, rx err=0

mehrmals sogar. Doch früher oder später bekomme ich

./linux-serial-test -f -e -S -p /dev/ttyAMA0 -b 921600 -i5 -o5 Linux serial test app Flush RX buffer. Error, count: 12316, expected 1c, got 22 c 8 /dev/ttyAMA0: count for this session: rx=12315, tx=16427, rx err=1

(Etwas zusätzliche CPU - Last erhöht die Chancen)

Ich erwarte 1c, bekomme aber 22. Warum?

#7742497
Lesenswert?

Harald schrieb:

Doch früher oder später bekomme ich ./linux-serial-test -f -e -S -p /dev/ttyAMA0 -b 921600 -i5 -o5

[...]

Error, count: 12316, expected 1c, got 22 c 8 /dev/ttyAMA0: count for this session: rx=12315, tx=16427, rx err=1 (Etwas zusätzliche CPU - Last erhöht die Chancen)

Da fehlt die Zeile mit "overrun = 156". Aus der schließe ich, dass diese Kombination von Hardware, Betriebssystem und Programm schlicht und einfach zu langsam ist.

#7742530
Lesenswert?

Harald schrieb:

Für den RPI sind die 961k "krum"

Du meinst die 921.6k, die sind gerade für ihn, und er kann sie. Das zeigt

Der Witz war:

Harald schrieb:

sende [...] Daten zu mir selbst

Für jeden Controller ist jede Baudrate "perfekt", wenn er mit sich selbst spricht.

Du hast 3 Probleme:

  • 961k ist für den RPI krumm
  • 500k ist für Deinen Quarz krumm
  • Du verlierst Zeichen beim Empfang.

Nichts davon kannst Du im Loop testen, weil A) es lokal keine Baudratenfehler gibt und B) der Sender ggf. langsamer sendet (oder im Gegenteil die TX-Interrupts Rechenleistung klauen)

Wenn Du trotzdem im Loop Fehler hast, dann musst Du die vorab beheben. Bei mindestens doppelter Baudrate oder Auslastung!

Wenn Du die Baudraten nicht misst (kein Oszi), dann kommen mögliche Konfig-Fehler noch hinzu.

Im Übrigen spricht auch nix dagegen, einen glatten Quarz zu nehmen, solange die gewünschten Baudraten mit dem RPI matchen. Mitlesen am PC ist kein Problem: Seriell-USB-Umsetzer können z.B. 1MBaud perfekt. Und wenn sie z.B. 250k nicht können, nimmt man einen zweiten RPI, der auf einer Baudrate horcht und das auf einer geeigneten (höheren) rauspustet.

OP #7742996
Lesenswert?

Bruno V. schrieb:

Für jeden Controller ist jede Baudrate "perfekt", wenn er mit sich selbst spricht.

Das ist schon klar. Ich unterstelle dem rpi einfach mal dass auch 921k rauskommen wenn ich die verlange, ansonsten rechne ich mit einem Fehlercode beim Konfigurieren. Vor allem gehe ich davon aus dass Sende- und Empfangsrate identisch sind (unterschiedliche werden im code auch nicht angefordert).

Wie auch immer, ob nun 961k oder 921k6. Rpi und avr haben halten sich daran, siehe Oszillogramme. Ich habe also ein einziges Problem: ich bekomme sporadisch falsche Zeichen zum Lesen. Ich weiß nicht einmal ob sie falsch rausgehen oder beim Lesen kaputt gehen.

Angehängte Dateien:
#7743007
Lesenswert?

Harald schrieb:

Rpi und avr haben halten sich daran, siehe Oszillogramme.

Super. Die Werte sind perfekt.

Ich habe also ein einziges Problem: ich bekomme sporadisch falsche Zeichen zum Lesen. Ich weiß nicht einmal ob sie falsch rausgehen oder beim Lesen kaputt gehen.

"Nicht rausgehen" würde einen SW-Fehler bedeuten, da i.d.R. die Daten einer Nachricht komplett vorliegen und der TX-Fertig-Interrupt solange aktiv bleibt, bis das nächste Zeichen geholt oder errechnet worden ist und ins Sende-Register eingestellt wurde. Typischer Fehler wäre, wenn TX-Interrupt und Main gleichzeitig unveriegelt auf der Nachricht arbeiten.

"Nicht empfangen" passiert auch ohne SW-Fehler, einfach weil es an Rechenleistung fehlt (bei 1-Byte Fifo muss der Prozessor dauerhaft in weniger als 10µs reagieren). Allerdings gibt es i.d.R. Flags, die das melden. Framing-Error oder Overrun. Zähle die einfach mal mit.

OP #7743413
Lesenswert?

Bruno V. schrieb:

Mitlesen am PC ist kein Problem

Das ist überhaupt die Idee! Ich schließe ein SW - Problem, versursacht durch den Schreib / Lesewechsel am RPI nicht aus. Mit dem parallel geschalteten uart am PC habe ich eine neutrale Instanz die nur liest.

Der avr benutzt nur den Leseinterrupt. Ausgehende Nachrichten werden aus der main geschrieben. Die eingehenden werden vom Interrupt in eine queue transferiert, die wiederum von der main abgearbeitet wird. Das sollte so passen.

(Firma: 1984now) #7743440
Lesenswert?

Harald schrieb:

Der Meinung war ich bis gerade eben auch. Jetzt sehe ich das etwas anders. Tatsache ist, am Quarz steht ein stabiler Sinus mit 2V pp an, gemessen mit 1:10 Teiler am Tastkopf.

Das "Stottern" kannst du mit einem Oszi überhaupt nicht sehen. Jedenfalls nicht, wenn du am Quarz selber misst.

Wenn du einen µC hast, bei dem man den erzeugten Takt auch wieder ausleiten kann, dann wird das schon eher was, wenn du halt an diesem Ausgang misst. Ist mit einem einfachen Oszi aber auch hier nicht ganz einfach zu erkennen.

Der muß mindestens eine integrierte Frequenzmessung bieten, dann sieht man das an diesem Messwert. Auf dem grafischen Rechteck auf dem Display ist das allenfalls nur an einem "unnormalen" Jitter der Flanken zu bemerken, selbst wenn der Frequenzmesswert schon einen recht erheblichen Anteil "ausgefallener" Takte signalisiert. Man muss schon einige Erfahrung haben, um diesen Jitter zu sehen und korrekt einzuschätzen.

OP #7744060
Lesenswert?

Bruno V. schrieb:

961k ist für den RPI krumm

Bruno,

da ist doch was Wahres dran. Der rpi kann die 921k6 schon, aber diese rate scheint nicht seine bevorzugte zu sein. Wenn ich's recht verstehe (https://www.raspberrypi.org/app/uploads/2012/02/BCM2835-ARM-Peripherals.pdf) kann er gar nicht beliebige Takte erzeugen, sondern teilt auch nur einen Basistakt herunter. Der ist halt hoch genug (48MHz?) um bei niedrigen Raten kleinste Abweichungen zu erreichen. Bei > 115200 wird's dann zunehmend wackeliger. Ausgenommen die 500000, wie bestätigt durch den RC - getakteten avr. 750000 gehen auch. Darum habe ich den avr jetzt mit 12.0 MHz Quarz laufen, dann kriegt er diese Rate auch glatt hin. Zudem ist er innerhalb der spezifizierten Frequenz für 3V3.

Allerdings sind die 750000 nicht in der üblichen Baudrate - Liste vorhanden. Für das OS sind sie dann krumm. Zum Glück kann man jedoch (in Grenzen) über einen Umweg dann doch beliebige Raten setzen.

#7744308
Lesenswert?

Harald schrieb:

Bei > 115200 wird's dann zunehmend wackeliger.

Dein Oszi-Mitschnitt zeigt, dass alles OK ist. Von daher alles gut.

Am Ende braucht ein Uart für den Empfang einen Takt von 16xBaudrate, also z.B. 16MHz bei 1MBaud. (Für das Senden würde ein 1MHz-Takt völlig ausreichen)

Das "Zählen" der Takte erfolgt ab dem Takt, der die Startflanke erkannt hat, ich nenne den mal Takt 0 (T0). Das Startbit geht dann bis T15. Alle weiteren Bits werden dann in der Mitte abgetastet, meist 3 Mal, um "glitche" auszufiltern. Bit n wird also bei T(n * 16 + 6), T(n * 16 + 7) und T(n * 16 + 8) abgetastet (Mehrheit gewinnt).

tl;dr;: Für nMBaud brauchst Du einen Takt T von 16*n Herz. Dieser Takt T muss aus einem internen Takt erzeugt werden, meist aus dem Quarz (bzw. dessen Vervielfachern). Mit 48MHz-Clock kannst Du 1MBaud (16MHz-Takt) durch zählen bis 3 erzeugen (Baudraten-Register-Wert = 2). Bei 921KBaud (14.745MHz) bräuchtest Du "Fraktionale Teiler". D.H., manche Takte sind 3 Clockzyklen, manche 4. Das bietet nicht jeder µC.

Dein RPI sollte aber 1 GHz Clock haben, so dass sich 14.x MHz genügend genau "zählen" lassen.

OP #7744609
Lesenswert?

Bruno V. schrieb:

Das "Zählen" der Takte erfolgt ab dem Takt

OK, verstehe. Und das scannen des Starts erfolgt für jedes eingehende Paket, oder nur periodisch / pro "session" / burst / etc?

Bruno V. schrieb:

Dein RPI sollte aber 1 GHz Clock haben

Den kann man wohl konfigurieren. Ich habe ihn mal auf

init_uart_clock=12000000

gesetzt, das wäre perfekt für die 750000. Ich kann aber keinen Unterschied zum default feststellen.

Nebenbei habe ich noch einen banana pi zero 2W mit einem Arduino verdrahtet, prinzipiell genauso wie die rpi / avr - Kombination. Der Arduino läuft also mit 16MHz bei 3V3. Weit außerhalb der specs, aber ohne Ausfälle.

Gast #7744655
Lesenswert?

Harald schrieb:

Und das scannen des Starts erfolgt für jedes eingehende Paket, oder nur periodisch / pro "session" burst etc?

Ich kenne die Raspberry Pi Modelle nicht im Detail, aber normalerweise wird das Startbit für jedes Byte erneut gesucht. Deswegen hilft bei gestörten Leitungen die Einstellung "2 Stop-Bits senden" oft, auch wenn der Empfänger nur eins benötigt.

#7744663
Lesenswert?

Harald schrieb:

OK, verstehe. Und das scannen des Starts erfolgt für jedes eingehende Paket, oder nur periodisch / pro "session" burst etc?

Jedes Byte ist für sich abgeschlossen. Sonst wären 3% Baudratentoleranz nicht zu erreichen. Wenn Du es Dir aufzeichnest oder durchdenkst: Ab der Mitte des Stop-Bits muss der Empfänger wieder bereit sein, das nächste Startbit zu erkennen. Sonst dürfte der Sender nicht "back to back" senden.

zu 2 Stoppbits:

Die Einstellung von 2 Stopp-Bits hilft bei der Synchronisation, vor allem wenn der Empfänger "mitten im Datenstrom" eingeschaltet wird. Der Empfänger kann beliebige 1-0-Flanken nicht vom Startbit unterscheiden. Durch 2 aufeinanderfolgende 1-Bits am Ende (2 Stopp-Bits) ist der Empfänger spätestens nach ein paar Bytes synchronisiert.

10011001100

Ein positiver Effekt bei Baudraten-Abweichung ist nur dann gegeben, wenn die Uart-Einstellung 2 (oder 1.5) Stoppbits nur auf TX, nicht auf RX wirkt (was bei manchen der Fall ist).

Gast #7745022
Lesenswert?

Bruno V. schrieb:

Ein positiver Effekt bei Baudraten-Abweichung ist nur dann gegeben, wenn die Uart-Einstellung 2 (oder 1.5) Stoppbits nur auf TX, nicht auf RX wirkt (was bei manchen der Fall ist).

Ist das nicht generell immer so?

Bei AVR, STM32 und PC ist es jedenfalls so. Siehe

"The receiver ignores the second stop bit. An FE (frame error) will therefore only be detected in the cases where the first stop bit is zero." https://ww1.microchip.com/downloads/en/DeviceDoc/Atmel-7810-Automotive-Microcontrollers-ATmega328P_Datasheet.pdf

"The second stop bit is not checked for framing error. The RXNE flag is set at the end of the first stop bit" https://www.st.com/resource/en/reference_manual/rm0316-stm32f303xbcde-stm32f303x68-stm32f328x8-stm32f358xc-stm32f398xe-advanced-armbased-mcus-stmicroelectronics.pdf

"The Receiver checks the first Stop-bit only, regardless of the number of Stop bits selected." https://sys.cs.fau.de/extern/lehre/ws23/bs/uebung/aufgabe2/uart-8250a.pdf

#7745074
Lesenswert?

Harald schrieb:

Veit D. schrieb:

Wenn du sowieso 5V zur Verfügung hast, warum dann den AVR mit 3,3V versorgen?

Die gpio des rpi arbeiten mit 3.3V, ohne Pegelwandelung bringt man die beiden nicht zusammen wenn der avr mit 5V läuft.

Hallo,

ich melde mich nochmal deswegen. Man benötigt dafür nicht unbedingt eine separate Pegelwandlung. 3,3V vom RPI sind für den AVR sicheres High Signal. Die 5V vom AVR bringt man über einen Spannungsteiler an den RPI. Für USART ist das ausreichend, weil man 2 getrennte Leitungen für TX und RX hat.

Übrigens, wenn man "dauerhaft" ein 'U' sendet, erhält man auf der USART Leitung ein Taktsignal. Vielleicht hilft das bei der Fehlersuche.

Du kannst zum Test mit deiner Baudrate deutlich runtergehen, ob sich dann immer noch Zeichen verschlucken. Und lasse dir einmal auf beiden Controllern den Wert des eingestellten Baudratenregisters ausgeben und rechne das nach.

#7745093
Lesenswert?

Monk schrieb:

Ist das nicht generell immer so?

Hab ich auch immer gedacht. Leider hatten wir mindestens einen anderen. Muss ich morgen raussuchen.

Im Datenblatt ist es oft schwer zu finden, weil es nicht um die Auswertung geht, sondern um den Zeitpunkt, an dem der Receiver für ein neues Startbit bereit ist (in der Mitte des ersten Stoppbits).

OP #7745174
Lesenswert?

Veit D. schrieb:

Du kannst zum Test mit deiner Baudrate deutlich runtergehen, ob sich dann immer noch Zeichen verschlucken

Jetzt läuft der avr ja mit 12 MHz. Das reicht dicke für meine Zwecke, somit reichen die 3V3. Den Spannungsteiler kann ich nicht ohne weiteres probieren, weil tx und rx direkt verbunden sind um die Flanken sauber zu halten.

Ich glaube mittlerweile eher dass der rpi die Schwachstelle ist weil: * Die Fehlerrate mit steigender baudrate ansteigt * Die Fehlerrate mit steigender CPU - Last ansteigt * Ein OS im Betrieb ist, das kann nicht hexen * Die fifos der SBC auch nur 24 (rpi) bzw 64 (bpi) bytes gross sind

Auf dem rpi bin ich mit 350000 baud auf der sicheren Seite. Auch mit voll ausgelasteter CPU (vier Endlosschleifen per bash im Hintergrund) läuft das stundenlang fehlerfrei. Die vom OS gemeldeten "overrun" sind 0. Verdoppele ich auf 750000, so bewirkt zusätzliche CPU - Last oft overruns und potentielle Übertragungsfehler.

Mit dem banana pi sieht es ähnlich aus, der ist bei 500000 stabil, kann aber gar keine 1000000.

"Fehler" heißt hier also Versagen im Stresstest, der bezüglich Nachrichten - Anzahl und - Frequenz weitab praktischer Anforderungen ist. In Sachen CPU - Auslastung ist er u. U. gar nicht so extrem, für den Fall das der SBC auch als git - server etc. missbraucht wird.

#7745645
Lesenswert?

Hallo,

das bedeutet, wenn das Raspi OS bremst, das nur die Datenrichtung vom AVR zum Raspi Probleme bereitet. Vom Raspi zum AVR sollte mit jeder Baudrate funktionieren, nehme ich an.

Verwendest du die Desktop Version vom Raspi OS oder die ohne Desktop? Wenn mit Desktop, könntest du nochmal die Light ohne Desktop ausprobieren.

OP #7751919
Lesenswert?

Veit D. schrieb:

Hallo,

das bedeutet, wenn das Raspi OS bremst, das nur die Datenrichtung vom AVR zum Raspi Probleme bereitet. Vom Raspi zum AVR sollte mit jeder Baudrate funktionieren, nehme ich an.

Ja, soweit ich sagen kann ist der rpi das Nadelöhr. Und immer für Überraschung gut: Das bisherige Exemplar habe ich durch Unachtsamkeit geschrottet. Ein neues allerdings bestand mit gleichem Setup nicht einmal den CPU - Stresstest, ab einer gewissen Temperatur aufwärts brach das wifi zusammen. Ursache ist wohl eine zu niedrige interne Versorgungsspannung. Mit dem Eintrag over_voltage=2 in der /boot/config.txt klappts dann wieder...

In Sachen uart sieht es jetzt so aus: Der avr läuft quarzbetrieben mit 12 MHz@3V3. Das Quarzgehäuse habe ich auf Masse gelegt. Tatsächlich ist der uart leicht mit Taktstörungen aus dem Tritt zu bringen. Berühren des Quarzes ist vielleicht nur eine Möglichkeit davon und immerhin ist das wifi des rpi nicht so weit entfernt. Die Baudrate ist 750000 und somit eher unüblich. Nicht alle Terminal - Programme können sie. Die SW am rpi nutzt libc/termios2 um sie einzustellen. Siehe https://github.com/npat-efault/picocom.git Der eigentliche Trick ist, dem rpi nicht zu viel zuzumuten. Bei höheren Baudraten kommt der einfach nicht mehr nach, wenn er bei starker CPU - Last gleichzeitig Senden und Empfangen soll. Falls nötig muss der avr also eine kleine Pause nach dem Senden eines Paketes machen.

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