node/test/parallel/test-child-process-fork-regr-gh-2847.js
Ruben Bridgewater 1698c8e165 errors: fix and improve error types
1) Add missing lazy assert call
2) Remove obsolete error type
3) Name undocumented error type more appropriate
4) Consolidate error type style (rely on util.format
   instead of using a function)
5) Uppercase the first letter from error messages
6) Improve some internal error parameters

PR-URL: https://github.com/nodejs/node/pull/13857
Reviewed-By: Refael Ackermann <refack@gmail.com>
Reviewed-By: James M Snell <jasnell@gmail.com>
Reviewed-By: Colin Ihrig <cjihrig@gmail.com>
Reviewed-By: Michael Dawson <michael_dawson@ca.ibm.com>
2017-06-28 20:00:25 +02:00

70 lines
1.9 KiB
JavaScript

// Before https://github.com/nodejs/node/pull/2847 a child process trying
// (asynchronously) to use the closed channel to it's creator caused a segfault.
'use strict';
const common = require('../common');
const assert = require('assert');
const cluster = require('cluster');
const net = require('net');
if (!cluster.isMaster) {
// Exit on first received handle to leave the queue non-empty in master
process.on('message', function() {
process.exit(1);
});
return;
}
const server = net.createServer(function(s) {
if (common.isWindows) {
s.on('error', function(err) {
// Prevent possible ECONNRESET errors from popping up
if (err.code !== 'ECONNRESET')
throw err;
});
}
setTimeout(function() {
s.destroy();
}, 100);
}).listen(0, function() {
const worker = cluster.fork();
function send(callback) {
const s = net.connect(server.address().port, function() {
worker.send({}, s, callback);
});
// https://github.com/nodejs/node/issues/3635#issuecomment-157714683
// ECONNREFUSED or ECONNRESET errors can happen if this connection is still
// establishing while the server has already closed.
// EMFILE can happen if the worker __and__ the server had already closed.
s.on('error', function(err) {
if ((err.code !== 'ECONNRESET') &&
(err.code !== 'ECONNREFUSED') &&
(err.code !== 'EMFILE')) {
throw err;
}
});
}
worker.process.once('close', common.mustCall(function() {
// Otherwise the crash on `channel.fd` access may happen
assert.strictEqual(worker.process.channel, null);
server.close();
}));
worker.on('online', function() {
send(function(err) {
assert.ifError(err);
send(function(err) {
// Ignore errors when sending the second handle because the worker
// may already have exited.
if (err && err.message !== 'Channel closed') {
throw err;
}
});
});
});
});