Socket-Optionsfunktion Funktion: Methoden zum Lesen und Setzen von Socket-Dateideskriptorattributen #include <sys/scoket.h> int getsockopt (int sockfd, int level, int option_name, void* option_value, socklen_t* restrict option_len); int setsockopt (int sockfd, int level, int option_name, const void* option_value, socklen_t option_len); Die Socket-Optionstabelle sieht wie folgt aus: Die Funktionen getsockopt und setsockopt geben bei Erfolg 0 und bei einem Fehler -1 zurück und setzen errno. Für den Server sind einige Socket-Optionen nur gültig, wenn sie vor dem Aufruf des Listen-Systemaufrufs für den Listening-Socket festgelegt wurden. Dies liegt daran, dass der Verbindungs-Socket nur durch den Accept-Aufruf zurückgegeben werden kann und die durch Accept aus der Abhörwarteschlange akzeptierte Verbindung mindestens die ersten beiden Schritte des TCP-Drei-Wege-Handshakes abgeschlossen hat (da die Verbindung in der Abhörwarteschlange mindestens den Status SYN_RCVD erreicht hat). Dies bedeutet, dass der Server ein TCP-Synchronisierungssegment an die empfangene Verbindung gesendet hat. Allerdings sollten einige Socket-Optionen im TCP-Synchronisierungssegment festgelegt werden, z. B. die TCP-Maximalsegmentoption. Für diese Situation bietet Linux Entwicklern die folgende Lösung: Legen Sie diese Socket-Optionen für den Listening-Socket fest. Anschließend erbt der von Accept zurückgegebene Verbindungs-Socket diese Optionen automatisch. Diese Optionen sind: SO_DEBUG, SO_DONTROUTE, SO_KEEPALIVE, SO_LINGER, SO_OOBINLINE, SO_RCVBUF, SO_RCVLOWAT, SO_SNDBUF, SO_SNDLOWAT, TCP_MAXSEG und TCP_NODELAY. Für den Client sollten diese Socket-Optionen vor dem Aufruf der Verbindungsfunktion festgelegt werden, da nach der erfolgreichen Rückgabe des Verbindungsaufrufs der TCP-Drei-Wege-Handshake abgeschlossen ist. SO_REUSEADDR-Option Wir haben den TIME_WAIT-Status von TCP-Verbindungen bereits besprochen und erwähnt, dass das Serverprogramm durch Festlegen der Socket-Option SO_REUSEADDR die Verwendung der von der Verbindung im TIME_WAIT-Status belegten Socket-Adresse erzwingen kann. #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <assert.h> #include <stdio.h> #include <unistd.h> #include <stdlib.h> #include <errno.h> #include <string.h> int main( int argc, char* argv[] ) { wenn(argc <= 2) { printf( "Verwendung: %s IP-Adresse Portnummer\n", Basisname( argv[0] ) ); Rückgabe 1; } const char* ip = argv[1]; Port wird als Portnummer bezeichnet. int sock = socket( PF_INET, SOCK_STREAM, 0 ); behaupten( Socke >= 0 ); int Wiederverwendung = 1; setsockopt( sock, SOL_SOCKET, SO_REUSEADDR, &wiederverwenden, sizeof( wiederverwenden ) ); Struktur sockaddr_in Adresse; bzero( &Adresse, Größe von(Adresse)); Adresse.sin_family = AF_INET; inet_pton( AF_INET, ip, &Adresse.sin_addr ); Adresse.sin_port = htons(Port); int ret = bind(sock, (Struktur sockaddr*)&Adresse, sizeof(Adresse)); behaupten( ret != -1 ); ret = listen( Socke, 5 ); behaupten( ret != -1 ); Struktur sockaddr_in Client; socklen_t client_addrlength = Größe von (Client); int connfd = akzeptieren( sock, ( Struktur sockaddr* )&client, &client_addrlength ); wenn ( connfd < 0 ) { printf( "fehlernummer ist: %d\n", errno ); } anders { Zeichen Remote [INET_ADDRSTRLEN]; printf( "verbunden mit IP: %s und Port: %d\n", inet_ntop( AF_INET, &client.sin_addr, remote, INET_ADDRSTRLEN ), ntohs( client.sin_port ) ); schließen( connfd ); } schließen (Socke); gebe 0 zurück; } Nachdem setsocketopt festgelegt wurde, kann die daran gebundene Socket-Adresse sofort wiederverwendet werden, auch wenn sich der Sock im Status TIME_WAIT befindet. Darüber hinaus können wir geschlossene Sockets auch schnell wiederverwenden, indem wir den Kernelparameter /proc/sys/net/ipv4/tcp_tw_recycle ändern, sodass die TCP-Verbindung überhaupt nicht in den Zustand TIME_WAIT wechselt und die Anwendung die lokale Socket-Adresse sofort wiederverwenden kann. Optionen SO_RCVBUF und SO_SNDBUF Die Optionen SO_RCVBUF und SO_SNDBUF stellen die Größen des TCP-Empfangspuffers bzw. des Sendepuffers dar. Wenn wir jedoch setsockopt verwenden, um die Größe des TCP-Empfangspuffers und des Sendepuffers festzulegen, verdoppelt das System seinen Wert und er darf nicht kleiner als sein Mindestwert sein. Der Mindestwert für den TCP-Empfangspuffer beträgt 256 Byte und der Mindestwert für den Sendepuffer beträgt 2048 Byte (verschiedene Systeme können jedoch unterschiedliche Standardmindestwerte haben). Darüber hinaus können wir die Kernelparameter /proc/sys/net/ipv4/tcp_rmem und /proc/sys/net/ipv4/tcp_wmem direkt ändern, um zu erzwingen, dass der TCP-Empfangspuffer und der Sendepuffer keine Mindestgrößenbeschränkung haben. Ändern Sie das Client-Programm des TCP-Sendepuffers: #include <sys/socket.h> #include <arpa/inet.h> #include <assert.h> #include <stdio.h> #include <unistd.h> #include <string.h> #include <stdlib.h> #define BUFFER_SIZE 512 int main( int argc, char* argv[] ) { wenn(argc <= 3) { printf( "Verwendung: %s IP-Adresse Portnummer Sendepuffergröße\n", Basisname( argv[0] ) ); Rückgabe 1; } const char* ip = argv[1]; Port wird als Portnummer bezeichnet. Struktur sockaddr_in Serveradresse; bzero( &Serveradresse, Größe von( Serveradresse ) ); server_address.sin_family = AF_INET; inet_pton( AF_INET, ip, &Serveradresse.sin_addr ); server_address.sin_port = htons(Port); int sock = socket( PF_INET, SOCK_STREAM, 0 ); behaupten( Socke >= 0 ); int sendbuf = atoi( argv[3] ); int len = sizeof( sendbuf ); setsockopt( sock, SOL_SOCKET, SO_SNDBUF, &sendbuf, sizeof( sendbuf ) ); getsockopt( sock, SOL_SOCKET, SO_SNDBUF, &sendbuf, ( socklen_t* )&len ); printf( "die Größe des TCP-Sendepuffers nach der Einstellung ist %d\n", sendbuf ); wenn (Verbinden(Sock, (Struktur Sockaddr*)&Serveradresse, Größe von(Serveradresse)) != -1) { Zeichenpuffer [PUFFERGRÖSSE]; memset(Puffer, „a“, PUFFERGRÖSSE); sende(sock, puffer, PUFFERGRÖSSE, 0); } schließen (Socke); gebe 0 zurück; } Ändern Sie das Serverprogramm des TCP-Empfangspuffers: #include <sys/socket.h> #include <netinet/in.h> #include <arpa/inet.h> #include <assert.h> #include <stdio.h> #include <unistd.h> #include <stdlib.h> #include <errno.h> #include <string.h> #define BUFFER_SIZE 1024 int main( int argc, char* argv[] ) { wenn(argc <= 3) { printf( "Verwendung: %s IP-Adresse Portnummer Empfangspuffergröße\n", Basisname( argv[0] ) ); Rückgabe 1; } const char* ip = argv[1]; Port wird als Portnummer bezeichnet. Struktur sockaddr_in Adresse; bzero( &Adresse, Größe von(Adresse)); Adresse.sin_family = AF_INET; inet_pton( AF_INET, ip, &Adresse.sin_addr ); Adresse.sin_port = htons(Port); int sock = socket( PF_INET, SOCK_STREAM, 0 ); behaupten( Socke >= 0 ); : In diesem Fall wird die Anweisung recvbuf = atoi( argv[3] ); int len = sizeof(recvbuf); setsockopt( sock, SOL_SOCKET, SO_RCVBUF, &recvbuf, sizeof( recvbuf ) ); getsockopt( sock, SOL_SOCKET, SO_RCVBUF, &recvbuf, ( socklen_t* )&len ); printf( "die Größe des Empfangspuffers nach dem Einstellen ist %d\n", recvbuf ); int ret = bind(sock, (Struktur sockaddr*)&Adresse, sizeof(Adresse)); behaupten( ret != -1 ); ret = listen( Socke, 5 ); behaupten( ret != -1 ); Struktur sockaddr_in Client; socklen_t client_addrlength = Größe von (Client); int connfd = akzeptieren( sock, ( Struktur sockaddr* )&client, &client_addrlength ); wenn ( connfd < 0 ) { printf( "fehlernummer ist: %d\n", errno ); } anders { Zeichenpuffer [PUFFERGRÖSSE]; memset(Puffer, '\0', PUFFERGRÖSSE); während (recv (connfd, Puffer, Puffergröße-1, 0) > 0) {} schließen(connfd); } schließen (Socke); gebe 0 zurück; } Laufergebnisse:
Wie oben erklärt: Wenn wir setsockopt verwenden, um die Größe des TCP-Empfangspuffers und des Sendepuffers festzulegen, verdoppelt das System seinen Wert und er darf nicht kleiner als sein Mindestwert sein. Optionen SO_RCVLOWAT und SO_SNDLOWAT
SO_LINGER-Option Die Option SO_LINGER wird verwendet, um das Verhalten des Systemaufrufs „Close“ beim Schließen einer TCP-Verbindung zu steuern. Wenn wir den Systemaufruf „close“ zum Schließen eines Sockets verwenden, wird „close“ standardmäßig sofort zurückgegeben, und das TCP-Modul ist dafür verantwortlich, die verbleibenden Daten im dem Socket entsprechenden TCP-Sendepuffer an die andere Partei zu senden. Wenn wir den Wert der Option SO_LINGER festlegen, müssen wir dem Systemaufruf setsockopt (getsockopt) eine Struktur vom Typ Linger übergeben, die wie folgt definiert ist: #include <sys/socket.h> Struktur verweilen { int l_onoff; //Diese Option ein- (ungleich 0) oder ausschalten (0) int l_linger; //Verweildauer};
Das Obige ist der vollständige Inhalt dieses Artikels. Ich hoffe, er wird für jedermanns Studium hilfreich sein. Ich hoffe auch, dass jeder 123WORDPRESS.COM unterstützen wird. Das könnte Sie auch interessieren:
|
<<: Vue verwendet dynamische Komponenten, um einen TAB-Umschalteffekt zu erzielen
>>: Centos7-Installation und Konfiguration von Mysql5.7
Letztes Jahr habe ich aufgrund von Projektanforde...
Zusammenfassung: Dieser Artikel erläutert hauptsä...
Dies ist der zu erzielende Effekt: Sie können seh...
Nachdem Sie VMware installiert und eine neue virt...
Hintergrund Der Unternehmenscode wird Dritten zur...
Dieser Artikel beschreibt anhand eines Beispiels ...
I. Einleitung 1: SSL-Zertifikat Mein Domänenname ...
Vorwort Ich habe zuvor eine Komponente im Ladesti...
In diesem Artikel wird hauptsächlich die Installa...
In diesem Artikelbeispiel wird der spezifische Ja...
Win10 + Ubuntu 20.04 LTS Dual-System-Installation...
Grundlegende Einführung in robots.txt Robots.txt i...
Inhaltsverzeichnis Überblick Die vier Hauptobjekt...
1. Rendern JD-Effekt Simulationseffekt 2. Grundsa...
[Wer ist nslookup?] 】 Der Befehl nslookup ist ein...