Hallo zusammen,
ich habe aktuell folgedes Problem:
Ich sende von einem Atmega8 aus 2 Byte per RS485 an eine SPS. Es kommen
auch 2 Byte an, jedoch ist nur der Inhalt des ersten Bytes korrekt
übertragen. Im 2. sind falsche Werte enthalten.
Die Baudrate ist 19200.
Auf der Sendeseite wird ein Atmega8 mit einem MAX485 verwendet. Baudrate
ist dort ebenfalls 19200, interner Oszillator 8MHZ.
Was könnte dass sein?
Hat jemand eine Idee?
> Hat jemand eine Idee?
- Was passiert wenn du mehr als zwei schickst? -> Ist immer nur das
letzte Byte Müll? In dem Fall lass die Richtungsumschaltung noch etwas
länger als Treiber arbeiten, nicht direkt nach dem Stopbit auf Empfänger
schalten
- Wie sehen die Signale vor/hinter deinem RS485-Treiber aus?
- Wie groß ist der Potentialunterschied zwischen der SPS und deiner
Schaltung?
- Was passiert bei 4800/9600 Baud?
Ralf
Erstmal Verkabelung prüfen. Hast du neben den Signalleitungen A und B
auch die Masseleitung angeschlossen? Dies wird häufig vernachlässigt und
kann gravierende Übertragungsstörungen nach sich ziehen (abhängig von
der verwendeten Hardware).
Wenn du dies bejahen kannst, würde ich an deiner Stelle mir die Signal
(A zu GND, B zu GND) mal mit einem Scope anschauen und prüfen, ob die
(gewollten) Bytes auch wirklich gesendet werden... Bei 19200 Baud und
nur 2 Bytes geht das wohl noch ganz bequem.
Gruß Thomas
Wird der DE (Driver Enable) Pin eventuell zu früh losgelassen? Falls
deine Sendefunktion Interrupts verwendet, sollte DE erst beim 'Transmit
Complete' Interrupt umgeschaltet werden und nicht schon im 'Data
Register Empty' Interrupt.
Also als Abschlusswiderstand verwende ich jeweils 110 Ohm, hatte leider
keine 120er mehr. Das dürfte aber nichts machen oder?
Die Leitungslänge beträgt aber aktuell auch gerade mal 20 cm.
Ich habe verschiedene Baudraten getestet. Es is immer das selbe, das 1.
Byte passt und das 2. ist fehlerhaft. Ich habe es auch mit verschiedenen
Werten der Bytes getestet. Aber immer das selbe.
Ich verwende aktuell den Sendeinterrupt für die Richtungsumschaltung und
habe sogar noch eine Verzögerung von 50ms eingebaut, nachdem der
Interrupt ausgelöst wurde wird noch gewartet bevor das Senden
umgeschaltet. Oder sind 50ms immer noch zu kurz? Normal müsste das doch
mehr als ausreichend sein oder?
Ich werde nun nochmals Testen was passiert wenn ich mehr als 2 Byte
sende.
Wie kann ich denn den Oszillator richtig kalibrieren? Ich verwende den
Internen Ozillator mit 8MHZ. Quarzfrequenz ist ebenfalls auf 8MHz
eingestellt.
Peter B. schrieb:> Wie kann ich denn den Oszillator richtig kalibrieren? Ich verwende den> Internen Ozillator mit 8MHZ.
Das ist im Datenblatt unter Calibrated Internal RC Oscillator
beschrieben.
Der interne Oszillator kann deutlich von der Nennfrequenz abweichen. Da
aber Byte 1 richtig übertragen wird, scheint der nicht ganz daneben zu
liegen.
Guck dir das Timing mit einem Oszi an, das spart viel Rätselraterei
Peter B. schrieb:> Ich verwende aktuell den Sendeinterrupt für die Richtungsumschaltung [...]
Welchen "Sendeinterrupt"? Wie hardy schon schrieb, darf DE erst beim
'Transmit Complete' Interrupt umgeschaltet werden und nicht schon im
'Data Register Empty' Interrupt.
> und habe sogar noch eine Verzögerung von 50ms eingebaut, [...]
Solche Verzögerungen haben etwas magisches und zeugen meist davon, dass
jemand etwas nicht richtig verstanden hat. Nicht machen. Stattdessen
richtig machen.
> nachdem der Interrupt ausgelöst wurde wird noch gewartet [...]
Nochmal: nachdem WELCHER Interrupt ausgelöst wurde?
> Ich verwende den Internen Ozillator mit 8MHZ.
Es gibt 2 Möglichkeiten:
1. Nur das letzte Byte geht kaputt. Dann liegts an Deiner
Richtungsumschaltung
2. Dein Oszillator arbeitet zu ungenau für 19200 Bd.
Gruß,
Frank
Mal mit dem Scope nachmessen. Ob alle bits durchkommen sieht man
schnell. Das Timing ist kaum machbr. Denn die 2% sieht man mit einem
einfachen scope nicht. allenfalls mit einem MSO und tiefem Speicher.
Nach 100Bytes.
Peter B. schrieb:> Auf der Sendeseite wird ein Atmega8 mit einem MAX485 verwendet. Baudrate> ist dort ebenfalls 19200, interner Oszillator 8MHZ.
Wiederholung: Interner Oszillator ist Mist.
Meine Erfahrung: Nach dem Auslösen des TXC-Interrupts muss bis zur
Richtungsumschaltung des MAX485 noch eine kurze Pause sein. Da reichen
sicher ein paar Bitlängen. Es braucht zwischen Auswertung des Interrupt
und der Richtungsumschaltung nur etwas Code zu sein. Also nicht in der
ISR umschalten. Möglicherweise sind noch nicht alle Bits aus dem MAX
raus.
>Möglicherweise sind noch nicht alle Bits aus dem MAX raus.
Diese Formulierung hat in der E-Technik nix zu suchen. Es läßt sich doch
feststellen, wann das Senden beendet ist. Dann erst die Richtung des MAX
umschalten. Zeitverzögerungen sind der gleiche Mist.
slow schrieb:> Diese Formulierung hat in der E-Technik nix zu suchen.
Das kann ich mir vorstellen.
> Es läßt sich doch feststellen, wann das Senden beendet ist.
Aber eben nicht per Software. Wenn das letzte Bit aus dem Mega raus ist,
habe ich den Eindruck, dass es aber aus dem MAX noch nicht raus ist. Ab
wann ist es jetzt "gestattet" die Richtung umzuschalten? Da habe ich im
Datenblatt nichts gefunden. Eventuell reicht die Umschaltverzögerung ja
aus bzw. der MAX wartet mit Umschalten selbst bis alles gesendet ist
(kann eigentlich nicht sein). Zumindest hatte ich den gleichen Effekt
und es damit gelöst: In ISR Flag setzen -> in main-loop auswerten ->
Richtung umschalten.
Hi
>Aber eben nicht per Software. Wenn das letzte Bit aus dem Mega raus ist,>habe ich den Eindruck, dass es aber aus dem MAX noch nicht raus ist.
Der Max485 hat eine typische Verzögerungszeit Eingang-Ausgang von 30ns.
Ein Controllerbefehl dauert bei 8MHz 125ns. Auch der Einsprung in eine
Interruptroutine braucht mehrere Takte. Die Bits sind also schneller aus
dem Max raus, als der Controller reagieren kann.
MfG Spess
Ok ich habe gerade gesehen, dass der µC von der Software mit &HAE
kalibriert wird. Macht dass denn einen Sinn bei einer Oszillation von
8MHz und 18299 Baud?
Oktav Oschi schrieb:> Wenn man das TxComplete als Interrupt nimmt, dann wird das Stopbit> abgeschnitten. Wenn das nicht erwuenscht ist, muss man einen Timer> nehmen.
Könnte man den Sender auf 2 Stopbits einstellen und damit eine Bitzeit
gewinnen, wenn der Empfänger nur eins braucht?
MfG Klaus
Hi
>Wenn man das TxComplete als Interrupt nimmt, dann wird das Stopbit>abgeschnitten. Wenn das nicht erwuenscht ist, muss man einen Timer>nehmen.
Blödsinn. TXC wird nach den Stoppbits gesetzt.
MfG Spess
Oktav Oschi schrieb:> Wenn man das TxComplete als Interrupt nimmt, dann wird das Stopbit> abgeschnitten.
Bist Du Dir da wirklich sicher?
Aus der ATMEL-Doku für z.B. Atmega168:
• Bit 6 - TXCn: USART Transmit Complete
This flag bit is set when the entire frame in the Transmit Shift
Register has been shifted out and there are no new data currently
present in the transmit buffer (UDRn). The TXCn Flag bit is
automatically cleared when a transmit complete interrupt is executed, or
it can be cleared by writing a one to its bit location. The TXCn Flag
can generate a Transmit Complete interrupt (see description of the
TXCIEn bit).
Und weiter:
The Transmit Complete (TXCn) Flag bit is set one when the entire frame
in the Transmit Shift Register has been shifted out and there are no new
data currently present in the transmit buffer. The TXCn Flag bit is
automatically cleared when a transmit complete interrupt is executed, or
it can be cleared by writing a one to its bit location. The TXCn Flag is
useful in half-duplex communication interfaces (like the RS-485
standard), where a transmitting application must enter receive mode and
free the communication bus immediately after completing the
transmission.
Für mich ist ein kompletter "Frame" erst dann gesendet, wenn auch das
Stop-Bit raus ist. Ich benutze jedenfalls auch die Richtungsumschaltung
bei RS485-Anwendungen aus dem TXC-Interrupt heraus und hatte damit noch
nie Probleme.
spess53 schrieb:> Der Max485 hat eine typische Verzögerungszeit Eingang-Ausgang von 30ns.
Ich hab' mir beim Datenblatt-Lesen noch mal Mühe gegeben ;-) ...
10..60ns
Da kann eigentlich nichts passieren!
Frank M. schrieb:> Ich benutze jedenfalls auch die Richtungsumschaltung> bei RS485-Anwendungen aus dem TXC-Interrupt heraus und hatte damit noch> nie Probleme.
Trotzdem: Ich hatte sie, deshalb:
Ralf G. schrieb:> In ISR Flag setzen -> in main-loop auswerten ->> Richtung umschalten.
@ Frank M. (ukw) Benutzerseite
>Für mich ist ein kompletter "Frame" erst dann gesendet, wenn auch das>Stop-Bit raus ist. Ich benutze jedenfalls auch die Richtungsumschaltung>bei RS485-Anwendungen aus dem TXC-Interrupt heraus und hatte damit noch>nie Probleme.
Das ist auch so. Zumindest bei den AVRs. Bei den PICs ist es teilweise
NICHT so, da wird das STOP-Bit abgeschnitten, wenn man nicht per
Software wartet.
MFG
Falk
Auch wenn der kalibriert ist ist die Frequenz vom internen RC stark
Spannungs und auch leicht Temperaturabhängig. Am besten Kalibriert man
immer bei Verbindungsaufbau mit dem Rechner. Und man kalibriert sich am
besten mit dem Quarz des PCs. Man läßt den PC z.B. das ASCII Zeichen "U"
Senden. dies ist Binär eine Folge von 0en und 1en auf der Seriellen
Schnittstelle. Mißt man nun im µC per Software die Zeit für einen
Bitwechsel hat man eine Referenzzeit die vom Quarz des PCs abgeleitet
ist. Damit kann man nun den passenden Baudratendivisor oder den internen
RC.Osz. einstellen.
Oktav Oschi schrieb:> Das Timing ist kaum machbr. Denn die 2% sieht man mit einem> einfachen scope nicht.
Es geht nicht darum, die 2% Frequenzabweichung absolut zu sehen, sondern
festzustellen, ob die gesamte Länge eines seriell übertragenen Bytes bei
Sendung von beiden Seiten auf deutlich besser als eine halbe Bitdauer
gleich ist. Und das sollte mit jedem Scope gehen, wenn der Trigger
steht.