threshold-elgamal 0.1.31 → 0.1.32

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/dist/constants.js CHANGED
@@ -1,6 +1,3 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.GROUPS = void 0;
4
1
  /*
5
2
  The GROUPS object defines cryptographic parameters for different levels
6
3
  of finite field Diffie-Hellman (FFDHE) key exchanges.
@@ -14,7 +11,7 @@ exports.GROUPS = void 0;
14
11
 
15
12
  Reference: https://datatracker.ietf.org/doc/rfc7919/
16
13
  */
17
- exports.GROUPS = {
14
+ export const GROUPS = {
18
15
  // Parameters for 2048-bit prime modulus group
19
16
  ffdhe2048: {
20
17
  primeBits: 2048, // Size of the prime in bits, default security level suitable for current applications
package/dist/elgamal.js CHANGED
@@ -1,8 +1,5 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.decrypt = exports.encrypt = exports.generateParameters = void 0;
4
- const bigint_mod_arith_1 = require("bigint-mod-arith");
5
- const utils_1 = require("./utils/utils");
1
+ import { modPow, modInv } from 'bigint-mod-arith';
2
+ import { getRandomBigIntegerInRange, getGroup } from "./utils/utils.js";
6
3
  /**
7
4
  * Generates the parameters for the ElGamal encryption, including the prime, generator,
8
5
  * and key pair (public and private keys).
@@ -10,13 +7,12 @@ const utils_1 = require("./utils/utils");
10
7
  * @param {2048 | 3072 | 4096} primeBits - The bit length for the prime number. Supports 2048, 3072, or 4096 bits.
11
8
  * @returns {Parameters} The generated parameters including the prime, generator, publicKey, and privateKey.
12
9
  */
13
- const generateParameters = (primeBits = 2048) => {
14
- const { prime, generator } = (0, utils_1.getGroup)(primeBits); // Use getGroup to fetch the prime and generator
15
- const privateKey = (0, utils_1.getRandomBigIntegerInRange)(2n, prime - 1n);
16
- const publicKey = (0, bigint_mod_arith_1.modPow)(generator, privateKey, prime);
10
+ export const generateParameters = (primeBits = 2048) => {
11
+ const { prime, generator } = getGroup(primeBits); // Use getGroup to fetch the prime and generator
12
+ const privateKey = getRandomBigIntegerInRange(2n, prime - 1n);
13
+ const publicKey = modPow(generator, privateKey, prime);
17
14
  return { prime, generator, publicKey, privateKey };
18
15
  };
19
- exports.generateParameters = generateParameters;
20
16
  /**
21
17
  * Encrypts a secret using ElGamal encryption.
22
18
  *
@@ -26,17 +22,16 @@ exports.generateParameters = generateParameters;
26
22
  * @param {bigint} generator - The generator used in the encryption system. Defaults to the 2048-bit group's generator.
27
23
  * @returns {EncryptedMessage} The encrypted secret, consisting of two BigIntegers (c1 and c2).
28
24
  */
29
- const encrypt = (secret, publicKey, prime = (0, utils_1.getGroup)().prime, generator = (0, utils_1.getGroup)().generator) => {
25
+ export const encrypt = (secret, publicKey, prime = getGroup().prime, generator = getGroup().generator) => {
30
26
  if (secret >= Number(prime)) {
31
27
  throw new Error('Message is too large for direct encryption');
32
28
  }
33
- const randomNumber = (0, utils_1.getRandomBigIntegerInRange)(1n, prime - 1n);
34
- const c1 = (0, bigint_mod_arith_1.modPow)(generator, randomNumber, prime);
29
+ const randomNumber = getRandomBigIntegerInRange(1n, prime - 1n);
30
+ const c1 = modPow(generator, randomNumber, prime);
35
31
  const messageBigInt = BigInt(secret);
36
- const c2 = ((0, bigint_mod_arith_1.modPow)(publicKey, randomNumber, prime) * messageBigInt) % prime;
32
+ const c2 = (modPow(publicKey, randomNumber, prime) * messageBigInt) % prime;
37
33
  return { c1, c2 };
38
34
  };
39
- exports.encrypt = encrypt;
40
35
  /**
41
36
  * Decrypts an ElGamal encrypted secret.
42
37
  *
@@ -45,9 +40,8 @@ exports.encrypt = encrypt;
45
40
  * @param {bigint} privateKey - The private key used for decryption.
46
41
  * @returns {number} The decrypted secret as an integer.
47
42
  */
48
- const decrypt = (encryptedMessage, prime, privateKey) => {
49
- const ax = (0, bigint_mod_arith_1.modPow)(encryptedMessage.c1, privateKey, prime);
50
- const plaintext = ((0, bigint_mod_arith_1.modInv)(ax, prime) * encryptedMessage.c2) % prime;
43
+ export const decrypt = (encryptedMessage, prime, privateKey) => {
44
+ const ax = modPow(encryptedMessage.c1, privateKey, prime);
45
+ const plaintext = (modInv(ax, prime) * encryptedMessage.c2) % prime;
51
46
  return Number(plaintext);
52
47
  };
53
- exports.decrypt = decrypt;
package/dist/index.js CHANGED
@@ -1,18 +1,4 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getGroup = exports.multiplyEncryptedValues = exports.getRandomBigIntegerInRange = exports.thresholdDecrypt = exports.combineDecryptionShares = exports.createDecryptionShare = exports.combinePublicKeys = exports.generateKeyShares = exports.generateKeys = exports.decrypt = exports.encrypt = exports.generateParameters = void 0;
4
- const elgamal_1 = require("./elgamal");
5
- Object.defineProperty(exports, "generateParameters", { enumerable: true, get: function () { return elgamal_1.generateParameters; } });
6
- Object.defineProperty(exports, "encrypt", { enumerable: true, get: function () { return elgamal_1.encrypt; } });
7
- Object.defineProperty(exports, "decrypt", { enumerable: true, get: function () { return elgamal_1.decrypt; } });
8
- const thresholdElgamal_1 = require("./thresholdElgamal");
9
- Object.defineProperty(exports, "generateKeys", { enumerable: true, get: function () { return thresholdElgamal_1.generateKeys; } });
10
- Object.defineProperty(exports, "generateKeyShares", { enumerable: true, get: function () { return thresholdElgamal_1.generateKeyShares; } });
11
- Object.defineProperty(exports, "combinePublicKeys", { enumerable: true, get: function () { return thresholdElgamal_1.combinePublicKeys; } });
12
- Object.defineProperty(exports, "createDecryptionShare", { enumerable: true, get: function () { return thresholdElgamal_1.createDecryptionShare; } });
13
- Object.defineProperty(exports, "combineDecryptionShares", { enumerable: true, get: function () { return thresholdElgamal_1.combineDecryptionShares; } });
14
- Object.defineProperty(exports, "thresholdDecrypt", { enumerable: true, get: function () { return thresholdElgamal_1.thresholdDecrypt; } });
15
- const utils_1 = require("./utils/utils");
16
- Object.defineProperty(exports, "getRandomBigIntegerInRange", { enumerable: true, get: function () { return utils_1.getRandomBigIntegerInRange; } });
17
- Object.defineProperty(exports, "multiplyEncryptedValues", { enumerable: true, get: function () { return utils_1.multiplyEncryptedValues; } });
18
- Object.defineProperty(exports, "getGroup", { enumerable: true, get: function () { return utils_1.getGroup; } });
1
+ import { generateParameters, encrypt, decrypt } from "./elgamal.js";
2
+ import { generateKeys, generateKeyShares, combinePublicKeys, createDecryptionShare, combineDecryptionShares, thresholdDecrypt, } from "./thresholdElgamal.js";
3
+ import { getRandomBigIntegerInRange, multiplyEncryptedValues, getGroup, } from "./utils/utils.js";
4
+ export { generateParameters, encrypt, decrypt, generateKeys, generateKeyShares, combinePublicKeys, createDecryptionShare, combineDecryptionShares, thresholdDecrypt, getRandomBigIntegerInRange, multiplyEncryptedValues, getGroup, };
@@ -1,8 +1,5 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.thresholdDecrypt = exports.combineDecryptionShares = exports.createDecryptionShare = exports.combinePublicKeys = exports.generateKeyShares = exports.generateKeys = exports.evaluatePolynomial = void 0;
4
- const bigint_mod_arith_1 = require("bigint-mod-arith");
5
- const utils_1 = require("./utils/utils");
1
+ import { modPow, modInv } from 'bigint-mod-arith';
2
+ import { generatePolynomial, getGroup } from "./utils/utils.js";
6
3
  /**
7
4
  * Evaluates a polynomial at a given point using modular arithmetic.
8
5
  *
@@ -11,14 +8,13 @@ const utils_1 = require("./utils/utils");
11
8
  * @param {bigint} prime - The prime modulus.
12
9
  * @returns {bigint} The result of the polynomial evaluation.
13
10
  */
14
- const evaluatePolynomial = (polynomial, x, prime) => {
11
+ export const evaluatePolynomial = (polynomial, x, prime) => {
15
12
  let result = 0n;
16
13
  for (let i = 0; i < polynomial.length; i++) {
17
14
  result = (result + polynomial[i] * BigInt(x) ** BigInt(i)) % prime;
18
15
  }
19
16
  return result;
20
17
  };
21
- exports.evaluatePolynomial = evaluatePolynomial;
22
18
  /**
23
19
  * Generates a single key share for a participant in a threshold ElGamal cryptosystem.
24
20
  *
@@ -27,20 +23,19 @@ exports.evaluatePolynomial = evaluatePolynomial;
27
23
  * @param {2048 | 3072 | 4096} primeBits - The bit length of the prime modulus (default: 2048).
28
24
  * @returns { privateKey: bigint; publicKey: bigint} The key share containing a private and public key share for the participant.
29
25
  */
30
- const generateKeys = (index, threshold, primeBits = 2048) => {
31
- const group = (0, utils_1.getGroup)(primeBits);
26
+ export const generateKeys = (index, threshold, primeBits = 2048) => {
27
+ const group = getGroup(primeBits);
32
28
  const prime = group.prime;
33
29
  const generator = group.generator;
34
- const polynomial = (0, utils_1.generatePolynomial)(threshold, prime);
35
- let privateKey = (0, exports.evaluatePolynomial)(polynomial, index, prime);
30
+ const polynomial = generatePolynomial(threshold, prime);
31
+ let privateKey = evaluatePolynomial(polynomial, index, prime);
36
32
  // Ensure non-zero private key, adjusting index if necessary
37
33
  while (privateKey === 0n) {
38
- privateKey = (0, exports.evaluatePolynomial)(polynomial, index + 1, prime);
34
+ privateKey = evaluatePolynomial(polynomial, index + 1, prime);
39
35
  }
40
- const publicKey = (0, bigint_mod_arith_1.modPow)(generator, privateKey, prime);
36
+ const publicKey = modPow(generator, privateKey, prime);
41
37
  return { privateKey, publicKey };
42
38
  };
43
- exports.generateKeys = generateKeys;
44
39
  /**
45
40
  * Generates key shares for a threshold ElGamal cryptosystem.
46
41
  *
@@ -49,15 +44,14 @@ exports.generateKeys = generateKeys;
49
44
  * @param {2048 | 3072 | 4096} primeBits - The bit length of the prime modulus (default: 2048).
50
45
  * @returns {{ privateKey: bigint; publicKey: bigint }[]} An array of key shares, each containing a private and public key share.
51
46
  */
52
- const generateKeyShares = (n, threshold, primeBits = 2048) => {
47
+ export const generateKeyShares = (n, threshold, primeBits = 2048) => {
53
48
  const keyShares = [];
54
49
  for (let i = 1; i <= n; i++) {
55
- const keyShare = (0, exports.generateKeys)(i, threshold, primeBits);
50
+ const keyShare = generateKeys(i, threshold, primeBits);
56
51
  keyShares.push(keyShare);
57
52
  }
58
53
  return keyShares;
59
54
  };
60
- exports.generateKeyShares = generateKeyShares;
61
55
  /**
62
56
  * Combines multiple public keys into a single public key.
63
57
  *
@@ -65,8 +59,7 @@ exports.generateKeyShares = generateKeyShares;
65
59
  * @param {bigint} prime - The prime modulus used in the ElGamal system.
66
60
  * @returns {bigint} The combined public key.
67
61
  */
68
- const combinePublicKeys = (publicKeys, prime = (0, utils_1.getGroup)().prime) => publicKeys.reduce((combinedPublicKey, current) => (combinedPublicKey * current) % prime, 1n);
69
- exports.combinePublicKeys = combinePublicKeys;
62
+ export const combinePublicKeys = (publicKeys, prime = getGroup().prime) => publicKeys.reduce((combinedPublicKey, current) => (combinedPublicKey * current) % prime, 1n);
70
63
  /**
71
64
  * Performs a partial decryption on a ciphertext using an individual's private key share.
72
65
  *
@@ -75,8 +68,7 @@ exports.combinePublicKeys = combinePublicKeys;
75
68
  * @param {bigint} prime - The prime modulus used in the ElGamal system. Defaults to the 2048-bit group prime.
76
69
  * @returns {bigint} The result of the partial decryption.
77
70
  */
78
- const createDecryptionShare = (encryptedMessage, privateKey, prime = (0, utils_1.getGroup)().prime) => (0, bigint_mod_arith_1.modPow)(encryptedMessage.c1, privateKey, prime);
79
- exports.createDecryptionShare = createDecryptionShare;
71
+ export const createDecryptionShare = (encryptedMessage, privateKey, prime = getGroup().prime) => modPow(encryptedMessage.c1, privateKey, prime);
80
72
  /**
81
73
  * Combines partial decryptions from multiple parties into a single decryption factor.
82
74
  *
@@ -84,14 +76,13 @@ exports.createDecryptionShare = createDecryptionShare;
84
76
  * @param {bigint} prime - The prime modulus used in the ElGamal system. Defaults to the 2048-bit group prime.
85
77
  * @returns {bigint} The combined decryption factor.
86
78
  */
87
- const combineDecryptionShares = (decryptionShares, prime = (0, utils_1.getGroup)().prime) => {
79
+ export const combineDecryptionShares = (decryptionShares, prime = getGroup().prime) => {
88
80
  let result = 1n;
89
81
  for (const partialDecryption of decryptionShares) {
90
82
  result = (result * partialDecryption) % prime;
91
83
  }
92
84
  return result;
93
85
  };
94
- exports.combineDecryptionShares = combineDecryptionShares;
95
86
  /**
96
87
  * Decrypts an encrypted secret using the combined partial decryptions in a threshold ElGamal scheme.
97
88
  *
@@ -100,9 +91,8 @@ exports.combineDecryptionShares = combineDecryptionShares;
100
91
  * @param {bigint} prime - The prime modulus used in the ElGamal system. Defaults to the 2048-bit group prime.
101
92
  * @returns {number} The decrypted secret, assuming it was small enough to be directly encrypted.
102
93
  */
103
- const thresholdDecrypt = (encryptedMessage, combinedDecryptionShares, prime = (0, utils_1.getGroup)().prime) => {
104
- const combinedDecryptionInverse = (0, bigint_mod_arith_1.modInv)(combinedDecryptionShares, prime);
94
+ export const thresholdDecrypt = (encryptedMessage, combinedDecryptionShares, prime = getGroup().prime) => {
95
+ const combinedDecryptionInverse = modInv(combinedDecryptionShares, prime);
105
96
  const plaintext = (encryptedMessage.c2 * combinedDecryptionInverse) % prime;
106
97
  return Number(plaintext);
107
98
  };
108
- exports.thresholdDecrypt = thresholdDecrypt;
package/dist/types.js CHANGED
@@ -1,2 +1 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
1
+ export {};
@@ -1,60 +1,52 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.votingTest = exports.homomorphicMultiplicationTest = exports.testSecureEncryptionAndDecryption = exports.thresholdSetup = exports.getRandomScore = void 0;
4
- const vitest_1 = require("vitest");
5
- const elgamal_1 = require("../elgamal");
6
- const thresholdElgamal_1 = require("../thresholdElgamal");
7
- const utils_1 = require("./utils");
8
- const getRandomScore = (min = 1, max = 10) => Math.floor(Math.random() * (max - min + 1)) + min;
9
- exports.getRandomScore = getRandomScore;
10
- const thresholdSetup = (partiesCount, threshold, primeBits = 2048) => {
11
- const { prime, generator } = (0, utils_1.getGroup)(primeBits);
12
- const keyShares = (0, thresholdElgamal_1.generateKeyShares)(partiesCount, threshold, primeBits);
1
+ import { expect } from 'vitest';
2
+ import { encrypt } from "../elgamal.js";
3
+ import { generateKeyShares, combinePublicKeys, createDecryptionShare, combineDecryptionShares, thresholdDecrypt, } from "../thresholdElgamal.js";
4
+ import { multiplyEncryptedValues, getGroup } from "./utils.js";
5
+ export const getRandomScore = (min = 1, max = 10) => Math.floor(Math.random() * (max - min + 1)) + min;
6
+ export const thresholdSetup = (partiesCount, threshold, primeBits = 2048) => {
7
+ const { prime, generator } = getGroup(primeBits);
8
+ const keyShares = generateKeyShares(partiesCount, threshold, primeBits);
13
9
  const publicKeys = keyShares.map((ks) => ks.publicKey);
14
- const commonPublicKey = (0, thresholdElgamal_1.combinePublicKeys)(publicKeys, prime);
10
+ const commonPublicKey = combinePublicKeys(publicKeys, prime);
15
11
  return { keyShares, commonPublicKey, prime, generator };
16
12
  };
17
- exports.thresholdSetup = thresholdSetup;
18
- const testSecureEncryptionAndDecryption = (participantsCount, threshold, secret) => {
19
- const { keyShares, commonPublicKey, prime, generator } = (0, exports.thresholdSetup)(participantsCount, threshold);
20
- const encryptedMessage = (0, elgamal_1.encrypt)(secret, commonPublicKey, prime, generator);
13
+ export const testSecureEncryptionAndDecryption = (participantsCount, threshold, secret) => {
14
+ const { keyShares, commonPublicKey, prime, generator } = thresholdSetup(participantsCount, threshold);
15
+ const encryptedMessage = encrypt(secret, commonPublicKey, prime, generator);
21
16
  const selectedDecryptionShares = keyShares
22
17
  .sort(() => Math.random() - 0.5)
23
18
  .slice(0, threshold)
24
- .map(({ privateKey }) => (0, thresholdElgamal_1.createDecryptionShare)(encryptedMessage, privateKey, prime));
25
- const combinedDecryptionShares = (0, thresholdElgamal_1.combineDecryptionShares)(selectedDecryptionShares, prime);
26
- const decryptedMessage = (0, thresholdElgamal_1.thresholdDecrypt)(encryptedMessage, combinedDecryptionShares, prime);
27
- (0, vitest_1.expect)(decryptedMessage).toBe(secret);
19
+ .map(({ privateKey }) => createDecryptionShare(encryptedMessage, privateKey, prime));
20
+ const combinedDecryptionShares = combineDecryptionShares(selectedDecryptionShares, prime);
21
+ const decryptedMessage = thresholdDecrypt(encryptedMessage, combinedDecryptionShares, prime);
22
+ expect(decryptedMessage).toBe(secret);
28
23
  };
29
- exports.testSecureEncryptionAndDecryption = testSecureEncryptionAndDecryption;
30
- const homomorphicMultiplicationTest = (participantsCount, threshold, messages) => {
24
+ export const homomorphicMultiplicationTest = (participantsCount, threshold, messages) => {
31
25
  const expectedProduct = messages.reduce((product, secret) => product * secret, 1);
32
- const { keyShares, commonPublicKey, prime, generator } = (0, exports.thresholdSetup)(participantsCount, threshold);
33
- const encryptedMessages = messages.map((secret) => (0, elgamal_1.encrypt)(secret, commonPublicKey, prime, generator));
34
- const encryptedProduct = encryptedMessages.reduce((product, encryptedMessage) => (0, utils_1.multiplyEncryptedValues)(product, encryptedMessage, prime), { c1: 1n, c2: 1n });
26
+ const { keyShares, commonPublicKey, prime, generator } = thresholdSetup(participantsCount, threshold);
27
+ const encryptedMessages = messages.map((secret) => encrypt(secret, commonPublicKey, prime, generator));
28
+ const encryptedProduct = encryptedMessages.reduce((product, encryptedMessage) => multiplyEncryptedValues(product, encryptedMessage, prime), { c1: 1n, c2: 1n });
35
29
  const selectedDecryptionShares = keyShares
36
30
  .sort(() => Math.random() - 0.5)
37
31
  .slice(0, threshold)
38
- .map(({ privateKey }) => (0, thresholdElgamal_1.createDecryptionShare)(encryptedProduct, privateKey, prime));
39
- const combinedDecryptionShares = (0, thresholdElgamal_1.combineDecryptionShares)(selectedDecryptionShares, prime);
40
- const decryptedProduct = (0, thresholdElgamal_1.thresholdDecrypt)(encryptedProduct, combinedDecryptionShares, prime);
41
- (0, vitest_1.expect)(decryptedProduct).toBe(expectedProduct);
32
+ .map(({ privateKey }) => createDecryptionShare(encryptedProduct, privateKey, prime));
33
+ const combinedDecryptionShares = combineDecryptionShares(selectedDecryptionShares, prime);
34
+ const decryptedProduct = thresholdDecrypt(encryptedProduct, combinedDecryptionShares, prime);
35
+ expect(decryptedProduct).toBe(expectedProduct);
42
36
  };
43
- exports.homomorphicMultiplicationTest = homomorphicMultiplicationTest;
44
- const votingTest = (participantsCount, threshold, candidatesCount) => {
45
- const { keyShares, commonPublicKey, prime, generator } = (0, exports.thresholdSetup)(participantsCount, threshold);
46
- const votesMatrix = Array.from({ length: participantsCount }, () => Array.from({ length: candidatesCount }, () => (0, exports.getRandomScore)(1, 10)));
37
+ export const votingTest = (participantsCount, threshold, candidatesCount) => {
38
+ const { keyShares, commonPublicKey, prime, generator } = thresholdSetup(participantsCount, threshold);
39
+ const votesMatrix = Array.from({ length: participantsCount }, () => Array.from({ length: candidatesCount }, () => getRandomScore(1, 10)));
47
40
  const expectedProducts = Array.from({ length: candidatesCount }, (_, candidateIndex) => votesMatrix.reduce((product, votes) => product * votes[candidateIndex], 1));
48
- const encryptedVotesMatrix = votesMatrix.map((votes) => votes.map((vote) => (0, elgamal_1.encrypt)(vote, commonPublicKey, prime, generator)));
49
- const encryptedProducts = Array.from({ length: candidatesCount }, (_, candidateIndex) => encryptedVotesMatrix.reduce((product, encryptedVotes) => (0, utils_1.multiplyEncryptedValues)(product, encryptedVotes[candidateIndex], prime), { c1: 1n, c2: 1n }));
41
+ const encryptedVotesMatrix = votesMatrix.map((votes) => votes.map((vote) => encrypt(vote, commonPublicKey, prime, generator)));
42
+ const encryptedProducts = Array.from({ length: candidatesCount }, (_, candidateIndex) => encryptedVotesMatrix.reduce((product, encryptedVotes) => multiplyEncryptedValues(product, encryptedVotes[candidateIndex], prime), { c1: 1n, c2: 1n }));
50
43
  const partialDecryptionsMatrix = encryptedProducts.map((product) => keyShares
51
44
  .slice(0, threshold)
52
- .map((keyShare) => (0, thresholdElgamal_1.createDecryptionShare)(product, keyShare.privateKey, prime)));
45
+ .map((keyShare) => createDecryptionShare(product, keyShare.privateKey, prime)));
53
46
  const decryptedProducts = partialDecryptionsMatrix.map((decryptionShares) => {
54
- const combinedDecryptionShares = (0, thresholdElgamal_1.combineDecryptionShares)(decryptionShares, prime);
47
+ const combinedDecryptionShares = combineDecryptionShares(decryptionShares, prime);
55
48
  const encryptedProduct = encryptedProducts[partialDecryptionsMatrix.indexOf(decryptionShares)];
56
- return (0, thresholdElgamal_1.thresholdDecrypt)(encryptedProduct, combinedDecryptionShares, prime);
49
+ return thresholdDecrypt(encryptedProduct, combinedDecryptionShares, prime);
57
50
  });
58
- (0, vitest_1.expect)(decryptedProducts).toEqual(expectedProducts);
51
+ expect(decryptedProducts).toEqual(expectedProducts);
59
52
  };
60
- exports.votingTest = votingTest;
@@ -1,7 +1,4 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.generatePolynomial = exports.multiplyEncryptedValues = exports.getRandomBigIntegerInRange = exports.getGroup = exports.randomBigint = void 0;
4
- const constants_1 = require("../constants");
1
+ import { GROUPS } from "../constants.js";
5
2
  /**
6
3
  * Generates a random BigInt of exactly the specified number of bits.
7
4
  * The function calculates the required number of hexadecimal digits to represent
@@ -17,7 +14,7 @@ const constants_1 = require("../constants");
17
14
  * const randomBigInt = generateRandomBigIntFromBits(128);
18
15
  * console.log(randomBigInt);
19
16
  */
20
- const randomBigint = (bits) => {
17
+ export const randomBigint = (bits) => {
21
18
  // Ensure bits is positive and greater than zero to avoid infinite loop
22
19
  if (bits <= 0) {
23
20
  throw new RangeError('Bit length must be greater than 0');
@@ -34,44 +31,41 @@ const randomBigint = (bits) => {
34
31
  // Combine, convert to BigInt, and return
35
32
  return BigInt(`0x${firstDigit}${remainingDigits}`);
36
33
  };
37
- exports.randomBigint = randomBigint;
38
34
  /**
39
35
  * Retrieves the group parameters for a given prime bit length.
40
36
  *
41
37
  * @param {2048 | 3072 | 4096} primeBits - The bit length of the prime modulus (2048, 3072, or 4096).
42
38
  * @returns {Object} The group parameters including prime and generator.
43
39
  */
44
- const getGroup = (primeBits = 2048) => {
40
+ export const getGroup = (primeBits = 2048) => {
45
41
  switch (primeBits) {
46
42
  case 2048:
47
- return constants_1.GROUPS.ffdhe2048;
43
+ return GROUPS.ffdhe2048;
48
44
  case 3072:
49
- return constants_1.GROUPS.ffdhe3072;
45
+ return GROUPS.ffdhe3072;
50
46
  case 4096:
51
- return constants_1.GROUPS.ffdhe4096;
47
+ return GROUPS.ffdhe4096;
52
48
  default:
53
49
  throw new Error('Unsupported bit length');
54
50
  }
55
51
  };
56
- exports.getGroup = getGroup;
57
52
  /**
58
53
  * Generates a random bigint within a specified range.
59
54
  * @param {bigint} min - The minimum value (inclusive).
60
55
  * @param {bigint} max - The maximum value (exclusive).
61
56
  * @returns {bigint} A random bigint within the specified range.
62
57
  */
63
- const getRandomBigIntegerInRange = (min, max) => {
58
+ export const getRandomBigIntegerInRange = (min, max) => {
64
59
  const range = max - min + 1n;
65
60
  // Determine the number of bits needed for the range
66
61
  const bitsNeeded = range.toString(2).length;
67
62
  // Generate a random bigint within the calculated bits
68
- let num = (0, exports.randomBigint)(bitsNeeded);
63
+ let num = randomBigint(bitsNeeded);
69
64
  // Adjust the number to our range
70
65
  num = num % range;
71
66
  // Add the minimum to align with our desired range
72
67
  return min + num;
73
68
  };
74
- exports.getRandomBigIntegerInRange = getRandomBigIntegerInRange;
75
69
  /**
76
70
  * Performs homomorphic multiplication on two encrypted values, allowing for encrypted arithmetic operations.
77
71
  * @param {EncryptedMessage} value1 - The first encrypted value.
@@ -79,12 +73,11 @@ exports.getRandomBigIntegerInRange = getRandomBigIntegerInRange;
79
73
  * @param {bigint} prime - The prime modulus used in the encryption system. Defaults to the 2048-bit group prime.
80
74
  * @returns {EncryptedMessage} The result of the multiplication, as a new encrypted message.
81
75
  */
82
- const multiplyEncryptedValues = (value1, value2, prime = (0, exports.getGroup)().prime) => {
76
+ export const multiplyEncryptedValues = (value1, value2, prime = getGroup().prime) => {
83
77
  const c1Multiplied = (value1.c1 * value2.c1) % prime;
84
78
  const c2Multiplied = (value1.c2 * value2.c2) % prime;
85
79
  return { c1: c1Multiplied, c2: c2Multiplied };
86
80
  };
87
- exports.multiplyEncryptedValues = multiplyEncryptedValues;
88
81
  /**
89
82
  * Generates a random polynomial of a specified degree, to be used in Shamir's Secret Sharing scheme.
90
83
  * The polynomial is of the form f(x) = a0 + a1*x + a2*x^2 + ... + a_{threshold-1}*x^{threshold-1},
@@ -93,11 +86,10 @@ exports.multiplyEncryptedValues = multiplyEncryptedValues;
93
86
  * @param {bigint} prime - The prime modulus used in the system, to ensure operations are performed in a finite field.
94
87
  * @returns {bigint[]} An array representing the polynomial coefficients `[a0, a1, ..., a_{threshold-1}]`.
95
88
  */
96
- const generatePolynomial = (threshold, prime) => {
97
- const polynomial = [(0, exports.getRandomBigIntegerInRange)(2n, prime - 1n)]; // constant term is the "master" private key
89
+ export const generatePolynomial = (threshold, prime) => {
90
+ const polynomial = [getRandomBigIntegerInRange(2n, prime - 1n)]; // constant term is the "master" private key
98
91
  for (let i = 1; i < threshold; i++) {
99
- polynomial.push((0, exports.getRandomBigIntegerInRange)(0n, prime - 1n)); // random coefficients
92
+ polynomial.push(getRandomBigIntegerInRange(0n, prime - 1n)); // random coefficients
100
93
  }
101
94
  return polynomial;
102
95
  };
103
- exports.generatePolynomial = generatePolynomial;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "threshold-elgamal",
3
- "version": "0.1.31",
3
+ "version": "0.1.32",
4
4
  "description": "Threshold ElGamal in TypeScript",
5
5
  "author": "Piotr Piech <piotr@piech.dev>",
6
6
  "license": "MIT",