Dies mag programmierungsbezogen erscheinen, aber dies ist eine Frage des Betriebssystems.
Ich schreibe einen kleinen Hochleistungsdämon, der Tausende von Verbindungen pro Sekunde benötigt. Es funktioniert gut unter Linux (speziell Ubuntu 9.10 unter EC2). Wenn ich unter Mac OS X ein paar tausend Verbindungen (ungefähr 16350) in einen Benchmark werfe, der einfach eine Verbindung öffnet, es tut und die Verbindung schließt, bleibt das Benchmark-Programm einige Sekunden lang hängen und wartet darauf, dass ein Socket verfügbar wird bevor Sie fortfahren (oder eine Zeitüberschreitung im Prozess).
Ich habe sowohl Apache Bench als auch Siege verwendet (um sicherzustellen, dass es nicht die Benchmark-Anwendung ist).
Warum / wie begrenzt Mac OS X die RATE, mit der Sockets verwendet werden können, und kann ich dies verhindern?
Oder ist noch etwas los?
Ich weiß, dass es ein Dateideskriptor-Limit gibt, aber das treffe ich nicht. Es gibt keinen Fehler beim Akzeptieren eines Sockets, es bleibt einfach eine Weile nach dem ersten (ungefähr) 16000 hängen und wartet - ich nehme an - darauf, dass das Betriebssystem einen Socket freigibt. Dies sollte nicht passieren, da alle vorherigen Sockets zu diesem Zeitpunkt geschlossen sind. Sie sollen mit der Geschwindigkeit verfügbar sein, mit der sie geschlossen sind, und zwar unter Ubuntu, aber unter Mac OS X scheint es eine Art Verzögerung von mehreren (5-10?) Sekunden zu geben.
Ich habe versucht, mit ulimit in alle Richtungen zu optimieren. Nada.
quelle
Antworten:
Mac OS X beginnt bei 49152 mit dem Öffnen kurzlebiger Ports. Portnummern sind 16-Bit-Ganzzahlen ohne Vorzeichen, sodass 65535 Ports möglich sind. 65535 - 49152 = 16383. Ich glaube, Sie haben 16K-Ports in TIME_WAIT.
Update : Möglicherweise möchten Sie sich die folgenden sysctl (8) -Variablen ansehen:
Ich denke, wenn Sie hifirst auf einen niedrigeren Wert einstellen, erhöhen Sie die Anzahl der kurzlebigen Ports, die auf Ihrem System verfügbar sind.
Möglicherweise gibt es eine Socket-Option oder etwas, das den Stack anweist, grundsätzlich gegen die TCP-Spezifikation zu verstoßen und einen nicht standardmäßigen Wert für TIME_WAIT zu verwenden, aber ich bin nicht genug von einem Mac OS X-Socket-Programmierer, um das zu wissen.
Update 2 : Sie möchten wahrscheinlich setsockopt (2) verwenden, um SO_REUSEADDR festzulegen.
quelle