diff --git a/doc/api/http.markdown b/doc/api/http.markdown index 68ea23ccc2c46e..260d22de1d93db 100644 --- a/doc/api/http.markdown +++ b/doc/api/http.markdown @@ -117,7 +117,7 @@ sent to the server on that socket. If a client connection emits an 'error' event - it will forwarded here. -### server.listen(port, [hostname], [callback]) +### server.listen(port, [hostname], [backlog], [callback]) Begin accepting connections on the specified port and hostname. If the hostname is omitted, the server will accept connections directed to any @@ -125,6 +125,11 @@ IPv4 address (`INADDR_ANY`). To listen to a unix socket, supply a filename instead of port and hostname. +Backlog is the maximum length of the queue of pending connections. +The actual length will be determined by your OS through sysctl settings such as +`tcp_max_syn_backlog` and `somaxconn` on linux. The default value of this +parameter is 511 (not 512). + This function is asynchronous. The last parameter `callback` will be added as a listener for the ['listening'](net.html#event_listening_) event. See also [net.Server.listen()](net.html#server.listen). diff --git a/doc/api/net.markdown b/doc/api/net.markdown index 6908f61d08e42a..a10076ef89a916 100644 --- a/doc/api/net.markdown +++ b/doc/api/net.markdown @@ -121,12 +121,17 @@ The `connectListener` parameter will be added as an listener for the This class is used to create a TCP or UNIX server. A server is a `net.Socket` that can listen for new incoming connections. -### server.listen(port, [host], [listeningListener]) +### server.listen(port, [host], [backlog], [listeningListener]) Begin accepting connections on the specified `port` and `host`. If the `host` is omitted, the server will accept connections directed to any IPv4 address (`INADDR_ANY`). A port value of zero will assign a random port. +Backlog is the maximum length of the queue of pending connections. +The actual length will be determined by your OS through sysctl settings such as +`tcp_max_syn_backlog` and `somaxconn` on linux. The default value of this +parameter is 511 (not 512). + This function is asynchronous. When the server has been bound, ['listening'](#event_listening_) event will be emitted. the last parameter `listeningListener` will be added as an listener for the diff --git a/lib/net.js b/lib/net.js index fa1900e1706b30..bbd0c1fcf383a5 100644 --- a/lib/net.js +++ b/lib/net.js @@ -56,7 +56,7 @@ if (process.env.NODE_DEBUG && /net/.test(process.env.NODE_DEBUG)) { function isPipeName(s) { - return typeof s === 'string' && toPort(s) === false; + return typeof s === 'string' && toNumber(s) === false; } @@ -161,7 +161,7 @@ exports.Stream = Socket; // Legacy naming. Socket.prototype.listen = function() { var self = this; self.on('connection', arguments[0]); - listen(self, null, null); + listen(self, null, null, null); }; @@ -747,7 +747,7 @@ util.inherits(Server, events.EventEmitter); exports.Server = Server; -function toPort(x) { return (x = Number(x)) >= 0 ? x : false; } +function toNumber(x) { return (x = Number(x)) >= 0 ? x : false; } var createServerHandle = exports._createServerHandle = @@ -786,7 +786,7 @@ var createServerHandle = exports._createServerHandle = }; -Server.prototype._listen2 = function(address, port, addressType) { +Server.prototype._listen2 = function(address, port, addressType, backlog) { var self = this; var r = 0; @@ -805,7 +805,10 @@ Server.prototype._listen2 = function(address, port, addressType) { self._handle.onconnection = onconnection; self._handle.socket = self; - r = self._handle.listen(self._backlog || 128); + // Use a backlog of 512 entries. We pass 511 to the listen() call because + // the kernel does: backlogsize = roundup_pow_of_two(backlogsize + 1); + // which will thus give us a backlog of 512 entries. + r = self._handle.listen(backlog || 511); if (r) { self._handle.close(); @@ -822,15 +825,15 @@ Server.prototype._listen2 = function(address, port, addressType) { }; -function listen(self, address, port, addressType) { +function listen(self, address, port, addressType, backlog) { if (process.env.NODE_UNIQUE_ID) { var cluster = require('cluster'); cluster._getServer(self, address, port, addressType, function(handle) { self._handle = handle; - self._listen2(address, port, addressType); + self._listen2(address, port, addressType, backlog); }); } else { - self._listen2(address, port, addressType); + self._listen2(address, port, addressType, backlog); } } @@ -843,36 +846,41 @@ Server.prototype.listen = function() { self.once('listening', lastArg); } - var port = toPort(arguments[0]); + var port = toNumber(arguments[0]); + + // The third optional argument is the backlog size. + // When the ip is omitted it can be the second argument. + var backlog = toNumber(arguments[1]) || toNumber(arguments[2]); var TCP = process.binding('tcp_wrap').TCP; if (arguments.length == 0 || typeof arguments[0] == 'function') { // Don't bind(). OS will assign a port with INADDR_ANY. // The port can be found with server.address() - listen(self, null, null); + listen(self, null, null, backlog); } else if (arguments[0] instanceof TCP) { self._handle = arguments[0]; - listen(self, null, -1, -1); + listen(self, null, -1, -1, backlog); } else if (isPipeName(arguments[0])) { // UNIX socket or Windows pipe. var pipeName = self._pipeName = arguments[0]; - listen(self, pipeName, -1, -1); + listen(self, pipeName, -1, -1, backlog); } else if (typeof arguments[1] == 'undefined' || - typeof arguments[1] == 'function') { + typeof arguments[1] == 'function' || + typeof arguments[1] == 'number') { // The first argument is the port, no IP given. - listen(self, '0.0.0.0', port, 4); + listen(self, '0.0.0.0', port, 4, backlog); } else { - // The first argument is the port, the second an IP + // The first argument is the port, the second an IP. require('dns').lookup(arguments[1], function(err, ip, addressType) { if (err) { self.emit('error', err); } else { - listen(self, ip || '0.0.0.0', port, ip ? addressType : 4); + listen(self, ip || '0.0.0.0', port, ip ? addressType : 4, backlog); } }); } diff --git a/test/simple/test-net-server-bind.js b/test/simple/test-net-server-bind.js index b5b83bf2feaaed..0951aa246209a1 100644 --- a/test/simple/test-net-server-bind.js +++ b/test/simple/test-net-server-bind.js @@ -62,9 +62,34 @@ server2.listen(common.PORT + 1, function() { }); +// Backlog argument + +var address3; +var server3 = net.createServer(function(socket) { }); + +server3.listen(common.PORT + 2, '0.0.0.0', 127, function() { + address3 = server3.address(); + console.log('address3 %j', address3); + server3.close(); +}); + + +// Backlog argument without host argument + +var address4; +var server4 = net.createServer(function(socket) { }); + +server4.listen(common.PORT + 3, 127, function() { + address4 = server4.address(); + console.log('address4 %j', address4); + server4.close(); +}); + process.on('exit', function() { assert.ok(address0.port > 100); assert.equal(common.PORT, address1.port); assert.equal(common.PORT + 1, address2.port); + assert.equal(common.PORT + 2, address3.port); + assert.equal(common.PORT + 3, address4.port); });