PingPong(wie im IRC) - Winsock - Wie umsetzen?
-
Hi,
ich habe folgendes Problem:Ich habe einen Server und einen Client, und der Server muss die Möglichkeit haben festzustellen, ob der Client noch verbunden ist, das muss auch in Spezialsituationen wie Stromausfall etc. funktionieren.
Ich habe daher gedacht ich könnte es so wie im IRC machen: Ping...Pong...
Die Frage ist: Wie setze ich das am Besten mit Winsock um?
Danke
PingPongMann
-
Stell die Frage konkreter, so kann man nicht vernünftig antworten.
-
Okay... Ich habe folgenden Code und möchte nun das besage PingPong programmieren. Wie muss ich den Code abändern?
Ich habe den Code der übersichthalber von c-worker.ch genommen, da mein Code inzwischen schon sehr lang ist. Ich werde dann das Prinzip übernehmen. Danke
#pragma comment( lib, "ws2_32.lib" ) #include <windows.h> #include <winsock2.h> // bei manchan compilern muss man nur windows.h includieren (zB VC++) #include <stdio.h> #define MAX_CLIENTS 10 int startWinsock(void) { WSADATA wsa; return WSAStartup(MAKEWORD(2,0),&wsa); } int main() { long rc; SOCKET acceptSocket; //SOCKET connectedSocket; SOCKADDR_IN addr; char buf[256]; char buf2[300]; // zusätzliche Variabeln FD_SET fdSet; SOCKET clients[MAX_CLIENTS]; int i; // Winsock starten rc=startWinsock(); if(rc!=0) { printf("Fehler: startWinsock, fehler code: %d\n",rc); return 1; } else { printf("Winsock gestartet!\n"); } // Socket erstellen acceptSocket=socket(AF_INET,SOCK_STREAM,0); if(acceptSocket==INVALID_SOCKET) { printf("Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n",WSAGetLastError()); return 1; } else { printf("Socket erstellt!\n"); } // Socket binden memset(&addr,0,sizeof(SOCKADDR_IN)); addr.sin_family=AF_INET; addr.sin_port=htons(12345); addr.sin_addr.s_addr=INADDR_ANY; // gewisse compiler brauchen hier ADDR_ANY rc=bind(acceptSocket,(SOCKADDR*)&addr,sizeof(SOCKADDR_IN)); if(rc==SOCKET_ERROR) { printf("Fehler: bind, fehler code: %d\n",WSAGetLastError()); return 1; } else { printf("Socket an port 12345 gebunden\n"); } // In den listen Modus rc=listen(acceptSocket,10); if(rc==SOCKET_ERROR) { printf("Fehler: listen, fehler code: %d\n",WSAGetLastError()); return 1; } else { printf("acceptSocket ist im listen Modus....\n"); } for(i=0;i<MAX_CLIENTS;i++) { clients[i]=INVALID_SOCKET; } while(1) { FD_ZERO(&fdSet); // Inhalt leeren FD_SET(acceptSocket,&fdSet); // Den Socket der verbindungen annimmt hinzufügen // alle gültigen client sockets hinzufügen (nur die die nicht INVALID_SOCKET sind) for(i=0;i<MAX_CLIENTS;i++) { if(clients[i]!=INVALID_SOCKET) { FD_SET(clients[i],&fdSet); } } rc=select(0,&fdSet,NULL,NULL,NULL); // nicht vergessen den ersten parameter bei anderen betriebssystem anzugeben if(rc==SOCKET_ERROR) { printf("Fehler: select, fehler code: %s\n",WSAGetLastError()); return 1; } // acceptSocket is im fd_set? => verbindung annehmen (sofern es platz hat) if(FD_ISSET(acceptSocket,&fdSet)) { // einen freien platz für den neuen client suchen, und die verbingung annehmen for(i=0;i<MAX_CLIENTS;i++) { if(clients[i]==INVALID_SOCKET) { clients[i]=accept(acceptSocket,NULL,NULL); printf("Neuen Client angenommen (%d)\n",i); break; } } } // prüfen wlecher client sockets im fd_set sind for(i=0;i<MAX_CLIENTS;i++) { if(clients[i]==INVALID_SOCKET) { continue; // ungültiger socket, d.h. kein verbunder client an dieser position im array } if(FD_ISSET(clients[i],&fdSet)) { rc=recv(clients[i],buf,256,0); // prüfen ob die verbindung geschlossen wurde oder ein fehler auftrat if(rc==0 || rc==SOCKET_ERROR) { printf("Client %d hat die Verbindung geschlossen\n",i); closesocket(clients[i]); // socket schliessen clients[i]=INVALID_SOCKET; // seinen platz wieder freigeben } else { buf[rc]='\0'; // daten ausgeben und eine antwort senden printf("Client %d hat folgendes gesandt: %s\n",i,buf); // antwort senden sprintf(buf2,"Du mich auch %s\n",buf); send(clients[i],buf2,(int)strlen(buf2),0); } } } } }
-
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
-
xXxXxXxXxXx schrieb:
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
Falsch, -100 Punkte.
-
^^ schrieb:
xXxXxXxXxXx schrieb:
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
Falsch, -100 Punkte.
Beweis mir das Gegenteil du Hochstapler!
-
du sendest dem client ein ping-paket, dessen inhalt und form du selbst bestimmst. meine empfehlung: die ping-kennung (z.b. als string "PING"), einen timecode (z.b. von GetTickCount()) und eine sequenznummer (beliebig, z.b. eine zufallszahl).
die sequenznummer dient als sicherheit, damit man dir nicht so einfach ein gefälschtes oder ungültiges pong unterschieben kann. wie du die generierst ist egal, der server muss sie sich nur merken bis das pong zurückkommt oder bis zum time-out.diese daten schickst du an den client. der tut nichts anderes als aus dem "PING" ein "PONG" zu machen und das ganze wieder zurückzuschicken.
der server merkt sich alle gesendeten pings in einer liste. erhält er ein passendes pong, prüft er die sequenznummer. stimmt sie überein, ist der client noch am leben. das ping wird aus der liste enfernt. aus dem timecode kannst du dir dann die signallaufzeit ausrechnen.
kommt innerhalb von 30 (oder x) sekunden kein pong, ist der client tot.
-
xXxXxXxXxXx schrieb:
^^ schrieb:
xXxXxXxXxXx schrieb:
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
Falsch, -100 Punkte.
Beweis mir das Gegenteil du Hochstapler!
Da hab ich keine Lust zu, da es offensichtlich ist das es geht.^^
-
vorschlag schrieb:
du sendest dem client ein ping-paket, dessen inhalt und form du selbst bestimmst. meine empfehlung: die ping-kennung (z.b. als string "PING"), einen timecode (z.b. von GetTickCount()) und eine sequenznummer (beliebig, z.b. eine zufallszahl).
die sequenznummer dient als sicherheit, damit man dir nicht so einfach ein gefälschtes oder ungültiges pong unterschieben kann. wie du die generierst ist egal, der server muss sie sich nur merken bis das pong zurückkommt oder bis zum time-out.diese daten schickst du an den client. der tut nichts anderes als aus dem "PING" ein "PONG" zu machen und das ganze wieder zurückzuschicken.
der server merkt sich alle gesendeten pings in einer liste. erhält er ein passendes pong, prüft er die sequenznummer. stimmt sie überein, ist der client noch am leben. das ping wird aus der liste enfernt. aus dem timecode kannst du dir dann die signallaufzeit ausrechnen.
kommt innerhalb von 30 (oder x) sekunden kein pong, ist der client tot.Das hatte ich auch vor, es hinkt jedoch an der kompletten Umsetzung. Genau aus dem Grund bitte ich auch um Code. Ich hab bisher immer aus Code gelernt, jedoch fehlt mir für diesen konkreten Fall ein Beispielcode.
Danke!
-
^^ schrieb:
xXxXxXxXxXx schrieb:
^^ schrieb:
xXxXxXxXxXx schrieb:
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
Falsch, -100 Punkte.
Beweis mir das Gegenteil du Hochstapler!
Da hab ich keine Lust zu, da es offensichtlich ist das es geht.^^
Sieht schlecht für dich aus^^
-
Klaus^^^^ schrieb:
^^ schrieb:
xXxXxXxXxXx schrieb:
^^ schrieb:
xXxXxXxXxXx schrieb:
Sowas lässt sich mit Winsock leider nicht realisieren, sonst hättest du auch schon eine Antwort erhalten.
Falsch, -100 Punkte.
Beweis mir das Gegenteil du Hochstapler!
Da hab ich keine Lust zu, da es offensichtlich ist das es geht.^^
Sieht schlecht für dich aus^^
^^ roflé