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

Enable --security-revert to be used in NODE_OPTIONS environment variable #52017

Open
singyantam opened this issue Mar 8, 2024 · 27 comments · May be fixed by #52365
Open

Enable --security-revert to be used in NODE_OPTIONS environment variable #52017

singyantam opened this issue Mar 8, 2024 · 27 comments · May be fixed by #52365
Labels
feature request Issues that request new features to be added to Node.js. security Issues and PRs related to security.

Comments

@singyantam
Copy link

What is the problem this feature will solve?

When Nodejs is used for AWS lambda, the only mechanism available to supply Nodejs options is via NODE_OPTIONS environment variable. The recent Feb 24 security release started blocking use of RSA_PKCS1_PADDING in crypto module's privateDecrypt method. For any major company that always keep up to date with security patches, this new release immediate block Nodejs lambda's ability to process legacy data that was encrypted with RSA_PKCS1_PADDING.

If the --security-revert option can be specified via NODE_OPTIONS, we have the mechanism to allow Nodejs Lambda's to continue processing legacy data while remediation is developed and implemented.

What is the feature you are proposing to solve the problem?

Just allow --security-revert to be specified and acknowledge using NODE_OPTIONS - and not restrict it to be on the command line.

What alternatives have you considered?

No other possibility when dealing with AWS Lambda Nodejs runtime.

@singyantam singyantam added the feature request Issues that request new features to be added to Node.js. label Mar 8, 2024
@WilliamABradley
Copy link

I'm running into the same issue with AWS Lambda, and hit this with an API that is outside of my control.

As a workaround, we can use node-rsa:

const crypto = require("crypto");
const NodeRSA = require("node-rsa");

const keypair = crypto.generateKeyPairSync("rsa", {
  modulusLength: 2048,
});

const data = Buffer.from("Hello, World!");

const encrypted = crypto.publicEncrypt(
  {
    key: keypair.publicKey,
    padding: crypto.constants.RSA_PKCS1_PADDING,
  },
  data
);
console.log("encrypted: ", encrypted.toString("base64"));

const keyRSA = new NodeRSA(
  keypair.privateKey.export({ format: "pem", type: "pkcs1" }),
  "private",
  {
    encryptionScheme: "pkcs1",
  }
);

// By default it will use the node crypto library with the CVE
keyRSA.setOptions({ environment: "browser" });

const decrypted = keyRSA.decrypt(encrypted);
console.log("decrypted: ", decrypted.toString());

@singyantam
Copy link
Author

singyantam commented Mar 10, 2024 via email

@WilliamABradley
Copy link

Yeah, I'm not a fan of the workaround (and adding another dependency), and would much rather be able to disable the CVE block with an environment variable or other method.

@fliodhais
Copy link

The workaround isn't ideal but at least it works in the case of AWS lambda environment where we can't just simply pass in the NODE_OPTIONS unfortunately this is a good patch solution.

@mhdawson
Copy link
Member

I'm surprised that NODE_OPTIONS does not support the security revert command line options. We'll have to see if that was on purpose on an omission due to the way options are allowed in NODE_OPTIONS.

@mhdawson
Copy link
Member

It seems like it was a specific decision at the time - #12028 (comment)

@mhdawson
Copy link
Member

I've reached out to one of the other maintainers that was part of the original PR/discussion to see if we still believe the exclusion from NODE_OPTIONS is the right way to go.

@melihbirim
Copy link

Having node-rsa and environment attribute to 'browser' solved the problem on my end. But the problem is having a fix on node that does break all the code we have without clarifying the exact real solution.
Any system, without a change should work as it is. It just drops the trust on the node versions in which we are not responsible to update to the latest version like in AWS lambda.

@mhdawson
Copy link
Member

Talked with one of the other maintainers re the earlier concerns about including --cve-revert in NODE_OPTIONS and those concerns still apply.

One idea we came up with was the option of adding and api along the lines of

