148 lines
3.9 KiB
Rust
148 lines
3.9 KiB
Rust
use libc::{size_t};
|
|
use super::arith::FieldT;
|
|
|
|
#[repr(C)]
|
|
struct R1ConstraintSystem;
|
|
|
|
#[repr(C)]
|
|
pub struct LinearTerm {
|
|
pub coeff: FieldT,
|
|
pub index: size_t
|
|
}
|
|
|
|
extern "C" {
|
|
fn tinysnark_new_r1cs(primary: size_t, aux: size_t) -> *mut R1ConstraintSystem;
|
|
fn tinysnark_drop_r1cs(cs: *mut R1ConstraintSystem);
|
|
fn tinysnark_satisfy_test(cs: *mut R1ConstraintSystem, primary: *const FieldT, aux: *const FieldT) -> bool;
|
|
fn tinysnark_add_constraint(cs: *mut R1ConstraintSystem,
|
|
a: *const LinearTerm,
|
|
a_len: size_t,
|
|
b: *const LinearTerm,
|
|
b_len: size_t,
|
|
c: *const LinearTerm,
|
|
c_len: size_t
|
|
);
|
|
}
|
|
|
|
pub struct ConstraintSystem {
|
|
cs: *mut R1ConstraintSystem,
|
|
primary_size: usize,
|
|
aux_size: usize
|
|
}
|
|
|
|
impl Drop for ConstraintSystem {
|
|
fn drop(&mut self) {
|
|
unsafe { tinysnark_drop_r1cs(self.cs) }
|
|
}
|
|
}
|
|
|
|
impl ConstraintSystem {
|
|
pub fn new(primary_size: usize, aux_size: usize) -> ConstraintSystem {
|
|
ConstraintSystem {
|
|
cs: unsafe { tinysnark_new_r1cs(primary_size, aux_size) },
|
|
primary_size: primary_size,
|
|
aux_size: aux_size
|
|
}
|
|
}
|
|
|
|
pub fn add_constraint(&mut self, a: &[LinearTerm], b: &[LinearTerm], c: &[LinearTerm])
|
|
{
|
|
unsafe {
|
|
tinysnark_add_constraint(
|
|
self.cs,
|
|
a.get_unchecked(0),
|
|
a.len(),
|
|
b.get_unchecked(0),
|
|
b.len(),
|
|
c.get_unchecked(0),
|
|
c.len()
|
|
);
|
|
}
|
|
}
|
|
|
|
pub fn test(&self, primary: &[FieldT], aux: &[FieldT]) -> bool
|
|
{
|
|
assert_eq!(primary.len(), self.primary_size);
|
|
assert_eq!(aux.len(), self.aux_size);
|
|
|
|
unsafe {
|
|
tinysnark_satisfy_test(self.cs, primary.get_unchecked(0), aux.get_unchecked(0))
|
|
}
|
|
}
|
|
}
|
|
|
|
#[repr(C)]
|
|
struct R1CSKeypair;
|
|
|
|
pub struct Keypair {
|
|
kp: *mut R1CSKeypair,
|
|
primary_size: usize,
|
|
aux_size: usize
|
|
}
|
|
|
|
impl Keypair {
|
|
pub fn new(constraint_system: &ConstraintSystem) -> Keypair {
|
|
Keypair {
|
|
kp: unsafe { tinysnark_gen_keypair(constraint_system.cs) },
|
|
primary_size: constraint_system.primary_size,
|
|
aux_size: constraint_system.aux_size
|
|
}
|
|
}
|
|
}
|
|
|
|
impl Drop for Keypair {
|
|
fn drop(&mut self) {
|
|
unsafe { tinysnark_drop_keypair(self.kp) }
|
|
}
|
|
}
|
|
|
|
extern "C" {
|
|
fn tinysnark_gen_keypair(cs: *mut R1ConstraintSystem) -> *mut R1CSKeypair;
|
|
fn tinysnark_drop_keypair(cs: *mut R1CSKeypair);
|
|
}
|
|
|
|
#[repr(C)]
|
|
struct R1CSProof;
|
|
|
|
pub struct Proof {
|
|
proof: *mut R1CSProof
|
|
}
|
|
|
|
impl Proof {
|
|
pub fn new(keypair: &Keypair, primary: &[FieldT], aux: &[FieldT])
|
|
-> Proof
|
|
{
|
|
assert_eq!(primary.len(), keypair.primary_size);
|
|
assert_eq!(aux.len(), keypair.aux_size);
|
|
|
|
unsafe {
|
|
Proof {
|
|
proof: tinysnark_gen_proof(keypair.kp, primary.get_unchecked(0), aux.get_unchecked(0))
|
|
}
|
|
}
|
|
}
|
|
|
|
pub fn verify(&self, keypair: &Keypair, primary: &[FieldT]) -> bool {
|
|
assert_eq!(primary.len(), keypair.primary_size);
|
|
|
|
unsafe {
|
|
tinysnark_verify_proof(self.proof, keypair.kp, primary.get_unchecked(0))
|
|
}
|
|
}
|
|
}
|
|
|
|
impl Drop for Proof {
|
|
fn drop(&mut self) {
|
|
unsafe { tinysnark_drop_proof(self.proof) }
|
|
}
|
|
}
|
|
|
|
extern "C" {
|
|
fn tinysnark_gen_proof(keypair: *mut R1CSKeypair,
|
|
primary: *const FieldT,
|
|
aux: *const FieldT) -> *mut R1CSProof;
|
|
fn tinysnark_verify_proof(proof: *mut R1CSProof,
|
|
keypair: *mut R1CSKeypair,
|
|
primary: *const FieldT) -> bool;
|
|
fn tinysnark_drop_proof(proof: *mut R1CSProof);
|
|
} |