Skip to content

Commit dae283d

Browse files
committed
crypto: refactoring internals, add WebCrypto
Fixes: #678 Refs: #26854 Signed-off-by: James M Snell <jasnell@gmail.com> PR-URL: #35093 Reviewed-By: Matteo Collina <matteo.collina@gmail.com> Reviewed-By: Anna Henningsen <anna@addaleax.net> Reviewed-By: Michaël Zasso <targos@protonmail.com> Reviewed-By: Rich Trott <rtrott@gmail.com>
1 parent ba77dc8 commit dae283d

File tree

149 files changed

+28390
-8575
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

149 files changed

+28390
-8575
lines changed

.github/CODEOWNERS

+1-1
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@
5959
/lib/crypto.js @nodejs/crypto
6060
/lib/tls.js @nodejs/crypto @nodejs/net
6161
/src/node_crypto* @nodejs/crypto
62-
/src/node_crypto_common* @nodejs/crypto @nodejs/quic
62+
/src/crypto/* @nodejs/crypto @nodejs/quic
6363

6464
# http
6565

benchmark/crypto/hkdf.js

+44
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,44 @@
1+
'use strict';
2+
3+
const common = require('../common.js');
4+
const assert = require('assert');
5+
const {
6+
hkdf,
7+
hkdfSync
8+
} = require('crypto');
9+
10+
const bench = common.createBenchmark(main, {
11+
sync: [0, 1],
12+
size: [10, 64, 1024],
13+
key: ['a', 'secret', 'this-is-a-much-longer-secret'],
14+
salt: ['', 'salt'],
15+
info: ['', 'info'],
16+
hash: ['sha256', 'sha512'],
17+
n: [1e3],
18+
});
19+
20+
function measureSync(n, size, salt, info, hash, key) {
21+
bench.start();
22+
for (let i = 0; i < n; ++i)
23+
hkdfSync(hash, key, salt, info, size);
24+
bench.end(n);
25+
}
26+
27+
function measureAsync(n, size, salt, info, hash, key) {
28+
let remaining = n;
29+
function done(err) {
30+
assert.ifError(err);
31+
if (--remaining === 0)
32+
bench.end(n);
33+
}
34+
bench.start();
35+
for (let i = 0; i < n; ++i)
36+
hkdf(hash, key, salt, info, size, done);
37+
}
38+
39+
function main({ n, sync, size, salt, info, hash, key }) {
40+
if (sync)
41+
measureSync(n, size, salt, info, hash, key);
42+
else
43+
measureAsync(n, size, salt, info, hash, key);
44+
}

benchmark/crypto/keygen.js

+71
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
'use strict';
2+
3+
const common = require('../common.js');
4+
const assert = require('assert');
5+
const {
6+
generateKeyPair,
7+
generateKeyPairSync
8+
} = require('crypto');
9+
10+
const bench = common.createBenchmark(main, {
11+
method: ['rsaSync', 'rsaAsync', 'dsaSync', 'dsaAsync'],
12+
n: [1e2],
13+
});
14+
15+
const methods = {
16+
rsaSync(n) {
17+
bench.start();
18+
for (let i = 0; i < n; ++i) {
19+
generateKeyPairSync('rsa', {
20+
modulusLength: 1024,
21+
publicExponent: 0x10001
22+
});
23+
}
24+
bench.end(n);
25+
},
26+
27+
rsaAsync(n) {
28+
let remaining = n;
29+
function done(err) {
30+
assert.ifError(err);
31+
if (--remaining === 0)
32+
bench.end(n);
33+
}
34+
bench.start();
35+
for (let i = 0; i < n; ++i)
36+
generateKeyPair('rsa', {
37+
modulusLength: 512,
38+
publicExponent: 0x10001
39+
}, done);
40+
},
41+
42+
dsaSync(n) {
43+
bench.start();
44+
for (let i = 0; i < n; ++i) {
45+
generateKeyPairSync('dsa', {
46+
modulusLength: 512,
47+
divisorLength: 256,
48+
});
49+
}
50+
bench.end(n);
51+
},
52+
53+
dsaAsync(n) {
54+
let remaining = n;
55+
function done(err) {
56+
assert.ifError(err);
57+
if (--remaining === 0)
58+
bench.end(n);
59+
}
60+
bench.start();
61+
for (let i = 0; i < n; ++i)
62+
generateKeyPair('dsa', {
63+
modulusLength: 512,
64+
divisorLength: 256,
65+
}, done);
66+
},
67+
};
68+
69+
function main({ n, method }) {
70+
methods[method](n);
71+
}

benchmark/crypto/webcrypto-digest.js

+58
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
'use strict';
2+
3+
const common = require('../common.js');
4+
const {
5+
createHash,
6+
webcrypto: {
7+
subtle,
8+
getRandomValues
9+
}
10+
} = require('crypto');
11+
12+
const bench = common.createBenchmark(main, {
13+
sync: ['createHash', 'subtle'],
14+
data: [10, 20, 50, 100],
15+
method: ['SHA-1', 'SHA-256', 'SHA-384', 'SHA-512'],
16+
n: [1e3],
17+
});
18+
19+
const kMethods = {
20+
'SHA-1': 'sha1',
21+
'SHA-256': 'sha256',
22+
'SHA-384': 'sha384',
23+
'SHA-512': 'sha512'
24+
};
25+
26+
// This benchmark only looks at clock time and ignores factors
27+
// such as event loop delay, event loop utilization, and memory.
28+
// As such, it is expected that the synchronous legacy method
29+
// will always be faster in clock time.
30+
31+
function measureLegacy(n, data, method) {
32+
method = kMethods[method];
33+
bench.start();
34+
for (let i = 0; i < n; ++i) {
35+
createHash(method).update(data).digest();
36+
}
37+
bench.end(n);
38+
}
39+
40+
function measureSubtle(n, data, method) {
41+
const ec = new TextEncoder();
42+
data = ec.encode(data);
43+
const jobs = new Array(n);
44+
bench.start();
45+
for (let i = 0; i < n; i++)
46+
jobs[i] = subtle.digest(method, data);
47+
Promise.all(jobs).then(() => bench.end(n)).catch((err) => {
48+
process.nextTick(() => { throw err; });
49+
});
50+
}
51+
52+
function main({ n, sync, data, method }) {
53+
data = getRandomValues(Buffer.alloc(data));
54+
switch (sync) {
55+
case 'createHash': return measureLegacy(n, data, method);
56+
case 'subtle': return measureSubtle(n, data, method);
57+
}
58+
}

0 commit comments

Comments
 (0)