Entwickler-Ecke

IO, XML und Registry - SerialPort: DataReceive-Event auf ein bestimmtes Zeichen


jodo63 - Fr 22.04.11 11:19
Titel: SerialPort: DataReceive-Event auf ein bestimmtes Zeichen
Hallo,

ich möchte in C# das Event "DataReceived" der seriellen Schnittstelle auf ein bestimmtes Zeichen auslösen, zB. wenn ein CR empfangen wird. Damit möchte ich erreichen, das ein Datenstream weder eine feste Länge haben muß noch das die serielle Schnittelle auf ein Timeout warten muß. Viele Geräte senden z.B. ein festes Protokollformat mit CR/LF oder ETX als Abschluß.

Wer hat sowas schonmal programmiert und kann mir ein paar Tips geben?

Gruß

Joachim


jaenicke - Fr 22.04.11 12:01

Hallo und :welcome:

Vorweg: Ich habe den seriellen Anschluss bisher nicht in C# benutzt, dafür schon oft in Delphi. Ich nehme nicht an, dass sich das besonders unterscheidet.

Dabei benutze ich entweder einen Thread, der auf Daten oder einen Abbruch wartet, oder ich lese im Event, dass Daten empfangen wurden, alle vorhandenen Daten aus und füge sie zu den bereits empfangenen Daten hinzu.

Für den ersten Fall gibt es in C# WaitHandle.WaitAny als Äquivalent zur API-Funktion WaitForMultipleObjects unter Windows. Damit kannst du einerseits auf den seriellen Anschluss und andererseits auf ein Abbruchevent warten, so dass du den Wartevorgang sauber beenden kannst.
Damit habe ich aber nicht so gute Erfahrungen gemacht. Theoretisch sollte es so gehen, praktisch kam manchmal nie ein Event vom seriellen Anschluss.

In beiden Fällen ist das Vorgehen danach identisch:
Wenn die Transmission komplett ist (ich also z.B. das Endzeichen gefunden habe oder die gewünschte Länge erreicht ist oder ...), löse ich ein internes Event aus, dem ich diese Daten mitgebe.

Wenn ich mit der Windows API arbeite, gibt es auch weitere Events, aber die scheint es unter C# nicht zu geben. Insofern ist die Analyse der empfangenen Daten und ein eigenes Event bei Erfolg denke ich die beste Variante.


Ralf Jansen - Fr 22.04.11 12:24

Ich würde auch gegen DataReceived plädieren und für einen eigenen Thread. In diesem Thread kannst du dann einfach die ReadTo [http://msdn.microsoft.com/de-de/library/system.io.ports.serialport.readto.aspx] benutzen um auf das passende Abschlusszeichen zu warten und den Buffer bis dahin auszulesen. Um nicht ewig zu warten einfach den ReadTimeout [http://msdn.microsoft.com/de-de/library/system.io.ports.serialport.readtimeout.aspx] passend setzen.


jodo63 - Fr 22.04.11 12:25

Hallo Sebastian,

danke für die Info. Die Methode ist die "Zufuß"-Methode. Ich dachte, es gibt vielleicht in der Klasse SerialPort bereits eine implementierte Methode die entsprechend nur parametiert werden braucht. Ähnlich der in LabWindows CVI, wo ich ein Receive Callback auf das Event RxChar (Any chararcters received) oder RxFlag (Termination charater received) parametrieren kann.

Gruß

Joachim


jodo63 - Fr 22.04.11 12:29

Hallo Ralf,

während ich die Antwort füe Sebastian geschrienben habe ist dein Beitrag eingegangen. Wie es aussieht werden ich wohl ein Verfahren ähnlich deines Vorschlages programmieren. Standartmäßig ist der Timerout max. 2 Zeichenlängen.

Danke und Gruß

Joachim