node/test/parallel/test-webcrypto-keygen-kmac.js
Filip Skokan 8ec37ebbd6
crypto: support non-byte WebCrypto lengths and cSHAKE
Add shared bit-length helpers for WebCrypto operations that accept bit
sequences whose length is not byte-aligned.

Use the helpers for cSHAKE output, ECDH-derived bits, HMAC/KMAC key
generation/import/derivation, and KMAC sign/verify output. Preserve the
requested bit length in CryptoKey algorithm metadata while storing and
exporting rounded-up byte material with unused low bits cleared.

Keep byte-multiple validation for algorithms whose specs require it.

Extend the lower-end of KMAC's key length support.

Enable cSHAKE customization and functionName parameters.

Signed-off-by: Filip Skokan <panva.ip@gmail.com>
PR-URL: https://github.com/nodejs/node/pull/63988
Reviewed-By: James M Snell <jasnell@gmail.com>
Reviewed-By: Yagiz Nizipli <yagiz@nizipli.com>
2026-06-20 18:42:04 +02:00

55 lines
1.3 KiB
JavaScript

'use strict';
const common = require('../common');
if (!common.hasCrypto)
common.skip('missing crypto');
const { hasOpenSSL } = require('../common/crypto');
if (!hasOpenSSL(3))
common.skip('requires OpenSSL >= 3');
const assert = require('assert');
const { types: { isCryptoKey } } = require('util');
const { subtle } = globalThis.crypto;
const usages = ['sign', 'verify'];
async function test(name, length) {
length ??= name === 'KMAC128' ? 128 : 256;
const key = await subtle.generateKey({
name,
length,
}, true, usages);
assert(key);
assert(isCryptoKey(key));
assert.strictEqual(key.type, 'secret');
assert.strictEqual(key.toString(), '[object CryptoKey]');
assert.strictEqual(key.extractable, true);
assert.deepStrictEqual(key.usages, usages);
assert.strictEqual(key.algorithm.name, name);
assert.strictEqual(key.algorithm.length, length);
assert.strictEqual(key.algorithm, key.algorithm);
assert.strictEqual(key.usages, key.usages);
const raw = await subtle.exportKey('raw-secret', key);
assert.strictEqual(raw.byteLength, Math.ceil(length / 8));
}
const kTests = [
['KMAC128', 0],
['KMAC128', 128],
['KMAC128', 256],
['KMAC128'],
['KMAC256', 0],
['KMAC256', 128],
['KMAC256', 256],
['KMAC256'],
];
const tests = Promise.all(kTests.map((args) => test(...args)));
tests.then(common.mustCall());