| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1697,8 +1697,8 @@ added: v15.8.0 | |||
| 1697 | 1697 | ||
| 1698 | 1698 | * Type: {boolean} | |
| 1699 | 1699 | ||
| 1700 | - The `public` parameter is used to specify that the key is to be interpreted | ||
| 1701 | - as a public key. | ||
| 1700 | + The `public` parameter is used to specify that the `'raw'` format key is to be | ||
| 1701 | + interpreted as a public key. **Default:** `false`. | ||
| 1702 | 1702 | ||
| 1703 | 1703 | ### `NODE-SCRYPT` Algorithm | |
| 1704 | 1704 | <!-- YAML | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -253,10 +253,6 @@ async function ecImportKey( | |||
| 253 | 253 | namedCurve, | |
| 254 | 254 | 'algorithm.namedCurve', | |
| 255 | 255 | ObjectKeys(kNamedCurveAliases)); | |
| 256 | - // Only used for NODE-EDnnnn key variants to distinguish between | ||
| 257 | - // importing a raw public key or raw private key. | ||
| 258 | - if (algorithm.public !== undefined) | ||
| 259 | - validateBoolean(algorithm.public, 'algorithm.public'); | ||
| 260 | 256 | let keyObject; | |
| 261 | 257 | const usagesSet = new SafeSet(keyUsages); | |
| 262 | 258 | let checkNamedCurve = true; | |
@@ -266,6 +262,24 @@ async function ecImportKey( | |||
| 266 | 262 | throw new ERR_INVALID_ARG_TYPE('keyData', 'KeyObject', keyData); | |
| 267 | 263 | if (keyData.type === 'secret') | |
| 268 | 264 | throw lazyDOMException('Invalid key type', 'InvalidAccessException'); | |
| 265 | + | ||
| 266 | + switch (namedCurve) { | ||
| 267 | + case 'NODE-X25519': | ||
| 268 | + // Fall through | ||
| 269 | + case 'NODE-X448': | ||
| 270 | + checkNamedCurve = false; | ||
| 271 | + if (algorithm.name !== 'ECDH') | ||
| 272 | + throw lazyDOMException('Invalid algorithm name.', 'DataError'); | ||
| 273 | + break; | ||
| 274 | + case 'NODE-ED25519': | ||
| 275 | + // Fall through | ||
| 276 | + case 'NODE-ED448': | ||
| 277 | + checkNamedCurve = false; | ||
| 278 | + if (algorithm.name !== namedCurve) | ||
| 279 | + throw lazyDOMException('Invalid algorithm name.', 'DataError'); | ||
| 280 | + break; | ||
| 281 | + } | ||
| 282 | + | ||
| 269 | 283 | verifyAcceptableEcKeyUse(name, keyData.type, usagesSet); | |
| 270 | 284 | keyObject = keyData; | |
| 271 | 285 | break; | |
@@ -296,8 +310,24 @@ async function ecImportKey( | |||
| 296 | 310 | case 'OKP': { | |
| 297 | 311 | checkNamedCurve = false; | |
| 298 | 312 | const isPublic = keyData.d === undefined; | |
| 299 | - const type = | ||
| 300 | - namedCurve === 'NODE-X25519' || 'NODE-X448' ? 'ECDH' : 'ECDSA'; | ||
| 313 | + | ||
| 314 | + let type; | ||
| 315 | + switch (namedCurve) { | ||
| 316 | + case 'NODE-ED25519': | ||
| 317 | + // Fall through | ||
| 318 | + case 'NODE-ED448': | ||
| 319 | + type = `NODE-${keyData.crv.toUpperCase()}`; | ||
| 320 | + break; | ||
| 321 | + case 'NODE-X25519': | ||
| 322 | + // Fall through | ||
| 323 | + case 'NODE-X448': | ||
| 324 | + type = 'ECDH'; | ||
| 325 | + break; | ||
| 326 | + } | ||
| 327 | + | ||
| 328 | + if (algorithm.name !== type) | ||
| 329 | + throw lazyDOMException('Invalid algorithm name.', 'DataError'); | ||
| 330 | + | ||
| 301 | 331 | verifyAcceptableEcKeyUse( | |
| 302 | 332 | type, | |
| 303 | 333 | isPublic ? 'public' : 'private', | |
@@ -364,8 +394,12 @@ async function ecImportKey( | |||
| 364 | 394 | // Fall through | |
| 365 | 395 | case 'NODE-X448': | |
| 366 | 396 | checkNamedCurve = false; | |
| 397 | + if (algorithm.public !== undefined) | ||
| 398 | + validateBoolean(algorithm.public, 'algorithm.public'); | ||
| 399 | + if (algorithm.name !== 'ECDH') | ||
| 400 | + throw lazyDOMException('Invalid algorithm name.', 'DataError'); | ||
| 367 | 401 | verifyAcceptableEcKeyUse( | |
| 368 | - 'ECDH', | ||
| 402 | + algorithm.name, | ||
| 369 | 403 | algorithm.public === true ? 'public' : 'private', | |
| 370 | 404 | usagesSet); | |
| 371 | 405 | keyObject = createECRawKey(namedCurve, keyData, algorithm.public); | |
@@ -374,8 +408,12 @@ async function ecImportKey( | |||
| 374 | 408 | // Fall through | |
| 375 | 409 | case 'NODE-ED448': | |
| 376 | 410 | checkNamedCurve = false; | |
| 411 | + if (algorithm.public !== undefined) | ||
| 412 | + validateBoolean(algorithm.public, 'algorithm.public'); | ||
| 413 | + if (algorithm.name !== namedCurve) | ||
| 414 | + throw lazyDOMException('Invalid algorithm name.', 'DataError'); | ||
| 377 | 415 | verifyAcceptableEcKeyUse( | |
| 378 | - 'ECDSA', | ||
| 416 | + algorithm.name, | ||
| 379 | 417 | algorithm.public === true ? 'public' : 'private', | |
| 380 | 418 | usagesSet); | |
| 381 | 419 | keyObject = createECRawKey(namedCurve, keyData, algorithm.public); | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -6,7 +6,10 @@ if (!common.hasCrypto) | |||
| 6 | 6 | common.skip('missing crypto'); | |
| 7 | 7 | ||
| 8 | 8 | const assert = require('assert'); | |
| 9 | - const { subtle } = require('crypto').webcrypto; | ||
| 9 | + const { | ||
| 10 | + generateKeyPairSync, | ||
| 11 | + webcrypto: { subtle } | ||
| 12 | + } = require('crypto'); | ||
| 10 | 13 | ||
| 11 | 14 | async function generateKey(namedCurve) { | |
| 12 | 15 | return subtle.generateKey( | |
@@ -365,3 +368,52 @@ assert.rejects( | |||
| 365 | 368 | { | |
| 366 | 369 | message: /Unsupported named curves for ECDSA/ | |
| 367 | 370 | }); | |
| 371 | + | ||
| 372 | + { | ||
| 373 | + for (const asymmetricKeyType of ['ed25519', 'ed448']) { | ||
| 374 | + const { publicKey, privateKey } = generateKeyPairSync(asymmetricKeyType); | ||
| 375 | + for (const keyObject of [publicKey, privateKey]) { | ||
| 376 | + const namedCurve = `NODE-${asymmetricKeyType.toUpperCase()}`; | ||
| 377 | + subtle.importKey( | ||
| 378 | + 'node.keyObject', | ||
| 379 | + keyObject, | ||
| 380 | + { name: namedCurve, namedCurve }, | ||
| 381 | + true, | ||
| 382 | + keyObject.type === 'private' ? ['sign'] : ['verify'], | ||
| 383 | + ).then((cryptoKey) => { | ||
| 384 | + assert.strictEqual(cryptoKey.type, keyObject.type); | ||
| 385 | + assert.strictEqual(cryptoKey.algorithm.name, namedCurve); | ||
| 386 | + }, common.mustNotCall()); | ||
| 387 | + | ||
| 388 | + assert.rejects( | ||
| 389 | + subtle.importKey( | ||
| 390 | + 'node.keyObject', | ||
| 391 | + keyObject, | ||
| 392 | + { | ||
| 393 | + name: 'ECDSA', | ||
| 394 | + namedCurve, | ||
| 395 | + }, | ||
| 396 | + true, | ||
| 397 | + keyObject.type === 'private' ? ['sign'] : ['verify'] | ||
| 398 | + ), | ||
| 399 | + { | ||
| 400 | + message: /Invalid algorithm name/ | ||
| 401 | + }); | ||
| 402 | + | ||
| 403 | + assert.rejects( | ||
| 404 | + subtle.importKey( | ||
| 405 | + 'node.keyObject', | ||
| 406 | + keyObject, | ||
| 407 | + { | ||
| 408 | + name: 'ECDH', | ||
| 409 | + namedCurve, | ||
| 410 | + }, | ||
| 411 | + true, | ||
| 412 | + keyObject.type === 'private' ? ['deriveBits', 'deriveKey'] : [], | ||
| 413 | + ), | ||
| 414 | + { | ||
| 415 | + message: /Invalid algorithm name/ | ||
| 416 | + }); | ||
| 417 | + } | ||
| 418 | + } | ||
| 419 | + } | ||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -6,7 +6,11 @@ if (!common.hasCrypto) | |||
| 6 | 6 | common.skip('missing crypto'); | |
| 7 | 7 | ||
| 8 | 8 | const assert = require('assert'); | |
| 9 | - const { subtle } = require('crypto').webcrypto; | ||
| 9 | + | ||
| 10 | + const { | ||
| 11 | + generateKeyPairSync, | ||
| 12 | + webcrypto: { subtle } | ||
| 13 | + } = require('crypto'); | ||
| 10 | 14 | ||
| 11 | 15 | // X25519 and X448 are ECDH named curves that should work | |
| 12 | 16 | // with the existing ECDH mechanisms with no additional | |
@@ -260,7 +264,7 @@ assert.rejects( | |||
| 260 | 264 | namedCurve: 'NODE-X25519' | |
| 261 | 265 | }, | |
| 262 | 266 | true, | |
| 263 | - ['deriveBits']).then(common.mustCall()); | ||
| 267 | + ['deriveBits']).then(common.mustCall(), common.mustNotCall()); | ||
| 264 | 268 | ||
| 265 | 269 | // Public JWK import | |
| 266 | 270 | subtle.importKey( | |
@@ -275,5 +279,22 @@ assert.rejects( | |||
| 275 | 279 | namedCurve: 'NODE-X25519' | |
| 276 | 280 | }, | |
| 277 | 281 | true, | |
| 278 | - []).then(common.mustCall()); | ||
| 282 | + []).then(common.mustCall(), common.mustNotCall()); | ||
| 283 | + | ||
| 284 | + for (const asymmetricKeyType of ['x25519', 'x448']) { | ||
| 285 | + const { publicKey, privateKey } = generateKeyPairSync(asymmetricKeyType); | ||
| 286 | + for (const keyObject of [publicKey, privateKey]) { | ||
| 287 | + const namedCurve = `NODE-${asymmetricKeyType.toUpperCase()}`; | ||
| 288 | + subtle.importKey( | ||
| 289 | + 'node.keyObject', | ||
| 290 | + keyObject, | ||
| 291 | + { name: 'ECDH', namedCurve }, | ||
| 292 | + true, | ||
| 293 | + keyObject.type === 'private' ? ['deriveBits', 'deriveKey'] : [], | ||
| 294 | + ).then((cryptoKey) => { | ||
| 295 | + assert.strictEqual(cryptoKey.type, keyObject.type); | ||
| 296 | + assert.strictEqual(cryptoKey.algorithm.name, 'ECDH'); | ||
| 297 | + }, common.mustNotCall()); | ||
| 298 | + } | ||
| 299 | + } | ||
| 279 | 300 | } | |
| Back | FazBrowse Home | New Git URL |
0 commit comments