WinSock2: Problem mit Accept-Socket...
-
Hi,
ich erstelle nach dem Beispiel von der MSDN einen Accept-Socket. Bei mir sieht das so aus:
addrinfo Hints, *pRes = NULL; ::memset(&Hints, 0, sizeof(addrinfo)); Hints.ai_family = AF_INET; Hints.ai_socktype = SOCK_STREAM; Hints.ai_protocol = IPPROTO_TCP; Hints.ai_flags = AI_PASSIVE; if (::getaddrinfo(NULL, sPort.c_str(), &Hints, &pRes) != 0) {} if ((Comm::Socket = ::socket(pRes->ai_family, pRes->ai_socktype, pRes->ai_protocol)) == INVALID_SOCKET) {} if (::bind(Comm::Socket, pRes->ai_addr, static_cast<int>(pRes->ai_addrlen)) != 0) {} ::freeaddrinfo(pRes);Wenn ich dann "listen(...)" aufrufe, versucht der Server sofort (hab mit Timestamps geschaut) eine Verbindung aufzubauen, obwohl ich noch keinen Client darauf angesetzt habe. Ich hab verschiedenste Ports ausprobiert, bei allen ist es das gleiche. Ich hab auch schon meinen Rechner vom INet getrennt...
Wenn der Server dann versucht einen Socket mit "accept(...)" zu erstellen, hat dieser den Wert "INVALID_SOCKET".Die Variante von Codeproject funktioniert bei mir nicht. Dort schlägt "bind()" mit Fehler 10038 (von WSAGetLastError()) fehl.
Hat jemand ne Idee, woran es liegen oder wie ich die Sache angehen könnte? Vielleicht bin ich ja auch einfach betriebsblind und seh meinen Fehler nicht.

Thx, Maffe
-
Der Server baut nie bei "listen" eine Verbindung auf.... er horcht vielleicht mal, aber Vebinden tut sich der Client...
-
Gut, Fehler meiner Seite. Der Server versucht sofort nach Aufruf des "listen(...)" mit "accept(...)" eine angefragte Verbindung aufzubauen, obwohl ich noch keinen Client drauf angesetzt habe.

-
hä?
-
Was liefert "listen" zurück?
Welchen Port nimmst Du denn?
Zieh doch mal das Netzwerkabel...
-
"listen()" liefert 0.
Der Port ist 24837. Aber ich hab's auch schon mit 12000 und beliebigen anderen 5-stelligen Ports versucht. Hab kein Netzwerkkabel drin. Und die WLAN-Karte hatte ich schon deaktiviert, was zu keiner Veränderung führt.
-
poste mal ein vollständigen quelltext
-
Hmm und was soll das bringen? Ich mach dann nur noch in nem Thread:
if (::listen(Comm::Socket, MAX_CLIENTS) != 0) //#define MAX_CLIENTS 10 {} SOCKET ClientSock; ClientSock = ::accept(Comm::Socket, NULL, NULL); if (ClientSock == INVALID_SOCKET) {}
-
Bist Du *ganz* sicher, das "listen" 0 liefert??? Kann ich mir eigentlich nicht vorstellen...
Was noch aus der Doku zu beachten ist:
If listen is called on an already listening socket, it will return success without changing the backlog.
Du rufst nicht zufällig das "listen" zweimal auf?
-
Nachdem du die Frage aufgeworfen hast, hab ich nochmal den Debugger drüber gejagt...und ja ich bin mir sicher.

Aber erklären kann ich's mir auch nicht.Wenn ich bei "accept(...)" eine Auswertung der From-Werte mache:
sockaddr_in From; int FromLen = sizeof(From); ::memset (&From, 0, sizeof(From)); SOCKET ClientSock = INVALID_SOCKET; ClientSock = ::accept(Comm::Socket, (sockaddr*)&From, &FromLen);stehen auch unsinnige Werte in "From":
From.sin_family = 0
From.sin_port = 0
FromLen = 16[Edit]
Jochen Kalmbach schrieb:
Du rufst nicht zufällig das "listen" zweimal auf?
Nö eigentlich nicht. Der Ablauf ist ja prinzipiell so, dass der Server mit dem Accept-Socket erstellt wird. Wenn die Initialisierung korrekt abgelaufen ist, wird der Thread mit dem "listen()" gestartet.
[/Edit]
-
Hmm und was soll das bringen?
Wenn der Fehler auch bei mir kommt kann ich ihn dir beheben

