serial port (com port) senden und empfangen
-
Guten Morgen zusammen,
ich habe da mein "kleines" aber feines problem zurzeit. Und zwar wie der Titel schon sagt würde ich gern über den com port Daten senden und empfangen.
Ich habe hier alles durchsucht und auch reichlich gegooglet leider komm ich nicht wirklich zu was handfestemEs handelt sich um eine karte die einige Daten gespeichert hat und wenn ich an diese ein $ sende sendet die karte die daten über den com port.
Nur wie bewerkstellige ich das unter Windows Xp und am besten reinem Ansi C.der code den ich bisher gefunden und angepasst hab besteht lediglich aus reinem senden.
int main(void) { DCB dcb; DWORD iBytesWritten; unsigned char ucMsg = 0x24; // zu sendendes Zeichen (1) HANDLE hCom = CreateFile ("COM1", GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL); dcb.DCBlength = sizeof(DCB); // Laenge des Blockes MUSS gesetzt sein! GetCommState (hCom, &dcb); // COM-Einstellungen holen und aendern dcb.BaudRate = 9600; // Baudrate dcb.ByteSize = 8; // Datenbits dcb.Parity = NOPARITY; // Parität dcb.StopBits = ONESTOPBIT; // Stopbits SetCommState (hCom, &dcb); // COM-Einstellungen speichern CloseHandle (hCom); // COM1 schließen getch(); return 0; }
Könnt ihr mir vielleicht weiterhelfen? wie kann ich prüfen ob ich überhaupt eine verbdindung hab und wie könnt ich die daten empfangen?
danke im voraus
Gruß
Martin
-
soo also ich hab ma weiter getestet.. und bin bissl vorangekommen..
ich kann entweder senden oder lesen aber nicht beides, es geht auch nicht mit GENERIC_ALL, hat da jemand ne idee?hier der momentane code
#include <stdio.h> #include <conio.h> #include <windows.h> int main(void) { DCB dcb; DWORD iBytesWritten; DWORD iBytesReceived; char daten[10000]; int i; unsigned char ucMsg = 0x24; // zu sendendes Zeichen (1) HANDLE hCom = CreateFile ("COM1", GENERIC_WRITE, 0, NULL, OPEN_EXISTING, 0, NULL); dcb.DCBlength = sizeof(DCB); // Laenge des Blockes MUSS gesetzt sein! GetCommState (hCom, &dcb); // COM-Einstellungen holen und aendern dcb.BaudRate = 9600; // Baudrate dcb.ByteSize = 8; // Datenbits dcb.Parity = NOPARITY; // Parität dcb.StopBits = ONESTOPBIT; // Stopbits SetCommState (hCom, &dcb); // COM-Einstellungen speichern //----------------------------------------------------------------------------- i = WriteFile (hCom, &ucMsg, 1, &iBytesWritten, NULL); // Senden eines Bytes if (i == 0) { printf("\nfuck das hat wohl ncih geklappt\n\n"); } else { printf("\nPrima es geht ja doch!\n\n"); } CloseHandle (hCom); // COM1 schließen getch(); return 0; }
-
so sollte es gehen mit CreateFile:
HANDLE hcomm = CreateFile ("COM1", GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
v0id schrieb:
...am besten reinem Ansi C.
mit ansi-c probier:
FILE *f = fopen ("COM1:", "w+");
mit ansi-c kannste aber nicht die baudrate usw. einstellen
-
Danke Sehr, das hat mich auf jedenfall schon weiter gebracht.
nur hier mal wieder der ganze code, nurhab ich ein problem das ich gar nicht mehr versteh.
und zwar les ich die 50 zeichen ein.. das sind auf der karte deutlich mehr... jedoch hab ca. nach 15-20 zeichen immer ab da an nur noch leerzeichen.
es wirkt so als wenn die karte die daten zu langsam anliefern würde, jedoch stimmen die baud daten usw.
Woran könnte es noch liegen?code:
#include <stdio.h> #include <conio.h> #include <windows.h> int main(void) { DCB dcb; DWORD iBytesWritten; DWORD iBytesReceived; char daten[10000]; int i; HANDLE hCom2; unsigned char ucMsg = 0x24; // zu sendendes Zeichen (1) HANDLE hCom = CreateFile ("COM1", GENERIC_READ | GENERIC_WRITE, 0, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL); //---- hCom ---- dcb.DCBlength = sizeof(DCB); // Laenge des Blockes MUSS gesetzt sein! GetCommState (hCom, &dcb); // COM-Einstellungen holen und aendern dcb.BaudRate = 9600; // Baudrate dcb.ByteSize = 8; // Datenbits dcb.Parity = NOPARITY; // Parität dcb.StopBits = ONESTOPBIT; // Stopbits SetCommState (hCom, &dcb); // COM-Einstellungen speichern dcb.fRtsControl = RTS_CONTROL_HANDSHAKE; //----------------------------------------------------------------------------- i = WriteFile (hCom, &ucMsg, 1, &iBytesWritten, NULL); // Senden eines Bytes if (i == 0) { printf("\nfuck das hat wohl ncih geklappt\n\n"); } else { printf("\nPrima es geht ja doch!\n\n"); } //----------------------------------------------------------------------------- printf("\n\n\nhier text: "); i = ReadFile(hCom, daten, 50, &iBytesReceived, NULL); // Empfangen der Bytes i= 0; while (i != 50 ) { printf("%c", daten[i++]); } printf("ENDE"); if (i == 0) { printf("\nfuck das LESEN geht wohl nicht\n\n"); } else { printf("\nPrima DAT GEEEHT\n\n"); } CloseHandle (hCom); // COM1 (hCom) schließen //----------------------------------------------------------------------------- getch(); return 0; }
-
v0id schrieb:
while (i != 50 ) { printf("%c", daten[i++]); }
vielleicht so?
while (i < iBytesReceived) { printf("%c", daten[i++]); }
-
Hallo @all, ich bin neu hier!
unsigned char ucMsg = 0x24; // zu sendendes Zeichen (1)
1. Was bedeutet 0x24 ?
2. Kann ich hier auch normalen Text senden? Wie?
-
Dieser Thread wurde von Moderator/in c.rackwitz aus dem Forum ANSI C in das Forum WinAPI verschoben.
Im Zweifelsfall bitte auch folgende Hinweise beachten:
C/C++ Forum :: FAQ - Sonstiges :: Wohin mit meiner Frage?Dieses Posting wurde automatisch erzeugt.
-
Für serielle Kommunikation Rate ich zu fertigen Klasse, da es sich zwar trivial anhört, es aber nicht so ist...
http://www.codeproject.com/system/serial.asp
-
coolzero0001 schrieb:
Hallo @all, ich bin neu hier!
unsigned char ucMsg = 0x24; // zu sendendes Zeichen (1)
1. Was bedeutet 0x24 ?
2. Kann ich hier auch normalen Text senden? Wie?es ist " $ " zeichen, was gesendet wird
-
@m@ster, merzy!
Ich wollte mit dem "HyperTerm" das Zeichen einlesen, das geht nicht, da immer nur ein Prog. auf den Port zugreifen kann.
Oder gibt es doch eine möglichkeit dieses ("$") gesendete Bit zu empfangen?
-
das empfangen funktioniert doch über ReadFile() oder missverstehe ich Dich gerade?
Ich bekomm leider nur immernoch nicht den gesammten Datensatz, nur ab einer unbestimmten stelle Leerzeichen im Array
-
v0id schrieb:
Ich bekomm leider nur immernoch nicht den gesammten Datensatz, nur ab einer unbestimmten stelle Leerzeichen im Array
versuch's mit so einer funktion:
int COMM_Read (HANDLE hcomm) { DWORD commerr; COMSTAT comstat; DWORD bytes_read; BYTE the_byte; // sind daten da? ClearCommError (hcomm, &commerr, &comstat); if (comstat.cbInQue == 0) return -1; // noch nichts im buffer // mindestens 1 byte im buffer -> abholen ReadFile (hcomm, &the_byte, 1, &bytes_read, NULL); return (int)the_byte; }
die gibt entweder einen wert (das zeichen) zurück oder -1 wenn nichts empfangen wurde.
verwenden kannste die funktion dann so:
BYTE buffer[50]; int idx; ... // 50 bytes einlesen idx = 0; while (idx < 50) { int result = COMM_Read(hcomm); // das hcomm kommt von CreateFile if (result != -1) buffer[idx++] = (BYTE)result; } ...
btw: damit das ohne verzögerungen läuft, sollteste mit SetCommTimeouts() alles auf 0 setzen.
-
Den ganzen Thread hier könnten wir uns sparen, wenn man fertige Klassen verwenden würde...
http://www.codeproject.com/system/serial.asp
-
Jochen Kalmbach schrieb:
Den ganzen Thread hier könnten wir uns sparen, wenn man fertige Klassen verwenden würde...
der op hatte ursprünglich ins ansi-c forum geschrieben. ich gehe davon aus, dass er 'C' ohne ++ verwendet.
-
jap so schauts aus, die seite hatte ich auch bereits gefunden!
Aber Danke Dir @net und den restlichen Anderen natürlich auch, hat mir gut weitergeholfen.
hab zwar meine schleife noch nciht ganz sauber, quick&dirty halt aber viel mehr zeit dafür hab ich leider auch nicht.