Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Issue 14736 tls ipv6 address #14772

Closed
wants to merge 15 commits into from

Conversation

mattiash
Copy link

Resolves issue #14736.

Checklist
  • make -j4 test (UNIX), or vcbuild test (Windows) passes
  • tests and/or benchmarks are included
  • documentation is changed or added
  • commit message follows commit guidelines
Affected core subsystem(s)

tls

@nodejs-github-bot nodejs-github-bot added http Issues or PRs related to the http subsystem. tls Issues and PRs related to the tls subsystem. labels Aug 11, 2017
// abc:123 => abc
// [::1] => ::1
// [::1]:123 => ::1
options.servername = hostHeader.replace(/:[^\]]+$/, '')
Copy link
Contributor

@mscdex mscdex Aug 11, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why not combine both regexps for efficiency?:

options.servername = hostHeader.replace(/^(?:\[([^\]]*)\].*)|(?:([^:]*).*)$/, '$1$2');

I tried a few different variations on the above regexp, and that one seemed to execute the fastest, at least on node v8.3.0.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I ran a benchmark on your regexp (regexp1), my regexp (regexp2) and a variant that doesn't use regexps (t3). See https://gist.github.com/mattiash/f19f7d862dce54db955267e03319b2d2

The result from my benchmark was that the two regexp-solution was actually faster than your one-regexp-solution, but the fastest was my new variant without any regexp.

$ node --version
v8.3.0
$ node index.js
regexp1 x 360,816 ops/sec ±1.15% (88 runs sampled)
regexp2 x 514,166 ops/sec ±1.21% (87 runs sampled)
t3 x 1,195,766 ops/sec ±1.38% (87 runs sampled)
Fastest is t3
$ node --version
v6.3.1
$ node index.js
regexp1 x 592,158 ops/sec ±0.95% (84 runs sampled)
regexp2 x 758,064 ops/sec ±1.21% (87 runs sampled)
t3 x 829,918 ops/sec ±1.18% (85 runs sampled)
Fastest is t3

I'll update the PR to use the t3 variant

lib/tls.js Outdated
@@ -163,6 +163,33 @@ function check(hostParts, pattern, wildcards) {
return true;
}

exports._canonicalIp = function(address) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd generally prefer not introducing new _-prefixed methods. Non-public methods should be moved into lib/internal/ and used from there.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

@mattiash
Copy link
Author

Is there anything else I need to do before this can be merged? We are using TLS with certificates that sign IPv4 addresses today, and we are very eager to add support for IPv6 which requires support for TLS with certificates that sign IPv6 addresses.

@jasnell
Copy link
Member

jasnell commented Aug 21, 2017

It needs a bit of additional review. I've added a couple of folks to the "Reviewers" list.

@jasnell
Copy link
Member

jasnell commented Aug 23, 2017

const b = ['0', '0', '0', '0', '0', '0', '0', '0'];

const s = address.split('::');
if (s.length === 2) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Is there actually any IPv6 without the two dots?

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. The :: notation is just an abbreviation for any number of zero-bytes. There can very well be an IPv6-address without any zero-bytes. And the address comes from the Host-header, so it might be that the http-client requested an address with the IPv6 address spelled out, e.g. https://[0.0.0.0.0.0.0.1] for localhost.

}
}

return b.join(':');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If you want to improve the performance you could do the following to improve it further.

  • use string concatenation and not use the b array at all. And at the end add "0:".repeat(restLen).
  • replace the RegExp with a loop that checks something like var n = 0; while (str.charCodeAt(n++) === 48); so you know what part you want to slice out.
  • use address.indexOf('::') and address.split(':') directly. You know until where the first part and until where the second part will go because of the indexOf and you only have to split a single time instead of three times (you could optimize this the same as the RegExp by using a loop and not splitting at all. It should be even faster).
  • The if (s1[n]) is not necessary as far as I see it. The current test cases have no entry that does not match but in case e.g. :fe80::0000: is a valid entry, just check the very first/last entry if it is entry and count down the length.

But this is out of my perspective not that important as a first draft and should not hold off the PR from being merged.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This code is run once per https-request, and only if the host is specified with an IPv6 address. The code is already quite complex as it is and I would not like to complicate it further right now.