-
Gut das seh ich ein.
Der komplette Quelltext wäre ein bisschen viel hier, deswegen hab ich wirklich nur die WinSock-Sachen reingeschrieben.
-
Und ein neues Projekt anlegen wo nur die WinSock Sachen drin sind und das den Fehler zeigt willst du nicht?

-
Doch mach ich grad. Vielleicht liegt's ja am Thread, aber das kann ich mir eigentlich nicht vorstellen.
-
#include <Winsock2.h> #include <Windows.h> #include <ws2tcpip.h> #include <iphlpapi.h> #include <conio.h> #include <iostream> using namespace std; #define DEF_PORT "24837" int main (const int argc, const char** argv) { addrinfo *pRes = NULL; addrinfo Hints; ::memset(&Hints, 0, sizeof(addrinfo)); Hints.ai_family = AF_INET; Hints.ai_socktype = SOCK_STREAM; Hints.ai_protocol = IPPROTO_TCP; Hints.ai_flags = AI_PASSIVE; int iRet = 0; if (iRet = ::getaddrinfo(NULL, DEF_PORT, &Hints, &pRes) != 0) return -1; SOCKET Accept = INVALID_SOCKET; if ((Accept = ::socket(pRes->ai_family, pRes->ai_socktype, pRes->ai_protocol)) == INVALID_SOCKET) return -2; if (::bind(Accept, pRes->ai_addr, static_cast<int>(pRes->ai_addrlen)) != 0) { ::closesocket(Accept); return -3; } ::freeaddrinfo(pRes); SOCKET Client = INVALID_SOCKET; while (_getch() != 27) { cout << "Start \"listen()\"\n"; if ((iRet = ::listen(Accept, 10)) != 0) { cerr << "Error: \"listen()\" -> " << iRet << "\n"; break; } if ((Client = ::accept(Accept, NULL, NULL)) == INVALID_SOCKET) { cerr << "Error: \"accept()\" -> INVALID_SOCKET\n"; break; } cout << "Client verbunden.\n"; } system("Pause"); ::closesocket(Accept); return 0; }So jetzt bin ich ganz verwirrt. Jetzt wird die Anwendung mit "-1" beendet. Ich hab jetzt aber nur die Winsock-Sachen per c&p eingefügt und die Klassenelement mit lokalen Variablen ersetzt.
"iRet" hat den Wert "1".[Edit]
Hab das WSAStartUp() vergessen. Sorry.
[/Edit]
-
Hast du auch WSAStartup aufgerufen?
-
#include <Winsock2.h> #include <Windows.h> #include <ws2tcpip.h> #include <iphlpapi.h> #include <conio.h> #include <iostream> using namespace std; #define DEF_PORT "24837" int main (const int argc, const char** argv) { WSAData wsa; if (::WSAStartup(MAKEWORD(2,0), &wsa) != 0) return -11; addrinfo *pRes = NULL; addrinfo Hints; ::memset(&Hints, 0, sizeof(addrinfo)); Hints.ai_family = AF_INET; Hints.ai_socktype = SOCK_STREAM; Hints.ai_protocol = IPPROTO_TCP; Hints.ai_flags = AI_PASSIVE; int iRet = 0; if (iRet = ::getaddrinfo(NULL, DEF_PORT, &Hints, &pRes) != 0) return -1; SOCKET Accept = INVALID_SOCKET; if ((Accept = ::socket(pRes->ai_family, pRes->ai_socktype, pRes->ai_protocol)) == INVALID_SOCKET) return -2; if (::bind(Accept, pRes->ai_addr, static_cast<int>(pRes->ai_addrlen)) != 0) { ::closesocket(Accept); return -3; } ::freeaddrinfo(pRes); SOCKET Client = INVALID_SOCKET; while (_getch() != 27) { cout << "Start \"listen()\"\n"; if ((iRet = ::listen(Accept, 10)) != 0) { cerr << "Error: \"listen()\" -> " << iRet << "\n"; break; } if ((Client = ::accept(Accept, NULL, NULL)) == INVALID_SOCKET) { cerr << "Error: \"accept()\" -> INVALID_SOCKET\n"; break; } cout << "Client verbunden.\n"; } system("Pause"); ::closesocket(Accept); ::WSACleanup(); return 0; }So jetzt aber. Jetzt blockiert er auch ganz normal im Lauschzustand. Versteh ich nicht.