process.cveRevert('cve...")

that could be used to turn on a revert programatically. That would require an update to the Node.js application and would not flow through to spawned processes (similar to command line options I think), but would give another option versus the command line.

@singyantam would that approach work in your situation?

@WilliamABradley
Copy link

I think that would work for us, I was wondering if I could set process.CVE_... to true manually (As that is true when the security revert is applied), but seeing as this logic is in native code and not userland, that would not do anything.

@singyantam
Copy link
Author

singyantam commented Mar 14, 2024 via email

mhdawson added a commit to mhdawson/io.js that referenced this issue Mar 15, 2024
Refs: nodejs#52017

Add API to enable CVE reverts for use in environments
where the command line option cannot be used.

Signed-off-by: Michael Dawson <midawson@redhat.com>
@mhdawson
Copy link
Member

Draft PR from looking at adding process.cveRevert - #52090

@jasnell could you take a llook and let me know if the approach looks ok to you. If so I'll add the documentation. The other question I have is if we might want to leave in a few test entries like I have so that we could have tests to validate the functionality. People could enable them, but of course they would have no effect so I'm thinking it might be ok as a tradeoff for being able to have some testing. If you agree that makes sense I could then add some tests as well.

@andclt
Copy link

andclt commented Mar 20, 2024

No other possibility when dealing with AWS Lambda Nodejs runtime.

Not as handy as NODE_OPTIONS env var, but it is possible to set --security-revert command line option in Lambda by using a wrapper script: https://docs.aws.amazon.com/lambda/latest/dg/runtimes-modify.html#runtime-wrapper

@mhdawson
Copy link
Member

@singyantam would the wrapper script suggestion in #52017 (comment) work for you ?

@singyantam
Copy link
Author

singyantam commented Mar 20, 2024 via email

@mhdawson
Copy link
Member

mhdawson commented Mar 25, 2024

@singyantam in that case I think you trying to explain your challenge more in #52090 might be useful. Right now it's not gaining traction.

@if-fi
Copy link

if-fi commented Mar 30, 2024

We are facing the same problem i Google/Firebase Cloud Functions since yesterday.
The NodeRsa workaround does work, but adding --security-revert in NODE_OPTIONS would be much cleaner solution.

@tniessen
Copy link
Member

Is the main concern with NODE_OPTIONS that it might be inherited by child processes unintentionally?

@mhdawson
Copy link
Member

mhdawson commented Apr 2, 2024

@tniessen I believe that would be the concern.

@tniessen
Copy link
Member

tniessen commented Apr 2, 2024

My main concern with process.cveRevert is that it can also be used with --require and thus effectively through NODE_OPTIONS, but I do see the advantage of not implicitly inheriting it unless someone intentionally uses NODE_OPTIONS that way. Still, regardless of the threat model, I think it might be preferable to only allow such security-critical configuration before any user code runs.

Does AWS allow setting other environment variables? Theoretically, we could also add a new environment variable NODE_SECURITY_REVERT that, if set, emits a warning, is applied just like --security-revert, and is then cleared unless the value ends with +sticky or so. (This is not elegant by any means, of course, I'm just trying to come up with workarounds.)

@WilliamABradley
Copy link

@tniessen AWS Lambdas can set any environment variable, it is just modifying node arguments which is difficult

bluelovers added a commit to bluelovers/ws-rest that referenced this issue Apr 3, 2024
…46809

RSA_PKCS1_PADDING is no longer supported for private decryption, this can be reverted with --security-revert=CVE-2023-46809

nodejs/node#52017
@mhdawson
Copy link
Member

mhdawson commented Apr 3, 2024

@tniessen great to have other suggestions. The main different as I understand it is that the user could control the propagation, right?

@tniessen
Copy link
Member

tniessen commented Apr 4, 2024

@mhdawson Yes, and no user code can change the setting at runtime (except for child processes, but users can always pass --security-revert to child processes as well). It would also work for hypothetical scenarios in which some configuration is only possible before running user code, e.g., if it's some V8 flag or libuv setup or so.

tniessen added a commit to tniessen/node that referenced this issue Apr 4, 2024
Some vendors do not allow passing custom command-line flags to the node
executable. There are concerns around allowing --security-revert in
NODE_OPTIONS because it might be inherited by child processes
unintentionally.

This patch introduces a new environment variable that, if set, is unset
immediately unless it ends with "+sticky". Aside from that optional
suffix, its value is a comma-separated list of CVE identifiers for which
the respective security patches should be reverted.

Closes: nodejs#52017
@tniessen tniessen linked a pull request Apr 4, 2024 that will close this issue
@tniessen
Copy link
Member

tniessen commented Apr 4, 2024

Alternative PR: #52365

tniessen added a commit to tniessen/node that referenced this issue Apr 6, 2024
Some vendors do not allow passing custom command-line flags to the node
executable. There are concerns around allowing --security-revert in
NODE_OPTIONS because it might be inherited by child processes
unintentionally.

This patch introduces a new environment variable that, if set, is unset
immediately unless it ends with "+sticky". Aside from that optional
suffix, its value is a comma-separated list of CVE identifiers for which
the respective security patches should be reverted.

Closes: nodejs#52017
tniessen added a commit to tniessen/node that referenced this issue Apr 8, 2024
Some vendors do not allow passing custom command-line flags to the node
executable. There are concerns around allowing --security-revert in
NODE_OPTIONS because it might be inherited by child processes
unintentionally.

This patch introduces a new environment variable that, if set, is unset
immediately unless it ends with "+sticky". Aside from that optional
suffix, its value is a comma-separated list of CVE identifiers for which
the respective security patches should be reverted.

Closes: nodejs#52017
@tniessen
Copy link
Member

tniessen commented Apr 8, 2024

@singyantam @WilliamABradley @if-fi Could you please check if #52365 would solve this issue for you?

tniessen added a commit to tniessen/node that referenced this issue Apr 8, 2024
Some vendors do not allow passing custom command-line flags to the node
executable. There are concerns around allowing --security-revert in
NODE_OPTIONS because it might be inherited by child processes
unintentionally.

This patch introduces a new environment variable that, if set, is unset
immediately unless it ends with "+sticky". Aside from that optional
suffix, its value is a comma-separated list of CVE identifiers for which
the respective security patches should be reverted.

Closes: nodejs#52017
@tniessen tniessen added the security Issues and PRs related to security. label Apr 8, 2024
@if-fi
Copy link

if-fi commented Apr 8, 2024

@singyantam @WilliamABradley @if-fi Could you please check if #52365 would solve this issue for you?

It looks like it would solve the Google Cloud Functions issue.

tniessen added a commit to tniessen/node that referenced this issue Apr 19, 2024
Some vendors do not allow passing custom command-line flags to the node
executable. There are concerns around allowing --security-revert in
NODE_OPTIONS because it might be inherited by child processes
unintentionally.

This patch introduces a new environment variable that, if set, is unset
immediately unless it ends with "+sticky". Aside from that optional
suffix, its value is a comma-separated list of CVE identifiers for which
the respective security patches should be reverted.

Closes: nodejs#52017
@extremeheat
Copy link

From a library standpoint, requiring users to use command line or environment variables to revert seems relatively high friction especially as it's code that has worked before and suddenly stops working on a new node version.

I do understand the security rationale for this change, but is there a reason an override couldn't be added to a call parameter and not relying on environment variables or runtime options (which we don't have much control over from lib standpoint)? We may have to switch to a pure JS implementation to handle this cleanly (thanks @WilliamABradley for the snippet).

+1 to mhdawson's proposal:

process.cveRevert('cve...")

in #52090 -- this would be great!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature request Issues that request new features to be added to Node.js. security Issues and PRs related to security.
Projects
Status: Awaiting Triage
Development

Successfully merging a pull request may close this issue.

9 participants