@noble/curves 0.5.1 → 0.6.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.
Files changed (60) hide show
  1. package/README.md +49 -8
  2. package/lib/_shortw_utils.d.ts +11 -26
  3. package/lib/abstract/bls.d.ts +51 -35
  4. package/lib/abstract/bls.js +77 -139
  5. package/lib/abstract/{group.d.ts → curve.d.ts} +31 -1
  6. package/lib/abstract/{group.js → curve.js} +39 -2
  7. package/lib/abstract/edwards.d.ts +30 -81
  8. package/lib/abstract/edwards.js +225 -420
  9. package/lib/abstract/hash-to-curve.d.ts +25 -6
  10. package/lib/abstract/hash-to-curve.js +40 -12
  11. package/lib/abstract/modular.d.ts +20 -7
  12. package/lib/abstract/modular.js +80 -51
  13. package/lib/abstract/montgomery.js +3 -4
  14. package/lib/abstract/poseidon.d.ts +29 -0
  15. package/lib/abstract/poseidon.js +115 -0
  16. package/lib/abstract/utils.d.ts +5 -34
  17. package/lib/abstract/utils.js +23 -63
  18. package/lib/abstract/weierstrass.d.ts +56 -79
  19. package/lib/abstract/weierstrass.js +509 -641
  20. package/lib/bls12-381.d.ts +1 -0
  21. package/lib/bls12-381.js +75 -65
  22. package/lib/bn.js +1 -1
  23. package/lib/ed25519.d.ts +7 -5
  24. package/lib/ed25519.js +87 -84
  25. package/lib/ed448.d.ts +3 -0
  26. package/lib/ed448.js +88 -84
  27. package/lib/esm/abstract/bls.js +77 -139
  28. package/lib/esm/abstract/{group.js → curve.js} +37 -1
  29. package/lib/esm/abstract/edwards.js +223 -418
  30. package/lib/esm/abstract/hash-to-curve.js +38 -11
  31. package/lib/esm/abstract/modular.js +77 -50
  32. package/lib/esm/abstract/montgomery.js +4 -7
  33. package/lib/esm/abstract/poseidon.js +109 -0
  34. package/lib/esm/abstract/utils.js +21 -59
  35. package/lib/esm/abstract/weierstrass.js +508 -640
  36. package/lib/esm/bls12-381.js +86 -76
  37. package/lib/esm/bn.js +1 -1
  38. package/lib/esm/ed25519.js +85 -83
  39. package/lib/esm/ed448.js +86 -83
  40. package/lib/esm/jubjub.js +6 -5
  41. package/lib/esm/p256.js +11 -9
  42. package/lib/esm/p384.js +11 -9
  43. package/lib/esm/p521.js +13 -12
  44. package/lib/esm/secp256k1.js +118 -157
  45. package/lib/esm/stark.js +104 -39
  46. package/lib/jubjub.d.ts +3 -2
  47. package/lib/jubjub.js +6 -5
  48. package/lib/p192.d.ts +22 -52
  49. package/lib/p224.d.ts +22 -52
  50. package/lib/p256.d.ts +25 -52
  51. package/lib/p256.js +13 -10
  52. package/lib/p384.d.ts +25 -52
  53. package/lib/p384.js +13 -10
  54. package/lib/p521.d.ts +25 -52
  55. package/lib/p521.js +15 -13
  56. package/lib/secp256k1.d.ts +26 -42
  57. package/lib/secp256k1.js +118 -157
  58. package/lib/stark.d.ts +36 -21
  59. package/lib/stark.js +107 -39
  60. package/package.json +14 -9
package/lib/stark.d.ts CHANGED
@@ -1,6 +1,7 @@
1
- import { ProjectivePointType } from './abstract/weierstrass.js';
1
+ import { ProjPointType } from './abstract/weierstrass.js';
2
2
  import * as cutils from './abstract/utils.js';
3
- declare type ProjectivePoint = ProjectivePointType<bigint>;
3
+ import { Field } from './abstract/modular.js';
4
+ declare type ProjectivePoint = ProjPointType<bigint>;
4
5
  export declare const starkCurve: import("./abstract/weierstrass.js").CurveFn;
5
6
  declare function getPublicKey0x(privKey: Hex, isCompressed?: boolean): Uint8Array;
6
7
  declare function getSharedSecret0x(privKeyA: Hex, pubKeyB: Hex): Uint8Array;
