@noble/curves 0.1.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/LICENSE +21 -0
- package/README.md +71 -0
- package/index.js +1 -0
- package/lib/esm/modular.js +148 -0
- package/lib/esm/package.json +7 -0
- package/lib/esm/shortw.js +1058 -0
- package/lib/esm/utils.js +67 -0
- package/lib/modular.d.ts +25 -0
- package/lib/modular.js +158 -0
- package/lib/shortw.d.ts +164 -0
- package/lib/shortw.js +1062 -0
- package/lib/utils.d.ts +8 -0
- package/lib/utils.js +77 -0
- package/package.json +75 -0
package/LICENSE
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
The MIT License (MIT)
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2022 Paul Miller (https://paulmillr.com)
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the “Software”), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in
|
|
13
|
+
all copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
21
|
+
THE SOFTWARE.
|
package/README.md
ADDED
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
# noble-curves
|
|
2
|
+
|
|
3
|
+
Minimal, zero-dependency JS implementation of elliptic curve cryptography.
|
|
4
|
+
|
|
5
|
+
Implements Short Weierstrass curves with ECDSA signature scheme.
|
|
6
|
+
|
|
7
|
+
To keep the package minimal, no curve definitions are provided out-of-box.
|
|
8
|
+
Main reason for that is the fact hashing library is usually required for full functionality. Use separate package that defines popular curves: `micro-curve-definitions` for P192, P224, P256, P384, P521, secp256k1, stark curve, bn254, pasta (pallas/vesta) - it depends on `@noble/hashes`.
|
|
9
|
+
|
|
10
|
+
Future plans:
|
|
11
|
+
|
|
12
|
+
- Edwards, Twisted Edwards & Montgomery curves
|
|
13
|
+
- hash-to-curve standard
|
|
14
|
+
- pairings
|
|
15
|
+
|
|
16
|
+
### This library belongs to _noble_ crypto
|
|
17
|
+
|
|
18
|
+
> **noble-crypto** — high-security, easily auditable set of contained cryptographic libraries and tools.
|
|
19
|
+
|
|
20
|
+
- No dependencies, small files
|
|
21
|
+
- Easily auditable TypeScript/JS code
|
|
22
|
+
- Supported in all major browsers and stable node.js versions
|
|
23
|
+
- All releases are signed with PGP keys
|
|
24
|
+
- Check out [homepage](https://paulmillr.com/noble/) & all libraries:
|
|
25
|
+
[secp256k1](https://github.com/paulmillr/noble-secp256k1),
|
|
26
|
+
[ed25519](https://github.com/paulmillr/noble-ed25519),
|
|
27
|
+
[bls12-381](https://github.com/paulmillr/noble-bls12-381),
|
|
28
|
+
[hashes](https://github.com/paulmillr/noble-hashes),
|
|
29
|
+
[curves](https://github.com/paulmillr/noble-curves)
|
|
30
|
+
|
|
31
|
+
## Usage
|
|
32
|
+
|
|
33
|
+
Use NPM in node.js / browser, or include single file from
|
|
34
|
+
[GitHub's releases page](https://github.com/paulmillr/noble-curves/releases):
|
|
35
|
+
|
|
36
|
+
## Usage
|
|
37
|
+
|
|
38
|
+
```sh
|
|
39
|
+
npm install @noble/curves
|
|
40
|
+
```
|
|
41
|
+
|
|
42
|
+
```ts
|
|
43
|
+
// Short Weierstrass curve
|
|
44
|
+
import shortw from '@noble/curves/shortw';
|
|
45
|
+
import { sha256 } from '@noble/hashes/sha256';
|
|
46
|
+
import { hmac } from '@noble/hashes/hmac';
|
|
47
|
+
import { concatBytes, randomBytes } from '@noble/hashes/utils';
|
|
48
|
+
|
|
49
|
+
export const secp256k1 = shortw({
|
|
50
|
+
a: 0n,
|
|
51
|
+
b: 7n,
|
|
52
|
+
// Field over which we'll do calculations
|
|
53
|
+
P: 2n ** 256n - 2n ** 32n - 2n ** 9n - 2n ** 8n - 2n ** 7n - 2n ** 6n - 2n ** 4n - 1n,
|
|
54
|
+
// Curve order, total count of valid points in the field
|
|
55
|
+
n: 0xfffffffffffffffffffffffffffffffebaaedce6af48a03bbfd25e8cd0364141n,
|
|
56
|
+
// Base point (x, y) aka generator point
|
|
57
|
+
Gx: 55066263022277343669578718895168534326250603453777594175500187360389116729240n,
|
|
58
|
+
Gy: 32670510020758816978083085130507043184471273380659243275938904335757337482424n,
|
|
59
|
+
hash: sha256,
|
|
60
|
+
hmac: (k: Uint8Array, ...msgs: Uint8Array[]) => hmac(sha256, key, concatBytes(...msgs)),
|
|
61
|
+
randomBytes: randomBytes
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
// secp256k1.getPublicKey(priv)
|
|
65
|
+
// secp256k1.sign(msg, priv)
|
|
66
|
+
// secp256k1.verify(sig, msg, pub)
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
## License
|
|
70
|
+
|
|
71
|
+
MIT (c) Paul Miller [(https://paulmillr.com)](https://paulmillr.com), see LICENSE file.
|
package/index.js
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
throw new Error('Incorrect usage. Import submodules instead');
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
/*! @noble/curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
|
|
2
|
+
const _0n = BigInt(0);
|
|
3
|
+
const _1n = BigInt(1);
|
|
4
|
+
const _2n = BigInt(2);
|
|
5
|
+
const _3n = BigInt(3);
|
|
6
|
+
const _4n = BigInt(4);
|
|
7
|
+
const _5n = BigInt(5);
|
|
8
|
+
const _8n = BigInt(8);
|
|
9
|
+
// Calculates a modulo b
|
|
10
|
+
export function mod(a, b) {
|
|
11
|
+
const result = a % b;
|
|
12
|
+
return result >= _0n ? result : b + result;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Efficiently exponentiate num to power and do modular division.
|
|
16
|
+
* @example
|
|
17
|
+
* powMod(2n, 6n, 11n) // 64n % 11n == 9n
|
|
18
|
+
*/
|
|
19
|
+
export function pow(num, power, modulo) {
|
|
20
|
+
if (modulo <= _0n || power < _0n)
|
|
21
|
+
throw new Error('Expected power/modulo > 0');
|
|
22
|
+
if (modulo === _1n)
|
|
23
|
+
return _0n;
|
|
24
|
+
let res = _1n;
|
|
25
|
+
while (power > _0n) {
|
|
26
|
+
if (power & _1n)
|
|
27
|
+
res = (res * num) % modulo;
|
|
28
|
+
num = (num * num) % modulo;
|
|
29
|
+
power >>= _1n;
|
|
30
|
+
}
|
|
31
|
+
return res;
|
|
32
|
+
}
|
|
33
|
+
// Does x ^ (2 ^ power) mod p. pow2(30, 4) == 30 ^ (2 ^ 4)
|
|
34
|
+
export function pow2(x, power, modulo) {
|
|
35
|
+
let res = x;
|
|
36
|
+
while (power-- > _0n) {
|
|
37
|
+
res *= res;
|
|
38
|
+
res %= modulo;
|
|
39
|
+
}
|
|
40
|
+
return res;
|
|
41
|
+
}
|
|
42
|
+
// Inverses number over modulo
|
|
43
|
+
export function invert(number, modulo) {
|
|
44
|
+
if (number === _0n || modulo <= _0n) {
|
|
45
|
+
throw new Error(`invert: expected positive integers, got n=${number} mod=${modulo}`);
|
|
46
|
+
}
|
|
47
|
+
// Eucledian GCD https://brilliant.org/wiki/extended-euclidean-algorithm/
|
|
48
|
+
let a = mod(number, modulo);
|
|
49
|
+
let b = modulo;
|
|
50
|
+
// prettier-ignore
|
|
51
|
+
let x = _0n, y = _1n, u = _1n, v = _0n;
|
|
52
|
+
while (a !== _0n) {
|
|
53
|
+
const q = b / a;
|
|
54
|
+
const r = b % a;
|
|
55
|
+
const m = x - u * q;
|
|
56
|
+
const n = y - v * q;
|
|
57
|
+
// prettier-ignore
|
|
58
|
+
b = a, a = r, x = u, y = v, u = m, v = n;
|
|
59
|
+
}
|
|
60
|
+
const gcd = b;
|
|
61
|
+
if (gcd !== _1n)
|
|
62
|
+
throw new Error('invert: does not exist');
|
|
63
|
+
return mod(x, modulo);
|
|
64
|
+
}
|
|
65
|
+
/**
|
|
66
|
+
* Takes a list of numbers, efficiently inverts all of them.
|
|
67
|
+
* @param nums list of bigints
|
|
68
|
+
* @param p modulo
|
|
69
|
+
* @returns list of inverted bigints
|
|
70
|
+
* @example
|
|
71
|
+
* invertBatch([1n, 2n, 4n], 21n);
|
|
72
|
+
* // => [1n, 11n, 16n]
|
|
73
|
+
*/
|
|
74
|
+
export function invertBatch(nums, modulo) {
|
|
75
|
+
const scratch = new Array(nums.length);
|
|
76
|
+
// Walk from first to last, multiply them by each other MOD p
|
|
77
|
+
const lastMultiplied = nums.reduce((acc, num, i) => {
|
|
78
|
+
if (num === _0n)
|
|
79
|
+
return acc;
|
|
80
|
+
scratch[i] = acc;
|
|
81
|
+
return mod(acc * num, modulo);
|
|
82
|
+
}, _1n);
|
|
83
|
+
// Invert last element
|
|
84
|
+
const inverted = invert(lastMultiplied, modulo);
|
|
85
|
+
// Walk from last to first, multiply them by inverted each other MOD p
|
|
86
|
+
nums.reduceRight((acc, num, i) => {
|
|
87
|
+
if (num === _0n)
|
|
88
|
+
return acc;
|
|
89
|
+
scratch[i] = mod(acc * scratch[i], modulo);
|
|
90
|
+
return mod(acc * num, modulo);
|
|
91
|
+
}, inverted);
|
|
92
|
+
return scratch;
|
|
93
|
+
}
|
|
94
|
+
// Calculates Legendre symbol: num^((P-1)/2)
|
|
95
|
+
export function legendre(num, fieldPrime) {
|
|
96
|
+
return pow(num, (fieldPrime - _1n) / _2n, fieldPrime);
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Calculates square root of a number in a finite field.
|
|
100
|
+
* Used to calculate y - the square root of y².
|
|
101
|
+
*/
|
|
102
|
+
export function sqrt(number, modulo) {
|
|
103
|
+
const n = number;
|
|
104
|
+
const P = modulo;
|
|
105
|
+
const p1div4 = (P + _1n) / _4n;
|
|
106
|
+
// P = 3 (mod 4)
|
|
107
|
+
// sqrt n = n^((P+1)/4)
|
|
108
|
+
if (P % _4n === _3n)
|
|
109
|
+
return pow(n, p1div4, P);
|
|
110
|
+
// P = 5 (mod 8)
|
|
111
|
+
if (P % _8n === _5n) {
|
|
112
|
+
const n2 = mod(n * _2n, P);
|
|
113
|
+
const v = pow(n2, (P - _5n) / _8n, P);
|
|
114
|
+
const nv = mod(n * v, P);
|
|
115
|
+
const i = mod(_2n * nv * v, P);
|
|
116
|
+
const r = mod(nv * (i - _1n), P);
|
|
117
|
+
return r;
|
|
118
|
+
}
|
|
119
|
+
// Other cases: Tonelli-Shanks algorithm
|
|
120
|
+
if (legendre(n, P) !== _1n)
|
|
121
|
+
throw new Error('Cannot find square root');
|
|
122
|
+
let q, s, z;
|
|
123
|
+
for (q = P - _1n, s = 0; q % _2n === _0n; q /= _2n, s++)
|
|
124
|
+
;
|
|
125
|
+
if (s === 1)
|
|
126
|
+
return pow(n, p1div4, P);
|
|
127
|
+
for (z = _2n; z < P && legendre(z, P) !== P - _1n; z++)
|
|
128
|
+
;
|
|
129
|
+
let c = pow(z, q, P);
|
|
130
|
+
let r = pow(n, (q + _1n) / _2n, P);
|
|
131
|
+
let t = pow(n, q, P);
|
|
132
|
+
let t2 = _0n;
|
|
133
|
+
while (mod(t - _1n, P) !== _0n) {
|
|
134
|
+
t2 = mod(t * t, P);
|
|
135
|
+
let i;
|
|
136
|
+
for (i = 1; i < s; i++) {
|
|
137
|
+
if (mod(t2 - _1n, P) === _0n)
|
|
138
|
+
break;
|
|
139
|
+
t2 = mod(t2 * t2, P);
|
|
140
|
+
}
|
|
141
|
+
let b = pow(c, BigInt(1 << (s - i - 1)), P);
|
|
142
|
+
r = mod(r * b, P);
|
|
143
|
+
c = mod(b * b, P);
|
|
144
|
+
t = mod(t * c, P);
|
|
145
|
+
s = i;
|
|
146
|
+
}
|
|
147
|
+
return r;
|
|
148
|
+
}
|