Hi,
ich arbeite momentan an einem CAN-Bootloader, bei dem ich momentan an
einem Problem mit der seriellen Verbindung hänge.
Ich verwende einen atmega168 in Kombination mit einem MCP2515 um die
Daten auf den CAN-Bus zu schreiben. Der atmega nimmt dabei die Daten
über UART vom PC entgegen und legt sie momentan noch byte-weise auf den
Bus, wo sie ein anderer atmega32 empfängt und dann später als Bootloader
in seinen Flash schreiben soll.
Das übertragen funktioniert momentan auch problemlos. Ich hab den
atmega32 testweise seine empfangenen Daten über UART ausgeben lassen und
es treten keine Fehler auf. Als Testdaten benutze ich ein .hex file, da
dieses ja auch später übertragen werden soll.
Für das spätere Übertragen möchte ich immer 8 byte über UART vom PC
einlesen und diese über den CAN-Bus weiter reichen und eine Bestätigung
des Empfängers auf dem CAN-Bus abwarten. Um einen Buffer Overlow beim
Empfänger der Daten über UART zu vermeiden möchte ich diesen mittels
Software Flow Control über das Zeichen 0x13 stoppen und nach der
Bestätigung mit 0x11 fortsetzen.
Um das ganze erstmal so zu testen möchte ich die über UART empfangenen
Daten direkt wieder über UART an den PC zurücksenden. Ich benutze in
beide Richtungen einen Buffer.
Mein eigentliches Problem ist jetzt jedoch, dass trotz des XOFF Bytes
immer noch weiter gesendet wird. Zum senden verwende ich am PC (linux)
das Programm Minicom mit eingeschaltetem Software Flow Control.
Ich kann mir leider nicht erklären warum das geschieht. Es werden keine
Binärdaten übertragen, wo XON enthalten sein könnte, da ich minicom
extra auf ASCII eingestellt hab.
Ich hab das ganze auch mittels
Probiert. Leider bei beiden das selbe Ergebniss, der Empfangspuffer
läuft nach kürzester Zeit über, da der Sendepuffer wohl nicht mit dem
schreiben nach kommt.
Da ich mich nicht als Profi der Materie bezeichnen würde, kann ich
leider auch nicht ausschließen, dass es vielleicht auch ein
grundlegender Fehler ist. Ich hab meinen Code mal in den Anhang gepackt.
Dabei handelt es sich um das eigentliche Programm zum Empfangen (Main.c)
und die Implementierung der UART Kommunikation (UART.*).
Ich bin Softwaretechnisch auch für andere Vorschläge offen, wie ich die
Daten vom Computer per UART an den atmega geschickt bekomme. Die
Software sollte nur unter Linux verfügbar sein.
Als letztes vielleicht noch kurz zur Hardware. Da mein PC keine
seriellen Anschlüsse hat verwende ich ein mySmartUSB bei einer Baudrate
von 9600. Da die Kommunikation bei nicht zeitkritischen Sachen
fehlerfrei funktioniert, sollte das glaub ich als Fehlerquelle
auszuschließen sein.
Gruß,
toti
Hört der Sender (PC) gar nicht auf zu senden oder hört er erst auf, wenn
der Buffer schon übergelaufen ist?
Ansonsten lege ich bei solchen Geräten die Baudrate immer so, daß ich
die Daten mit Sicherheit verarbeiten kann.
Gruß
Jobst
Hi,
das senden endet gar nicht. Der buffer läuft über und sobald wieder
etwas frei ist im buffer läd er wieder rein und läuft danach wieder
über. Das XOFF wird also nicht zu spät erkannt sondern scheinbar gar
nicht.
Das mit der Baudrate wäre natürlich eine Möglichkeit aber ich würde dem
Problem gerne auf den grund gehen. Das ganze muss ja am ende auf den
can-bus geschrieben werden und dann in den Flash geschrieben werden und
wenn ich dabei den datenfluss kontrollieren kann wäre das wohl schon
besser.
Gruß,
Toti
Torsten W. schrieb:> stty -F /dev/ttyUSB0 9600 cs8 -cstopb -parenb ixon ixoff
Hallo Torsten,
nach obiger Zeile vermute ich, dass du über USB -> seriell Adapter die
Daten am PC ausgibst.
Bei einem USB -> seriell Adapter ist der XON/XOFF Handshake (wie auch
RTS/CTS) Sache genau dieses Adapters.
Mal einen von einer anderen Firma verwenden, vielleicht kann deiner das
nicht !!???
Hi,
also als USB<->UART Schnittstelle wird beim MySmartUSB mk2.11 ein CP2102
von Silicon Labs verwendet. Der sollte laut Datenblatt eigentlich
Software Handshaking unterstützen.
Leider bietet das MySmartUSB nicht viele Informationen zum Thema
Pinbelegung. Im Datenblatt wird zwar an einer Stelle geschrieben, dass
es UART mittels Hardware Handshake unterstützt, aber an keiner Stelle
wird beschrieben wo die Anschlüsse für CTS und RTS sind, weswegen ich
die Möglichkeit des Hardware Handshakes erst mal ganz außen vor gelassen
hab.
Noch bedauerlicher ist aber, dass es noch nicht mal einen Schaltplan im
Internet zu finden gibt (könnte natürlich auch an meiner Unfähigkeit
beim Suchen liegen).
Glücklicherweise lassen sich die Leiterbahnen vom CP2102 aber gut
verfolgen und daher die PINS für CTS und RTS ausfindig machen.
Per Hardware Handshaking funktioniert der Flow Control ohne Probleme,
wodurch mein Problem nun im Grunde gelöst ist und ich wohl noch besser
bedient bin als mit Software Flow Control.
Ich würde mich aber trotzdem freuen wenn jemand noch eine Idee hätte,
warum es per XON/XOFF nicht funktioniert. Da der Controller es ja
eigentlich unterstützt würde mich das sehr interessieren.
Vielen dank auf jeden Fall für die Antworten bis jetzt.
Gruß,
toti
Ohne mir den Rest jetzt näher angeschaut zu haben:
Du darfst nur ixon setzen, nicht auch noch ixoff. Letzteres hat unter
Unix/Linux eine ganz andere Bedeutung, siehe auch "man stty".
Auszug:
[-]ixoff
enable sending of start/stop characters
[-]ixon
enable XON/XOFF flow control
Gruß,
Frank
Hi,
ich hab es sowohl mit als auch ohne -ixoff probiert. Ohne Erfolg. Mit
Minicom hat es ja auch nicht funktioniert, da wird es separat
eingestellt.
Gruß,
toti
Rolle schrieb:> Bei einem USB -> seriell Adapter ist der XON/XOFF Handshake (...)> Sache genau dieses Adapters.
Eigentlich nicht, der sollte die Handshake-Bytes einfach nur weiter
senden.
Einem
1
cat output.hex > /dev/ttyUSB0
ist es allerdings sowieso völlig egal ob da was über die Leitung
reinkommt oder nicht, XON/XOFF kann man damit vergessen. Minicom sollte
das allerdings können.
Wenn ich mir aber die obige Software ansehe, dann wird zwar nach jedem
empfangenen Byte ein XOFF zurück gesendet (allerdings auch erst nach dem
Übertragen via CAN), anschließend dann das empfangene Byte und dann
direkt danach aber auch wieder ein XON. Minicom dürfte also die meiste
Zeit den XON-Zustand sehen und frisch und fröhlich weiter senden. Das
Senden eines XOFF heißt dazu noch lange nicht, das dann keine Daten mehr
ankommen! Wenn das XOFF irgendwann mal beim Terminalprogramm ankommt,
sollte dieses zwar keine weiteren Daten mehr senden, alles was sich aber
z.B. noch im FIFO des auf dem MB des PC implementierten UART befindet
geht erstmal trotzdem über die Leitung. Und da wie schon gesagt die
obige Software mehr oder wenige direkt nach dem XOFF wieder ein XON
sendet haut dann auch das Teminalprogramm diesen FIFO erstmal wieder
komplett voll. Kein Wunder, daß da die Buffer überlaufen. Zumal während
der Verarbeitung eines einzigen Bytes (über CAN senden, XOFF+Byte+XON
über UART senden) mindestens schon die nächsten 3 Bytes empfangen und im
Receivebuffer abgelegt wurden.
Mittels XON/XOFF einem PC+beliebigem Terminalprogramm beibringen zu
wollen nur 8 Bytes zu senden und dann zu warten ist nahezu unmöglich. So
etwas geht maximal via Hardware-Handshake oder spezieller Software, die
von sich aus nach 8 Bytes wartet.
Via XON/XOFF könnte höchstens sowas in der Art gehen:
1
// ...
2
uart_putc_buffert(XOFF);
3
while(1==1){
4
// ...
5
if(rec&UART_NO_DATA){
6
uart_putc_buffert(XON);
7
uart_putc_buffert(XOFF);
8
}elseif(rec&UART_BUFFER_OVERFLOW){
9
sendUSART("Buffer Overflow!\n\r");
10
}else{
11
unsignedchartmp=((unsignedchar)rec);
12
write_message_to_can(0b1,1,&tmp);
13
uart_putc_buffert((unsignedchar)rec);
14
}
15
}
und dann hoffen/beten, daß die 64 Byte Receivebuffer auf dem AVR
ausreichen.
Hi,
bezüglich der Unterstützung des Adapters bin ich eigentlich auch immer
davon ausgegangen, dass das wie der Name schon sagt, eine Software Sache
ist und das Terminalprogramm für das erkennen der XOFF/XON Zeichen
zuständig ist.
Um die Funktionalität des Software Handshakes generell zu testen hab ich
Testweise mal einen delay_ms(2000); hinter den Befehl zum Senden von
XOFF gepackt. Das sollte zwar das überlaufen des Buffers wie du
beschrieben hast nicht verhindern, aber zumindest sollte Minicom dann ja
knapp zwei Sekunden das Senden pausieren, bis nach dem delay wieder das
XON gesendet wird. Leider hat auch das nicht funktioniert. Minicom hat
einfach weiter gesendet.
Gruß,
toti