Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
[package]
name = "rescue_prime"
type = "bin"
authors = [""]

[dependencies]
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
input = ["72", "101", "108", "108", "111", "32", "87", "111", "114", "108", "100", "33", "32", "84", "104", "105", "115", "32", "105", "115", "32", "97", "32", "116", "101", "115", "116", "32", "109", "115", "103", "46"]
209 changes: 209 additions & 0 deletions benchmarking-suite/frameworks/noir/circuits/rescue_prime/src/main.nr
Original file line number Diff line number Diff line change
@@ -0,0 +1,209 @@
global ROUNDS: u32 = 20;
global M: u32 = 2;
global RATE: u32 = M - 1;
global MDS: [[Field; 2]; 2] = [
[21888242871839275222246405745257275088548364400416034343698204186575808495612, 6],
[21888242871839275222246405745257275088548364400416034343698204186575808495587, 31]
];

global RC: [Field; 80] = [
15697361631448404487274768602668939825074111741823345832894704473981253317170,
9080481432229903380115438213067511849060701402222160905335780624465482194226,
10546221173746079008417900781685142616628381578500718917162200032981740147921,
12385405709335687367210828574241143040645050565893931286211204777495851043609,
531616977721353565374475582738065516128911689551106838332675818433255157809,
6450358868146511102205448592463711460530106605106308061419175719485525540167,
3513052829370777766680030939557222162492045494261521555362252286730452000116,
8990187030387799052320523326467116373567258001290905760030809536695872172648,
17295802290862132793002301697105464204439460629594101797477785802305164785840,
11804553718013044924869320197086635065017745738986667161446535112350367547082,
10048242788911215019569293232840568695583883814049703042421221336997933829871,
7346398966306157726470567950784625423006373010216755477996383070514028671398,
1468342549403691578902675062440405592755257914331733539585980634706443617862,
20519841246631821035638178251082052108601058063613169717283532990478932702243,
14620781597698727005854889892106901507027484092196599098435672990330180180691,
12411531875746030376648409534739175046780539230183335896369187600691503971361,
19604334607103327950722599004089798966986650536600062623762413343064099798109,
1241341554806352791858214403617336752102282019754427201666265419887512995978,
3202606705731993422111112340099874906015393987606058360135034921092863522004,
19179709535904028423301481038437354480702351025742448613360139280772073480913,
18013497525986824688336626520296620203950769984449505490460029566741924159593,
21274270640801061156165846887939236043096483195340764018141920806622079295069,
13865049440612158990323504973253066303737576545206522621505144041573447016769,
2883445590853186600081290823390725491831491628785916365692561006549993107980,
13292182972095177145614735704534020980769806960867964800217010533464405262431,
17203209982485067425727732295774891779585157359487460423340308650576259390621,
9527650920125591253580338940228274466862105971188754234417793077219038817573,
18318553319997702342610498730790973590859049558800737994424107212276065001017,
19474814489335682254720155035789855270283630956810003232860294805477004758533,
4382892606269943862637546511962855623806214046301709876105279195408005645631,
18828863711337382639946457344839497706760405012435731272331585871915923508871,
11962733134274187283224249510678130247989400196672305863913711872539202382126,
297400476947545794734084974553246901202600089801718129639441731055620948076,
10886711505998384034729501295996115711311132258899431600759926456900955754180,
12278177449415342861126927770988483947909988485388344098806549196671360968351,
414065439715594409448382340532035110217215140426896524939130787395865529338,
6209950577917046377802222244857391481485789351511546535126988871026558442320,
21117445149768370144485275061378044804688054126709317741986747301162426733667,
16946209028924170233662559629288759777753383698869274483281433758921660041450,
19234695425257778033245766537045504553119307935808795500106332388596412334866,
5581352464726806706513641728827766330540855818867133173782767525621229409371,
7597962668583388329425395416219920381607125246106845942417506570706834273179,
19765912433776254057191413402668335957839914254320614315910184708873664937965,
712458681674213989635145566448985502060839177599824515722305070066770488788,
11956277525835497301310163199459285159243900024425662850375911140625714453055,
375421310522073004931216252339572573721268694939846040398775165532883391145,
670233076295937000834379469539614497666118243927704787235753360347755333213,
3963423187353060958758804518605903806238836058461336916655395459005523659260,
8655380302907519195049407735948669917197066739722614340929738120803211109099,
8002837738408268933119744985412844278172464372321607326902640577483106435147,
13814215007722446076802328304781264567938228122924275233032157814774025355654,
1301805677819804308092440241283084213099971147648315381480335463158078390236,
7542694910867675525657699379855568103754501384311641989627846102480287239529,
17195410687285352957395352658787062705657772625539738357439514214448807572578,
1850251841829189639861887952069233578000942492674363348798045643661039893485,
7496574378257568835557392357440421320634592756736890356726070890394561054708,
13308163253733136531187016783093954251604983611570520981660536154089490085609,
11744001976156316830051958580030839314581137654029591820781989763930820629466,
16001830682981642383938365049197967946704082656374363177248434046467448610752,
3345912325918299850263926785402171284890217052042660982149273865440338794299,
16755665978604422126931113586732982262653486470339056214169398884622442611854,
17805302906384340240864352508421805703234310797024796567683573878790454335167,
14771257948888391868353293618085386651827152150625546791424881211695617608839,
3145082263654835042905414918171697069275335766432050530267857969927552525325,
20835528768580685087780656823157273583910922092925035723011395485667456970079,
20215393241325782529231184191217931941985973210884134343153014310273447361596,
3654318209037701430491178387125718197536931425871979053450125600168528310373,
7372644141820433830298675751729842824712104977662817574209512374822214218600,
12601089151965102160130596650922011321733333558040461506769773089174555033124,
1287501226503339800509922990078339171251120134741939369419331249714337752973,
6587583968874615334648084517425504603064646385203349267603734334316394255089,
2653310096807041565152687796807283074703029398341847096498443292295742704720,
4582907957009852941903271316265667306547946199474367274856184004703265456779,
13703540599939293680552117249152419810242955353999539770066271687985973664528,
3573704660705175113787323648852917658030622463503514493926185830431740964508,
175262338833418353543646432390834222383395205919679149701497473773757396637,
2234470614306351481931719734525283664260382326431590366734659719492586891342,
8319069004178488595162998988756240608152557824213923966396374597856756144814,
14412696734180155628283626728549856651146330257298555914382198498324408147108,
3055219533471541857956070957707119175532045543822556512823202896077811109419,
];

