@noble/curves 1.8.1 → 1.8.2

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.
Files changed (174) hide show
  1. package/README.md +278 -418
  2. package/_shortw_utils.d.ts +2 -2
  3. package/_shortw_utils.js +2 -2
  4. package/abstract/bls.d.ts +5 -5
  5. package/abstract/bls.d.ts.map +1 -1
  6. package/abstract/bls.js +14 -15
  7. package/abstract/bls.js.map +1 -1
  8. package/abstract/curve.d.ts +10 -2
  9. package/abstract/curve.d.ts.map +1 -1
  10. package/abstract/curve.js +81 -78
  11. package/abstract/curve.js.map +1 -1
  12. package/abstract/edwards.d.ts +2 -2
  13. package/abstract/edwards.d.ts.map +1 -1
  14. package/abstract/edwards.js +55 -69
  15. package/abstract/edwards.js.map +1 -1
  16. package/abstract/hash-to-curve.d.ts +5 -4
  17. package/abstract/hash-to-curve.d.ts.map +1 -1
  18. package/abstract/hash-to-curve.js +20 -18
  19. package/abstract/hash-to-curve.js.map +1 -1
  20. package/abstract/modular.d.ts.map +1 -1
  21. package/abstract/modular.js +9 -9
  22. package/abstract/montgomery.js +12 -12
  23. package/abstract/poseidon.d.ts +1 -1
  24. package/abstract/poseidon.js +3 -3
  25. package/abstract/tower.d.ts +2 -2
  26. package/abstract/tower.js +13 -13
  27. package/abstract/utils.d.ts +4 -2
  28. package/abstract/utils.d.ts.map +1 -1
  29. package/abstract/utils.js +25 -14
  30. package/abstract/utils.js.map +1 -1
  31. package/abstract/weierstrass.d.ts +17 -4
  32. package/abstract/weierstrass.d.ts.map +1 -1
  33. package/abstract/weierstrass.js +97 -80
  34. package/abstract/weierstrass.js.map +1 -1
  35. package/bls12-381.d.ts +1 -1
  36. package/bls12-381.js +41 -41
  37. package/bls12-381.js.map +1 -1
  38. package/bn254.d.ts +2 -2
  39. package/bn254.js +29 -29
  40. package/bn254.js.map +1 -1
  41. package/ed25519.d.ts +8 -6
  42. package/ed25519.d.ts.map +1 -1
  43. package/ed25519.js +65 -66
  44. package/ed25519.js.map +1 -1
  45. package/ed448.d.ts +6 -6
  46. package/ed448.d.ts.map +1 -1
  47. package/ed448.js +50 -52
  48. package/ed448.js.map +1 -1
  49. package/esm/_shortw_utils.d.ts +2 -2
  50. package/esm/_shortw_utils.js +1 -1
  51. package/esm/abstract/bls.d.ts +5 -5
  52. package/esm/abstract/bls.d.ts.map +1 -1
  53. package/esm/abstract/bls.js +5 -6
  54. package/esm/abstract/bls.js.map +1 -1
  55. package/esm/abstract/curve.d.ts +10 -2
  56. package/esm/abstract/curve.d.ts.map +1 -1
  57. package/esm/abstract/curve.js +77 -74
  58. package/esm/abstract/curve.js.map +1 -1
  59. package/esm/abstract/edwards.d.ts +2 -2
  60. package/esm/abstract/edwards.d.ts.map +1 -1
  61. package/esm/abstract/edwards.js +36 -50
  62. package/esm/abstract/edwards.js.map +1 -1
  63. package/esm/abstract/hash-to-curve.d.ts +5 -4
  64. package/esm/abstract/hash-to-curve.d.ts.map +1 -1
  65. package/esm/abstract/hash-to-curve.js +4 -2
  66. package/esm/abstract/hash-to-curve.js.map +1 -1
  67. package/esm/abstract/modular.d.ts.map +1 -1
  68. package/esm/abstract/modular.js +1 -1
  69. package/esm/abstract/montgomery.js +2 -2
  70. package/esm/abstract/poseidon.d.ts +1 -1
  71. package/esm/abstract/poseidon.js +1 -1
  72. package/esm/abstract/tower.d.ts +2 -2
  73. package/esm/abstract/tower.js +5 -5
  74. package/esm/abstract/utils.d.ts +4 -2
  75. package/esm/abstract/utils.d.ts.map +1 -1
  76. package/esm/abstract/utils.js +24 -13
  77. package/esm/abstract/utils.js.map +1 -1
  78. package/esm/abstract/weierstrass.d.ts +17 -4
  79. package/esm/abstract/weierstrass.d.ts.map +1 -1
  80. package/esm/abstract/weierstrass.js +70 -53
  81. package/esm/abstract/weierstrass.js.map +1 -1
  82. package/esm/bls12-381.d.ts +1 -1
  83. package/esm/bls12-381.js +9 -9
  84. package/esm/bls12-381.js.map +1 -1
  85. package/esm/bn254.d.ts +2 -2
  86. package/esm/bn254.js +7 -7
  87. package/esm/bn254.js.map +1 -1
  88. package/esm/ed25519.d.ts +8 -6
  89. package/esm/ed25519.d.ts.map +1 -1
  90. package/esm/ed25519.js +20 -21
  91. package/esm/ed25519.js.map +1 -1
  92. package/esm/ed448.d.ts +6 -6
  93. package/esm/ed448.d.ts.map +1 -1
  94. package/esm/ed448.js +13 -15
  95. package/esm/ed448.js.map +1 -1
  96. package/esm/jubjub.d.ts +1 -4
  97. package/esm/jubjub.d.ts.map +1 -1
  98. package/esm/jubjub.js +1 -60
  99. package/esm/jubjub.js.map +1 -1
  100. package/esm/misc.d.ts +15 -0
  101. package/esm/misc.d.ts.map +1 -0
  102. package/esm/misc.js +101 -0
  103. package/esm/misc.js.map +1 -0
  104. package/esm/p256.d.ts +8 -5
  105. package/esm/p256.d.ts.map +1 -1
  106. package/esm/p256.js +13 -12
  107. package/esm/p256.js.map +1 -1
  108. package/esm/p384.d.ts +8 -5
  109. package/esm/p384.d.ts.map +1 -1
  110. package/esm/p384.js +14 -15
  111. package/esm/p384.js.map +1 -1
  112. package/esm/p521.d.ts +6 -5
  113. package/esm/p521.d.ts.map +1 -1
  114. package/esm/p521.js +19 -28
  115. package/esm/p521.js.map +1 -1
  116. package/esm/pasta.d.ts +1 -7
  117. package/esm/pasta.d.ts.map +1 -1
  118. package/esm/pasta.js +1 -33
  119. package/esm/pasta.js.map +1 -1
  120. package/esm/secp256k1.d.ts +15 -10
  121. package/esm/secp256k1.d.ts.map +1 -1
  122. package/esm/secp256k1.js +18 -14
  123. package/esm/secp256k1.js.map +1 -1
  124. package/jubjub.d.ts +1 -4
  125. package/jubjub.d.ts.map +1 -1
  126. package/jubjub.js +5 -63
  127. package/jubjub.js.map +1 -1
  128. package/misc.d.ts +15 -0
  129. package/misc.d.ts.map +1 -0
  130. package/misc.js +106 -0
  131. package/misc.js.map +1 -0
  132. package/p256.d.ts +8 -5
  133. package/p256.d.ts.map +1 -1
  134. package/p256.js +19 -18
  135. package/p256.js.map +1 -1
  136. package/p384.d.ts +8 -5
  137. package/p384.d.ts.map +1 -1
  138. package/p384.js +19 -20
  139. package/p384.js.map +1 -1
  140. package/p521.d.ts +6 -5
  141. package/p521.d.ts.map +1 -1
  142. package/p521.js +23 -32
  143. package/p521.js.map +1 -1
  144. package/package.json +14 -10
  145. package/pasta.d.ts +1 -7
  146. package/pasta.d.ts.map +1 -1
  147. package/pasta.js +4 -34
  148. package/pasta.js.map +1 -1
  149. package/secp256k1.d.ts +15 -10
  150. package/secp256k1.d.ts.map +1 -1
  151. package/secp256k1.js +57 -53
  152. package/secp256k1.js.map +1 -1
  153. package/src/_shortw_utils.ts +2 -2
  154. package/src/abstract/bls.ts +9 -9
  155. package/src/abstract/curve.ts +88 -79
  156. package/src/abstract/edwards.ts +47 -54
  157. package/src/abstract/hash-to-curve.ts +7 -5
  158. package/src/abstract/modular.ts +1 -1
  159. package/src/abstract/montgomery.ts +2 -2
  160. package/src/abstract/poseidon.ts +1 -1
  161. package/src/abstract/tower.ts +6 -6
  162. package/src/abstract/utils.ts +26 -15
  163. package/src/abstract/weierstrass.ts +89 -75
  164. package/src/bls12-381.ts +10 -10
  165. package/src/bn254.ts +8 -8
  166. package/src/ed25519.ts +24 -22
  167. package/src/ed448.ts +18 -17
  168. package/src/jubjub.ts +5 -63
  169. package/src/misc.ts +117 -0
  170. package/src/p256.ts +13 -12
  171. package/src/p384.ts +18 -15
  172. package/src/p521.ts +27 -32
  173. package/src/pasta.ts +1 -39
  174. package/src/secp256k1.ts +19 -15