The if (s1[n]) is needed for '::1'

assert.strictEqual(tls.canonicalIp('fe80::'), 'fe80:0:0:0:0:0:0:0');
assert.strictEqual(
tls.canonicalIp('fe80::0000:0010:0001'),
'fe80:0:0:0:0:0:10:1');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It would be good to have some more test cases if there are any more out of the ordinary ones. It has been a long time that I checked how a valid IPv6 looks like.

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your comment made me realize that I didn't test IPv6-addresses without double colons. And of course that didn't work. Fix coming up.

@BridgeAR
Copy link
Member

BridgeAR commented Sep 2, 2017

PTAL @nodejs/http @nodejs/crypto

@BridgeAR
Copy link
Member

This needs some reviews @nodejs/collaborators

// of a TLS certificate

const assert = require('assert');
const tls = require('internal/tls');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this test work without // Flags: --expose-internals? (See the testing guide)

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You're right, it actually doesn't. I have added that flag now. While debugging this I looked at the other tests in the test/internet/ directory and realised that they all needed internet access (which my test doesn't). I therefore moved the test to test/parallel which should make sure that it gets run by make test

@BridgeAR
Copy link
Member

@nodejs/tsc PTAL.

@mattiash this needs a rebase.

@mattiash
Copy link
Author

@BridgeAR Should I rebase it now before the review is done, or will that interrupt the review process?

@BridgeAR
Copy link
Member

@mattiash it is always best to rebase and to have a clean state to review. Otherwise changed could come in be missed afterwards.

@mattiash
Copy link
Author

Branch rebased as requested. The only conflict was that someone had created internal/tls.js (which I also had) so I did a trivial merge. make -j4 test still passes for me locally.

@mscdex
Copy link
Contributor

mscdex commented Sep 22, 2017

FWIW it looks like there's something up with the author part of the commits' metadata. Perhaps there is a difference in author and committer email addresses or something?

@mattiash
Copy link
Author

FWIW it looks like there's something up with the author part of the commits' metadata. Perhaps there is a difference in author and committer email addresses or something?

Yes, I wrote the patch at work and rebased it from home, that's why the author/committer don't match. I'll rebase again to avoid any confusion. Sorry for the trouble.

@BridgeAR
Copy link
Member

@nodejs/http @nodejs/crypto PTAL. This needs some LGs

@mattiash
Copy link
Author

Note to reviewers: https://github.com/mattiash/test-checkServerIdentity explains what the problem is and contains a test-case that fails with node 8.5.0 but succeeds with the code from this PR.

Copy link
Member

@bnoordhuis bnoordhuis left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This PR adds a fourth IPv6 address parser. We currently have:

  1. net.isIPv6() (which calls out to uv_inet_pton()),
  2. the --inspect=[::0]:1234 parser in src/node_debug_options.cc and
  3. the URL parser (which also parses IPv6 addresses) in src/node_url.cc.

Rather than adding yet another parser, there is probably a way to share code with one of them.

Failing that, a binding method could be added that calls uv_inet_pton() and uv_inet_ntop() to normalize an address. That would ensure consistency with other parts of node.

uv_inet_ntop() will canonicalize them to short form, not long form. I don't think that matters but if it does, you could always replace it with a snprintf() that prints the octets to string.

@jasnell
Copy link
Member

jasnell commented Sep 25, 2017

I have to agree with @bnoordhuis. Reusing one of the existing ipv6 parsing routines is best.

@mattiash
Copy link
Author

Thanks for the review. I looked at the different IPv6 parsing routines already in node, but I couldn't find anything that I could use out of the box to convert IPv6 addresses to a canonical format. I used @bnoordhuis suggestion about uv_inet_ntop/pton which works for my purposes.


args.GetReturnValue().Set(String::NewFromUtf8(isolate, canonical_ip));
} else {
args.GetReturnValue().Set(Undefined(isolate));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Default return value is undefined. No reason to set it here if it hasn't be set prior.

@mattiash
Copy link
Author

Default return value is undefined. No reason to set it here if it hasn't be set prior.

Fixed.

Copy link
Member

@bnoordhuis bnoordhuis left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left some comments but nearly there.

// [::1] => ::1
// [::1]:123 => ::1
if (hostHeader.startsWith('[')) {
options.servername = hostHeader.split(']')[0].substr(1);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

.split(']', 1) is more efficient.

For bonus performance points, if you're going to slice the string anyway, call .indexOf() and then .substr(1, index) (and default index to hostHeader.length if it's -1.)

Lastly, I would say that it should pass on the string untouched if it doesn't contain a matching ].

@@ -1935,6 +1935,30 @@ void IsIPv6(const FunctionCallbackInfo<Value>& args) {
}
}

