Sockets / Ports
-
Hallöle!
So ich wagte mich nun etwas in die Netzwerkprogrammierung und war erst mal begeistert wie "einfach" dieses Client-Server-Modell srukturiert ist!
Natürlich weiß ich, dass das ja aber auch nur der Anfang ist, und dass alles noch viel viel komplizierter werden wird (steht so zumindest in meinem Buch!).Jedoch habe ich noch ein paar grobe Verständnisprobleme mit den Sockets und ihrem Verhältnis gegenüber den Ports:
Client-Programm:
#include <windows.h> #include <winsock2.h> #include <stdio.h> #include <iostream> using namespace std; //Prototypen int startWinsock(void); int main() { long rc; SOCKET s; SOCKADDR_IN addr; char buf[256]; // Winsock starten rc = startWinsock(); if(rc != 0) { cout << "Fehler: startWinsock, fehler code: %d\n" << rc; return 1; } else { cout << "Winsock gestartet!\n"; } // Socket erstellen s = socket(AF_INET, SOCK_STREAM, 0); if(s == INVALID_SOCKET) { cout << "Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n" << WSAGetLastError(); return 1; } else cout << "Socket erstellt!\n"; // Verbinden memset(&addr, 0, sizeof(SOCKADDR_IN)); // zuerst alles auf 0 setzten addr.sin_family = AF_INET; addr.sin_port = htons(12345); // wir verwenden mal port 12345 addr.sin_addr.s_addr = inet_addr("127.0.0.1"); // zielrechner ist unser eigener rc = connect(s, (SOCKADDR*)&addr, sizeof(SOCKADDR)); if(rc == SOCKET_ERROR) { cout << "Fehler: connect gescheitert, Fehler code: %d\n" << WSAGetLastError(); system("pause>nul"); return 1; } else cout << "Verbunden mit 127.0.0.1..\n"; // Daten austauschen while(rc != SOCKET_ERROR) { cout << "Zeichenfolge eingeben [max 256]: "; gets(buf); send(s, buf, strlen(buf), 0); rc = recv(s, buf, 256, 0); if(rc == 0) { cout << "Server hat die Verbindung getrennt..\n"; break; } if(rc == SOCKET_ERROR) { cout << "Fehler: recv, fehler code: %d\n" << WSAGetLastError(); break; } buf[rc]= '\0'; cout << "\nServer antwortet: %s\n" << buf; } closesocket(s); WSACleanup(); return 0; } int startWinsock(void) { WSADATA wsa; return WSAStartup(MAKEWORD(2,0),&wsa); }Serverprogramm:
#include <windows.h> #include <winsock2.h> #include <stdio.h> #include <iostream> using namespace std; //Prototypen int startWinsock(void); int main() { long rc; SOCKET acceptSocket; SOCKET connectedSocket; SOCKADDR_IN addr; char buf[256]; char buf2[300]; // Winsock starten rc = startWinsock(); if(rc != 0) { cout << "Fehler: startWinsock, fehler code: %d\n" << rc; return 1; } else cout << "Winsock gestartet!\n"; // Socket erstellen acceptSocket = socket(AF_INET, SOCK_STREAM, 0); if(acceptSocket == INVALID_SOCKET) { cout << "Fehler: Der Socket konnte nicht erstellt werden, fehler code: %d\n" << WSAGetLastError(); return 1; } else cout << "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 = ADDR_ANY; rc = bind(acceptSocket, (SOCKADDR*)&addr, sizeof(SOCKADDR_IN)); if(rc == SOCKET_ERROR) { cout << "Fehler: bind, fehler code: %d\n" << WSAGetLastError(); return 1; } else cout <<"Socket an port 12345 gebunden\n"; // In den listen Modus rc = listen(acceptSocket,10); if(rc == SOCKET_ERROR) { cout << "Fehler: listen, fehler code: %d\n" << WSAGetLastError(); return 1; } else cout << "acceptSocket ist im listen Modus....\n"; // Verbindung annehmen connectedSocket = accept(acceptSocket, NULL, NULL); if(connectedSocket == INVALID_SOCKET) { cout << "Fehler: accept, fehler code: %d\n" << WSAGetLastError(); return 1; } else printf("Neue Verbindung wurde akzeptiert!\n"); // Daten austauschen while(rc != SOCKET_ERROR) { rc = recv(connectedSocket, buf, 256, 0); if(rc == 0) { cout << "Server hat die Verbindung getrennt..\n"; break; } if(rc == SOCKET_ERROR) { cout << "Fehler: recv, fehler code: %d\n" << WSAGetLastError(); break; } buf[rc] = '\0'; cout << "Client sendet: %s\n" << buf; sprintf(buf2, "Du mich auch %s", buf); rc = send(connectedSocket, buf2, strlen(buf2), 0); } closesocket(acceptSocket); closesocket(connectedSocket); WSACleanup(); return 0; } int startWinsock(void) { WSADATA wsa; return WSAStartup(MAKEWORD(2,0), &wsa); }Das bekannte und typische Anfänger-Tutorial zur Socketprogrammierung.
Nun meine Fragen:Wieso werden hier Ports erfunden wie "12345" und wieso läuft das Ganze dann auch noch?? Soweit ich weiß benötigt man in so einem Falle doch den Port 80, oder???
Jetzt möchte ich das Ganze mal übers I-net laufen lassen. Dann muss ich doch die IP 127.0.0.1 in meine IP (Beispiel 84.158.13.7) umschreiben, oder?
Aber damit ist es dann doch nicht getan, oder? Wenn ich mit einem Kumpel chatten wollte, dann reicht es doch nicht, wenn ich die IP so umwandle und ihm dann das Clientprogramm schicke, oder? Was muss ich da umschreiben und was genau muss ich mit dem Serverprogramm machen?Woher weiß das Clientprogramm, dass es meinem Serverprogramm etwas schicken muss? Mein Serverprogramm beinhaltet nirgends irgendwelche IP-infos, sondern lediglich die Portnummer 12345. Aber im Internet gibts doch tausende von Servern...woher weiß dann das Clientprogramm, dass es zu meinem Serverprogramm muss?? Ich werde daraus noch nicht ganz schlau!
Hm..hoffentlich habe ich jetzt niemanden verwirrt mit diesen Fragen

