@ocap/mcrypto 1.29.14 → 1.29.16
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/esm/index.d.mts +1 -1
- package/esm/signer/ed25519.d.mts +10 -0
- package/esm/signer/ed25519.mjs +17 -0
- package/esm/signer/secp256k1.mjs +17 -9
- package/lib/index.d.cts +1 -1
- package/lib/signer/ed25519.cjs +17 -0
- package/lib/signer/ed25519.d.cts +10 -0
- package/lib/signer/secp256k1.cjs +17 -9
- package/package.json +3 -3
package/esm/index.d.mts
CHANGED
|
@@ -39,7 +39,7 @@ interface SignerType {
|
|
|
39
39
|
sign(data: BytesType, sk: BytesType, encoding?: 'Uint8Array'): Uint8Array;
|
|
40
40
|
sign(data: BytesType, sk: BytesType, encoding?: EncodingType): BytesType;
|
|
41
41
|
/** extra is JSON string for passkey signer containing {authenticatorData, clientDataJSON} */
|
|
42
|
-
verify(data: BytesType,
|
|
42
|
+
verify(data: BytesType, signature: BytesType, pk: BytesType, extra?: string): boolean;
|
|
43
43
|
ethHash?(data: string): string;
|
|
44
44
|
ethSign?(data: string, sk: string): string;
|
|
45
45
|
ethVerify?(data: string, pk: string, signature: BytesType): boolean;
|
package/esm/signer/ed25519.d.mts
CHANGED
|
@@ -25,6 +25,16 @@ declare class Ed25519Signer extends _default$1 {
|
|
|
25
25
|
* @memberof Ed25519Signer
|
|
26
26
|
*/
|
|
27
27
|
genKeyPair(encoding?: EncodingType, userSeed?: BytesType): KeyPairType;
|
|
28
|
+
/**
|
|
29
|
+
* Validate that a 64-byte key (in seed|pk format) has a matching embedded public key.
|
|
30
|
+
* Note: Cross-platform keys (e.g. Elixir) may use private_scalar|pk format where
|
|
31
|
+
* the first 32 bytes are NOT a seed, so this check only applies to seed|pk format keys.
|
|
32
|
+
*
|
|
33
|
+
* @param {Uint8Array} skBytes - 64-byte key to validate
|
|
34
|
+
* @returns {boolean} true if embedded pk matches seed-derived pk
|
|
35
|
+
* @throws {Error} if the key is not 64 bytes
|
|
36
|
+
*/
|
|
37
|
+
validateKeyPair(sk: BytesType): boolean;
|
|
28
38
|
/**
|
|
29
39
|
* Get publicKey from secretKey
|
|
30
40
|
*
|
package/esm/signer/ed25519.mjs
CHANGED
|
@@ -41,6 +41,23 @@ var Ed25519Signer = class extends signer_default {
|
|
|
41
41
|
};
|
|
42
42
|
}
|
|
43
43
|
/**
|
|
44
|
+
* Validate that a 64-byte key (in seed|pk format) has a matching embedded public key.
|
|
45
|
+
* Note: Cross-platform keys (e.g. Elixir) may use private_scalar|pk format where
|
|
46
|
+
* the first 32 bytes are NOT a seed, so this check only applies to seed|pk format keys.
|
|
47
|
+
*
|
|
48
|
+
* @param {Uint8Array} skBytes - 64-byte key to validate
|
|
49
|
+
* @returns {boolean} true if embedded pk matches seed-derived pk
|
|
50
|
+
* @throws {Error} if the key is not 64 bytes
|
|
51
|
+
*/
|
|
52
|
+
validateKeyPair(sk) {
|
|
53
|
+
const skBytes = toUint8Array(sk);
|
|
54
|
+
if (skBytes.byteLength !== 64) throw new Error("validateKeyPair requires a 64-byte key");
|
|
55
|
+
const seed = skBytes.slice(0, 32);
|
|
56
|
+
const derivedPk = ed.getPublicKey(seed);
|
|
57
|
+
const embeddedPk = skBytes.slice(32, 64);
|
|
58
|
+
return derivedPk.length === embeddedPk.length && derivedPk.every((b, i) => b === embeddedPk[i]);
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
44
61
|
* Get publicKey from secretKey
|
|
45
62
|
*
|
|
46
63
|
* @param {hex|buffer|base58|Uint8Array} sk - can be either a hex encoded string or a buffer
|
package/esm/signer/secp256k1.mjs
CHANGED
|
@@ -57,23 +57,31 @@ var Secp256k1Signer = class extends signer_default {
|
|
|
57
57
|
* Sign a message and get the signature hex
|
|
58
58
|
*/
|
|
59
59
|
sign(message, sk, encoding = "hex") {
|
|
60
|
-
|
|
61
|
-
try {
|
|
62
|
-
msg = toUint8Array(message);
|
|
63
|
-
} catch (_err) {}
|
|
60
|
+
const msg = toUint8Array(message);
|
|
64
61
|
return encode(`0x${secp256k1.keyFromPrivate(toBuffer(sk)).sign(stripHexPrefix(msg), { canonical: true }).toDER("hex")}`, encoding);
|
|
65
62
|
}
|
|
66
63
|
/**
|
|
67
64
|
* Verify if a signature is valid
|
|
68
65
|
*/
|
|
69
66
|
verify(message, signature, pk) {
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
67
|
+
const msg = toUint8Array(message);
|
|
68
|
+
const sigHex = stripHexPrefix(toHex(signature));
|
|
69
|
+
const sigBuf = Buffer.from(sigHex, "hex");
|
|
70
|
+
if (sigBuf.length > 6 && sigBuf[0] === 48) {
|
|
71
|
+
const sLenIndex = 4 + sigBuf[3] + 1;
|
|
72
|
+
if (sLenIndex < sigBuf.length) {
|
|
73
|
+
const sLen = sigBuf[sLenIndex];
|
|
74
|
+
const sStart = sLenIndex + 1;
|
|
75
|
+
if (sStart + sLen <= sigBuf.length) {
|
|
76
|
+
const sValue = new BN(sigBuf.slice(sStart, sStart + sLen));
|
|
77
|
+
const halfOrder = secp256k1.curve.n.shrn(1);
|
|
78
|
+
if (sValue.cmp(halfOrder) > 0) return false;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
74
82
|
let pkBuffer = toBuffer(pk);
|
|
75
83
|
if (this.pkHasFormatPrefix === false && pkBuffer[0] !== 4 && pkBuffer.byteLength === 64) pkBuffer = Buffer.concat([Uint8Array.from([4]), Uint8Array.from(pkBuffer)]);
|
|
76
|
-
return secp256k1.keyFromPublic(pkBuffer).verify(stripHexPrefix(msg),
|
|
84
|
+
return secp256k1.keyFromPublic(pkBuffer).verify(stripHexPrefix(msg), sigHex);
|
|
77
85
|
}
|
|
78
86
|
};
|
|
79
87
|
var secp256k1_default = new Secp256k1Signer();
|
package/lib/index.d.cts
CHANGED
|
@@ -39,7 +39,7 @@ interface SignerType {
|
|
|
39
39
|
sign(data: BytesType, sk: BytesType, encoding?: 'Uint8Array'): Uint8Array;
|
|
40
40
|
sign(data: BytesType, sk: BytesType, encoding?: EncodingType): BytesType;
|
|
41
41
|
/** extra is JSON string for passkey signer containing {authenticatorData, clientDataJSON} */
|
|
42
|
-
verify(data: BytesType,
|
|
42
|
+
verify(data: BytesType, signature: BytesType, pk: BytesType, extra?: string): boolean;
|
|
43
43
|
ethHash?(data: string): string;
|
|
44
44
|
ethSign?(data: string, sk: string): string;
|
|
45
45
|
ethVerify?(data: string, pk: string, signature: BytesType): boolean;
|
package/lib/signer/ed25519.cjs
CHANGED
|
@@ -45,6 +45,23 @@ var Ed25519Signer = class extends require_protocols_signer.default {
|
|
|
45
45
|
};
|
|
46
46
|
}
|
|
47
47
|
/**
|
|
48
|
+
* Validate that a 64-byte key (in seed|pk format) has a matching embedded public key.
|
|
49
|
+
* Note: Cross-platform keys (e.g. Elixir) may use private_scalar|pk format where
|
|
50
|
+
* the first 32 bytes are NOT a seed, so this check only applies to seed|pk format keys.
|
|
51
|
+
*
|
|
52
|
+
* @param {Uint8Array} skBytes - 64-byte key to validate
|
|
53
|
+
* @returns {boolean} true if embedded pk matches seed-derived pk
|
|
54
|
+
* @throws {Error} if the key is not 64 bytes
|
|
55
|
+
*/
|
|
56
|
+
validateKeyPair(sk) {
|
|
57
|
+
const skBytes = (0, _ocap_util.toUint8Array)(sk);
|
|
58
|
+
if (skBytes.byteLength !== 64) throw new Error("validateKeyPair requires a 64-byte key");
|
|
59
|
+
const seed = skBytes.slice(0, 32);
|
|
60
|
+
const derivedPk = _noble_ed25519.getPublicKey(seed);
|
|
61
|
+
const embeddedPk = skBytes.slice(32, 64);
|
|
62
|
+
return derivedPk.length === embeddedPk.length && derivedPk.every((b, i) => b === embeddedPk[i]);
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
48
65
|
* Get publicKey from secretKey
|
|
49
66
|
*
|
|
50
67
|
* @param {hex|buffer|base58|Uint8Array} sk - can be either a hex encoded string or a buffer
|
package/lib/signer/ed25519.d.cts
CHANGED
|
@@ -25,6 +25,16 @@ declare class Ed25519Signer extends _default$1 {
|
|
|
25
25
|
* @memberof Ed25519Signer
|
|
26
26
|
*/
|
|
27
27
|
genKeyPair(encoding?: EncodingType, userSeed?: BytesType): KeyPairType;
|
|
28
|
+
/**
|
|
29
|
+
* Validate that a 64-byte key (in seed|pk format) has a matching embedded public key.
|
|
30
|
+
* Note: Cross-platform keys (e.g. Elixir) may use private_scalar|pk format where
|
|
31
|
+
* the first 32 bytes are NOT a seed, so this check only applies to seed|pk format keys.
|
|
32
|
+
*
|
|
33
|
+
* @param {Uint8Array} skBytes - 64-byte key to validate
|
|
34
|
+
* @returns {boolean} true if embedded pk matches seed-derived pk
|
|
35
|
+
* @throws {Error} if the key is not 64 bytes
|
|
36
|
+
*/
|
|
37
|
+
validateKeyPair(sk: BytesType): boolean;
|
|
28
38
|
/**
|
|
29
39
|
* Get publicKey from secretKey
|
|
30
40
|
*
|
package/lib/signer/secp256k1.cjs
CHANGED
|
@@ -61,23 +61,31 @@ var Secp256k1Signer = class extends require_protocols_signer.default {
|
|
|
61
61
|
* Sign a message and get the signature hex
|
|
62
62
|
*/
|
|
63
63
|
sign(message, sk, encoding = "hex") {
|
|
64
|
-
|
|
65
|
-
try {
|
|
66
|
-
msg = (0, _ocap_util.toUint8Array)(message);
|
|
67
|
-
} catch (_err) {}
|
|
64
|
+
const msg = (0, _ocap_util.toUint8Array)(message);
|
|
68
65
|
return require_encode.encode(`0x${secp256k1.keyFromPrivate((0, _ocap_util.toBuffer)(sk)).sign((0, _ocap_util.stripHexPrefix)(msg), { canonical: true }).toDER("hex")}`, encoding);
|
|
69
66
|
}
|
|
70
67
|
/**
|
|
71
68
|
* Verify if a signature is valid
|
|
72
69
|
*/
|
|
73
70
|
verify(message, signature, pk) {
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
71
|
+
const msg = (0, _ocap_util.toUint8Array)(message);
|
|
72
|
+
const sigHex = (0, _ocap_util.stripHexPrefix)((0, _ocap_util.toHex)(signature));
|
|
73
|
+
const sigBuf = Buffer.from(sigHex, "hex");
|
|
74
|
+
if (sigBuf.length > 6 && sigBuf[0] === 48) {
|
|
75
|
+
const sLenIndex = 4 + sigBuf[3] + 1;
|
|
76
|
+
if (sLenIndex < sigBuf.length) {
|
|
77
|
+
const sLen = sigBuf[sLenIndex];
|
|
78
|
+
const sStart = sLenIndex + 1;
|
|
79
|
+
if (sStart + sLen <= sigBuf.length) {
|
|
80
|
+
const sValue = new _ocap_util.BN(sigBuf.slice(sStart, sStart + sLen));
|
|
81
|
+
const halfOrder = secp256k1.curve.n.shrn(1);
|
|
82
|
+
if (sValue.cmp(halfOrder) > 0) return false;
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
}
|
|
78
86
|
let pkBuffer = (0, _ocap_util.toBuffer)(pk);
|
|
79
87
|
if (this.pkHasFormatPrefix === false && pkBuffer[0] !== 4 && pkBuffer.byteLength === 64) pkBuffer = Buffer.concat([Uint8Array.from([4]), Uint8Array.from(pkBuffer)]);
|
|
80
|
-
return secp256k1.keyFromPublic(pkBuffer).verify((0, _ocap_util.stripHexPrefix)(msg),
|
|
88
|
+
return secp256k1.keyFromPublic(pkBuffer).verify((0, _ocap_util.stripHexPrefix)(msg), sigHex);
|
|
81
89
|
}
|
|
82
90
|
};
|
|
83
91
|
var secp256k1_default = new Secp256k1Signer();
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@ocap/mcrypto",
|
|
3
|
-
"version": "1.29.
|
|
3
|
+
"version": "1.29.16",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Crypto lib that provides signer,crypter,hasher interface",
|
|
6
6
|
"keywords": [
|
|
@@ -48,7 +48,7 @@
|
|
|
48
48
|
"esm"
|
|
49
49
|
],
|
|
50
50
|
"devDependencies": {
|
|
51
|
-
"@ocap/e2e-test": "1.29.
|
|
51
|
+
"@ocap/e2e-test": "1.29.16",
|
|
52
52
|
"@types/crypto-js": "^4.2.2",
|
|
53
53
|
"@types/elliptic": "^6.4.18",
|
|
54
54
|
"@types/node": "^22.7.5",
|
|
@@ -76,7 +76,7 @@
|
|
|
76
76
|
"dependencies": {
|
|
77
77
|
"@noble/ed25519": "^3.0.0",
|
|
78
78
|
"@noble/hashes": "^2.0.1",
|
|
79
|
-
"@ocap/util": "1.29.
|
|
79
|
+
"@ocap/util": "1.29.16",
|
|
80
80
|
"@simplewebauthn/server": "^13.0.0",
|
|
81
81
|
"bn.js": "5.2.3",
|
|
82
82
|
"crypto-js": "^4.2.0",
|