mirror of
https://github.com/selfxyz/self.git
synced 2026-01-10 07:08:10 -05:00
242 lines
7.4 KiB
TypeScript
242 lines
7.4 KiB
TypeScript
import { wasm as wasmTester } from 'circom_tester';
|
|
import { describe, it } from 'mocha';
|
|
import path from 'path';
|
|
import {
|
|
generateMalleableRsaPssInputs,
|
|
generateMockRsaPssInputs,
|
|
} from './generateMockInputsRsaPss.js';
|
|
import { expect } from 'chai';
|
|
import { fullAlgorithms, sigAlgs, AdditionalCases } from './testcase/rsapss.js';
|
|
import { fileURLToPath } from 'url';
|
|
|
|
const __dirname = path.dirname(fileURLToPath(import.meta.url));
|
|
|
|
describe('VerifyRsapss Circuit Test', function () {
|
|
this.timeout(0);
|
|
|
|
const testSuite = process.env.FULL_TEST_SUITE === 'true' ? fullAlgorithms : sigAlgs;
|
|
|
|
testSuite.forEach((algorithm) => {
|
|
AdditionalCases[algorithm.algo]?.forEach((additionalCase) => {
|
|
it(`${additionalCase.title} for ${algorithm.algo}_${algorithm.saltLength} with additional case`, async function () {
|
|
this.timeout(0);
|
|
const signature = additionalCase.signature;
|
|
const modulus = additionalCase.modulus;
|
|
const message = additionalCase.message;
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
const witness = await circuit.calculateWitness({
|
|
signature,
|
|
modulus,
|
|
message,
|
|
});
|
|
|
|
// Check constraints
|
|
await circuit.checkConstraints(witness);
|
|
} catch (error) {
|
|
if (additionalCase.shouldFail) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
} else {
|
|
throw error;
|
|
}
|
|
}
|
|
});
|
|
});
|
|
|
|
it(`should verify RSA-PSS signature using the circuit for ${algorithm.algo}_${algorithm.saltLength}`, async function () {
|
|
this.timeout(0);
|
|
// Generate inputs using the utility function
|
|
const { signature, modulus, message } = generateMockRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
// Run circuit with inputs
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
// Log the inputs for debugging
|
|
console.log(`Testing algorithm: ${algorithm.algo} with salt length: ${algorithm.saltLength}`);
|
|
|
|
const witness = await circuit.calculateWitness({
|
|
signature,
|
|
modulus,
|
|
message,
|
|
});
|
|
|
|
// Check constraints
|
|
await circuit.checkConstraints(witness);
|
|
});
|
|
|
|
it('Should fail to verify RSA-PSS signature with invalid signature', async function () {
|
|
const { signature, modulus, message } = generateMockRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
const invalidSignature = [...signature];
|
|
const randomIndex = Math.floor(Math.random() * signature.length);
|
|
invalidSignature[randomIndex] = String((BigInt(signature[randomIndex]) + 1n).toString());
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
await circuit.calculateWitness({
|
|
signature: invalidSignature,
|
|
modulus,
|
|
message,
|
|
});
|
|
} catch (error) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
}
|
|
});
|
|
|
|
it('Should fail to verify RSA-PSS signature with invalid message', async function () {
|
|
const { signature, modulus, message } = generateMockRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
// Flip one bit in the message
|
|
const invalidMessage = [...message];
|
|
const randomIndex = Math.floor(Math.random() * message.length);
|
|
invalidMessage[randomIndex] = invalidMessage[randomIndex] === 0 ? 1 : 0;
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
await circuit.calculateWitness({
|
|
signature,
|
|
modulus,
|
|
message: invalidMessage,
|
|
});
|
|
} catch (error) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
}
|
|
});
|
|
|
|
it('Should reject signatures greater than or equal to modulus', async function () {
|
|
const { signature, modulus, message, n, k } = generateMockRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
const largeSignature = [...signature];
|
|
largeSignature[k - 1] = String(BigInt(modulus[k - 1]) + 1n);
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
await circuit.calculateWitness({
|
|
signature: largeSignature,
|
|
modulus,
|
|
message,
|
|
});
|
|
throw new Error('Circuit accepted signature >= modulus');
|
|
} catch (error) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
}
|
|
});
|
|
|
|
it('Should reject malleable signatures (signature + modulus)', async function () {
|
|
const { signature, modulus, message } = generateMalleableRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
await circuit.calculateWitness({
|
|
signature,
|
|
modulus,
|
|
message,
|
|
});
|
|
throw new Error('Circuit accepted malleable signature');
|
|
} catch (error) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
}
|
|
});
|
|
|
|
it('Should Fails when chunk has more bits than n', async function () {
|
|
const { signature, modulus, message } = generateMockRsaPssInputs(
|
|
algorithm.algo,
|
|
algorithm.saltLength
|
|
);
|
|
|
|
let overflowSignature = [...signature];
|
|
overflowSignature[0] = String(BigInt(2) ** BigInt(122));
|
|
|
|
const circuit = await wasmTester(
|
|
path.join(
|
|
__dirname,
|
|
`../../circuits/tests/utils/rsapss/test_${algorithm.algo}_${algorithm.saltLength}.circom`
|
|
),
|
|
{
|
|
include: ['node_modules', 'node_modules/@zk-kit/binary-merkle-root.circom/src'],
|
|
}
|
|
);
|
|
|
|
try {
|
|
await circuit.calculateWitness({
|
|
signature: overflowSignature,
|
|
modulus,
|
|
message,
|
|
});
|
|
throw new Error('Circuit accepted malleable signature');
|
|
} catch (error) {
|
|
expect(error.message).to.include('Assert Failed');
|
|
}
|
|
});
|
|
});
|
|
});
|