@@ -1,6 +1,19 @@
1
1
  /**
2
2
  * Short Weierstrass curve methods. The formula is: y² = x³ + ax + b.
3
3
  *
4
+ * ### Parameters
5
+ *
6
+ * To initialize a weierstrass curve, one needs to pass following params:
7
+ *
8
+ * * a: formula param
9
+ * * b: formula param
10
+ * * Fp: finite Field over which we'll do calculations. Can be complex (Fp2, Fp12)
11
+ * * n: Curve prime subgroup order, total count of valid points in the field
12
+ * * Gx: Base point (x, y) aka generator point x coordinate
13
+ * * Gy: ...y coordinate
14
+ * * h: cofactor, usually 1. h*n = curve group order (n is only subgroup order)
15
+ * * lowS: whether to enable (default) or disable "low-s" non-malleable signatures
16
+ *
4
17
  * ### Design rationale for types
5
18
  *
6
19
  * * Interaction between classes from different curves should fail:
@@ -25,26 +38,23 @@
25
38
  * @module
26
39
  */
27
40
  /*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
41
+ // prettier-ignore
28
42
  import {
29
- type AffinePoint,
30
- type BasicCurve,
31
- type Group,
32
- type GroupConstructor,
33
- pippenger,
34
- validateBasic,
35
- wNAF,
36
- } from './curve.js';
43
+ type AffinePoint, type BasicCurve, type Group, type GroupConstructor,
44
+ pippenger, validateBasic, wNAF,
45
+ } from './curve.ts';
46
+ // prettier-ignore
47
+ import {
48
+ Field, type IField, getMinHashLength, invert, mapHashToField, mod, validateField,
49
+ } from './modular.ts';
50
+ // prettier-ignore
37
51
  import {
38
- Field,
39
- type IField,
40
- getMinHashLength,
41
- invert,
42
- mapHashToField,
43
- mod,
44
- validateField,
45
- } from './modular.js';
46
- import * as ut from './utils.js';
47
- import { type CHash, type Hex, type PrivKey, abool, ensureBytes, memoized } from './utils.js';
52
+ type CHash, type Hex, type PrivKey,
53
+ aInRange, abool,
54
+ bitMask,
55
+ bytesToHex, bytesToNumberBE, concatBytes, createHmacDrbg, ensureBytes, hexToBytes,
56
+ inRange, isBytes, memoized, numberToBytesBE, numberToHexUnpadded, validateObject
57
+ } from './utils.ts';
48
58
 
49
59
  export type { AffinePoint };
50
60
  type HmacFnSync = (key: Uint8Array, ...messages: Uint8Array[]) => Uint8Array;
@@ -68,7 +78,7 @@ export type BasicWCurve<T> = BasicCurve<T> & {
68
78
  clearCofactor?: (c: ProjConstructor<T>, point: ProjPointType<T>) => ProjPointType<T>;
69
79
  };
70
80
 
71
- type Entropy = Hex | boolean;
81
+ export type Entropy = Hex | boolean;
72
82
  export type SignOpts = { lowS?: boolean; extraEntropy?: Entropy; prehash?: boolean };
73
83
  export type VerOpts = { lowS?: boolean; prehash?: boolean; format?: 'compact' | 'der' | undefined };
74
84
 
@@ -119,7 +129,7 @@ export type CurvePointsTypeWithLength<T> = Readonly<
119
129
 
120
130
  function validatePointOpts<T>(curve: CurvePointsType<T>): CurvePointsTypeWithLength<T> {
121
131
  const opts = validateBasic(curve);
122
- ut.validateObject(
132
+ validateObject(
123
133
  opts,
124
134
  {
125
135
  a: 'field',
@@ -159,8 +169,6 @@ export type CurvePointsRes<T> = {
159
169
  isWithinCurveOrder: (num: bigint) => boolean;
160
170
  };
161
171
 
162
- const { bytesToNumberBE: b2n, hexToBytes: h2b } = ut;
163
-
164
172
  export class DERErr extends Error {
165
173
  constructor(m = '') {
166
174
  super(m);
@@ -203,11 +211,11 @@ export const DER: IDER = {
203
211
  if (tag < 0 || tag > 256) throw new E('tlv.encode: wrong tag');
204
212
  if (data.length & 1) throw new E('tlv.encode: unpadded data');
205
213
  const dataLen = data.length / 2;
206
- const len = ut.numberToHexUnpadded(dataLen);
214
+ const len = numberToHexUnpadded(dataLen);
207
215
  if ((len.length / 2) & 0b1000_0000) throw new E('tlv.encode: long form length too big');
208
216
  // length of length with long form flag
209
- const lenLen = dataLen > 127 ? ut.numberToHexUnpadded((len.length / 2) | 0b1000_0000) : '';
210
- const t = ut.numberToHexUnpadded(tag);
217
+ const lenLen = dataLen > 127 ? numberToHexUnpadded((len.length / 2) | 0b1000_0000) : '';
218
+ const t = numberToHexUnpadded(tag);
211
219
  return t + lenLen + len + data;
212
220
  },
213
221
  // v - value, l - left bytes (unparsed)
@@ -245,7 +253,7 @@ export const DER: IDER = {
245
253
  encode(num: bigint): string {
246
254
  const { Err: E } = DER;
247
255
  if (num < _0n) throw new E('integer: negative integers are not allowed');
248
- let hex = ut.numberToHexUnpadded(num);
256
+ let hex = numberToHexUnpadded(num);
249
257
  // Pad with zero byte if negative flag is present
250
258
  if (Number.parseInt(hex[0], 16) & 0b1000) hex = '00' + hex;
251
259
  if (hex.length & 1) throw new E('unexpected DER parsing assertion: unpadded hex');
@@ -256,14 +264,13 @@ export const DER: IDER = {
256
264
  if (data[0] & 0b1000_0000) throw new E('invalid signature integer: negative');
257
265
  if (data[0] === 0x00 && !(data[1] & 0b1000_0000))
258
266
  throw new E('invalid signature integer: unnecessary leading zero');
259
- return b2n(data);
267
+ return bytesToNumberBE(data);
260
268
  },
261
269
  },
262
270
  toSig(hex: string | Uint8Array): { r: bigint; s: bigint } {
263
271
  // parse DER signature
264
272
  const { Err: E, _int: int, _tlv: tlv } = DER;
265
- const data = typeof hex === 'string' ? h2b(hex) : hex;
266
- ut.abytes(data);
273
+ const data = ensureBytes('signature', hex);
267
274
  const { v: seqBytes, l: seqLeftBytes } = tlv.decode(0x30, data);
268
275
  if (seqLeftBytes.length) throw new E('invalid signature: left bytes after parsing');
269
276
  const { v: rBytes, l: rLeftBytes } = tlv.decode(0x02, seqBytes);
@@ -293,7 +300,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
293
300
  CURVE.toBytes ||
294
301
  ((_c: ProjConstructor<T>, point: ProjPointType<T>, _isCompressed: boolean) => {
295
302
  const a = point.toAffine();
296
- return ut.concatBytes(Uint8Array.from([0x04]), Fp.toBytes(a.x), Fp.toBytes(a.y));
303
+ return concatBytes(Uint8Array.from([0x04]), Fp.toBytes(a.x), Fp.toBytes(a.y));
297
304
  });
298
305
  const fromBytes =
299
306
  CURVE.fromBytes ||
@@ -307,7 +314,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
307
314
  });
308
315
 
309
316
  /**
310
- * y² = x³ + ax + b: Short weierstrass curve formula
317
+ * y² = x³ + ax + b: Short weierstrass curve formula. Takes x, returns y².
311
318
  * @returns y²
312
319
  */