fn sbox(x: Field) -> Field {
x * x * x * x * x
}

// fn inv_sbox(x: Field) -> Field {
// // Since A = 5, the inverse S-box is x^(p-2)/5 mod p
// let exp: Field = 17510594297471420177797124596205820070838691520332827474958563349260646796493;
// let out = x.pow_32(exp);
// let out_2 = out * out;
// let out_4 = out_2 * out_2;
// assert(x == out_4 * out);

// out
// }
// Helper function to handle large exponents (256 bits)
// We mark it unconstrained so it doesn't generate massive gate counts
unconstrained fn pow_unconstrained(base: Field, exp: Field) -> Field {
let mut res: Field = 1;
// We explicitly tell the compiler to decompose into 254 bits
let bits = exp.to_le_bits::<254>();

for i in 0..254 {
// Square first (except possibly the very first iteration,
// but squaring 1 is still 1, so this is safe)
res *= res;

// If the bit is 1, multiply by the base
// Note: bits[253 - i] accesses the bits from Most Significant to Least Significant
if bits[253 - i] == 1 {
res *= base;
}
}
res
}

fn inv_sbox(x: Field) -> Field {
let exp: Field = 17510594297471420177797124596205820070838691520332827474958563349260646796493;

// Safety: The result is constrained by the assertion below: assert(x == out_4 * out);
let out = unsafe {
pow_unconstrained(x, exp)
};

// 2. Constrain the result (Secure)
// This is where the 3 gates come in.
let out_2 = out * out;
let out_4 = out_2 * out_2;
assert(x == out_4 * out); // Verifies out^5 == x

out
}
fn apply_sbox(state: &mut [Field; M]) {
for i in 0..M {
state[i] = sbox(state[i]);
}
}