@@ -9,7 +10,7 @@ declare function verify0x(signature: Hex, msgHash: Hex, pubKey: Hex): boolean;
9
10
  declare const CURVE: Readonly<{
10
11
  readonly nBitLength: number;
11
12
  readonly nByteLength: number;
12
- readonly Fp: import("./abstract/modular.js").Field<bigint>;
13
+ readonly Fp: Field<bigint>;
13
14
  readonly n: bigint;
14
15
  readonly h: bigint;
15
16
  readonly hEff?: bigint | undefined;
@@ -29,34 +30,22 @@ declare const CURVE: Readonly<{
29
30
  k2: bigint;
30
31
  };
31
32
  } | undefined;
32
- readonly isTorsionFree?: ((c: import("./abstract/weierstrass.js").ProjectiveConstructor<bigint>, point: ProjectivePointType<bigint>) => boolean) | undefined;
33
- readonly clearCofactor?: ((c: import("./abstract/weierstrass.js").ProjectiveConstructor<bigint>, point: ProjectivePointType<bigint>) => ProjectivePointType<bigint>) | undefined;
34
- readonly htfDefaults?: import("./abstract/hash-to-curve.js").htfOpts | undefined;
35
- readonly mapToCurve?: ((scalar: bigint[]) => {
36
- x: bigint;
37
- y: bigint;
38
- }) | undefined;
33
+ readonly isTorsionFree?: ((c: import("./abstract/weierstrass.js").ProjConstructor<bigint>, point: ProjPointType<bigint>) => boolean) | undefined;
34
+ readonly clearCofactor?: ((c: import("./abstract/weierstrass.js").ProjConstructor<bigint>, point: ProjPointType<bigint>) => ProjPointType<bigint>) | undefined;
39
35
  lowS: boolean;
40
36
  readonly hash: cutils.CHash;
41
37
  readonly hmac: (key: Uint8Array, ...messages: Uint8Array[]) => Uint8Array;
42
38
  readonly randomBytes: (bytesLength?: number | undefined) => Uint8Array;
43
- readonly truncateHash?: ((hash: Uint8Array, truncateOnly?: boolean | undefined) => bigint) | undefined;
44
- }>, Point: import("./abstract/weierstrass.js").PointConstructor<bigint>, ProjectivePoint: import("./abstract/weierstrass.js").ProjectiveConstructor<bigint>, Signature: import("./abstract/weierstrass.js").SignatureConstructor;
39
+ readonly bits2int?: ((bytes: Uint8Array) => bigint) | undefined;
40
+ readonly bits2int_modN?: ((bytes: Uint8Array) => bigint) | undefined;
41
+ }>, ProjectivePoint: import("./abstract/weierstrass.js").ProjConstructor<bigint>, Signature: import("./abstract/weierstrass.js").SignatureConstructor;
45
42
  export declare const utils: {
46
- mod: (a: bigint, b?: bigint | undefined) => bigint;
47
- invert: (number: bigint, modulo?: bigint | undefined) => bigint;
48
- _bigintToBytes: (num: bigint) => Uint8Array;
49
- _bigintToString: (num: bigint) => string;
50
43
  _normalizePrivateKey: (key: cutils.PrivKey) => bigint;
51
- _normalizePublicKey: (publicKey: import("./abstract/weierstrass.js").PubKey) => import("./abstract/weierstrass.js").PointType<bigint>;
52
- _isWithinCurveOrder: (num: bigint) => boolean;
53
- _isValidFieldElement: (num: bigint) => boolean;
54
- _weierstrassEquation: (x: bigint) => bigint;
55
44
  isValidPrivateKey(privateKey: cutils.PrivKey): boolean;
56
45
  hashToPrivateKey: (hash: cutils.Hex) => Uint8Array;
57
46
  randomPrivateKey: () => Uint8Array;
58
47
  };
59
- export { CURVE, Point, Signature, ProjectivePoint, getPublicKey0x as getPublicKey, getSharedSecret0x as getSharedSecret, sign0x as sign, verify0x as verify, };
48
+ export { CURVE, Signature, ProjectivePoint, getPublicKey0x as getPublicKey, getSharedSecret0x as getSharedSecret, sign0x as sign, verify0x as verify, };
60
49
  export declare const bytesToHexEth: (uint8a: Uint8Array) => string;
61
50
  export declare const strip0x: (hex: string) => string;
