diff --git a/libs/common/src/platform/abstractions/crypto-function.service.ts b/libs/common/src/platform/abstractions/crypto-function.service.ts index 9ba09d0879d..3597c208c3c 100644 --- a/libs/common/src/platform/abstractions/crypto-function.service.ts +++ b/libs/common/src/platform/abstractions/crypto-function.service.ts @@ -105,33 +105,4 @@ export abstract class CryptoFunctionService { * Do not use this for generating encryption keys. Use aesGenerateKey or rsaGenerateKeyPair instead. */ abstract randomBytes(length: number): Promise; - /** - * Generate a random asymmetric key pair using the given algorithm on the given curve - * - * x25519: Curve25519, does not use the curve parameter and will throw if passed in a non-nullish curve - * ecdh: Elliptic Curve Diffie-Hellman, uses the curve parameter to specify the curve to use - * P-256: NIST P-256 - * P-384: NIST P-384 - * P-521: NIST P-521 - * @param algorithm the algorithm to use - * @param curve the curve to use for ecdh, or undefined for x25519 - * @returns a promise that resolves to an object containing the private and public keys - */ - abstract diffieHellmanGenerateKeyPair( - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise<{ keyPair: CryptoKeyPair; publicKey: Uint8Array }>; - /** - * Derive a shared key from a private key and an external public key - * - * @param privateKey the private key to use - * @param publicKey the public key to use - * @returns a promise that resolves to the shared key bits - */ - abstract deriveSharedKeyBits( - privateKey: CryptoKey, - publicKeyRaw: Uint8Array, - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise; } diff --git a/libs/common/src/platform/services/web-crypto-function.service.spec.ts b/libs/common/src/platform/services/web-crypto-function.service.spec.ts index 2ed7e656e1e..743eca7f1f8 100644 --- a/libs/common/src/platform/services/web-crypto-function.service.spec.ts +++ b/libs/common/src/platform/services/web-crypto-function.service.spec.ts @@ -413,292 +413,6 @@ describe("WebCrypto Function Service", () => { expect(key.slice(0, 32)).not.toEqual(key.slice(32, 64)); }); }); - - describe("diffieHellmanGenerateKeyPair", () => { - describe("x25519", () => { - it("generates a key pair", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqualBuffer(publicFromKeyPair); - }); - }); - - describe("ecdh", () => { - describe.each(["P-256", "P-384", "P-521"] as const)("curve %s", (curve) => { - it("generates a key pair", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqualBuffer(publicFromKeyPair); - // Should be odd - expect(publicKey.byteLength % 2).toBe(1); - // First byte should be 0x04 - expect(publicKey[0]).toBe(0x04); - }); - }); - }); - }); - - describe("diffieHellmanGenerateKeyPair", () => { - describe("x25519", () => { - it("generates a key pair", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqual(new Uint8Array(publicFromKeyPair)); - }); - }); - - describe("ecdh", () => { - describe.each(["P-256", "P-384", "P-521"] as const)("curve %s", (curve) => { - it("generates a key pair", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = getWebCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqual(new Uint8Array(publicFromKeyPair)); - // Should be odd - expect(publicKey.byteLength % 2).toBe(1); - // First byte should be 0x04 - expect(publicKey[0]).toBe(0x04); - }); - }); - }); - }); - - describe("deriveSharedKeyBits", () => { - let cryptoFunctionService: WebCryptoFunctionService; - - beforeEach(() => { - cryptoFunctionService = getWebCryptoFunctionService(); - }); - - describe("x25519", () => { - const testVectors = Object.freeze({ - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - crv: "X25519", - d: "dwdtCnMYpX08FsFyUbJmRd9ML4frwJkqsXf7pR25LCo=", - x: "hSDwCYkwp1R0i33ctD73Wg2/Og0mOBr066SpjqqbTmo=", - kty: "OKP", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - crv: "X25519", - d: "XasIfmJKikt54X+Lg4AO5m87sSkmGLb9HC+LJ/+I4Os=", - x: "3p7bfXt9wbTTW2HC7OQ1Nz+DQ8hbeGdNrfx+FG+IK08=", - kty: "OKP", - }, - expected: "Sl2dW6TOLeFyjjv0gDUPJeB+IclH0Z4zdvCbPB4WF0I", // hex - }); - - it("computes the correct shared key for a test vector", async () => { - function testVectorToUint8Array(hex: string): Uint8Array { - return new Uint8Array(Buffer.from(hex, "hex")); - } - const aPrivateKey = await crypto.subtle.importKey("jwk", testVectors.a, "x25519", false, [ - "deriveBits", - ]); - const aPublicKey = new Uint8Array(Buffer.from(testVectors.a.x, "base64")); - const bPrivateKey = await crypto.subtle.importKey("jwk", testVectors.b, "x25519", false, [ - "deriveBits", - ]); - const bPublicKey = new Uint8Array(Buffer.from(testVectors.b.x, "base64")); - const expectedSharedKey = testVectorToUint8Array( - "4a5d9d5ba4ce2de1728e3bf480350f25e07e21c947d19e3376f09b3c1e161742", - ); - - const actualAB = await cryptoFunctionService.deriveSharedKeyBits( - aPrivateKey, - bPublicKey, - "x25519", - undefined, - ); - const actualBA = await cryptoFunctionService.deriveSharedKeyBits( - bPrivateKey, - aPublicKey, - "x25519", - undefined, - ); - - expect(actualAB).toEqual(expectedSharedKey); - expect(actualBA).toEqual(expectedSharedKey); - }); - }); - - describe("ecdh", () => { - // from rfc 7027 https://datatracker.ietf.org/doc/html/rfc7027.html#page-6 - const testVectors = Object.freeze({ - "P-256": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "slavLyCsXalaOmUgYA-cG4RFNxapMfWK5cnGFZXEsmE", - y: "fR3rqDZX_m9ba5OPD4EM4AecqltCTNyXsGmV6e5UYkk", - crv: "P-256", - d: "HauUPXMuCzvArJpcNJisBzfHq05MVPmHv1Ixd_8Trxk", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "UDVHYHeNMuViKX2ixvJfUdRkP2vYaLH5LEtaZj0Sp5U", - y: "ScRWbvlcz4IZc6h4SkUu6ejmho1hOrg3kUgEkpJf4OE", - crv: "P-256", - d: "xquL6bqtpdDaEoZ0h2HDwpXlPdX__w0xrr8VZLAS2wQ", - }, - expectedSharedKey: { - x: "89AFC39D41D3B327814B80940B042590F96556EC91E6AE7939BCE31F3A18BF2B", - y: "49C27868F4ECA2179BFD7D59B1E3BF34C1DBDE61AE12931648F43E59632504DE", - }, - }, - "P-384": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "0vsFRhdWTrrQyXF6MJcB3Lg-JjalCra973eA46nFNBwD4oLbTzpL514ZVNIb5nPG", - y: "_KZHmMem5pmjhKjAmQ2twvwkssOh5ww28ZXBabgOsCF3MYi-ICkvkqdVvdPNCPaM", - crv: "P-384", - d: "V7yD-hx8gep_0pw8nFTYD0pRVkxGGN9Uz1zL1Ynq99oSJBG-mceLkwhXACvTKN2o", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "4pgonl58vdZpXrBurolmIw85fAwIY0gMfNRYt1TZWY-kXYz5vKxhi1ycjqotiprR", - y: "CCFnRehKJtFX1-0zJWHcXaIpm09B88rq2nhmCRcc5E9NOdgh8dRyJw63o7c7F7XQ", - crv: "P-384", - d: "40D_ztyfZdBzV3CT8r5JC-SvZfGx4IfUnQNOzbgLcD98zvGcCH04Zs41JCEQ0t-y", - }, - }, - "P-521": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "APD7DZbPsfQ-9tDlc1gFnZGQg5seDx59BmKeFDRERULUqr3EYoxpH-8eutJoXaKCTdzdiXWYpG7nEO99Q6CQuR6Q", - y: "ACbcq7utMbQ5XRGwg-O23brBa29Gcaht6TRQvT9k3worJDQlKN-awn8b68HGMb8WEfJe2gFoPAB9D9Cr8sRT5W35", - crv: "P-521", - d: "AVeaaA3VUhbZfz_oJOCZjhg6gqxXjf96YDJ7rawtAnJDHxtLif7LHVQcOHRKiB6dN9al5KdCGhvo8eekMgRcDXPI", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "AD_GaHOGgjivKoC4C7L5P-fEUzvEpXKFSi32tmscW4NJqiCWQsekuR0EMNgXTw_7GTlrnsn5CcLHfianF3Way-bk", - y: "AcJO4Pl7_qys5QS0-XP_Wluy5KgBXZIIG5vmmDLK7Vhsl_30IP6_WPA5JkqEOHZs25uTMdEERvcJlw7EAItGrM5t", - crv: "P-521", - d: "ADYRyQSF0aLOcYGukdjtFEe5d_pI8wLoU5kNHXfUPoVDHqK02zC-bDRIjJB8f0VWBZYVs88WXFVabUzYlbFwcSi1", - }, - }, - }); - - describe.each(["P-256", "P-384", "P-521"] as const)("curve %s", (curve) => { - it("computes the correct shared key for a test vector", async () => { - const aPrivateKey = await crypto.subtle.importKey( - "jwk", - testVectors[curve].a, - { name: "ecdh", namedCurve: curve }, - true, - ["deriveBits"], - ); - const aPublicKey = Buffer.concat([ - new Uint8Array([0x04]), - Buffer.from(testVectors[curve].a.x, "base64"), - Buffer.from(testVectors[curve].a.y, "base64"), - ]); - const bPrivateKey = await crypto.subtle.importKey( - "jwk", - testVectors[curve].b, - { name: "ecdh", namedCurve: curve }, - true, - ["deriveBits"], - ); - const bPublicKey = Buffer.concat([ - new Uint8Array([0x04]), - Buffer.from(testVectors[curve].b.x, "base64"), - Buffer.from(testVectors[curve].b.y, "base64"), - ]); - - const actualAB = cryptoFunctionService.deriveSharedKeyBits( - aPrivateKey, - bPublicKey, - "ecdh", - curve, - ); - - const actualBA = cryptoFunctionService.deriveSharedKeyBits( - bPrivateKey, - aPublicKey, - "ecdh", - curve, - ); - - expect(actualAB).toEqual(actualBA); - }); - }); - }); - }); }); function testPbkdf2( diff --git a/libs/common/src/platform/services/web-crypto-function.service.ts b/libs/common/src/platform/services/web-crypto-function.service.ts index 3c115393e64..fb824d204fc 100644 --- a/libs/common/src/platform/services/web-crypto-function.service.ts +++ b/libs/common/src/platform/services/web-crypto-function.service.ts @@ -400,61 +400,6 @@ export class WebCryptoFunctionService implements CryptoFunctionService { return new Uint8Array(rawKey) as CsprngArray; } - async diffieHellmanGenerateKeyPair( - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise<{ - keyPair: CryptoKeyPair; - publicKey: Uint8Array; - }> { - if (algorithm === "x25519" && curve != null) { - throw new Error("x25519 does not use the curve parameter."); - } - - const keys = await this.subtle.generateKey( - { - name: algorithm, - namedCurve: curve, - }, - true, - ["deriveKey", "deriveBits"], - ); - return { - keyPair: keys, - publicKey: new Uint8Array(await this.subtle.exportKey("raw", keys.publicKey)), - }; - } - - async deriveSharedKeyBits( - privateKey: CryptoKey, - publicKeyRaw: Uint8Array, - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise { - if (algorithm === "x25519" && curve != null) { - throw new Error("x25519 does not use the curve parameter."); - } - - const publicKey = await crypto.subtle.importKey( - "raw", - publicKeyRaw, - { name: algorithm, namedCurve: curve }, - true, - [], - ); - - const dhSecret = await crypto.subtle.deriveBits( - { - name: algorithm, - public: publicKey, - }, - privateKey, - 256, - ); - - return new Uint8Array(dhSecret); - } - async rsaGenerateKeyPair(length: 1024 | 2048 | 4096): Promise<[Uint8Array, Uint8Array]> { const rsaParams = { name: "RSA-OAEP", diff --git a/libs/node/src/services/node-crypto-function.service.spec.ts b/libs/node/src/services/node-crypto-function.service.spec.ts index 201b3810b15..f068b13ea3e 100644 --- a/libs/node/src/services/node-crypto-function.service.spec.ts +++ b/libs/node/src/services/node-crypto-function.service.spec.ts @@ -325,238 +325,6 @@ describe("NodeCrypto Function Service", () => { expect(spy).toHaveBeenCalledWith(32); }); }); - - describe("diffieHellmanGenerateKeyPair", () => { - describe("x25519", () => { - it("generates a key pair", async () => { - const cryptoFunctionService = new NodeCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = new NodeCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "x25519", - undefined, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqual(new Uint8Array(publicFromKeyPair)); - }); - }); - - describe("ecdh", () => { - describe.each(["P-256", "P-384", "P-521"] as const)("curve %s", (curve) => { - it("generates a key pair", async () => { - const cryptoFunctionService = new NodeCryptoFunctionService(); - const { keyPair } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - expect(keyPair.privateKey).toBeDefined(); - expect(keyPair.publicKey).toBeDefined(); - }); - - it("pre-extracts the public key in raw format", async () => { - const cryptoFunctionService = new NodeCryptoFunctionService(); - const { keyPair, publicKey } = await cryptoFunctionService.diffieHellmanGenerateKeyPair( - "ecdh", - curve, - ); - const publicFromKeyPair = await crypto.subtle.exportKey("raw", keyPair.publicKey); - - expect(publicKey).toEqual(new Uint8Array(publicFromKeyPair)); - // Should be odd - expect(publicKey.byteLength % 2).toBe(1); - // First byte should be 0x04 - expect(publicKey[0]).toBe(0x04); - }); - }); - }); - }); - - describe("deriveSharedKeyBits", () => { - let cryptoFunctionService: NodeCryptoFunctionService; - - beforeEach(() => { - cryptoFunctionService = new NodeCryptoFunctionService(); - }); - - describe("x25519", () => { - const testVectors = Object.freeze({ - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - crv: "X25519", - d: "dwdtCnMYpX08FsFyUbJmRd9ML4frwJkqsXf7pR25LCo=", - x: "hSDwCYkwp1R0i33ctD73Wg2/Og0mOBr066SpjqqbTmo=", - kty: "OKP", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - crv: "X25519", - d: "XasIfmJKikt54X+Lg4AO5m87sSkmGLb9HC+LJ/+I4Os=", - x: "3p7bfXt9wbTTW2HC7OQ1Nz+DQ8hbeGdNrfx+FG+IK08=", - kty: "OKP", - }, - expected: "Sl2dW6TOLeFyjjv0gDUPJeB+IclH0Z4zdvCbPB4WF0I", // hex - }); - - it("computes the correct shared key for a test vector", async () => { - function testVectorToUint8Array(hex: string): Uint8Array { - return new Uint8Array(Buffer.from(hex, "hex")); - } - const aPrivateKey = await crypto.subtle.importKey("jwk", testVectors.a, "x25519", false, [ - "deriveBits", - ]); - const aPublicKey = new Uint8Array(Buffer.from(testVectors.a.x, "base64")); - const bPrivateKey = await crypto.subtle.importKey("jwk", testVectors.b, "x25519", false, [ - "deriveBits", - ]); - const bPublicKey = new Uint8Array(Buffer.from(testVectors.b.x, "base64")); - const expectedSharedKey = testVectorToUint8Array( - "4a5d9d5ba4ce2de1728e3bf480350f25e07e21c947d19e3376f09b3c1e161742", - ); - - const actualAB = await cryptoFunctionService.deriveSharedKeyBits( - aPrivateKey, - bPublicKey, - "x25519", - undefined, - ); - const actualBA = await cryptoFunctionService.deriveSharedKeyBits( - bPrivateKey, - aPublicKey, - "x25519", - undefined, - ); - - expect(actualAB).toEqual(expectedSharedKey); - expect(actualBA).toEqual(expectedSharedKey); - }); - }); - - describe("ecdh", () => { - // from rfc 7027 https://datatracker.ietf.org/doc/html/rfc7027.html#page-6 - const testVectors = Object.freeze({ - "P-256": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "slavLyCsXalaOmUgYA-cG4RFNxapMfWK5cnGFZXEsmE", - y: "fR3rqDZX_m9ba5OPD4EM4AecqltCTNyXsGmV6e5UYkk", - crv: "P-256", - d: "HauUPXMuCzvArJpcNJisBzfHq05MVPmHv1Ixd_8Trxk", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "UDVHYHeNMuViKX2ixvJfUdRkP2vYaLH5LEtaZj0Sp5U", - y: "ScRWbvlcz4IZc6h4SkUu6ejmho1hOrg3kUgEkpJf4OE", - crv: "P-256", - d: "xquL6bqtpdDaEoZ0h2HDwpXlPdX__w0xrr8VZLAS2wQ", - }, - expectedSharedKey: { - x: "89AFC39D41D3B327814B80940B042590F96556EC91E6AE7939BCE31F3A18BF2B", - y: "49C27868F4ECA2179BFD7D59B1E3BF34C1DBDE61AE12931648F43E59632504DE", - }, - }, - "P-384": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "0vsFRhdWTrrQyXF6MJcB3Lg-JjalCra973eA46nFNBwD4oLbTzpL514ZVNIb5nPG", - y: "_KZHmMem5pmjhKjAmQ2twvwkssOh5ww28ZXBabgOsCF3MYi-ICkvkqdVvdPNCPaM", - crv: "P-384", - d: "V7yD-hx8gep_0pw8nFTYD0pRVkxGGN9Uz1zL1Ynq99oSJBG-mceLkwhXACvTKN2o", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "4pgonl58vdZpXrBurolmIw85fAwIY0gMfNRYt1TZWY-kXYz5vKxhi1ycjqotiprR", - y: "CCFnRehKJtFX1-0zJWHcXaIpm09B88rq2nhmCRcc5E9NOdgh8dRyJw63o7c7F7XQ", - crv: "P-384", - d: "40D_ztyfZdBzV3CT8r5JC-SvZfGx4IfUnQNOzbgLcD98zvGcCH04Zs41JCEQ0t-y", - }, - }, - "P-521": { - a: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "APD7DZbPsfQ-9tDlc1gFnZGQg5seDx59BmKeFDRERULUqr3EYoxpH-8eutJoXaKCTdzdiXWYpG7nEO99Q6CQuR6Q", - y: "ACbcq7utMbQ5XRGwg-O23brBa29Gcaht6TRQvT9k3worJDQlKN-awn8b68HGMb8WEfJe2gFoPAB9D9Cr8sRT5W35", - crv: "P-521", - d: "AVeaaA3VUhbZfz_oJOCZjhg6gqxXjf96YDJ7rawtAnJDHxtLif7LHVQcOHRKiB6dN9al5KdCGhvo8eekMgRcDXPI", - }, - b: { - key_ops: ["deriveKey", "deriveBits"], - ext: true, - kty: "EC", - x: "AD_GaHOGgjivKoC4C7L5P-fEUzvEpXKFSi32tmscW4NJqiCWQsekuR0EMNgXTw_7GTlrnsn5CcLHfianF3Way-bk", - y: "AcJO4Pl7_qys5QS0-XP_Wluy5KgBXZIIG5vmmDLK7Vhsl_30IP6_WPA5JkqEOHZs25uTMdEERvcJlw7EAItGrM5t", - crv: "P-521", - d: "ADYRyQSF0aLOcYGukdjtFEe5d_pI8wLoU5kNHXfUPoVDHqK02zC-bDRIjJB8f0VWBZYVs88WXFVabUzYlbFwcSi1", - }, - }, - }); - - describe.each(["P-256", "P-384", "P-521"] as const)("curve %s", (curve) => { - it("computes the correct shared key for a test vector", async () => { - const aPrivateKey = await crypto.subtle.importKey( - "jwk", - testVectors[curve].a, - { name: "ecdh", namedCurve: curve }, - true, - ["deriveBits"], - ); - const aPublicKey = Buffer.concat([ - new Uint8Array([0x04]), - Buffer.from(testVectors[curve].a.x, "base64"), - Buffer.from(testVectors[curve].a.y, "base64"), - ]); - const bPrivateKey = await crypto.subtle.importKey( - "jwk", - testVectors[curve].b, - { name: "ecdh", namedCurve: curve }, - true, - ["deriveBits"], - ); - const bPublicKey = Buffer.concat([ - new Uint8Array([0x04]), - Buffer.from(testVectors[curve].b.x, "base64"), - Buffer.from(testVectors[curve].b.y, "base64"), - ]); - - const actualAB = cryptoFunctionService.deriveSharedKeyBits( - aPrivateKey, - bPublicKey, - "ecdh", - curve, - ); - - const actualBA = cryptoFunctionService.deriveSharedKeyBits( - bPrivateKey, - aPublicKey, - "ecdh", - curve, - ); - - expect(actualAB).toEqual(actualBA); - }); - }); - }); - }); }); function testPbkdf2( diff --git a/libs/node/src/services/node-crypto-function.service.ts b/libs/node/src/services/node-crypto-function.service.ts index 64239da003f..7fc8bf3c4b6 100644 --- a/libs/node/src/services/node-crypto-function.service.ts +++ b/libs/node/src/services/node-crypto-function.service.ts @@ -283,61 +283,6 @@ export class NodeCryptoFunctionService implements CryptoFunctionService { }); } - async diffieHellmanGenerateKeyPair( - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise<{ - keyPair: CryptoKeyPair; - publicKey: Uint8Array; - }> { - if (algorithm === "x25519" && curve != null) { - throw new Error("x25519 does not use the curve parameter."); - } - - const keys = await crypto.subtle.generateKey( - { - name: algorithm, - namedCurve: curve, - }, - true, - ["deriveKey", "deriveBits"], - ); - return { - keyPair: keys, - publicKey: new Uint8Array(await crypto.subtle.exportKey("raw", keys.publicKey)), - }; - } - - async deriveSharedKeyBits( - privateKey: CryptoKey, - publicKeyRaw: Uint8Array, - algorithm: "x25519" | "ecdh", - curve: undefined | "P-256" | "P-384" | "P-521", - ): Promise { - if (algorithm === "x25519" && curve != null) { - throw new Error("x25519 does not use the curve parameter."); - } - - const publicKey = await crypto.subtle.importKey( - "raw", - publicKeyRaw, - { name: algorithm, namedCurve: curve }, - true, - [], - ); - - const dhSecret = await crypto.subtle.deriveBits( - { - name: algorithm, - public: publicKey, - }, - privateKey, - 256, - ); - - return new Uint8Array(dhSecret); - } - aesGenerateKey(bitLength: 128 | 192 | 256 | 512): Promise { return this.randomBytes(bitLength / 8); }