镜像站点 · 本页由第三方 GitHub 只读镜像提供,非 GitHub 官方站点,不接受任何登录或凭据输入。前往 github.com
Skip to content

Crypto cant sign/verify prehashed inputs #60263

Description

@codermapuche

Version

Node.js v22.20.0 - Node.js v24.10.0

Platform

all

Subsystem

crypto

What steps will reproduce the bug?

const crypto = require('crypto');

const message		 	= Buffer.from('LmM8PqCO1QIpTse0s+MQEJ7YXOSZuqyjPCJ4tIZ+OrU=', 'base64'),
			prehash 	 	= crypto.createHash('sha256').update(message).digest();

const namedCurve 	= 'secp256k1',
			keyPair 	 	= crypto.generateKeyPairSync('ec', { namedCurve }),
			signature		= crypto.sign(null, prehash, {
											key					: keyPair.privateKey,
											dsaEncoding	: 'ieee-p1363'
										});

console.log(crypto.verify(null, message, {
	key					: keyPair.publicKey,
	dsaEncoding	: 'ieee-p1363'
}, signature), ' message internal-internal (must be false)');

console.log(crypto.verify(null, prehash, {
	key					: keyPair.publicKey,
	dsaEncoding	: 'ieee-p1363'
}, signature), ' prehash internal-internal (must be true)');

// Simple unitary test:
const PUBLIC_KEY_PEM = '-----BEGIN PUBLIC KEY-----\n' +
										 	'MFYwEAYHKoZIzj0CAQYFK4EEAAoDQgAE6Yvel06IICYJZ/XsuPEFTpDt0aU8dwLK\n' +
										 	'jvgxyYTeZ/vlS49/PDRIr5JDz+QNWFB9ZM9tf4i9SdT0LVtlgRj3dQ==\n' +
										 	'-----END PUBLIC KEY-----',
			publicKey 		 = crypto.createPublicKey(PUBLIC_KEY_PEM),
			signOfPreHash  = Buffer.from('Djv4wD3eWu8lHI3DrN2Dypdrirj+J1rfJD5O1B/Tw8sYy38jms77neECQ0S9LHpnWun+Jb9iOZNbYjH+CoVUnA==', 'base64');

console.log('== BUG HERE ==');

console.log(crypto.verify(null, message, {
	key					: publicKey,
	dsaEncoding	: 'ieee-p1363'
}, signOfPreHash), ' message external-internal (must be false)');

console.log(crypto.verify(null, prehash, {
	key					: publicKey,
	dsaEncoding	: 'ieee-p1363'
}, signOfPreHash), ' prehash external-internal (must be true)');

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

No precondition required.

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

When send null to algorithm param i expect that message payload be raw, prehashed, dont want an additional internal rehash. This make impossible verify or sign keeping compatibility with external systems.

What do you see instead?

crypto module ignore my null and place a sha256 algorithm instead, performing a double hash internally.

Additional information

Many external systems provide hash + signarure to verify, but we cannot do this because the implicit rehash of crypto module.

Activity

  1. codermapuche commented on Oct 15, 2025

    @codermapuche
    Author

    Also related: https://security.stackexchange.com/questions/239345/verify-signature-without-digest

    Maybe change openssl primitives called for this case is needed

  2. Martin-Luther commented on Oct 28, 2025

    @Martin-Luther

    I am having a similar issue after that I have upgraded from node js v22.18.0 to v22.20.0
    RangeError: Invalid key while trying to use Scrypt.verify.
    I am using scrypt-kdf.
    It was working perfectly before the upgrade.
    It still work on Mac OS X, but not on my Linux (Debian 11)

  3. codermapuche commented on Oct 28, 2025

    @codermapuche
    Author

    @Martin-Luther i dont sure what your problem is related to this bug, i think it was another thing.
    scrypt-kdf is a npm package what perform a wrapper over crypto.scrypt, this is not related with crypto.sign or crypto.verify.

    Maybe the best is open another issue for your case, in the scrypt-kdf repo not here.

    I can confirm what this bug is present from node v14.21.3 to v25.0, so is not a regression issue, sounds more like a feature request.

  4. added a commit that references this issue on Oct 28, 2025
  5. panva commented on Oct 28, 2025

    @panva
    Member

    When send null to algorithm param i expect that message payload be raw, prehashed, dont want an additional internal rehash.

    Do you expect such based on some of node's documentation? IIRC no documentation exists that should create such expectation.

  6. added
    cryptoIssues and PRs related to the crypto subsystem.
    feature requestIssues requesting new Node.js features.
    on Oct 28, 2025
  7. codermapuche commented on Oct 28, 2025

    @codermapuche
    Author

    @panva there’s no explicit documentation stating this behavior, so it can be interpreted as a feature request rather than a bug.

    When I pass null as the algorithm for an EC key, I expect the input to be treated as prehashed (raw).

    From the docs:

    Calculates and returns the signature for data using the given private key and algorithm. If algorithm is null or undefined, then the algorithm is dependent upon the key type.

    algorithm is required to be null or undefined for Ed25519, Ed448, and ML-DSA.

    I’m porting the Ethereum protocol to the native node:crypto module, and I’ve run into three requirements:

    1. support for the keccak256 hash algorithm
    2. access to the recovery parameters (r, s, and recovery id)
    3. the DevP2P protocol handshake, which requires signing fixed-length raw bytes (no internal hashing) is the current issue.

    To support this without breaking existing cases, adding a "raw" or "prehash" algorithm option might be the most consistent approach.

  8. Martin-Luther commented on Oct 28, 2025

    @Martin-Luther

    @codermapuche I said similar, not exactly the same. As you mentioned, scrypt-kdf is a wrapper. Excuse me if I am mistaking, but doesn't it means that it could be using the same methods to verify (over crypto.scrypt) ?
    Allow me to try with node::crypto.scrypt to see if there is a change. Then I will also try to install Node JS v25.0.0 to see if it behaves better.
    I do not think that what I am pointing here is a feature request, but a regression or as you put it, a potential problem with my installation. This was working with node js v22.18.0, before my upgrade.

    Thanks for your appreciated remarks.

  9. Martin-Luther commented on Oct 29, 2025

    @Martin-Luther

    @codermapuche I can confirm that everything is working with Node JS v25.0.0 .
    I also had an issue with my data.

  10. panva commented on Mar 19, 2026

    @panva
    Member

    A proposal is in #62345

  11. github-actions commented on Jul 20, 2026

    @github-actions
    Contributor

    This issue has been marked as stale due to 90 days of inactivity.
    It will be automatically closed in 30 days if no further activity occurs. If this is still relevant, please leave a comment or update it to keep it open.

  12. added
    staleIssues and PRs marked stale due to inactivity and scheduled for automatic closure.
    on Jul 20, 2026
  13. github-actions commented on Aug 20, 2026

    @github-actions
    Contributor

    This issue has been automatically closed after 30 days of inactivity following its stale status (no activity for a total of 120 days).
    If this is still relevant, feel free to reopen it or leave a comment with additional details so we can continue the discussion.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    cryptoIssues and PRs related to the crypto subsystem.feature requestIssues requesting new Node.js features.staleIssues and PRs marked stale due to inactivity and scheduled for automatic closure.

    Type

    No type

    Projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions