nomos-pocs/proof_of_leadership/anemoi/anemoi_4_to_1_Jubjub.circom

179 lines
3.9 KiB
Plaintext

//test
pragma circom 2.1.9;
include "anemoi_Jubjub_4_to_1_constants.circom";
template ark_layer_4_to_1(round_number) {
assert(round_number < 14);
signal input in[4];
signal output out[4];
var C[14][2] = C_4_to_1();
var D[14][2] = D_4_to_1();
out[0] <== in[0] + C[round_number][0];
out[1] <== in[1] + C[round_number][1];
out[2] <== in[2] + D[round_number][0];
out[3] <== in[3] + D[round_number][1];
}
template pow_alpha_4_to_1() { // ALPHA = 5
signal input in;
signal output out;
signal in2;
signal in4;
in2 <== in*in;
in4 <== in2 * in2;
out <== in4 * in;
}
template mds_layer_4_to_1() {
signal input in[4];
signal output out[4];
signal x0;
signal x1;
signal y0;
signal y1;
x0 <== in[0] + 7*in[1];
x1 <== 7*in[0] + 50*in[1];
y0 <== in[3] + 7*in[2];
y1 <== 7*in[3] + 50*in[2];
out[2] <== y0 + x0;
out[3] <== y1 + x1;
out[0] <== x0 + out[2];
out[1] <== x1 + out[3];
}
template s_box_4_to_1() {
signal input in[4];
signal output out[4];
//Calculation using open Flystel
var x0;
var y0;
x0 = in[0];
y0 = in[2];
x0 = x0 - 7 * (y0**2);
y0 = y0 - (x0**20974350070050476191779096203274386335076221000211055129041463479975432473805); // 1/ALPHA
x0 = x0 + 7 * (y0**2) + 14981678621464625851270783002338847382197300714436467949315331057125308909861; //DELTA
var x1;
var y1;
x1 = in[1];
y1 = in[3];
x1 = x1 - 7 * (y1**2);
y1 = y1 - (x1**20974350070050476191779096203274386335076221000211055129041463479975432473805); // 1/ALPHA
x1 = x1 + 7 * (y1**2) + 14981678621464625851270783002338847382197300714436467949315331057125308909861; //DELTA
out[0] <-- x0;
out[1] <-- x1;
out[2] <-- y0;
out[3] <-- y1;
//Verification using closed Flystel
component pow[2];
pow[0] = pow_alpha_4_to_1();
pow[1] = pow_alpha_4_to_1();
pow[0].in <== in[2] - out[2];
signal y0_2;
signal v0_2;
y0_2 <== in[2]*in[2];
v0_2 <==out[2]*out[2];
in[0] === pow[0].out + 7 * y0_2;
out[0] === pow[0].out + 7 * v0_2 + 14981678621464625851270783002338847382197300714436467949315331057125308909861;// DELTA
pow[1].in <== in[3] - out[3];
signal y1_2;
signal v1_2;
y1_2 <== in[3]*in[3];
v1_2 <==out[3]*out[3];
in[1] === pow[1].out + 7 * y1_2;
out[1] === pow[1].out + 7 * v1_2 + 14981678621464625851270783002338847382197300714436467949315331057125308909861;// DELTA
}
template round_4_to_1(round_number) {
signal input in[4];
signal output out[4];
component cst = ark_layer_4_to_1(round_number);
component mds = mds_layer_4_to_1();
component sbox = s_box_4_to_1();
cst.in[0] <== in[0];
cst.in[1] <== in[1];
cst.in[2] <== in[2];
cst.in[3] <== in[3];
mds.in[0] <== cst.out[0];
mds.in[1] <== cst.out[1];
mds.in[2] <== cst.out[2];
mds.in[3] <== cst.out[3];
sbox.in[0] <== mds.out[0];
sbox.in[1] <== mds.out[1];
sbox.in[2] <== mds.out[2];
sbox.in[3] <== mds.out[3];
out[0] <== sbox.out[0];
out[1] <== sbox.out[1];
out[2] <== sbox.out[2];
out[3] <== sbox.out[3];
}
template permutation_4_to_1(){
signal input in[4];
signal output out[4];
component rounds[14];
component mds = mds_layer_4_to_1();
for(var i = 0; i<14; i++){ //14 rounds
rounds[i] = round_4_to_1(i);
if(i==0){
rounds[i].in[0] <== in[0];
rounds[i].in[1] <== in[1];
rounds[i].in[2] <== in[2];
rounds[i].in[3] <== in[3];
} else {
rounds[i].in[0] <== rounds[i-1].out[0];
rounds[i].in[1] <== rounds[i-1].out[1];
rounds[i].in[2] <== rounds[i-1].out[2];
rounds[i].in[3] <== rounds[i-1].out[3];
}
}
mds.in[0] <== rounds[13].out[0];
mds.in[1] <== rounds[13].out[1];
mds.in[2] <== rounds[13].out[2];
mds.in[3] <== rounds[13].out[3];
out[0] <== mds.out[0];
out[1] <== mds.out[1];
out[2] <== mds.out[2];
out[3] <== mds.out[3];
}
template hash_4_to_1(){
signal input in[4];
signal output out;
component perm = permutation_4_to_1();
perm.in[0] <== in[0];
perm.in[1] <== in[1];
perm.in[2] <== in[2];
perm.in[3] <== in[3];
out <== in[0] + perm.out[0] + in[1] + perm.out[1] + in[2] + perm.out[2] + in[3] + perm.out[3];
}
//component main = hash_4_to_1();