62
51
  export declare const numberToHexEth: (num: bigint | number) => string;
@@ -70,3 +59,29 @@ export declare function pedersen(x: PedersenArg, y: PedersenArg): string;
70
59
  export declare function hashChain(data: PedersenArg[], fn?: typeof pedersen): PedersenArg;
71
60
  export declare const computeHashOnElements: (data: PedersenArg[], fn?: typeof pedersen) => PedersenArg;
72
61
  export declare const keccak: (data: Uint8Array) => bigint;
62
+ export declare const Fp253: Readonly<Field<bigint> & Required<Pick<Field<bigint>, "isOdd">>>;
63
+ export declare const Fp251: Readonly<Field<bigint> & Required<Pick<Field<bigint>, "isOdd">>>;
64
+ export declare function _poseidonMDS(Fp: Field<bigint>, name: string, m: number, attempt?: number): bigint[][];
65
+ export declare type PoseidonOpts = {
66
+ Fp: Field<bigint>;
67
+ rate: number;
68
+ capacity: number;
69
+ roundsFull: number;
70
+ roundsPartial: number;
71
+ };
72
+ export declare function poseidonBasic(opts: PoseidonOpts, mds: bigint[][]): {
73
+ (values: bigint[]): bigint[];
74
+ roundConstants: bigint[][];
75
+ };
76
+ export declare function poseidonCreate(opts: PoseidonOpts, mdsAttempt?: number): {
77
+ (values: bigint[]): bigint[];
78
+ roundConstants: bigint[][];
79
+ };
80
+ export declare const poseidonSmall: {
81
+ (values: bigint[]): bigint[];
82
+ roundConstants: bigint[][];
83
+ };
84
+ export declare function poseidonHash(x: bigint, y: bigint, fn?: {
85
+ (values: bigint[]): bigint[];
86
+ roundConstants: bigint[][];
87
+ }): bigint;
package/lib/stark.js CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.keccak = exports.computeHashOnElements = exports.hashChain = exports.pedersen = exports.getAccountPath = exports.ethSigToPrivate = exports.getStarkKey = exports.grindKey = exports.numberToHexEth = exports.strip0x = exports.bytesToHexEth = exports.verify = exports.sign = exports.getSharedSecret = exports.getPublicKey = exports.ProjectivePoint = exports.Signature = exports.Point = exports.CURVE = exports.utils = exports.starkCurve = void 0;
3
+ exports.poseidonHash = exports.poseidonSmall = exports.poseidonCreate = exports.poseidonBasic = exports._poseidonMDS = exports.Fp251 = exports.Fp253 = exports.keccak = exports.computeHashOnElements = exports.hashChain = exports.pedersen = exports.getAccountPath = exports.ethSigToPrivate = exports.getStarkKey = exports.grindKey = exports.numberToHexEth = exports.strip0x = exports.bytesToHexEth = exports.verify = exports.sign = exports.getSharedSecret = exports.getPublicKey = exports.ProjectivePoint = exports.Signature = exports.CURVE = exports.utils = exports.starkCurve = void 0;
4
4
  /*! noble-curves - MIT License (c) 2022 Paul Miller (paulmillr.com) */
5
5
  const sha3_1 = require("@noble/hashes/sha3");
6
6
  const sha256_1 = require("@noble/hashes/sha256");
@@ -8,10 +8,21 @@ const weierstrass_js_1 = require("./abstract/weierstrass.js");
8
8
  const cutils = require("./abstract/utils.js");
9
9
  const modular_js_1 = require("./abstract/modular.js");
10
10
  const _shortw_utils_js_1 = require("./_shortw_utils.js");
11
+ const poseidon = require("./abstract/poseidon.js");
12
+ const utils_1 = require("@noble/hashes/utils");
11
13
  // Stark-friendly elliptic curve
12
14
  // https://docs.starkware.co/starkex/stark-curve.html
13
15
  const CURVE_N = BigInt('3618502788666131213697322783095070105526743751716087489154079457884512865583');
14
16
  const nBitLength = 252;