fn apply_inv_sbox(state: &mut [Field; M]) {
for i in 0..M {
state[i] = inv_sbox(state[i]);
}
}

fn apply_mds(state: &mut [Field; M]) {
let mut new_state: [Field; M] = [0; M];
for i in 0..M {
for j in 0..M {
new_state[i] += MDS[i][j] * state[j];
}
}
*state = new_state;
}

fn add_round_constants(state: &mut [Field; M], round: u32, offset: u32) {
for j in 0..M {
state[j] += RC[round * M * 2 + j + offset];
}
}

fn rescue_round(state: &mut [Field; M], round: u32) {
apply_sbox(state);
apply_mds(state);
add_round_constants(state, round, 0);
apply_inv_sbox(state);
apply_mds(state);
add_round_constants(state, round, M as u32);
}

fn rescue_permutation(state: &mut [Field; M]) {
for round in 0..ROUNDS {
rescue_round(state, round);
}
}

fn rescue_prime_hash_generic<let N: u32> (input: [Field; N]) -> [Field; RATE] {
let mut state: [Field; M] = [0; M];
let num_chunks = N/RATE;
for i in 0..num_chunks {
for j in 0..RATE {
state[j] += input[i * RATE + j];
}
rescue_permutation(&mut state);
}
let mut output: [Field; RATE] = [0; RATE];
for i in 0..RATE {
output[i] = state[i];
}
output
}

fn main(input: [Field; 32]) -> pub [Field; 1] {
let mut padded_input: [Field; 33] = [0; 33];
for i in 0..32 {
padded_input[i] = input[i];
}
padded_input[32] = 1;
rescue_prime_hash_generic(padded_input)
}
Binary file not shown.

Large diffs are not rendered by default.

8 changes: 4 additions & 4 deletions benchmarking-suite/moPro/mopro-example-app/Config.toml
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
build_mode = "debug"
build_mode = "release"
target_adapters = [
"circom",
"noir",
"halo2",
"noir",
"circom",
]
target_platforms = ["android"]
android = ["x86_64-linux-android"]
android = ["aarch64-linux-android"]
auto_update = false

[update]

Large diffs are not rendered by default.

Binary file not shown.
19 changes: 18 additions & 1 deletion benchmarking-suite/moPro/mopro-example-app/flutter/lib/main.dart
Original file line number Diff line number Diff line change
Expand Up @@ -774,7 +774,7 @@ class _MainSelectionPageState extends State<MainSelectionPage> {
case 'halo2':
return ['Fibonacci'];
case 'noir':
return ['SHA256', 'Keccak256', 'Poseidon', 'MiMC', 'Pedersen', 'Blake2', 'Blake3'];
return ['SHA256', 'Keccak256', 'Poseidon', 'MiMC', 'Pedersen', 'Blake2', 'Blake3', 'RescuePrime'];
case 'risc0':
return ['Factor'];
default:
Expand Down Expand Up @@ -941,6 +941,7 @@ class _ProofResultPageState extends State<ProofResultPage> {
Uint8List? _noirSha256VerificationKey;
Uint8List? _noirBlake2VerificationKey;
Uint8List? _noirBlake3VerificationKey;
Uint8List? _noirRescuePrimeVerificationKey;

// Benchmarking timing
Duration? _proofGenerationTime;
Expand Down Expand Up @@ -1828,6 +1829,22 @@ class _ProofResultPageState extends State<ProofResultPage> {
}
verificationKey = _noirSha256VerificationKey;
break;
case 'RescuePrime':
assetPath = "assets/rescue_prime.json";
srsPath = "assets/rescue_prime.srs";
onChain = true;
if (_noirSha256VerificationKey == null) {
try {
final vkAsset = await rootBundle.load('assets/rescue_prime.vk');
_noirSha256VerificationKey = vkAsset.buffer.asUint8List();
} catch (e) {
_noirSha256VerificationKey = await moproFlutterPlugin.getNoirVerificationKey(
assetPath, srsPath, onChain, lowMemoryMode,
);
}
}
verificationKey = _noirSha256VerificationKey;
break;
case 'keccak256':
assetPath = "assets/keccak256.json";
srsPath = "assets/keccak256.srs";
Expand Down