void canonicalIP(const FunctionCallbackInfo<Value>& args) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Style: CanonicalIP

As well, I'd call it CanonicalizeIP for two reasons:

  1. It makes it clear it's an imperative, not a predicate (i.e., it transforms, it doesn't just check.)
  2. lI is almost indistinguishable from ll, II, etc. with some fonts. (Minor thing. Still.)

char canonical_ip[INET_ADDRSTRLEN];

int err = uv_inet_ntop(AF_INET, address_buffer, canonical_ip,
sizeof(canonical_ip));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Style: please line up the argument.


args.GetReturnValue().Set(String::NewFromUtf8(isolate, canonical_ip));
} else if (uv_inet_pton(AF_INET6, *ip, &address_buffer) == 0) {
char canonical_ip[INET6_ADDRSTRLEN];
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd just move this up a scope, it's big enough to hold IPv4 and IPv6 address strings. Shaves off a few lines of code.

assert.strictEqual(canonicalIP('fe80:0:0:0:0:0:0:0'), 'fe80::');
assert.strictEqual(
canonicalIP('fe80::0000:0010:0001'),
'fe80::10:1');
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This fits on one line. If it didn't, house style is to write it like this:

assert.strictEqual(canonicalIP('fe80::0000:0010:0001'),
                   'fe80::10:1');

Only if that wouldn't fit in 80 columns would you use one-argument-one-line style but then please indent by four spaces. (Truth be told, I would have expected the linter to complain about that.)

@mattiash
Copy link
Author

Addressed all comments from @bnoordhuis.

@apapirovski
Copy link
Member

apapirovski commented Nov 3, 2017

Landed in b6df87e

Congrats on becoming a Contributor @mattiasholmlund!

@apapirovski apapirovski closed this Nov 3, 2017
cjihrig pushed a commit to cjihrig/node that referenced this pull request Nov 6, 2017
- Properly handle IPv6 in Host header when setting servername.
- When comparing IP addresses against addresses in the subjectAltName
  field of a certificate, format the address correctly before
  doing the string comparison.

PR-URL: nodejs#14772
Fixes: nodejs#14736
Reviewed-By: Ben Noordhuis <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: James M Snell <[email protected]>
@cjihrig cjihrig mentioned this pull request Nov 6, 2017
@gibfahn gibfahn added the baking-for-lts PRs that need to wait before landing in a LTS release. label Nov 14, 2017
@MylesBorins
Copy link
Contributor

Letting this bake in Current a bit longer before landing into LTS

MylesBorins pushed a commit that referenced this pull request Dec 8, 2017
- Properly handle IPv6 in Host header when setting servername.
- When comparing IP addresses against addresses in the subjectAltName
  field of a certificate, format the address correctly before
  doing the string comparison.

PR-URL: #14772
Fixes: #14736
Reviewed-By: Ben Noordhuis <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: James M Snell <[email protected]>
@mattiasholmlund
Copy link
Contributor

Has this baked in master for long enough now to be considered for the v8 lts? The PR was included in Version 9.1.0 2017-11-07, so it has been out in the wild for over two months now.

mattiasholmlund added a commit to mattiasholmlund/node that referenced this pull request Jan 23, 2018
- Properly handle IPv6 in Host header when setting servername.
- When comparing IP addresses against addresses in the subjectAltName
  field of a certificate, format the address correctly before
  doing the string comparison.

PR-URL: nodejs#14772
Fixes: nodejs#14736
Reviewed-By: Ben Noordhuis <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: James M Snell <[email protected]>
@gibfahn gibfahn removed the baking-for-lts PRs that need to wait before landing in a LTS release. label Jan 26, 2018
gibfahn pushed a commit that referenced this pull request Jan 26, 2018
- Properly handle IPv6 in Host header when setting servername.
- When comparing IP addresses against addresses in the subjectAltName
  field of a certificate, format the address correctly before
  doing the string comparison.

PR-URL: #14772
Fixes: #14736
Reviewed-By: Ben Noordhuis <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: James M Snell <[email protected]>
@gibfahn
Copy link
Member

gibfahn commented Jan 26, 2018

Has this baked in master for long enough now to be considered for the v8 lts?

I think so, I've landed it on v8.x-staging.

MylesBorins pushed a commit that referenced this pull request Feb 27, 2018
- Properly handle IPv6 in Host header when setting servername.
- When comparing IP addresses against addresses in the subjectAltName
  field of a certificate, format the address correctly before
  doing the string comparison.

PR-URL: #14772
Fixes: #14736
Reviewed-By: Ben Noordhuis <[email protected]>
Reviewed-By: Anatoli Papirovski <[email protected]>
Reviewed-By: James M Snell <[email protected]>
@MylesBorins
Copy link
Contributor

backport to v6.x-staging in 8e7ac25

This was referenced Feb 27, 2018
MylesBorins added a commit that referenced this pull request Mar 6, 2018
Notable Changes:

* http, tls:
  - better support for IPv6 addresses (Mattias Holmlund)
    #14772

PR-URL: #19027
MylesBorins added a commit that referenced this pull request Mar 6, 2018
Notable Changes:

* http, tls:
  - better support for IPv6 addresses (Mattias Holmlund)
    #14772

PR-URL: #19027
gibfahn added a commit that referenced this pull request Mar 6, 2018
Notable changes:

* deps:
  * update V8 to 6.2.414.46 (Michaël Zasso) [#16413](#16413)
  * revert ABI breaking changes in V8 6.2 (Anna Henningsen) [#16413](#16413)
  * upgrade libuv to 1.19.1 (cjihrig) [#18260](#18260)
  * re land npm 5.6.0 (Myles Borins) [#18625](#18625)
  * ICU 60 bump (Steven R. Loomis) [#16876](#16876)
* crypto:
  * Support both OpenSSL 1.1.0 and 1.0.2 (David Benjamin) [#16130](#16130)
  * warn on invalid authentication tag length (Tobias Nießen) [#17566](#17566)
* async_hooks:
  * update defaultTriggerAsyncIdScope for perf (Anatoli Papirovski) [#18004](#18004)
  * use typed array stack as fast path (Anna Henningsen) [#17780](#17780)
  * use scope for defaultTriggerAsyncId (Andreas Madsen) [#17273](#17273)
  * separate missing from default context (Andreas Madsen) [#17273](#17273)
  * rename initTriggerId (Andreas Madsen) [#17273](#17273)
  * deprecate undocumented API (Andreas Madsen) [#16972](#16972)
  * add destroy event for gced AsyncResources (Sebastian Mayr) [#16998](#16998)
  * add trace events to async_hooks (Andreas Madsen) [#15538](#15538)
  * set HTTPParser trigger to socket (Andreas Madsen) [#18003](#18003)
  * add provider types for net server (Andreas Madsen) [#17157](#17157)
* n-api:
  * add helper for addons to get the event loop (Anna Henningsen) [#17109](#17109)
* cli:
  * add --stack-trace-limit to NODE_OPTIONS (Anna Henningsen) [#16495](#16495)
* console:
  * add support for console.debug (Benjamin Zaslavsky) [#17033](#17033)
* module:
  * add builtinModules (Jon Moss) [#16386](#16386)
  * replace default paths in require.resolve() (cjihrig) [#17113](#17113)
* src:
  * add helper for addons to get the event loop (Anna Henningsen) [#17109](#17109)
  * add process.ppid (cjihrig) [#16839](#16839)
* http:
  * support generic `Duplex` streams (Anna Henningsen) [#16267](#16267)
  * add rawPacket in err of `clientError` event (XadillaX) [#17672](#17672)
  * better support for IPv6 addresses (Mattias Holmlund) [#14772](#14772)
* net:
  * remove ADDRCONFIG DNS hint on Windows (Bartosz Sosnowski) [#17662](#17662)
* process:
  * fix reading zero-length env vars on win32 (Anna Henningsen) [#18463](#18463)
* tls:
  * unconsume stream on destroy (Anna Henningsen) [#17478](#17478)
* process:
  * improve unhandled rejection message (Madara Uchiha) [#17158](#17158)
* stream:
  * remove usage of *State.highWaterMark (Calvin Metcalf) [#12860](#12860)
* trace_events:
  * add executionAsyncId to init events (Andreas Madsen) [#17196](#17196)

PR-URL: #18336
gibfahn added a commit that referenced this pull request Mar 7, 2018
Notable changes:

* deps:
  * update V8 to 6.2.414.46 (Michaël Zasso) [#16413](#16413)
  * revert ABI breaking changes in V8 6.2 (Anna Henningsen) [#16413](#16413)
  * upgrade libuv to 1.19.1 (cjihrig) [#18260](#18260)
  * re land npm 5.6.0 (Myles Borins) [#18625](#18625)
  * ICU 60 bump (Steven R. Loomis) [#16876](#16876)
* crypto:
  * Support both OpenSSL 1.1.0 and 1.0.2 (David Benjamin) [#16130](#16130)
  * warn on invalid authentication tag length (Tobias Nießen) [#17566](#17566)
* async_hooks:
  * update defaultTriggerAsyncIdScope for perf (Anatoli Papirovski) [#18004](#18004)
  * use typed array stack as fast path (Anna Henningsen) [#17780](#17780)
  * use scope for defaultTriggerAsyncId (Andreas Madsen) [#17273](#17273)
  * separate missing from default context (Andreas Madsen) [#17273](#17273)
  * rename initTriggerId (Andreas Madsen) [#17273](#17273)
  * deprecate undocumented API (Andreas Madsen) [#16972](#16972)
  * add destroy event for gced AsyncResources (Sebastian Mayr) [#16998](#16998)
  * add trace events to async_hooks (Andreas Madsen) [#15538](#15538)
  * set HTTPParser trigger to socket (Andreas Madsen) [#18003](#18003)
  * add provider types for net server (Andreas Madsen) [#17157](#17157)
* n-api:
  * add helper for addons to get the event loop (Anna Henningsen) [#17109](#17109)
* cli:
  * add --stack-trace-limit to NODE_OPTIONS (Anna Henningsen) [#16495](#16495)
* console:
  * add support for console.debug (Benjamin Zaslavsky) [#17033](#17033)
* module:
  * add builtinModules (Jon Moss) [#16386](#16386)
  * replace default paths in require.resolve() (cjihrig) [#17113](#17113)
* src:
  * add helper for addons to get the event loop (Anna Henningsen) [#17109](#17109)
  * add process.ppid (cjihrig) [#16839](#16839)
* http:
  * support generic `Duplex` streams (Anna Henningsen) [#16267](#16267)
  * add rawPacket in err of `clientError` event (XadillaX) [#17672](#17672)
  * better support for IPv6 addresses (Mattias Holmlund) [#14772](#14772)
* net:
  * remove ADDRCONFIG DNS hint on Windows (Bartosz Sosnowski) [#17662](#17662)
* process:
  * fix reading zero-length env vars on win32 (Anna Henningsen) [#18463](#18463)
* tls:
  * unconsume stream on destroy (Anna Henningsen) [#17478](#17478)
* process:
  * improve unhandled rejection message (Madara Uchiha) [#17158](#17158)
* stream:
  * remove usage of *State.highWaterMark (Calvin Metcalf) [#12860](#12860)
* trace_events:
  * add executionAsyncId to init events (Andreas Madsen) [#17196](#17196)

PR-URL: #18336
MayaLekova pushed a commit to MayaLekova/node that referenced this pull request May 8, 2018
Notable Changes:

* http, tls:
  - better support for IPv6 addresses (Mattias Holmlund)
    nodejs#14772

PR-URL: nodejs#19027
MayaLekova pushed a commit to MayaLekova/node that referenced this pull request May 8, 2018
Notable changes:

* deps:
  * update V8 to 6.2.414.46 (Michaël Zasso) [nodejs#16413](nodejs#16413)
  * revert ABI breaking changes in V8 6.2 (Anna Henningsen) [nodejs#16413](nodejs#16413)
  * upgrade libuv to 1.19.1 (cjihrig) [nodejs#18260](nodejs#18260)
  * re land npm 5.6.0 (Myles Borins) [nodejs#18625](nodejs#18625)
  * ICU 60 bump (Steven R. Loomis) [nodejs#16876](nodejs#16876)
* crypto:
  * Support both OpenSSL 1.1.0 and 1.0.2 (David Benjamin) [nodejs#16130](nodejs#16130)
  * warn on invalid authentication tag length (Tobias Nießen) [nodejs#17566](nodejs#17566)
* async_hooks:
  * update defaultTriggerAsyncIdScope for perf (Anatoli Papirovski) [nodejs#18004](nodejs#18004)
  * use typed array stack as fast path (Anna Henningsen) [nodejs#17780](nodejs#17780)
  * use scope for defaultTriggerAsyncId (Andreas Madsen) [nodejs#17273](nodejs#17273)
  * separate missing from default context (Andreas Madsen) [nodejs#17273](nodejs#17273)
  * rename initTriggerId (Andreas Madsen) [nodejs#17273](nodejs#17273)
  * deprecate undocumented API (Andreas Madsen) [nodejs#16972](nodejs#16972)
  * add destroy event for gced AsyncResources (Sebastian Mayr) [nodejs#16998](nodejs#16998)
  * add trace events to async_hooks (Andreas Madsen) [nodejs#15538](nodejs#15538)
  * set HTTPParser trigger to socket (Andreas Madsen) [nodejs#18003](nodejs#18003)
  * add provider types for net server (Andreas Madsen) [nodejs#17157](nodejs#17157)
* n-api:
  * add helper for addons to get the event loop (Anna Henningsen) [nodejs#17109](nodejs#17109)
* cli:
  * add --stack-trace-limit to NODE_OPTIONS (Anna Henningsen) [nodejs#16495](nodejs#16495)
* console:
  * add support for console.debug (Benjamin Zaslavsky) [nodejs#17033](nodejs#17033)
* module:
  * add builtinModules (Jon Moss) [nodejs#16386](nodejs#16386)
  * replace default paths in require.resolve() (cjihrig) [nodejs#17113](nodejs#17113)
* src:
  * add helper for addons to get the event loop (Anna Henningsen) [nodejs#17109](nodejs#17109)
  * add process.ppid (cjihrig) [nodejs#16839](nodejs#16839)
* http:
  * support generic `Duplex` streams (Anna Henningsen) [nodejs#16267](nodejs#16267)
  * add rawPacket in err of `clientError` event (XadillaX) [nodejs#17672](nodejs#17672)
  * better support for IPv6 addresses (Mattias Holmlund) [nodejs#14772](nodejs#14772)
* net:
  * remove ADDRCONFIG DNS hint on Windows (Bartosz Sosnowski) [nodejs#17662](nodejs#17662)
* process:
  * fix reading zero-length env vars on win32 (Anna Henningsen) [nodejs#18463](nodejs#18463)
* tls:
  * unconsume stream on destroy (Anna Henningsen) [nodejs#17478](nodejs#17478)
* process:
  * improve unhandled rejection message (Madara Uchiha) [nodejs#17158](nodejs#17158)
* stream:
  * remove usage of *State.highWaterMark (Calvin Metcalf) [nodejs#12860](nodejs#12860)
* trace_events:
  * add executionAsyncId to init events (Andreas Madsen) [nodejs#17196](nodejs#17196)

PR-URL: nodejs#18336
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
http Issues or PRs related to the http subsystem. tls Issues and PRs related to the tls subsystem.
Projects
None yet
Development

Successfully merging this pull request may close these issues.