Skip to content

Commit deb0844

Browse files
committed
Update the AES module according to ToB's recommendations
1 parent 797a76e commit deb0844

File tree

3 files changed

+60
-19
lines changed

3 files changed

+60
-19
lines changed

packages/ethereum-cryptography/README.md

Lines changed: 35 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -267,16 +267,15 @@ like [pbkdf2](#pbkdf2-submodule) or [scrypt](#scrypt-submodule).
267267

268268
### Operation modes
269269

270-
This submodule works with different [block cipher modes of operation](https://en.wikipedia.org/wiki/Block_cipher_mode_of_operation).
271-
To choose one of them, you should pass the `mode` parameter a string with the
272-
same format as OpenSSL and Node use. You can take a look at them by running
273-
`openssl list -cipher-algorithms`.
270+
This submodule works with different [block cipher modes of operation](https://en.wikipedia.org/wiki/Block_cipher_mode_of_operation). If you are using this module in a new
271+
application, we recommend using the default.
274272

275-
In Node, any mode that its OpenSSL version supports can be used.
273+
While this module may work with any mode supported by OpenSSL, we only test it
274+
with `aes-128-ctr`, `aes-128-cbc`, and `aes-256-cbc`. If you use another module
275+
a warning will be printed in the console.
276276

277-
In the browser, we test it to work with the modes that are normally used in
278-
Ethereum libraries and applications. Those are `aes-128-ctr`, `aes-126-cbc`, and
279-
`aes-256-cbc`, but other modes may work.
277+
We only recommend using `aes-128-cbc` and `aes-256-cbc` to decrypt already
278+
encrypted data.
280279

281280
### Padding plaintext messages
282281

@@ -292,14 +291,38 @@ If you need to encrypt without padding or want to use another padding scheme,
292291
you can disable PKCS#7 padding by passing `false` as the last argument and
293292
handling padding yourself. Note that if you do this and your operation mode
294293
requires padding, `encrypt` will throw if your plaintext message isn't a
295-
multiple of `16.
294+
multiple of `16`.
295+
296+
This option is only present to enable the decryption of already encrypted data.
297+
To encrypt new data, we recommend using the default.
298+
299+
### IV reusing
300+
301+
The `iv` parameter of the `encrypt` function must be unique, or the security
302+
of the encryption algorithm can be compromissed.
303+
304+
You can generate a new `iv` using the `random` module.
305+
306+
Note that to decrypt a value, you have to provide the same `iv` used to encrypt
307+
it.
308+
309+
### How to handle errors with this module
310+
311+
Sensitive information can be leaked via error messages when using this module.
312+
To avoid this, you should make sure that the errors you return don't
313+
contain the exact reason for the error. Instead, errors must report general
314+
encryption/decryption failures.
315+
316+
Note that implementing this can mean catching all errors that can be thrown
317+
when calling on of this module's functions, and just throwing a new generic
318+
exception.
296319

297320
### Function types
298321

299322
```ts
300-
function encrypt(msg: Buffer, key: Buffer, iv: Buffer, mode: string, pkcs7PaddingEnabled = true): Buffer;
323+
function encrypt(msg: Buffer, key: Buffer, iv: Buffer, mode = "aes-128-ctr", pkcs7PaddingEnabled = true): Buffer;
301324

302-
function decrypt(cypherText: Buffer, key: Buffer, iv: Buffer, mode: string, pkcs7PaddingEnabled = true): Buffer
325+
function decrypt(cypherText: Buffer, key: Buffer, iv: Buffer, mode = "aes-128-ctr", pkcs7PaddingEnabled = true): Buffer
303326
```
304327

305328
### Example usage
@@ -311,8 +334,7 @@ console.log(
311334
encrypt(
312335
Buffer.from("message", "ascii"),
313336
Buffer.from("2b7e151628aed2a6abf7158809cf4f3c", "hex"),
314-
Buffer.from("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff", "hex"),
315-
"aes-128-cbc"
337+
Buffer.from("f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff", "hex")
316338
).toString("hex")
317339
);
318340
```

packages/ethereum-cryptography/src/aes.ts

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,24 @@
11
const browserifyAes = require("browserify-aes");
22

3+
const SUPPORTED_MODES = ["aes-128-ctr", "aes-128-cbc", "aes-256-cbc"];
4+
35
function ensureAesMode(mode: string) {
46
if (!mode.startsWith("aes-")) {
57
throw new Error(`AES submodule doesn't support mode ${mode}`);
68
}
79
}
810

11+
function warnIfUnsuportedMode(mode: string) {
12+
if (!SUPPORTED_MODES.includes(mode)) {
13+
console.warn("Using an unsupported AES mode. Consider using aes-128-ctr.");
14+
}
15+
}
16+
917
export function encrypt(
1018
msg: Buffer,
1119
key: Buffer,
1220
iv: Buffer,
13-
mode: string,
21+
mode = "aes-128-ctr",
1422
pkcs7PaddingEnabled = true
1523
): Buffer {
1624
ensureAesMode(mode);
@@ -28,7 +36,7 @@ export function decrypt(
2836
cypherText: Buffer,
2937
key: Buffer,
3038
iv: Buffer,
31-
mode: string,
39+
mode = "aes-128-ctr",
3240
pkcs7PaddingEnabled = true
3341
): Buffer {
3442
ensureAesMode(mode);

packages/ethereum-cryptography/test/test-vectors/aes.ts

Lines changed: 15 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,17 @@ const TEST_VECTORS = [
2323
"874d6191b620e3261bef6864990db6ce9806f66b7970fdff8617187bb9fffdff5ae4df3edbd5d35e5b4f09020db03eab1e031dda2fbe03d1792170a0f3009cee",
2424
pkcs7PaddingEnabled: true
2525
},
26+
// Same as the previous one, but with default params
27+
{
28+
mode: undefined,
29+
key: "2b7e151628aed2a6abf7158809cf4f3c",
30+
iv: "f0f1f2f3f4f5f6f7f8f9fafbfcfdfeff",
31+
msg:
32+
"6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710",
33+
cypherText:
34+
"874d6191b620e3261bef6864990db6ce9806f66b7970fdff8617187bb9fffdff5ae4df3edbd5d35e5b4f09020db03eab1e031dda2fbe03d1792170a0f3009cee",
35+
pkcs7PaddingEnabled: undefined
36+
},
2637
// CBC uses padding, but the NIST test vectors don't
2738
{
2839
mode: "aes-128-cbc",
@@ -94,15 +105,15 @@ export function createTests(
94105
msg: Buffer,
95106
key: Buffer,
96107
iv: Buffer,
97-
mode: string,
98-
pkcs7PaddingEnabled: boolean
108+
mode?: string,
109+
pkcs7PaddingEnabled?: boolean
99110
) => Buffer,
100111
decrypt: (
101112
cypherText: Buffer,
102113
key: Buffer,
103114
iv: Buffer,
104-
mode: string,
105-
pkcs7PaddingEnabled: boolean
115+
mode?: string,
116+
pkcs7PaddingEnabled?: boolean
106117
) => Buffer
107118
) {
108119
describe("aes", function() {

0 commit comments

Comments
 (0)