17
+ // Copy-pasted from weierstrass.ts
18
+ function bits2int(bytes) {
19
+ const delta = bytes.length * 8 - nBitLength;
20
+ const num = cutils.bytesToNumberBE(bytes);
21
+ return delta > 0 ? num >> BigInt(delta) : num;
22
+ }
23
+ function bits2int_modN(bytes) {
24
+ return (0, modular_js_1.mod)(bits2int(bytes), CURVE_N);
25
+ }
15
26
  exports.starkCurve = (0, weierstrass_js_1.weierstrass)({
16
27
  // Params: a, b
17
28
  a: BigInt(1),
@@ -29,33 +40,28 @@ exports.starkCurve = (0, weierstrass_js_1.weierstrass)({
29
40
  // Default options
30
41
  lowS: false,
31
42
  ...(0, _shortw_utils_js_1.getHash)(sha256_1.sha256),
32
- truncateHash: (hash, truncateOnly = false) => {
33
- // TODO: cleanup, ugly code
34
- // Fix truncation
35
- if (!truncateOnly) {
36
- let hashS = bytesToNumber0x(hash).toString(16);
37
- if (hashS.length === 63) {
38
- hashS += '0';
39
- hash = hexToBytes0x(hashS);
40
- }
43
+ // Custom truncation routines for stark curve
44
+ bits2int: (bytes) => {
45
+ while (bytes[0] === 0)
46
+ bytes = bytes.subarray(1);
47
+ return bits2int(bytes);
48
+ },
49
+ bits2int_modN: (bytes) => {
50
+ let hashS = cutils.bytesToNumberBE(bytes).toString(16);
51
+ if (hashS.length === 63) {
52
+ hashS += '0';
53
+ bytes = hexToBytes0x(hashS);
41
54
  }
42
55
  // Truncate zero bytes on left (compat with elliptic)
43
- while (hash[0] === 0)
44
- hash = hash.subarray(1);
45
- const byteLength = hash.length;
46
- const delta = byteLength * 8 - nBitLength; // size of curve.n (252 bits)
47
- let h = hash.length ? bytesToNumber0x(hash) : 0n;
48
- if (delta > 0)
49
- h = h >> BigInt(delta);
50
- if (!truncateOnly && h >= CURVE_N)
51
- h -= CURVE_N;
52
- return h;
56
+ while (bytes[0] === 0)
57
+ bytes = bytes.subarray(1);
58
+ return bits2int_modN(bytes);
53
59
  },
54
60
  });
55
61
  // Custom Starknet type conversion functions that can handle 0x and unpadded hex
56
62
  function hexToBytes0x(hex) {
57
63
  if (typeof hex !== 'string') {
58
- throw new TypeError('hexToBytes: expected string, got ' + typeof hex);
64
+ throw new Error('hexToBytes: expected string, got ' + typeof hex);
59
65
  }
60
66
  hex = (0, exports.strip0x)(hex);
61
67
  if (hex.length & 1)
@@ -75,7 +81,7 @@ function hexToBytes0x(hex) {
75
81
  }
76
82
  function hexToNumber0x(hex) {
77
83
  if (typeof hex !== 'string') {
78
- throw new TypeError('hexToNumber: expected string, got ' + typeof hex);
84
+ throw new Error('hexToNumber: expected string, got ' + typeof hex);
79
85
  }
80
86
  // Big Endian
81
87
  // TODO: strip vs no strip?
@@ -90,7 +96,7 @@ function ensureBytes0x(hex) {
90
96
  return hex instanceof Uint8Array ? Uint8Array.from(hex) : hexToBytes0x(hex);
91
97
  }
92
98
  function normalizePrivateKey(privKey) {
93
- return cutils.bytesToHex(ensureBytes0x(privKey)).padStart(32 * 2, '0');
99
+ return cutils.bytesToHex(ensureBytes0x(privKey)).padStart(64, '0');
94
100
  }
95
101
  function getPublicKey0x(privKey, isCompressed) {
96
102
  return exports.starkCurve.getPublicKey(normalizePrivateKey(privKey), isCompressed);
@@ -111,9 +117,8 @@ function verify0x(signature, msgHash, pubKey) {
111
117
  return exports.starkCurve.verify(sig, ensureBytes0x(msgHash), ensureBytes0x(pubKey));
112
118
  }
113
119
  exports.verify = verify0x;
114
- const { CURVE, Point, ProjectivePoint, Signature } = exports.starkCurve;
120
+ const { CURVE, ProjectivePoint, Signature } = exports.starkCurve;
115
121
  exports.CURVE = CURVE;
116
- exports.Point = Point;
117
122
  exports.ProjectivePoint = ProjectivePoint;
118
123
  exports.Signature = Signature;
119
124
  exports.utils = exports.starkCurve.utils;
@@ -129,17 +134,17 @@ function hashKeyWithIndex(key, index) {
129
134
  let indexHex = cutils.numberToHexUnpadded(index);
130
135
  if (indexHex.length & 1)
131
136
  indexHex = '0' + indexHex;
132
- return bytesToNumber0x((0, sha256_1.sha256)(cutils.concatBytes(key, hexToBytes0x(indexHex))));
137
+ return sha256Num(cutils.concatBytes(key, hexToBytes0x(indexHex)));
133
138
  }
134
139
  function grindKey(seed) {
135
140
  const _seed = ensureBytes0x(seed);
136
141
  const sha256mask = 2n ** 256n;
137
- const limit = sha256mask - exports.starkCurve.utils.mod(sha256mask, exports.starkCurve.CURVE.n);
142
+ const limit = sha256mask - (0, modular_js_1.mod)(sha256mask, CURVE_N);
138
143
  for (let i = 0;; i++) {
139
144
  const key = hashKeyWithIndex(_seed, i);
140
145
  // key should be in [0, limit)
141
146
  if (key < limit)
142
- return exports.starkCurve.utils.mod(key, exports.starkCurve.CURVE.n).toString(16);
147
+ return (0, modular_js_1.mod)(key, CURVE_N).toString(16);
143
148
  }
144
149
  }
145
150
  exports.grindKey = grindKey;
@@ -157,22 +162,22 @@ exports.ethSigToPrivate = ethSigToPrivate;
157
162
  const MASK_31 = 2n ** 31n - 1n;
158
163
  const int31 = (n) => Number(n & MASK_31);
159
164
  function getAccountPath(layer, application, ethereumAddress, index) {
160
- const layerNum = int31(bytesToNumber0x((0, sha256_1.sha256)(layer)));
161
- const applicationNum = int31(bytesToNumber0x((0, sha256_1.sha256)(application)));
165
+ const layerNum = int31(sha256Num(layer));
166
+ const applicationNum = int31(sha256Num(application));
162
167
  const eth = hexToNumber0x(ethereumAddress);
163
168
  return `m/2645'/${layerNum}'/${applicationNum}'/${int31(eth)}'/${int31(eth >> 31n)}'/${index}`;
164
169
  }
165
170
  exports.getAccountPath = getAccountPath;
166
171
  // https://docs.starkware.co/starkex/pedersen-hash-function.html
167
172
  const PEDERSEN_POINTS_AFFINE = [
168
- new Point(2089986280348253421170679821480865132823066470938446095505822317253594081284n, 1713931329540660377023406109199410414810705867260802078187082345529207694986n),
169
- new Point(996781205833008774514500082376783249102396023663454813447423147977397232763n, 1668503676786377725805489344771023921079126552019160156920634619255970485781n),
170
- new Point(2251563274489750535117886426533222435294046428347329203627021249169616184184n, 1798716007562728905295480679789526322175868328062420237419143593021674992973n),
171
- new Point(2138414695194151160943305727036575959195309218611738193261179310511854807447n, 113410276730064486255102093846540133784865286929052426931474106396135072156n),
172
- new Point(2379962749567351885752724891227938183011949129833673362440656643086021394946n, 776496453633298175483985398648758586525933812536653089401905292063708816422n),
173
+ new ProjectivePoint(2089986280348253421170679821480865132823066470938446095505822317253594081284n, 1713931329540660377023406109199410414810705867260802078187082345529207694986n, 1n),
174
+ new ProjectivePoint(996781205833008774514500082376783249102396023663454813447423147977397232763n, 1668503676786377725805489344771023921079126552019160156920634619255970485781n, 1n),
175
+ new ProjectivePoint(2251563274489750535117886426533222435294046428347329203627021249169616184184n, 1798716007562728905295480679789526322175868328062420237419143593021674992973n, 1n),
176
+ new ProjectivePoint(2138414695194151160943305727036575959195309218611738193261179310511854807447n, 113410276730064486255102093846540133784865286929052426931474106396135072156n, 1n),
177
+ new ProjectivePoint(2379962749567351885752724891227938183011949129833673362440656643086021394946n, 776496453633298175483985398648758586525933812536653089401905292063708816422n, 1n),
173
178
  ];
174
179
  // for (const p of PEDERSEN_POINTS) p._setWindowSize(8);
175
- const PEDERSEN_POINTS = PEDERSEN_POINTS_AFFINE.map(ProjectivePoint.fromAffine);
180
+ const PEDERSEN_POINTS = PEDERSEN_POINTS_AFFINE;
176
181
  function pedersenPrecompute(p1, p2) {
177
182
  const out = [];
178
183
  let p = p1;
@@ -211,7 +216,7 @@ function pedersenSingle(point, value, constants) {
211
216
  let x = pedersenArg(value);
212
217
  for (let j = 0; j < 252; j++) {
213
218
  const pt = constants[j];
214
- if (pt.x === point.x)
219
+ if (pt.px === point.px)
215
220
  throw new Error('Same point');
216
221
  if ((x & 1n) !== 0n)
217
222
  point = point.add(pt);
@@ -224,7 +229,7 @@ function pedersen(x, y) {
224
229
  let point = PEDERSEN_POINTS[0];
225
230
  point = pedersenSingle(point, x, PEDERSEN_POINTS1);
226
231
  point = pedersenSingle(point, y, PEDERSEN_POINTS2);
227
- return (0, exports.bytesToHexEth)(point.toAffine().toRawBytes(true).slice(1));
232
+ return (0, exports.bytesToHexEth)(point.toRawBytes(true).slice(1));
228
233
  }
229
234
  exports.pedersen = pedersen;
230
235
  function hashChain(data, fn = pedersen) {
@@ -240,6 +245,69 @@ exports.hashChain = hashChain;
240
245
  // Same as hashChain, but computes hash even for single element and order is not revesed
241
246
  const computeHashOnElements = (data, fn = pedersen) => [0, ...data, data.length].reduce((x, y) => fn(x, y));
242
247
  exports.computeHashOnElements = computeHashOnElements;
243
- const MASK_250 = 2n ** 250n - 1n;
248
+ const MASK_250 = cutils.bitMask(250);
244
249
  const keccak = (data) => bytesToNumber0x((0, sha3_1.keccak_256)(data)) & MASK_250;
245
250
  exports.keccak = keccak;
251
+ const sha256Num = (data) => cutils.bytesToNumberBE((0, sha256_1.sha256)(data));
252
+ // Poseidon hash
253
+ exports.Fp253 = (0, modular_js_1.Fp)(BigInt('14474011154664525231415395255581126252639794253786371766033694892385558855681')); // 2^253 + 2^199 + 1
254
+ exports.Fp251 = (0, modular_js_1.Fp)(BigInt('3618502788666131213697322783095070105623107215331596699973092056135872020481')); // 2^251 + 17 * 2^192 + 1
255
+ function poseidonRoundConstant(Fp, name, idx) {
256
+ const val = Fp.fromBytes((0, sha256_1.sha256)((0, utils_1.utf8ToBytes)(`${name}${idx}`)));
257
+ return Fp.create(val);
258
+ }
259
+ // NOTE: doesn't check eiginvalues and possible can create unsafe matrix. But any filtration here will break compatibility with starknet
260
+ // Please use only if you really know what you doing.
261
+ // https://eprint.iacr.org/2019/458.pdf Section 2.3 (Avoiding Insecure Matrices)
262
+ function _poseidonMDS(Fp, name, m, attempt = 0) {
263
+ const x_values = [];
264
+ const y_values = [];
265
+ for (let i = 0; i < m; i++) {
266
+ x_values.push(poseidonRoundConstant(Fp, `${name}x`, attempt * m + i));
267
+ y_values.push(poseidonRoundConstant(Fp, `${name}y`, attempt * m + i));
268
+ }
269
+ if (new Set([...x_values, ...y_values]).size !== 2 * m)
270
+ throw new Error('X and Y values are not distinct');
271
+ return x_values.map((x) => y_values.map((y) => Fp.inv(Fp.sub(x, y))));
272
+ }
273
+ exports._poseidonMDS = _poseidonMDS;
274
+ const MDS_SMALL = [
275
+ [3, 1, 1],
276
+ [1, -1, 1],
277
+ [1, 1, -2],
278
+ ].map((i) => i.map(BigInt));
279
+ function poseidonBasic(opts, mds) {
280
+ (0, modular_js_1.validateField)(opts.Fp);
281
+ if (!Number.isSafeInteger(opts.rate) || !Number.isSafeInteger(opts.capacity))
282
+ throw new Error(`Wrong poseidon opts: ${opts}`);
283
+ const m = opts.rate + opts.capacity;
284
+ const rounds = opts.roundsFull + opts.roundsPartial;
285
+ const roundConstants = [];
286
+ for (let i = 0; i < rounds; i++) {
287
+ const row = [];
288
+ for (let j = 0; j < m; j++)
289
+ row.push(poseidonRoundConstant(opts.Fp, 'Hades', m * i + j));
290
+ roundConstants.push(row);
291
+ }
292
+ return poseidon.poseidon({
293
+ ...opts,
294
+ t: m,
295
+ sboxPower: 3,
296
+ reversePartialPowIdx: true,
297
+ mds,
298
+ roundConstants,
299
+ });
300
+ }
301
+ exports.poseidonBasic = poseidonBasic;
302
+ function poseidonCreate(opts, mdsAttempt = 0) {
303
+ const m = opts.rate + opts.capacity;
304
+ if (!Number.isSafeInteger(mdsAttempt))
305
+ throw new Error(`Wrong mdsAttempt=${mdsAttempt}`);
306
+ return poseidonBasic(opts, _poseidonMDS(opts.Fp, 'HadesMDS', m, mdsAttempt));
307
+ }
308
+ exports.poseidonCreate = poseidonCreate;
309
+ exports.poseidonSmall = poseidonBasic({ Fp: exports.Fp251, rate: 2, capacity: 1, roundsFull: 8, roundsPartial: 83 }, MDS_SMALL);
310
+ function poseidonHash(x, y, fn = exports.poseidonSmall) {
311
+ return fn([x, y, 2n])[0];
312
+ }
313
+ exports.poseidonHash = poseidonHash;
package/package.json CHANGED
@@ -1,12 +1,12 @@
1
1
  {
2
2
  "name": "@noble/curves",
3
- "version": "0.5.1",
3
+ "version": "0.6.0",
4
4
  "description": "Minimal, auditable JS implementation of elliptic curve cryptography",
5
5
  "files": [
6
6
  "lib"
7
7
  ],
8
8
  "scripts": {
9
- "bench": "node benchmark/index.js",
9
+ "bench": "cd benchmark; node index.js",
10
10
  "build": "tsc && tsc -p tsconfig.esm.json",
11
11
  "build:release": "rollup -c rollup.config.js",
12
12
  "lint": "prettier --check 'src/**/*.{js,ts}' 'test/*.js'",
@@ -31,8 +31,8 @@
31
31
  "@types/node": "18.11.3",
32
32
  "fast-check": "3.0.0",
33
33
  "micro-bmark": "0.2.0",
34
- "micro-should": "0.2.0",
35
- "prettier": "2.6.2",
34
+ "micro-should": "0.3.0",
35
+ "prettier": "2.8.3",
36
36
  "rollup": "2.75.5",
37
37
  "typescript": "4.7.3"
38
38
  },
@@ -73,16 +73,21 @@
73
73
  "import": "./lib/esm/abstract/hash-to-curve.js",
74
74
  "default": "./lib/abstract/hash-to-curve.js"
75
75
  },
76
- "./abstract/group": {
77
- "types": "./lib/abstract/group.d.ts",
78
- "import": "./lib/esm/abstract/group.js",
79
- "default": "./lib/abstract/group.js"
76
+ "./abstract/curve": {
77
+ "types": "./lib/abstract/curve.d.ts",
78
+ "import": "./lib/esm/abstract/curve.js",
79
+ "default": "./lib/abstract/curve.js"
80
80
  },
81
81
  "./abstract/utils": {
82
82
  "types": "./lib/abstract/utils.d.ts",
83
83
  "import": "./lib/esm/abstract/utils.js",
84
84
  "default": "./lib/abstract/utils.js"
85
85
  },
86
+ "./abstract/poseidon": {
87
+ "types": "./lib/abstract/poseidon.d.ts",
88
+ "import": "./lib/esm/abstract/poseidon.js",
89
+ "default": "./lib/abstract/poseidon.js"
90
+ },
86
91
  "./_shortw_utils": {
87
92
  "types": "./lib/_shortw_utils.d.ts",
88
93
  "import": "./lib/esm/_shortw_utils.js",
@@ -189,4 +194,4 @@
189
194
  "url": "https://paulmillr.com/funding/"
190
195
  }
191
196
  ]
192
- }
197
+ }