Naja auf Hilfe für diese Fragen wäre ich wirklich sehr sehr dankbar!!
Ich denke wenn ich das Grundprinzip, an welchem ich hier offensichtlich noch scheitere, erst mal verstanden habe, dann fällt mir das Netzwerkprogrammieren wesentlich leichter!
Viele Grüße
Gapa
-
Gapa schrieb:
Wieso werden hier Ports erfunden wie "12345" und wieso läuft das Ganze dann auch noch?? Soweit ich weiß benötigt man in so einem Falle doch den Port 80, oder???
Es gibt ~65.000 Ports, wovon unter den ersten paar tausend ein paar eine Standard-Belegung haben, z.B. Port 80 für HTTP. Sogesehen kannst du die Ports nutzen die du willst, solange der Client den Server auf dem Port anspricht, auf dem dieser lauscht.
Gapa schrieb:
Jetzt möchte ich das Ganze mal übers I-net laufen lassen. Dann muss ich doch die IP 127.0.0.1 in meine IP (Beispiel 84.158.13.7) umschreiben, oder?
Aber damit ist es dann doch nicht getan, oder? Wenn ich mit einem Kumpel chatten wollte, dann reicht es doch nicht, wenn ich die IP so umwandle und ihm dann das Clientprogramm schicke, oder? Was muss ich da umschreiben und was genau muss ich mit dem Serverprogramm machen?Der Server muss keine IP wissen, er lauscht einfach auf dem PC, auf dem er läuft, auf einem bestimmten Port. Der Client muss sich dann mit dem Server verbinden, muss also dessen IP und den Port wissen. Übers Internet geht das prinzipiell genauso, es sei denn der Server sitzt hinter einem Router, dann musst du den entsprechenden Port "forwarden".
Gapa schrieb:
Woher weiß das Clientprogramm, dass es meinem Serverprogramm etwas schicken muss? Mein Serverprogramm beinhaltet nirgends irgendwelche IP-infos, sondern lediglich die Portnummer 12345. Aber im Internet gibts doch tausende von Servern...woher weiß dann das Clientprogramm, dass es zu meinem Serverprogramm muss?? Ich werde daraus noch nicht ganz schlau!
Hehe, das ist eigentlich ganz einfach
Der Programmierer des Client-Programms muss natürlich beim Programmieren entscheiden, wann wie wo verbunden und kommuniziert werden soll. Wenn dein Browser z.B. den HTML-Code einer Webseite runterladen will, sucht es sich die IP zu der von dir eingegebenen Adresse und schickt eine Nachricht hin, die irgendwo im HTTP-Protokoll spezifiziert ist. Der Server lauscht halt auf Verbindungen, merkt dass ein Client sich verbindet und er bekommt eine Nachricht. Seinerseits schickt er dann die HTML-Seite zurück.
-
Badestrand schrieb:
Gapa schrieb:
Jetzt möchte ich das Ganze mal übers I-net laufen lassen. Dann muss ich doch die IP 127.0.0.1 in meine IP (Beispiel 84.158.13.7) umschreiben, oder?
Aber damit ist es dann doch nicht getan, oder? Wenn ich mit einem Kumpel chatten wollte, dann reicht es doch nicht, wenn ich die IP so umwandle und ihm dann das Clientprogramm schicke, oder? Was muss ich da umschreiben und was genau muss ich mit dem Serverprogramm machen?Der Server muss keine IP wissen, er lauscht einfach auf dem PC, auf dem er läuft, auf einem bestimmten Port. Der Client muss sich dann mit dem Server verbinden, muss also dessen IP und den Port wissen. Übers Internet geht das prinzipiell genauso, es sei denn der Server sitzt hinter einem Router, dann musst du den entsprechenden Port "forwarden".
Ev. muss auf dem Server der Port auf eine entsprechende IP Adresse gebunden werden (bind). So können spezifische Adapter bzw. IP Adressen benutzt werden.
Funktioniert auch ohne, aber man kann wenn man es benötigt. :-))
Gruss Simon