@ledgerhq/hw-ledger-key-ring-protocol 0.2.1-nightly.0 → 0.2.1-spl-test.0
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/.turbo/turbo-build.log +1 -1
- package/CHANGELOG.md +3 -3
- package/lib/ApduDevice.d.ts.map +1 -1
- package/lib/ApduDevice.js +37 -41
- package/lib/ApduDevice.js.map +1 -1
- package/lib/CommandBlock.d.ts +4 -4
- package/lib/CommandBlock.d.ts.map +1 -1
- package/lib/CommandBlock.js +18 -35
- package/lib/CommandBlock.js.map +1 -1
- package/lib/CommandStream.d.ts +1 -1
- package/lib/CommandStream.d.ts.map +1 -1
- package/lib/CommandStream.js +5 -7
- package/lib/CommandStream.js.map +1 -1
- package/lib/Crypto.d.ts +11 -11
- package/lib/Crypto.d.ts.map +1 -1
- package/lib/Device.d.ts +1 -1
- package/lib/Device.d.ts.map +1 -1
- package/lib/Device.js +28 -36
- package/lib/Device.js.map +1 -1
- package/lib/NobleCrypto.d.ts +13 -15
- package/lib/NobleCrypto.d.ts.map +1 -1
- package/lib/NobleCrypto.js +90 -148
- package/lib/NobleCrypto.js.map +1 -1
- package/lib/StreamTreeCipher.d.ts.map +1 -1
- package/lib/StreamTreeCipher.js +32 -36
- package/lib/StreamTreeCipher.js.map +1 -1
- package/lib/__tests__/codec.js +33 -33
- package/lib/__tests__/codec.js.map +1 -1
- package/lib-es/ApduDevice.d.ts.map +1 -1
- package/lib-es/ApduDevice.js +37 -41
- package/lib-es/ApduDevice.js.map +1 -1
- package/lib-es/CommandBlock.d.ts +4 -4
- package/lib-es/CommandBlock.d.ts.map +1 -1
- package/lib-es/CommandBlock.js +18 -35
- package/lib-es/CommandBlock.js.map +1 -1
- package/lib-es/CommandStream.d.ts +1 -1
- package/lib-es/CommandStream.d.ts.map +1 -1
- package/lib-es/CommandStream.js +5 -7
- package/lib-es/CommandStream.js.map +1 -1
- package/lib-es/Crypto.d.ts +11 -11
- package/lib-es/Crypto.d.ts.map +1 -1
- package/lib-es/Device.d.ts +1 -1
- package/lib-es/Device.d.ts.map +1 -1
- package/lib-es/Device.js +28 -36
- package/lib-es/Device.js.map +1 -1
- package/lib-es/NobleCrypto.d.ts +13 -15
- package/lib-es/NobleCrypto.d.ts.map +1 -1
- package/lib-es/NobleCrypto.js +90 -148
- package/lib-es/NobleCrypto.js.map +1 -1
- package/lib-es/StreamTreeCipher.d.ts.map +1 -1
- package/lib-es/StreamTreeCipher.js +32 -36
- package/lib-es/StreamTreeCipher.js.map +1 -1
- package/lib-es/__tests__/codec.js +33 -33
- package/lib-es/__tests__/codec.js.map +1 -1
- package/package.json +2 -2
- package/src/ApduDevice.ts +10 -14
- package/src/CommandBlock.ts +11 -14
- package/src/CommandStream.ts +6 -8
- package/src/Crypto.ts +11 -11
- package/src/Device.ts +26 -34
- package/src/NobleCrypto.ts +20 -59
- package/src/StreamTreeCipher.ts +15 -15
- package/src/__tests__/codec.ts +32 -32
package/lib-es/NobleCrypto.js
CHANGED
|
@@ -1,12 +1,3 @@
|
|
|
1
|
-
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
|
|
2
|
-
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
|
|
3
|
-
return new (P || (P = Promise))(function (resolve, reject) {
|
|
4
|
-
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
|
|
5
|
-
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
|
|
6
|
-
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
|
|
7
|
-
step((generator = generator.apply(thisArg, _arguments || [])).next());
|
|
8
|
-
});
|
|
9
|
-
};
|
|
10
1
|
import * as secp256k1 from "secp256k1";
|
|
11
2
|
import * as ecc from "tiny-secp256k1";
|
|
12
3
|
import { BIP32Factory } from "bip32";
|
|
@@ -17,36 +8,30 @@ const AES_BLOCK_SIZE = 16;
|
|
|
17
8
|
const PRIVATE_KEY_SIZE = 32;
|
|
18
9
|
export class NobleCryptoSecp256k1 {
|
|
19
10
|
randomKeypair() {
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
return this.keypairFromSecretKey(pk);
|
|
26
|
-
});
|
|
11
|
+
let pk;
|
|
12
|
+
do {
|
|
13
|
+
pk = crypto.randomBytes(PRIVATE_KEY_SIZE);
|
|
14
|
+
} while (!secp256k1.privateKeyVerify(pk));
|
|
15
|
+
return this.keypairFromSecretKey(pk);
|
|
27
16
|
}
|
|
28
17
|
derivePrivate(xpriv, path) {
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
};
|
|
41
|
-
});
|
|
18
|
+
const pk = xpriv.slice(0, 32);
|
|
19
|
+
const chainCode = xpriv.slice(32);
|
|
20
|
+
let node = bip32.fromPrivateKey(Buffer.from(pk), Buffer.from(chainCode));
|
|
21
|
+
for (const index of path) {
|
|
22
|
+
node = node.derive(index);
|
|
23
|
+
}
|
|
24
|
+
return {
|
|
25
|
+
publicKey: this.to_array(node.publicKey),
|
|
26
|
+
privateKey: this.to_array(node.privateKey),
|
|
27
|
+
chainCode: this.to_array(node.chainCode),
|
|
28
|
+
};
|
|
42
29
|
}
|
|
43
30
|
keypairFromSecretKey(secretKey) {
|
|
44
|
-
return
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
};
|
|
49
|
-
});
|
|
31
|
+
return {
|
|
32
|
+
publicKey: secp256k1.publicKeyCreate(secretKey),
|
|
33
|
+
privateKey: secretKey,
|
|
34
|
+
};
|
|
50
35
|
}
|
|
51
36
|
derEncode(R, S) {
|
|
52
37
|
if (R[0] > 0x7f) {
|
|
@@ -69,18 +54,14 @@ export class NobleCryptoSecp256k1 {
|
|
|
69
54
|
};
|
|
70
55
|
}
|
|
71
56
|
sign(message, keyPair) {
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
return this.derEncode(signature.slice(0, 32), signature.slice(32, 64));
|
|
76
|
-
});
|
|
57
|
+
const signature = secp256k1.ecdsaSign(message, keyPair.privateKey).signature;
|
|
58
|
+
// DER encoding
|
|
59
|
+
return this.derEncode(signature.slice(0, 32), signature.slice(32, 64));
|
|
77
60
|
}
|
|
78
61
|
verify(message, signature, publicKey) {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
return secp256k1.ecdsaVerify(this.concat(R, S), message, publicKey);
|
|
83
|
-
});
|
|
62
|
+
// DER decoding
|
|
63
|
+
const { R, S } = this.derDecode(signature);
|
|
64
|
+
return secp256k1.ecdsaVerify(this.concat(R, S), message, publicKey);
|
|
84
65
|
}
|
|
85
66
|
to_array(buffer) {
|
|
86
67
|
return new Uint8Array(buffer);
|
|
@@ -116,53 +97,26 @@ export class NobleCryptoSecp256k1 {
|
|
|
116
97
|
}
|
|
117
98
|
return buffer;
|
|
118
99
|
}
|
|
119
|
-
pad(message) {
|
|
120
|
-
// ISO9797M2 implementation
|
|
121
|
-
const padLength = AES_BLOCK_SIZE - (message.length % AES_BLOCK_SIZE);
|
|
122
|
-
if (padLength === AES_BLOCK_SIZE) {
|
|
123
|
-
return message;
|
|
124
|
-
}
|
|
125
|
-
const padding = new Uint8Array(padLength);
|
|
126
|
-
padding[0] = 0x80;
|
|
127
|
-
padding.fill(0, 1);
|
|
128
|
-
return this.concat(message, padding);
|
|
129
|
-
}
|
|
130
|
-
unpad(message) {
|
|
131
|
-
// ISO9797M2 implementation
|
|
132
|
-
for (let i = message.length - 1; i >= 0; i--) {
|
|
133
|
-
if (message[i] === 0x80) {
|
|
134
|
-
return message.slice(0, i);
|
|
135
|
-
}
|
|
136
|
-
if (message[i] !== 0x00) {
|
|
137
|
-
return message;
|
|
138
|
-
}
|
|
139
|
-
}
|
|
140
|
-
throw new Error("Invalid padding");
|
|
141
|
-
}
|
|
142
100
|
encrypt(secret, nonce, message) {
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
return this.concat(bytes, cipher.getAuthTag());
|
|
152
|
-
});
|
|
101
|
+
const normalizedSecret = this.normalizeKey(secret);
|
|
102
|
+
const normalizeNonce = this.normalizeNonce(nonce);
|
|
103
|
+
const cipher = crypto.createCipheriv("aes-256-gcm", normalizedSecret, normalizeNonce);
|
|
104
|
+
cipher.setAutoPadding(false);
|
|
105
|
+
let result = cipher.update(this.to_hex(message), "hex", "hex");
|
|
106
|
+
result += cipher.final("hex");
|
|
107
|
+
const bytes = this.from_hex(result);
|
|
108
|
+
return this.concat(bytes, cipher.getAuthTag());
|
|
153
109
|
}
|
|
154
110
|
decrypt(secret, nonce, ciphertext) {
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
return this.from_hex(result);
|
|
165
|
-
});
|
|
111
|
+
const normalizedSecret = this.normalizeKey(secret);
|
|
112
|
+
const normalizeNonce = this.normalizeNonce(nonce);
|
|
113
|
+
const encryptedData = ciphertext.slice(0, ciphertext.length - AES_BLOCK_SIZE);
|
|
114
|
+
const authTag = ciphertext.slice(encryptedData.length);
|
|
115
|
+
const decipher = crypto.createDecipheriv("aes-256-gcm", normalizedSecret, normalizeNonce);
|
|
116
|
+
decipher.setAuthTag(authTag);
|
|
117
|
+
let result = decipher.update(this.to_hex(encryptedData), "hex", "hex");
|
|
118
|
+
result += decipher.final("hex");
|
|
119
|
+
return this.from_hex(result);
|
|
166
120
|
}
|
|
167
121
|
/**
|
|
168
122
|
* Ledger Live data are encrypted following pattern based on ECIES.
|
|
@@ -177,75 +131,63 @@ export class NobleCryptoSecp256k1 {
|
|
|
177
131
|
variable : Encrypted data
|
|
178
132
|
*/
|
|
179
133
|
encryptUserData(commandStreamPrivateKey, data) {
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
196
|
-
|
|
197
|
-
|
|
198
|
-
|
|
199
|
-
|
|
200
|
-
|
|
201
|
-
return result;
|
|
202
|
-
});
|
|
134
|
+
// Generate ephemeral key pair
|
|
135
|
+
const ephemeralKeypair = this.randomKeypair();
|
|
136
|
+
// Derive the shared secret using ECDH
|
|
137
|
+
const sharedSecret = this.ecdh(this.keypairFromSecretKey(commandStreamPrivateKey), ephemeralKeypair.publicKey);
|
|
138
|
+
// Normalize the shared secret to be used as AES key
|
|
139
|
+
const aesKey = this.computeSymmetricKey(sharedSecret, new Uint8Array());
|
|
140
|
+
// Generate a random IV (nonce)
|
|
141
|
+
const iv = crypto.randomBytes(16);
|
|
142
|
+
// Encrypt the data using AES-256-GCM
|
|
143
|
+
const cipher = crypto.createCipheriv("aes-256-gcm", aesKey, iv);
|
|
144
|
+
let encryptedData = cipher.update(data);
|
|
145
|
+
encryptedData = Buffer.concat([encryptedData, cipher.final()]);
|
|
146
|
+
const tag = cipher.getAuthTag();
|
|
147
|
+
// Serialize the format
|
|
148
|
+
const result = new Uint8Array(1 + ephemeralKeypair.publicKey.length + iv.length + tag.length + encryptedData.length);
|
|
149
|
+
result[0] = 0x00; // Version of the format
|
|
150
|
+
result.set(ephemeralKeypair.publicKey, 1);
|
|
151
|
+
result.set(iv, 34);
|
|
152
|
+
result.set(tag, 50);
|
|
153
|
+
result.set(encryptedData, 66);
|
|
154
|
+
return result;
|
|
203
155
|
}
|
|
204
156
|
decryptUserData(commandStreamPrivateKey, data) {
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
|
|
211
|
-
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
|
|
215
|
-
|
|
216
|
-
|
|
217
|
-
|
|
218
|
-
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
return new Uint8Array(decryptedData.buffer, decryptedData.byteOffset, decryptedData.byteLength);
|
|
224
|
-
});
|
|
157
|
+
const version = data[0];
|
|
158
|
+
if (version !== 0x00) {
|
|
159
|
+
throw new Error("Unsupported format version");
|
|
160
|
+
}
|
|
161
|
+
const ephemeralPublicKey = data.slice(1, 34);
|
|
162
|
+
const iv = data.slice(34, 50);
|
|
163
|
+
const tag = data.slice(50, 66);
|
|
164
|
+
const encryptedData = data.slice(66);
|
|
165
|
+
// Derive the shared secret using ECDH
|
|
166
|
+
const sharedSecret = this.ecdh(this.keypairFromSecretKey(commandStreamPrivateKey), ephemeralPublicKey);
|
|
167
|
+
// Normalize the shared secret to be used as AES key
|
|
168
|
+
const aesKey = this.computeSymmetricKey(sharedSecret, new Uint8Array());
|
|
169
|
+
// Decrypt the data using AES-256-GCM
|
|
170
|
+
const decipher = crypto.createDecipheriv("aes-256-gcm", aesKey, iv);
|
|
171
|
+
decipher.setAuthTag(tag);
|
|
172
|
+
let decryptedData = decipher.update(encryptedData);
|
|
173
|
+
decryptedData = Buffer.concat([decryptedData, decipher.final()]);
|
|
174
|
+
return new Uint8Array(decryptedData.buffer, decryptedData.byteOffset, decryptedData.byteLength);
|
|
225
175
|
}
|
|
226
176
|
randomBytes(size) {
|
|
227
|
-
return
|
|
228
|
-
return crypto.randomBytes(size);
|
|
229
|
-
});
|
|
177
|
+
return crypto.randomBytes(size);
|
|
230
178
|
}
|
|
231
179
|
ecdh(keyPair, publicKey) {
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
return point.slice(1);
|
|
237
|
-
});
|
|
180
|
+
const pubkey = Buffer.from(publicKey);
|
|
181
|
+
const privkey = Buffer.from(keyPair.privateKey);
|
|
182
|
+
const point = ecc.pointMultiply(pubkey, privkey, ecc.isPointCompressed(pubkey));
|
|
183
|
+
return point.slice(1);
|
|
238
184
|
}
|
|
239
185
|
computeSymmetricKey(privateKey, extra) {
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
return digest;
|
|
243
|
-
});
|
|
186
|
+
const digest = hmac("sha256", Buffer.from(extra)).update(Buffer.from(privateKey)).digest();
|
|
187
|
+
return digest;
|
|
244
188
|
}
|
|
245
189
|
hash(message) {
|
|
246
|
-
return
|
|
247
|
-
return crypto.createHash("sha256").update(Buffer.from(message)).digest();
|
|
248
|
-
});
|
|
190
|
+
return crypto.createHash("sha256").update(Buffer.from(message)).digest();
|
|
249
191
|
}
|
|
250
192
|
from_hex(hex) {
|
|
251
193
|
const bytes = new Uint8Array(hex.length / 2);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"NobleCrypto.js","sourceRoot":"","sources":["../src/NobleCrypto.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"NobleCrypto.js","sourceRoot":"","sources":["../src/NobleCrypto.ts"],"names":[],"mappings":"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"}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"StreamTreeCipher.d.ts","sourceRoot":"","sources":["../src/StreamTreeCipher.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAU,MAAM,GAAG,CAAC;AACnC,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE1C;;GAEG;AACH,oBAAY,oBAAoB;IAC9B,WAAW,IAAO;IAClB,WAAW,IAAO;CACnB;AAYD;;GAEG;AACH,qBAAa,gBAAgB;IAC3B,OAAO,CAAC,KAAK,CAAuB;IACpC,OAAO,CAAC,OAAO,CAAS;gBAEZ,IAAI,EAAE,oBAAoB,EAAE,MAAM,EAAE,MAAM;IAKtD,IAAI,IAAI,IAAI,oBAAoB,CAE/B;IAED;;;;;;;;;OASG;IACG,OAAO,CACX,IAAI,EAAE,UAAU,EAChB,IAAI,EAAE,MAAM,EAAE,EACd,OAAO,EAAE,UAAU,EACnB,KAAK,GAAE,UAAU,GAAG,IAAW,GAC9B,OAAO,CAAC,UAAU,CAAC;YAgCR,eAAe;
|
|
1
|
+
{"version":3,"file":"StreamTreeCipher.d.ts","sourceRoot":"","sources":["../src/StreamTreeCipher.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAU,MAAM,GAAG,CAAC;AACnC,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAE1C;;GAEG;AACH,oBAAY,oBAAoB;IAC9B,WAAW,IAAO;IAClB,WAAW,IAAO;CACnB;AAYD;;GAEG;AACH,qBAAa,gBAAgB;IAC3B,OAAO,CAAC,KAAK,CAAuB;IACpC,OAAO,CAAC,OAAO,CAAS;gBAEZ,IAAI,EAAE,oBAAoB,EAAE,MAAM,EAAE,MAAM;IAKtD,IAAI,IAAI,IAAI,oBAAoB,CAE/B;IAED;;;;;;;;;OASG;IACG,OAAO,CACX,IAAI,EAAE,UAAU,EAChB,IAAI,EAAE,MAAM,EAAE,EACd,OAAO,EAAE,UAAU,EACnB,KAAK,GAAE,UAAU,GAAG,IAAW,GAC9B,OAAO,CAAC,UAAU,CAAC;YAgCR,eAAe;IAmB7B,OAAO,CAAC,UAAU;IA4BlB,OAAO,CAAC,UAAU;IAkBlB;;;;;;;;;OASG;IACG,OAAO,CACX,IAAI,EAAE,UAAU,EAChB,IAAI,EAAE,MAAM,EAAE,EACd,eAAe,EAAE,UAAU,GAC1B,OAAO,CAAC,UAAU,CAAC;IAgCtB,OAAO,CAAC,eAAe;IAKvB,MAAM,CAAC,MAAM,CACX,MAAM,EAAE,MAAM,EACd,IAAI,GAAE,oBAAuD,GAC5D,gBAAgB;CAGpB"}
|
|
@@ -41,22 +41,22 @@ export class StreamTreeCipher {
|
|
|
41
41
|
encrypt(tree_1, path_1, message_1) {
|
|
42
42
|
return __awaiter(this, arguments, void 0, function* (tree, path, message, nonce = null) {
|
|
43
43
|
if (nonce === null) {
|
|
44
|
-
nonce =
|
|
44
|
+
nonce = crypto.randomBytes(16);
|
|
45
45
|
}
|
|
46
46
|
// Generate ephemeral key pair
|
|
47
|
-
const ephemeralKeyPair =
|
|
47
|
+
const ephemeralKeyPair = crypto.randomKeypair();
|
|
48
48
|
// Get the group public key
|
|
49
49
|
const groupKeypair = yield this.getGroupKeypair(tree, path);
|
|
50
50
|
// Compute the secret via ECDH
|
|
51
|
-
const secret =
|
|
51
|
+
const secret = crypto.ecdh(ephemeralKeyPair, groupKeypair.publicKey);
|
|
52
52
|
let encrypted = new Uint8Array(0);
|
|
53
53
|
switch (this._mode) {
|
|
54
54
|
case StreamTreeCipherMode.AES_256_CBC: {
|
|
55
|
-
encrypted =
|
|
55
|
+
encrypted = crypto.encrypt(secret, nonce, message);
|
|
56
56
|
break;
|
|
57
57
|
}
|
|
58
58
|
case StreamTreeCipherMode.AES_256_GCM: {
|
|
59
|
-
encrypted =
|
|
59
|
+
encrypted = crypto.encrypt(secret, nonce, message);
|
|
60
60
|
break;
|
|
61
61
|
}
|
|
62
62
|
default:
|
|
@@ -78,33 +78,31 @@ export class StreamTreeCipher {
|
|
|
78
78
|
}
|
|
79
79
|
// Compute the relative path from the event to the path parameter
|
|
80
80
|
const privateKey = (yield this._device.readKey(tree, path)).slice(0, 32);
|
|
81
|
-
const publicKey =
|
|
81
|
+
const publicKey = crypto.keypairFromSecretKey(privateKey).publicKey;
|
|
82
82
|
return { privateKey, publicKey };
|
|
83
83
|
});
|
|
84
84
|
}
|
|
85
85
|
encodeData(ephemeralPublicKey, nonce, data, message) {
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
return result;
|
|
107
|
-
});
|
|
86
|
+
const result = new Uint8Array(1 + 33 + nonce.length + TAG_LENGTH + data.length);
|
|
87
|
+
let offset = 0;
|
|
88
|
+
// Version
|
|
89
|
+
result[offset] = this._mode;
|
|
90
|
+
offset += 1;
|
|
91
|
+
// Ephemeral public key
|
|
92
|
+
result.set(ephemeralPublicKey, offset);
|
|
93
|
+
offset += ephemeralPublicKey.length;
|
|
94
|
+
// Nonce/IV
|
|
95
|
+
result.set(nonce, offset);
|
|
96
|
+
offset += nonce.length;
|
|
97
|
+
// Checksum
|
|
98
|
+
if (this._mode == StreamTreeCipherMode.AES_256_CBC) {
|
|
99
|
+
const checksum = this.computeChecksum(message);
|
|
100
|
+
result.set(checksum, offset);
|
|
101
|
+
offset += checksum.length;
|
|
102
|
+
}
|
|
103
|
+
// Encrypted data
|
|
104
|
+
result.set(data, offset);
|
|
105
|
+
return result;
|
|
108
106
|
}
|
|
109
107
|
decodeData(payload) {
|
|
110
108
|
const version = payload[0];
|
|
@@ -141,19 +139,19 @@ export class StreamTreeCipher {
|
|
|
141
139
|
const encryptedMessage = decodedPayload.encrypted;
|
|
142
140
|
const checksum = decodedPayload.checksum;
|
|
143
141
|
const sharedKeyPair = yield this.getGroupKeypair(tree, path);
|
|
144
|
-
const secret =
|
|
142
|
+
const secret = crypto.ecdh(sharedKeyPair, ephemeralKey);
|
|
145
143
|
let decrypted = new Uint8Array(0);
|
|
146
144
|
switch (this._mode) {
|
|
147
145
|
case StreamTreeCipherMode.AES_256_CBC: {
|
|
148
|
-
decrypted =
|
|
149
|
-
const computedChecksum =
|
|
146
|
+
decrypted = crypto.decrypt(secret, nonce, encryptedMessage);
|
|
147
|
+
const computedChecksum = this.computeChecksum(decrypted);
|
|
150
148
|
if (crypto.to_hex(computedChecksum) !== crypto.to_hex(checksum)) {
|
|
151
149
|
throw new Error("Invalid checksum");
|
|
152
150
|
}
|
|
153
151
|
break;
|
|
154
152
|
}
|
|
155
153
|
case StreamTreeCipherMode.AES_256_GCM: {
|
|
156
|
-
decrypted =
|
|
154
|
+
decrypted = crypto.decrypt(secret, nonce, encryptedMessage);
|
|
157
155
|
break;
|
|
158
156
|
}
|
|
159
157
|
default:
|
|
@@ -163,10 +161,8 @@ export class StreamTreeCipher {
|
|
|
163
161
|
});
|
|
164
162
|
}
|
|
165
163
|
computeChecksum(message) {
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
return hash.slice(0, 16);
|
|
169
|
-
});
|
|
164
|
+
const hash = crypto.hash(message);
|
|
165
|
+
return hash.slice(0, 16);
|
|
170
166
|
}
|
|
171
167
|
static create(device, mode = StreamTreeCipherMode.AES_256_GCM) {
|
|
172
168
|
return new StreamTreeCipher(mode, device);
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"StreamTreeCipher.js","sourceRoot":"","sources":["../src/StreamTreeCipher.ts"],"names":[],"mappings":";;;;;;;;;AAAA,OAAO,EAAU,MAAM,EAAE,MAAM,GAAG,CAAC;AAGnC;;GAEG;AACH,MAAM,CAAN,IAAY,oBAGX;AAHD,WAAY,oBAAoB;IAC9B,6EAAkB,CAAA;IAClB,6EAAkB,CAAA;AACpB,CAAC,EAHW,oBAAoB,KAApB,oBAAoB,QAG/B;AAED,MAAM,UAAU,GAAG,EAAE,CAAC;AAUtB;;GAEG;AACH,MAAM,OAAO,gBAAgB;IAI3B,YAAY,IAA0B,EAAE,MAAc;QACpD,IAAI,CAAC,KAAK,GAAG,IAAI,CAAC;QAClB,IAAI,CAAC,OAAO,GAAG,MAAM,CAAC;IACxB,CAAC;IAED,IAAI,IAAI;QACN,OAAO,IAAI,CAAC,KAAK,CAAC;IACpB,CAAC;IAED;;;;;;;;;OASG;IACG,OAAO;6DACX,IAAgB,EAChB,IAAc,EACd,OAAmB,EACnB,QAA2B,IAAI;YAE/B,IAAI,KAAK,KAAK,IAAI,EAAE,CAAC;gBACnB,KAAK,GAAG,MAAM,
|
|
1
|
+
{"version":3,"file":"StreamTreeCipher.js","sourceRoot":"","sources":["../src/StreamTreeCipher.ts"],"names":[],"mappings":"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"}
|
|
@@ -14,81 +14,81 @@ import { CommandStreamEncoder } from "../CommandStreamEncoder";
|
|
|
14
14
|
import { crypto } from "../Crypto";
|
|
15
15
|
import { CommandStream } from "..";
|
|
16
16
|
describe("Encode/Decode command stream tester", () => {
|
|
17
|
-
it("should encode and decode a byte", () =>
|
|
17
|
+
it("should encode and decode a byte", () => {
|
|
18
18
|
const byte = 42;
|
|
19
19
|
let buffer = new Uint8Array();
|
|
20
20
|
buffer = TLV.pushByte(buffer, 42);
|
|
21
21
|
const decoded = TLV.readVarInt(TLV.readTLV(buffer, 0));
|
|
22
22
|
expect(decoded.value).toBe(byte);
|
|
23
|
-
})
|
|
24
|
-
it("should encode and decode a Int32", () =>
|
|
23
|
+
});
|
|
24
|
+
it("should encode and decode a Int32", () => {
|
|
25
25
|
const varint = 0xdeadbeef;
|
|
26
26
|
let buffer = new Uint8Array();
|
|
27
27
|
buffer = TLV.pushInt32(buffer, varint);
|
|
28
28
|
const decoded = TLV.readVarInt(TLV.readTLV(buffer, 0));
|
|
29
29
|
expect(decoded.value).toBe(varint);
|
|
30
|
-
})
|
|
31
|
-
it("should encode and decode a string", () =>
|
|
30
|
+
});
|
|
31
|
+
it("should encode and decode a string", () => {
|
|
32
32
|
const str = "Hello World";
|
|
33
33
|
let buffer = new Uint8Array();
|
|
34
34
|
buffer = TLV.pushString(buffer, str);
|
|
35
35
|
const decoded = TLV.readString(TLV.readTLV(buffer, 0));
|
|
36
36
|
expect(decoded.value).toBe(str);
|
|
37
|
-
})
|
|
38
|
-
it("should encode and decode a hash", () =>
|
|
39
|
-
const hash =
|
|
37
|
+
});
|
|
38
|
+
it("should encode and decode a hash", () => {
|
|
39
|
+
const hash = crypto.hash(new Uint8Array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]));
|
|
40
40
|
let buffer = new Uint8Array();
|
|
41
41
|
buffer = TLV.pushHash(buffer, hash);
|
|
42
42
|
const decoded = TLV.readHash(TLV.readTLV(buffer, 0));
|
|
43
43
|
expect(crypto.to_hex(decoded.value)).toEqual(crypto.to_hex(hash));
|
|
44
|
-
})
|
|
45
|
-
it("should encode and decode bytes", () =>
|
|
44
|
+
});
|
|
45
|
+
it("should encode and decode bytes", () => {
|
|
46
46
|
const bytes = new Uint8Array([0, 1, 2, 3, 4, 5, 6, 7, 8, 9]);
|
|
47
47
|
let buffer = new Uint8Array();
|
|
48
48
|
buffer = TLV.pushBytes(buffer, bytes);
|
|
49
49
|
const decoded = TLV.readBytes(TLV.readTLV(buffer, 0));
|
|
50
50
|
expect(decoded.value).toEqual(bytes);
|
|
51
|
-
})
|
|
52
|
-
it("should encode and decode a signature", () =>
|
|
53
|
-
const alice =
|
|
54
|
-
const block =
|
|
51
|
+
});
|
|
52
|
+
it("should encode and decode a signature", () => {
|
|
53
|
+
const alice = crypto.randomKeypair();
|
|
54
|
+
const block = signCommandBlock(createCommandBlock(alice.publicKey, []), alice.publicKey, alice.privateKey);
|
|
55
55
|
let buffer = new Uint8Array();
|
|
56
56
|
buffer = TLV.pushSignature(buffer, block.signature);
|
|
57
57
|
const decoded = TLV.readSignature(TLV.readTLV(buffer, 0));
|
|
58
58
|
expect(decoded.value).toEqual(block.signature);
|
|
59
|
-
})
|
|
60
|
-
it("should encode and decode a public key", () =>
|
|
61
|
-
const alice =
|
|
59
|
+
});
|
|
60
|
+
it("should encode and decode a public key", () => {
|
|
61
|
+
const alice = crypto.randomKeypair();
|
|
62
62
|
let buffer = new Uint8Array();
|
|
63
63
|
buffer = TLV.pushPublicKey(buffer, alice.publicKey);
|
|
64
64
|
const decoded = TLV.readPublicKey(TLV.readTLV(buffer, 0));
|
|
65
65
|
expect(decoded.value).toEqual(alice.publicKey);
|
|
66
|
-
})
|
|
67
|
-
it("should encode and decode a stream. Encoding/Decoding should not alter the stream", () =>
|
|
68
|
-
const alice =
|
|
69
|
-
const groupPk =
|
|
70
|
-
const groupChainCode =
|
|
66
|
+
});
|
|
67
|
+
it("should encode and decode a stream. Encoding/Decoding should not alter the stream", () => {
|
|
68
|
+
const alice = crypto.randomKeypair();
|
|
69
|
+
const groupPk = crypto.randomKeypair();
|
|
70
|
+
const groupChainCode = crypto.randomBytes(32);
|
|
71
71
|
const xpriv = new Uint8Array(64);
|
|
72
|
-
const initializationVector =
|
|
72
|
+
const initializationVector = crypto.randomBytes(16);
|
|
73
73
|
xpriv.set(groupPk.privateKey);
|
|
74
74
|
xpriv.set(groupChainCode, 32);
|
|
75
|
-
const ephemeralPk =
|
|
76
|
-
const block1 =
|
|
77
|
-
new Seed(
|
|
75
|
+
const ephemeralPk = crypto.randomKeypair();
|
|
76
|
+
const block1 = signCommandBlock(createCommandBlock(alice.publicKey, [
|
|
77
|
+
new Seed(crypto.randomBytes(16), 0, groupPk.publicKey, initializationVector, xpriv, ephemeralPk.publicKey),
|
|
78
78
|
]), alice.publicKey, alice.privateKey);
|
|
79
|
-
const block2 =
|
|
80
|
-
new AddMember("Alice",
|
|
81
|
-
new PublishKey(
|
|
79
|
+
const block2 = signCommandBlock(createCommandBlock(alice.publicKey, [
|
|
80
|
+
new AddMember("Alice", crypto.randomBytes(32), Permissions.OWNER),
|
|
81
|
+
new PublishKey(crypto.randomBytes(16), crypto.randomBytes(32), crypto.randomBytes(32), crypto.randomBytes(32)),
|
|
82
82
|
]), alice.publicKey, alice.privateKey);
|
|
83
|
-
const block3 =
|
|
83
|
+
const block3 = signCommandBlock(createCommandBlock(alice.publicKey, []), alice.publicKey, alice.privateKey);
|
|
84
84
|
const stream = [block1, block2, block3];
|
|
85
85
|
const encoded = CommandStreamEncoder.encode(stream);
|
|
86
|
-
const digestEncoded =
|
|
86
|
+
const digestEncoded = crypto.hash(encoded);
|
|
87
87
|
const decoded = CommandStreamDecoder.decode(encoded);
|
|
88
88
|
const reencoded = CommandStreamEncoder.encode(decoded);
|
|
89
|
-
const digestReencoded =
|
|
89
|
+
const digestReencoded = crypto.hash(reencoded);
|
|
90
90
|
expect(digestEncoded).toEqual(digestReencoded);
|
|
91
|
-
})
|
|
91
|
+
});
|
|
92
92
|
it("decodes a specific command stream", () => __awaiter(void 0, void 0, void 0, function* () {
|
|
93
93
|
const tlv = "0101010220824b3168c79e8b61b599751c107117b5c9b647f2b6859de8a245952559707692062102a13e82cd0d2f77d1ab1434d8bd799571e54cd32e1121c5cf82217f8b0b713b6b01010315a8050c800000008000001080000000062103ccf74aa7775b3d39d6cbb0236acee7a7f980b9f6a556a4d814d44b0bd56cb77b05108c51eda6be26623ca919ed17333afcdb054019c0b60ede1692479cc04ce69eae6a0bd51941bab6f044f3dec10c11cf11e6253504d1df6b0aab7dc1996e4eaa7c6f92c29153c59534578901cd7ff4efcea1ae06210268abdb3d49ba4a274ce8660cde0d1eeaf1fea00e281218be775f6b3aefc39756113a040f7765622d746f6f6c732d6563626638062103a270456b0f95714cc61a6473e6b6d8db354a3c377281096bdd2439a5475ecbf80104ffffffff129a05100e5205b4a616b2a4d79b07b4a4932f560540669e741f38fee07956fb0dc0ea9978d55bd5d8424b0d0f66a2c5a45788f92d0ddc283138c7ba62c521de1d604ee7f847c5aed40a11536bbe742af0be8cfd4132062103a270456b0f95714cc61a6473e6b6d8db354a3c377281096bdd2439a5475ecbf80621027003755248202ea8a67d1fcdcd82d7f7022248f3af892fa5307d3ea250dc81050346304402204422a779fd08723d8cba19c0cc11ef7a24f6f1f459cb01598ff1a26f27ea8976022053a554d4f509223f2d08faa5de796fed13a9762f35da08e94884edd1f7c0d015";
|
|
94
94
|
const decoded = CommandStreamDecoder.decode(crypto.from_hex(tlv));
|