Skip to content

Commit a557d6c

Browse files
KasherMylesBorins
authored andcommitted
src: unconsume stream fix in internal http impl
When emitting a 'connection' event on a httpServer, the function connectionListener is called. Then, a new parser is created, and 'consume' method is called on the socket's externalStream. However, if this stream was already consumed and unconsumed, the process crashes with a cpp assert from the 'Consume' method in stream_base.h. This commit makes sure that no SIGABRT will be raised and the process will stay alive (after emitting the socket). PR-URL: #11015 Reviewed-By: Fedor Indutny <[email protected]> Reviewed-By: James M Snell <[email protected]>
1 parent d55d760 commit a557d6c

File tree

2 files changed

+25
-1
lines changed

2 files changed

+25
-1
lines changed

lib/_http_server.js

+3-1
Original file line numberDiff line numberDiff line change
@@ -350,9 +350,11 @@ function connectionListener(socket) {
350350
// Override on to unconsume on `data`, `readable` listeners
351351
socket.on = socketOnWrap;
352352

353+
// We only consume the socket if it has never been consumed before.
353354
var external = socket._handle._externalStream;
354-
if (external) {
355+
if (!socket._handle._consumed && external) {
355356
parser._consumed = true;
357+
socket._handle._consumed = true;
356358
parser.consume(external);
357359
}
358360
external = null;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
'use strict';
2+
const common = require('../common');
3+
const http = require('http');
4+
5+
const testServer = http.createServer((req, res) => {
6+
common.fail('Should not be called');
7+
res.end();
8+
});
9+
testServer.on('connect', common.mustCall((req, socket, head) => {
10+
socket.write('HTTP/1.1 200 Connection Established' + '\r\n' +
11+
'Proxy-agent: Node-Proxy' + '\r\n' +
12+
'\r\n');
13+
// This shouldn't raise an assertion in StreamBase::Consume.
14+
testServer.emit('connection', socket);
15+
testServer.close();
16+
}));
17+
testServer.listen(0, common.mustCall(() => {
18+
http.request({
19+
port: testServer.address().port,
20+
method: 'CONNECT'
21+
}, (res) => {}).end();
22+
}));

0 commit comments

Comments
 (0)