313
320
  function weierstrassEquation(x: T): T {
@@ -325,14 +332,14 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
325
332
 
326
333
  // Valid group elements reside in range 1..n-1
327
334
  function isWithinCurveOrder(num: bigint): boolean {
328
- return ut.inRange(num, _1n, CURVE.n);
335
+ return inRange(num, _1n, CURVE.n);
329
336
  }
330
337
  // Validates if priv key is valid and converts it to bigint.
331
338
  // Supports options allowedPrivateKeyLengths and wrapPrivateKey.
332
339
  function normPrivateKeyToScalar(key: PrivKey): bigint {
333
340
  const { allowedPrivateKeyLengths: lengths, nByteLength, wrapPrivateKey, n: N } = CURVE;
334
341
  if (lengths && typeof key !== 'bigint') {
335
- if (ut.isBytes(key)) key = ut.bytesToHex(key);
342
+ if (isBytes(key)) key = bytesToHex(key);
336
343
  // Normalize to hex string, pad. E.g. P521 would norm 130-132 char hex to 132-char bytes
337
344
  if (typeof key !== 'string' || !lengths.includes(key.length))
338
345
  throw new Error('invalid private key');
@@ -343,18 +350,18 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
343
350
  num =
344
351
  typeof key === 'bigint'
345
352
  ? key
346
- : ut.bytesToNumberBE(ensureBytes('private key', key, nByteLength));
353
+ : bytesToNumberBE(ensureBytes('private key', key, nByteLength));
347
354
  } catch (error) {
348
355
  throw new Error(
349
356
  'invalid private key, expected hex or ' + nByteLength + ' bytes, got ' + typeof key
350
357
  );
351
358
  }
352
359
  if (wrapPrivateKey) num = mod(num, N); // disabled by default, enabled for BLS
353
- ut.aInRange('private key', num, _1n, N); // num in range [1..N-1]
360
+ aInRange('private key', num, _1n, N); // num in range [1..N-1]
354
361
  return num;
355
362
  }
356
363
 
357
- function assertPrjPoint(other: unknown) {
364
+ function aprjpoint(other: unknown) {
358
365
  if (!(other instanceof Point)) throw new Error('ProjectivePoint expected');
359
366
  }
360
367
 
@@ -407,15 +414,17 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
407
414
  class Point implements ProjPointType<T> {
408
415
  static readonly BASE = new Point(CURVE.Gx, CURVE.Gy, Fp.ONE);
409
416
  static readonly ZERO = new Point(Fp.ZERO, Fp.ONE, Fp.ZERO);
417
+ readonly px: T;
418
+ readonly py: T;
419
+ readonly pz: T;
410
420
 
411
- constructor(
412
- readonly px: T,
413
- readonly py: T,
414
- readonly pz: T
415
- ) {
421
+ constructor(px: T, py: T, pz: T) {
416
422
  if (px == null || !Fp.isValid(px)) throw new Error('x required');
417
423
  if (py == null || !Fp.isValid(py)) throw new Error('y required');
418
424
  if (pz == null || !Fp.isValid(pz)) throw new Error('z required');
425
+ this.px = px;
426
+ this.py = py;
427
+ this.pz = pz;
419
428
  Object.freeze(this);
420
429
  }
421
430
 
@@ -489,7 +498,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
489
498
  * Compare one point to another.
490
499
  */
491
500
  equals(other: Point): boolean {
492
- assertPrjPoint(other);
501
+ aprjpoint(other);
493
502
  const { px: X1, py: Y1, pz: Z1 } = this;
494
503
  const { px: X2, py: Y2, pz: Z2 } = other;
495
504
  const U1 = Fp.eql(Fp.mul(X1, Z2), Fp.mul(X2, Z1));
@@ -552,7 +561,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
552
561
  // https://eprint.iacr.org/2015/1060, algorithm 1
553
562
  // Cost: 12M + 0S + 3*a + 3*b3 + 23add.
554
563
  add(other: Point): Point {
555
- assertPrjPoint(other);
564
+ aprjpoint(other);
556
565
  const { px: X1, py: Y1, pz: Z1 } = this;
557
566
  const { px: X2, py: Y2, pz: Z2 } = other;
558
567
  let X3 = Fp.ZERO, Y3 = Fp.ZERO, Z3 = Fp.ZERO; // prettier-ignore
@@ -619,7 +628,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
619
628
  */
620
629
  multiplyUnsafe(sc: bigint): Point {
621
630
  const { endo, n: N } = CURVE;
622
- ut.aInRange('scalar', sc, _0n, N);
631
+ aInRange('scalar', sc, _0n, N);
623
632
  const I = Point.ZERO;
624
633
  if (sc === _0n) return I;
625
634
  if (this.is0() || sc === _1n) return this;
@@ -657,7 +666,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
657
666
  */
658
667
  multiply(scalar: bigint): Point {
659
668
  const { endo, n: N } = CURVE;
660
- ut.aInRange('scalar', scalar, _1n, N);
669
+ aInRange('scalar', scalar, _1n, N);
661
670
  let point: Point, fake: Point; // Fake point is used to const-time mult
662
671
  if (endo) {
663
672
  const { k1neg, k1, k2neg, k2 } = endo.splitScalar(scalar);
@@ -720,7 +729,7 @@ export function weierstrassPoints<T>(opts: CurvePointsType<T>): CurvePointsRes<T
720
729
 
721
730
  toHex(isCompressed = true): string {
722
731
  abool('isCompressed', isCompressed);
723
- return ut.bytesToHex(this.toRawBytes(isCompressed));
732
+ return bytesToHex(this.toRawBytes(isCompressed));
724
733
  }
725
734
  }
726
735
  const _bits = CURVE.nBitLength;
@@ -777,7 +786,7 @@ function validateOpts(
777
786
  curve: CurveType
778
787
  ): Readonly<CurveType & { nByteLength: number; nBitLength: number }> {
779
788
  const opts = validateBasic(curve);
780
- ut.validateObject(
789
+ validateObject(
781
790
  opts,
782
791
  {
783
792
  hash: 'hash',
@@ -839,7 +848,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
839
848
  toBytes(_c, point, isCompressed: boolean): Uint8Array {
840
849
  const a = point.toAffine();
841
850
  const x = Fp.toBytes(a.x);
842
- const cat = ut.concatBytes;
851
+ const cat = concatBytes;
843
852
  abool('isCompressed', isCompressed);
844
853
  if (isCompressed) {
845
854
  return cat(Uint8Array.from([point.hasEvenY() ? 0x02 : 0x03]), x);
@@ -853,8 +862,8 @@ export function weierstrass(curveDef: CurveType): CurveFn {
853
862
  const tail = bytes.subarray(1);
854
863
  // this.assertValidity() is done inside of fromHex
855
864
  if (len === compressedLen && (head === 0x02 || head === 0x03)) {
856
- const x = ut.bytesToNumberBE(tail);
857
- if (!ut.inRange(x, _1n, Fp.ORDER)) throw new Error('Point is not on curve');
865
+ const x = bytesToNumberBE(tail);
866
+ if (!inRange(x, _1n, Fp.ORDER)) throw new Error('Point is not on curve');
858
867
  const y2 = weierstrassEquation(x); // y² = x³ + ax + b
859
868
  let y: bigint;
860
869
  try {
@@ -881,8 +890,8 @@ export function weierstrass(curveDef: CurveType): CurveFn {
881
890
  }
882
891
  },
883
892
  });
884
- const numToNByteStr = (num: bigint): string =>
885
- ut.bytesToHex(ut.numberToBytesBE(num, CURVE.nByteLength));
893
+ const numToNByteHex = (num: bigint): string =>
894
+ bytesToHex(numberToBytesBE(num, CURVE.nByteLength));
886
895
 
887
896
  function isBiggerThanHalfOrder(number: bigint) {
888
897
  const HALF = CURVE_ORDER >> _1n;
@@ -893,18 +902,22 @@ export function weierstrass(curveDef: CurveType): CurveFn {
893
902
  return isBiggerThanHalfOrder(s) ? modN(-s) : s;
894
903
  }
895
904
  // slice bytes num
896
- const slcNum = (b: Uint8Array, from: number, to: number) => ut.bytesToNumberBE(b.slice(from, to));
905
+ const slcNum = (b: Uint8Array, from: number, to: number) => bytesToNumberBE(b.slice(from, to));
897
906
 
898
907
  /**
899
908
  * ECDSA signature with its (r, s) properties. Supports DER & compact representations.
900
909
  */
901
910
  class Signature implements SignatureType {
902
- constructor(
903
- readonly r: bigint,
904
- readonly s: bigint,
905
- readonly recovery?: number
906
- ) {
907
- this.assertValidity();
911
+ readonly r: bigint;
912
+ readonly s: bigint;
913
+ readonly recovery?: number;
914
+ constructor(r: bigint, s: bigint, recovery?: number) {
915
+ aInRange('r', r, _1n, CURVE_ORDER); // r in [1..N]
916
+ aInRange('s', s, _1n, CURVE_ORDER); // s in [1..N]
917
+ this.r = r;
918
+ this.s = s;
919
+ if (recovery != null) this.recovery = recovery;
920
+ Object.freeze(this);
908
921
  }
909
922
 
910
923
  // pair (bytes of r, bytes of s)
@@ -921,10 +934,11 @@ export function weierstrass(curveDef: CurveType): CurveFn {
921
934
  return new Signature(r, s);
922
935
  }
923
936
 
924
- assertValidity(): void {
925
- ut.aInRange('r', this.r, _1n, CURVE_ORDER); // r in [1..N]
926
- ut.aInRange('s', this.s, _1n, CURVE_ORDER); // s in [1..N]
927
- }
937
+ /**
938
+ * @todo remove
939
+ * @deprecated
940
+ */
941
+ assertValidity(): void {}
928
942
 
929
943
  addRecoveryBit(recovery: number): RecoveredSignature {
930
944
  return new Signature(this.r, this.s, recovery) as RecoveredSignature;
@@ -937,7 +951,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
937
951
  const radj = rec === 2 || rec === 3 ? r + CURVE.n : r;
938
952
  if (radj >= Fp.ORDER) throw new Error('recovery id 2 or 3 invalid');
939
953
  const prefix = (rec & 1) === 0 ? '02' : '03';
940
- const R = Point.fromHex(prefix + numToNByteStr(radj));
954
+ const R = Point.fromHex(prefix + numToNByteHex(radj));
941
955
  const ir = invN(radj); // r^-1
942
956
  const u1 = modN(-h * ir); // -hr^-1
943
957
  const u2 = modN(s * ir); // sr^-1
@@ -958,7 +972,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
958
972
 
959
973
  // DER-encoded
960
974
  toDERRawBytes() {
961
- return ut.hexToBytes(this.toDERHex());
975
+ return hexToBytes(this.toDERHex());
962
976
  }
963
977
  toDERHex() {
964
978
  return DER.hexFromSig({ r: this.r, s: this.s });
@@ -966,10 +980,10 @@ export function weierstrass(curveDef: CurveType): CurveFn {
966
980
 
967
981
  // padded bytes of r, then padded bytes of s
968
982
  toCompactRawBytes() {
969
- return ut.hexToBytes(this.toCompactHex());
983
+ return hexToBytes(this.toCompactHex());
970
984
  }
971
985
  toCompactHex() {
972
- return numToNByteStr(this.r) + numToNByteStr(this.s);
986
+ return numToNByteHex(this.r) + numToNByteHex(this.s);
973
987
  }
974
988
  }
975
989
  type RecoveredSignature = Signature & { recovery: number };
@@ -1023,7 +1037,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1023
1037
  * Quick and dirty check for item being public key. Does not validate hex, or being on-curve.
1024
1038
  */
1025
1039
  function isProbPub(item: PrivKey | PubKey): boolean {
1026
- const arr = ut.isBytes(item);
1040
+ const arr = isBytes(item);
1027
1041
  const str = typeof item === 'string';
1028
1042
  const len = (arr || str) && (item as Hex).length;
1029
1043
  if (arr) return len === compressedLen || len === uncompressedLen;
@@ -1060,7 +1074,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1060
1074
  if (bytes.length > 8192) throw new Error('input is too large');
1061
1075
  // For curves with nBitLength % 8 !== 0: bits2octets(bits2octets(m)) !== bits2octets(m)
1062
1076
  // for some cases, since bytes.length * 8 is not actual bitLength.
1063
- const num = ut.bytesToNumberBE(bytes); // check for == u8 done here
1077
+ const num = bytesToNumberBE(bytes); // check for == u8 done here
1064
1078
  const delta = bytes.length * 8 - CURVE.nBitLength; // truncate to nBitLength leftmost bits
1065
1079
  return delta > 0 ? num >> BigInt(delta) : num;
1066
1080
  };
@@ -1070,14 +1084,14 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1070
1084
  return modN(bits2int(bytes)); // can't use bytesToNumberBE here
1071
1085
  };
1072
1086
  // NOTE: pads output with zero as per spec
1073
- const ORDER_MASK = ut.bitMask(CURVE.nBitLength);
1087
+ const ORDER_MASK = bitMask(CURVE.nBitLength);
1074
1088
  /**
1075
1089
  * Converts to bytes. Checks if num in `[0..ORDER_MASK-1]` e.g.: `[0..2^256-1]`.
1076
1090
  */
1077
1091
  function int2octets(num: bigint): Uint8Array {
1078
- ut.aInRange('num < 2^' + CURVE.nBitLength, num, _0n, ORDER_MASK);
1092
+ aInRange('num < 2^' + CURVE.nBitLength, num, _0n, ORDER_MASK);
1079
1093
  // works with order, can have different size than numToField!
1080
- return ut.numberToBytesBE(num, CURVE.nByteLength);
1094
+ return numberToBytesBE(num, CURVE.nByteLength);
1081
1095
  }
1082
1096
 
1083
1097
  // Steps A, D of RFC6979 3.2
@@ -1107,7 +1121,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1107
1121
  const e = ent === true ? randomBytes(Fp.BYTES) : ent; // generate random bytes OR pass as-is
1108
1122
  seedArgs.push(ensureBytes('extraEntropy', e)); // check for being bytes
1109
1123
  }
1110
- const seed = ut.concatBytes(...seedArgs); // Step D of RFC6979 3.2
1124
+ const seed = concatBytes(...seedArgs); // Step D of RFC6979 3.2
1111
1125
  const m = h1int; // NOTE: no need to call bits2int second time here, it is inside truncateHash!
1112
1126
  // Converts signature params into point w r/s, checks result for validity.
1113
1127
  function k2sig(kBytes: Uint8Array): RecoveredSignature | undefined {
@@ -1152,7 +1166,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1152
1166
  function sign(msgHash: Hex, privKey: PrivKey, opts = defaultSigOpts): RecoveredSignature {
1153
1167
  const { seed, k2sig } = prepSig(msgHash, privKey, opts); // Steps A, D of RFC6979 3.2.
1154
1168
  const C = CURVE;
1155
- const drbg = ut.createHmacDrbg<RecoveredSignature>(C.hash.outputLen, C.nByteLength, C.hmac);
1169
+ const drbg = createHmacDrbg<RecoveredSignature>(C.hash.outputLen, C.nByteLength, C.hmac);
1156
1170
  return drbg(seed, k2sig); // Steps B, C, D, E, F, G
1157
1171
  }
1158
1172
 
@@ -1189,7 +1203,7 @@ export function weierstrass(curveDef: CurveType): CurveFn {
1189
1203
  if ('strict' in opts) throw new Error('options.strict was renamed to lowS');
1190
1204
  if (format !== undefined && format !== 'compact' && format !== 'der')
1191
1205
  throw new Error('format must be compact or der');
1192
- const isHex = typeof sg === 'string' || ut.isBytes(sg);
1206
+ const isHex = typeof sg === 'string' || isBytes(sg);
1193
1207
  const isObj =
1194
1208
  !isHex &&
1195
1209
  !format &&
package/src/bls12-381.ts CHANGED
@@ -29,7 +29,7 @@
29
29
  * 4. Compatible with specs:
30
30
  * [cfrg-pairing-friendly-curves-11](https://tools.ietf.org/html/draft-irtf-cfrg-pairing-friendly-curves-11),
31
31
  * [cfrg-bls-signature-05](https://datatracker.ietf.org/doc/html/draft-irtf-cfrg-bls-signature-05),
32
- * [RFC 9380](https://www.rfc-editor.org/rfc/rfc9380).
32
+ * RFC 9380.
33
33
  *
34
34
  * ### Params
35
35
  * To verify curve parameters, see
@@ -59,10 +59,10 @@
59
59
  * @module
60
60
  */
61
61
  /*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
62
- import { sha256 } from '@noble/hashes/sha256';
62
+ import { sha256 } from '@noble/hashes/sha2';
63
63
  import { randomBytes } from '@noble/hashes/utils';
64
- import { bls, type CurveFn } from './abstract/bls.js';
65
- import * as mod from './abstract/modular.js';
64
+ import { bls, type CurveFn } from './abstract/bls.ts';
65
+ import { Field } from './abstract/modular.ts';
66
66
  import {
67
67
  bitGet,
68
68
  bitLen,
@@ -72,16 +72,16 @@ import {
72
72
  ensureBytes,
73
73
  type Hex,
74
74
  numberToBytesBE,
75
- } from './abstract/utils.js';
75
+ } from './abstract/utils.ts';
76
76
  // Types
77
- import { isogenyMap } from './abstract/hash-to-curve.js';
78
- import type { Fp, Fp12, Fp2, Fp6 } from './abstract/tower.js';
79
- import { psiFrobenius, tower12 } from './abstract/tower.js';
77
+ import { isogenyMap } from './abstract/hash-to-curve.ts';
78
+ import type { Fp, Fp12, Fp2, Fp6 } from './abstract/tower.ts';
79
+ import { psiFrobenius, tower12 } from './abstract/tower.ts';
80
80
  import {
81
81
  type AffinePoint,
82
82
  mapToCurveSimpleSWU,
83
83
  type ProjPointType,
84
- } from './abstract/weierstrass.js';
84
+ } from './abstract/weierstrass.ts';
85
85
 
86
86
  // Be friendly to bad ECMAScript parsers by not using bigint literals
87
87
  // prettier-ignore
@@ -164,7 +164,7 @@ const { Fp, Fp2, Fp6, Fp4Square, Fp12 } = tower12({
164
164
 
165
165
  // Finite field over r.
166
166
  // This particular field is not used anywhere in bls12-381, but it is still useful.
167
- const Fr = mod.Field(BigInt('0x73eda753299d7d483339d80809a1d80553bda402fffe5bfeffffffff00000001'));
167
+ const Fr = Field(BigInt('0x73eda753299d7d483339d80809a1d80553bda402fffe5bfeffffffff00000001'));
168
168
 
169
169
  // END OF CURVE FIELDS
170
170
 
package/src/bn254.ts CHANGED
@@ -45,20 +45,20 @@ Ate loop size: 6x+2
45
45
  * @module
46
46
  */
47
47
  /*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
48
- import { sha256 } from '@noble/hashes/sha256';
48
+ import { sha256 } from '@noble/hashes/sha2';
49
49
  import { randomBytes } from '@noble/hashes/utils';
50
- import { getHash } from './_shortw_utils.js';
50
+ import { getHash } from './_shortw_utils.ts';
51
51
  import {
52
52
  bls,
53
53
  type CurveFn as BLSCurveFn,
54
54
  type PostPrecomputeFn,
55
55
  type PostPrecomputePointAddFn,
56
- } from './abstract/bls.js';
57
- import { Field } from './abstract/modular.js';
58
- import type { Fp, Fp12, Fp2, Fp6 } from './abstract/tower.js';
59
- import { psiFrobenius, tower12 } from './abstract/tower.js';
60
- import { bitGet, bitLen, notImplemented } from './abstract/utils.js';
61
- import { type CurveFn, weierstrass } from './abstract/weierstrass.js';
56
+ } from './abstract/bls.ts';
57
+ import { Field } from './abstract/modular.ts';
58
+ import type { Fp, Fp12, Fp2, Fp6 } from './abstract/tower.ts';
59
+ import { psiFrobenius, tower12 } from './abstract/tower.ts';
60
+ import { bitGet, bitLen, notImplemented } from './abstract/utils.ts';
61
+ import { type CurveFn, weierstrass } from './abstract/weierstrass.ts';
62
62
  // prettier-ignore
63
63
  const _1n = BigInt(1), _2n = BigInt(2), _3n = BigInt(3);
64
64
  const _6n = BigInt(6);
package/src/ed25519.ts CHANGED
@@ -6,18 +6,18 @@
6
6
  * @module
7
7
  */
8
8
  /*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
9
- import { sha512 } from '@noble/hashes/sha512';
9
+ import { sha512 } from '@noble/hashes/sha2';
10
10
  import { concatBytes, randomBytes, utf8ToBytes } from '@noble/hashes/utils';
11
- import { type AffinePoint, type Group, pippenger } from './abstract/curve.js';
12
- import { type CurveFn, type ExtPointType, twistedEdwards } from './abstract/edwards.js';
11
+ import { type AffinePoint, type Group, pippenger } from './abstract/curve.ts';
12
+ import { type CurveFn, type ExtPointType, twistedEdwards } from './abstract/edwards.ts';
13
13
  import {
14
14
  createHasher,
15
15
  expand_message_xmd,
16
16
  type htfBasicOpts,
17
17
  type HTFMethod,
18
- } from './abstract/hash-to-curve.js';
19
- import { Field, FpSqrtEven, isNegativeLE, mod, pow2 } from './abstract/modular.js';
20
- import { montgomery, type CurveFn as XCurveFn } from './abstract/montgomery.js';
18
+ } from './abstract/hash-to-curve.ts';
19
+ import { Field, FpSqrtEven, isNegativeLE, mod, pow2 } from './abstract/modular.ts';
20
+ import { montgomery, type CurveFn as XCurveFn } from './abstract/montgomery.ts';
21
21
  import {
22
22
  bytesToHex,
23
23
  bytesToNumberLE,
@@ -25,12 +25,14 @@ import {
25
25
  equalBytes,
26
26
  type Hex,
27
27
  numberToBytesLE,
28
- } from './abstract/utils.js';
28
+ } from './abstract/utils.ts';
29
29
 
30
+ // 2n**255n - 19n
30
31
  const ED25519_P = BigInt(
31
32
  '57896044618658097711785492504343953926634992332820282019728792003956564819949'
32
33
  );
33
34
  // √(-1) aka √(a) aka 2^((p-1)/4)
35
+ // Fp.sqrt(Fp.neg(1))
34
36
  const ED25519_SQRT_M1 = /* @__PURE__ */ BigInt(
35
37
  '19681161376707505956807079304988542015446066515923890162744021073123829784752'
36
38
  );
@@ -91,7 +93,7 @@ function uvRatio(u: bigint, v: bigint): { isValid: boolean; value: bigint } {
91
93
  return { isValid: useRoot1 || useRoot2, value: x };
92
94
  }
93
95
 
94
- // Just in case
96
+ /** Weird / bogus points, useful for debugging. */
95
97
  export const ED25519_TORSION_SUBGROUP: string[] = [
96
98
  '0100000000000000000000000000000000000000000000000000000000000000',
97
99
  'c7176a703d4dd84fba3c0b760d10670f2a2053fa2c39ccc64ec7fd7792ac037a',
@@ -107,19 +109,15 @@ const Fp = /* @__PURE__ */ (() => Field(ED25519_P, undefined, true))();
107
109
 
108
110
  const ed25519Defaults = /* @__PURE__ */ (() =>
109
111
  ({
110
- // Param: a
111
- a: BigInt(-1), // Fp.create(-1) is proper; our way still works and is faster
112
- // d is equal to -121665/121666 over finite field.
113
- // Negative number is P - number, and division is invert(number, P)
112
+ // Removing Fp.create() will still work, and is 10% faster on sign
113
+ a: Fp.create(BigInt(-1)),
114
+ // d is -121665/121666 a.k.a. Fp.neg(121665 * Fp.inv(121666))
114
115
  d: BigInt('37095705934669439343138083508754565189542113879843219016388785533085940283555'),
115
- // Finite field 𝔽p over which we'll do calculations; 2n**255n - 19n
116
+ // Finite field 2n**255n - 19n
116
117
  Fp,
117
- // Subgroup order: how many points curve has
118
- // 2n**252n + 27742317777372353535851937790883648493n;
118
+ // Subgroup order 2n**252n + 27742317777372353535851937790883648493n;
119
119
  n: BigInt('7237005577332262213973186563042994240857116359379907606001950938285454250989'),
120
- // Cofactor
121
120
  h: _8n,
122
- // Base point (x, y) aka generator point
123
121
  Gx: BigInt('15112221349535400772501151409588531511454012693041857206046113283949847762202'),
124
122
  Gy: BigInt('46316835694926478169428394003475163141307993866256225615783033603165251855960'),
125
123
  hash: sha512,
@@ -313,7 +311,7 @@ const htf = /* @__PURE__ */ (() =>
313
311
  export const hashToCurve: HTFMethod<bigint> = /* @__PURE__ */ (() => htf.hashToCurve)();
314
312
  export const encodeToCurve: HTFMethod<bigint> = /* @__PURE__ */ (() => htf.encodeToCurve)();
315
313
 
316
- function assertRstPoint(other: unknown) {
314
+ function aristp(other: unknown) {
317
315
  if (!(other instanceof RistPoint)) throw new Error('RistrettoPoint expected');
318
316
  }
319
317
 
@@ -380,9 +378,12 @@ function calcElligatorRistrettoMap(r0: bigint): ExtendedPoint {
380
378
  class RistPoint implements Group<RistPoint> {
381
379
  static BASE: RistPoint;
382
380
  static ZERO: RistPoint;
381
+ private readonly ep: ExtendedPoint;
383
382
  // Private property to discourage combining ExtendedPoint + RistrettoPoint
384
383
  // Always use Ristretto encoding/decoding instead.
385
- constructor(private readonly ep: ExtendedPoint) {}
384
+ constructor(ep: ExtendedPoint) {
385
+ this.ep = ep;
386
+ }
386
387
 
387
388
  static fromAffine(ap: AffinePoint<bigint>): RistPoint {
388
389
  return new RistPoint(ed25519.ExtendedPoint.fromAffine(ap));
@@ -483,7 +484,7 @@ class RistPoint implements Group<RistPoint> {
483
484
 
484
485
  // Compare one point to another.
485
486
  equals(other: RistPoint): boolean {
486
- assertRstPoint(other);
487
+ aristp(other);
487
488
  const { ex: X1, ey: Y1 } = this.ep;
488
489
  const { ex: X2, ey: Y2 } = other.ep;
489
490
  const mod = ed25519.CURVE.Fp.create;
@@ -494,12 +495,12 @@ class RistPoint implements Group<RistPoint> {
494
495
  }
495
496
 
496
497
  add(other: RistPoint): RistPoint {
497
- assertRstPoint(other);
498
+ aristp(other);
498
499
  return new RistPoint(this.ep.add(other.ep));
499
500
  }
500
501
 
501
502
  subtract(other: RistPoint): RistPoint {
502
- assertRstPoint(other);
503
+ aristp(other);
503
504
  return new RistPoint(this.ep.subtract(other.ep));
504
505
  }
505
506
 
@@ -533,5 +534,6 @@ export const hashToRistretto255 = (msg: Uint8Array, options: htfBasicOpts): Rist
533
534
  const P = RistPoint.hashToCurve(uniform_bytes);
534
535
  return P;
535
536
  };
537
+ /** @deprecated */
536
538
  export const hash_to_ristretto255: (msg: Uint8Array, options: htfBasicOpts) => RistPoint =
537
539
  hashToRistretto255; // legacy