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

openssl-legacy-provider CLI argument doesn't seem to work as expected #47379

Closed
lokesh411 opened this issue Apr 3, 2023 · 13 comments
Closed

Comments

@lokesh411
Copy link

lokesh411 commented Apr 3, 2023

Version

v18.15.0

Platform

5.4.0-1089-azure #94~18.04.1-Ubuntu SMP Fri Aug 5 12:34:50 UTC 2022 x86_64 GNU/Linux

Subsystem

No response

What steps will reproduce the bug?

I recently upgraded the service that i was working on from node:14 to node:18, I was getting the following error
write EPROTO C057DCF6287F0000:error:0A000152:SSL routines:final_renegotiate:unsafe legacy renegotiation disabled
When i investigated a bit, I found that in node:17 openssl was upgraded to 3.0.0, which resulted in removing the support for legacy cipher algorithms. And the workaround for the same was running with --openssl-legacy-provider.
I tried running with this and it didn't work. Can you please help me here?

How often does it reproduce? Is there a required condition?

No response

What is the expected behavior? Why is that the expected behavior?

As per the documentation, --openssl-legacy-provider should work and it should switch to the legacy provider of openssl 3.0.0. But i was still getting the same error

What do you see instead?

write EPROTO C057DCF6287F0000:error:0A000152:SSL routines:final_renegotiate:unsafe legacy renegotiation disabled

Additional information

I tried running the service/script with the following command. (app.js is the file name)
node --openssl-legacy-provider app.js tried also doing this node app.js --openssl-legacy-provider

@mscdex
Copy link
Contributor

mscdex commented Apr 3, 2023

--openssl-legacy-provider only enables insecure algorithms (e.g. ciphers, hashes, etc.). The error you're encountering is specifically about TLS/SSL.

You can enable the unsafe legacy renegotiation by setting secureOptions: crypto.constants.SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION (or perhaps SSL_OP_LEGACY_SERVER_CONNECT) in your HTTPS request settings, but you really should not because it can open you up to man-in-the-middle attacks according to the related CVE-2009-3555. It's better to have the endpoint you're trying to connect to upgrade its TLS/SSL handling.

@lokesh411
Copy link
Author

Yes, I am also trying to upgrade the SSL cipher suites, but i would want to have a temporary workaround.
I tried the securedOptions as well, that works, but i want to enable this globally.
Is there anyway to use the unsafe legacy renegotiation globally in node:18, without any changes in the code base?

@mscdex
Copy link
Contributor

mscdex commented Apr 3, 2023

You should be able to set up an openssl.cnf that is configured appropriately and tell node to use that (e.g. setting the OPENSSL_CONF environment variable or passing the path on the command line via --openssl-config=...) for configuring OpenSSL's behavior.

@lokesh411
Copy link
Author

Understood, Thanks a lot for your time and information

@mikaello
Copy link

mikaello commented Apr 14, 2023

I think the error unsafe legacy renegotiation disabled is hitting many users on VPN or behind corporate firewalls not supporting RFC5746 secure renegotiation, for those users it doesn't help that the remote server supports it.

I have struggled a lot with this error, and in every case ended up downgrading to Node 16. I have tried both OPENSSL_CONF and NODE_OPTIONS='--openssl-config=...' for our applications, but it does not work. It seems like Node won't load the option defined in the provided config. This is the config I have used:

openssl_conf = openssl_init

[openssl_init]
ssl_conf = ssl_sect

[ssl_sect]
system_default = system_default_sect

[system_default_sect]
Options = UnsafeLegacyServerConnect

Since the option UnsafeLegacyServerConnect was unsupported in OpenSSL < 3.0.4, I have also tried the option UnsafeLegacyRenegotiation with no luck.

If someone finds a solution, please write about it :-)

@ckcr4lyf
Copy link
Contributor

If someone finds a solution, please write about it :-)

@mikaello you need to set the section name as nodejs_conf in the OpenSSL config file, introduced in #43124

So for example, you could use the following:

nodejs_conf = openssl_init

[openssl_init]
ssl_conf = ssl_sect

[ssl_sect]
system_default = system_default_sect

[system_default_sect]
Options = UnsafeLegacyRenegotiation

I've a PoC w/ docker if its of interest: https://github.com/ckcr4lyf/no-rfc5746/blob/ed83a446e4aaa08f1edaa96af9b41c91b56834f5/Dockerfile

@stillcollating
Copy link

stillcollating commented Jun 14, 2023

I have tried various combinations of all these settings on nodejs 18.16.0 windows x64, to no avail. I'm always getting "unsafe legacy renegotiation disabled". This is stemming from the transparent ssl proxy on my corporate network. I know I had this working awhile back (multiple months) on nodejs 18, and my notes only say to use --openssl-legacy-provider. Not sure if nodejs changed or our ssl snooper changed.

Setting secureOptions to either SSL_OP_LEGACY_SERVER_CONNECT or SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION does fix the problem. But I'm trying to get npm to work, so I need a more global setting.

When I use --openssl-config=xxxx I don't get any error even when I supply a nonexistent filename.. makes me wonder if this option is actually reading in the openssl.cnf I'm trying to give it. Tried both UnsafeLegacyRenegotiation and UnsafeLegacyServerConnect. Neither changed the behavior.

@ckcr4lyf
Copy link
Contributor

When I use --openssl-config=xxxx I don't get any error even when I supply a nonexistent filename..

@stillcollating what is the command when you're trying to pass it as CLI to npm? I am not sure if passing it via, e.g.

npm install abcd --openssl-config=xxxx

I think npm won't pass those down to node itself.

You can try and use the OPENSSL_CONF environment variable and see if that helps.

@ckcr4lyf
Copy link
Contributor

I know I had this working awhile back (multiple months) on nodejs 18

Do you remember which version of 18? The behavior of the section in openssl.cnf was changed in 18.4.

@stillcollating
Copy link

@ckcr4lyf I've been doing my testing with just nodejs using a test.js that calls https.request. If I set secureOptions with SSL_OP_LEGACY_SERVER_CONNECT or SSL_OP_ALLOW_UNSAFE_LEGACY_RENEGOTIATION the https.request works. I just need that to be the default behavior in any call to https.request. the openssl-config setting seems the most likely solution but it is not work for me thus far.

In windows command prompt I have been testing using: node --openssl-config=openssl.cnf test.js

openssl.cnf and test.js are in current working directory.

And test.js contains a call to https.request.

no error is given with a nonexistent openssl.cnf and supplying a valid openssl.cnf file with the suggested settings does not fix the issue. I also tried setting OPENSSL_CONF environment variable and no luck.

I get the feeling this is likely specific to the Windows version of node, but that's just a guess.

@ckcr4lyf
Copy link
Contributor

no error is given with a nonexistent openssl.cnf

Right, it is silently ignored

I get the feeling this is likely specific to the Windows version of node

I think you might be right, I can't confirm this as I'm on Linux, but when I later get access to a Windows PC I'll try.

@RunSeven
Copy link

I had a similar issue on Windows using node 18.17.0 and npm 9.6.7

I had some success using a variation on the above answers by @mikaello and @ckcr4lyf where either the last or first line is changed respectively.

nodejs_conf = openssl_init

[openssl_init]
ssl_conf = ssl_sect

[ssl_sect]
system_default = system_default_sect

[system_default_sect]
Options = UnsafeLegacyServerConnect 

@liudonghua123
Copy link
Contributor

I use export NODE_OPTIONS=--openssl-legacy-provider (linux/macos) or set NODE_OPTIONS=--openssl-legacy-provider (windows) for my node 18/20+.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

7 participants