nizk: pass optional random values for signature commitment

This commit is contained in:
Gijs Van Laer 2019-07-21 11:02:36 -04:00
parent 2e5d0d5a29
commit 20650bc7b0
5 changed files with 57 additions and 58 deletions

View File

@ -142,7 +142,7 @@ impl<E: Engine> ParamsUL<E> {
hm.mul_assign(m);
for i in 0..self.l as usize {
let signature = self.signatures.get(&decx[i].to_string()).unwrap();
let proofState = self.kp.prove_commitment(rng, &self.mpk, &signature);
let proofState = self.kp.prove_commitment(rng, &self.mpk, &signature, None, None);
V.push(proofState.blindSig.clone());
proofStates.push(proofState);
@ -642,11 +642,11 @@ mod tests {
let m1 = Fr::rand(rng);
let m2 = Fr::rand(rng);
let sig = kp.sign(rng, &vec! {m1, m2});
let state = kp.prove_commitment(rng, &params, &sig);
let state1 = kp.prove_commitment(rng, &params, &sig);
let state2 = kp.prove_commitment(rng, &params, &sig);
let state3 = kp.prove_commitment(rng, &params, &sig);
let state4 = kp.prove_commitment(rng, &params, &sig);
let state = kp.prove_commitment(rng, &params, &sig, None, None);
let state1 = kp.prove_commitment(rng, &params, &sig, None, None);
let state2 = kp.prove_commitment(rng, &params, &sig, None, None);
let state3 = kp.prove_commitment(rng, &params, &sig, None, None);
let state4 = kp.prove_commitment(rng, &params, &sig, None, None);
let a = vec! {state.a, state1.a, state2.a};
let a2 = vec! {state3.a, state4.a};
assert_eq!(hash::<Bls12>(a.clone(), vec!(D.clone())).is_zero(), false);

View File

@ -192,7 +192,7 @@ impl<E: Engine> CustomerWallet<E> {
// generate nizk proof of knowledge of commitment opening
pub fn generate_proof<R: Rng>(&mut self, csprng: &mut R, channel_token: &ChannelToken<E>) -> CommitmentProof<E> {
return CommitmentProof::<E>::new(csprng, &channel_token.comParams, &self.w_com.c1, &self.w_vec, &self.r);
return CommitmentProof::<E>::new(csprng, &channel_token.comParams, &self.w_com.c, &self.w_vec, &self.r);
}
}
@ -237,7 +237,7 @@ impl<E: Engine> MerchantWallet<E> {
}
pub fn verify_proof<R: Rng>(&self, csprng: &mut R, channel: &ChannelState<E>, com: &Commitment<E>, com_proof: &CommitmentProof<E>) -> Signature<E> {
let is_valid = util::verify(&self.comParams, &com.c1, &com_proof);
let is_valid = util::verify(&self.comParams, &com.c, &com_proof);
let cp = channel.cp.as_ref().unwrap();
if is_valid {
println!("Commitment PoK is valid!");

View File

@ -13,13 +13,13 @@ use std::fmt::LowerHex;
#[derive(Clone)]
pub struct PublicParams<E: Engine> {
pub g1: E::G1,
pub g2: E::G2
pub g2: E::G2,
}
#[derive(Clone)]
pub struct SecretKey<E: Engine> {
pub x: E::Fr,
pub y: Vec<E::Fr>
pub y: Vec<E::Fr>,
}
#[derive(Clone, Serialize, Deserialize)]
@ -61,19 +61,19 @@ pub struct BlindPublicKey<E: Engine> {
#[derive(Clone)]
pub struct Signature<E: Engine> {
pub h: E::G1,
pub H: E::G1
pub H: E::G1,
}
#[derive(Clone)]
pub struct KeyPair<E: Engine> {
pub secret: SecretKey<E>,
pub public: PublicKey<E>
pub public: PublicKey<E>,
}
#[derive(Clone)]
pub struct BlindKeyPair<E: Engine> {
pub secret: SecretKey<E>,
pub public: BlindPublicKey<E>
pub public: BlindPublicKey<E>,
}
#[derive(Clone)]
@ -83,7 +83,7 @@ pub struct ProofState<E: Engine> {
pub t: Vec<E::Fr>,
pub tt: E::Fr,
pub a: E::Fqk,
pub blindSig: Signature<E>
pub blindSig: Signature<E>,
}
#[derive(Clone)]
@ -91,14 +91,14 @@ pub struct SignatureProof<E: Engine> {
pub zx: E::Fr,
pub zsig: Vec<E::Fr>,
pub zv: E::Fr,
pub a: E::Fqk
pub a: E::Fqk,
}
impl<E: Engine> SecretKey<E> {
pub fn generate<R: Rng>(csprng: &mut R, l: usize) -> Self {
let mut y: Vec<E::Fr> = Vec::new();
for i in 0 .. l {
for i in 0..l {
let _y = E::Fr::rand(csprng);
y.push(_y);
}
@ -111,7 +111,7 @@ impl<E: Engine> SecretKey<E> {
let mut s = E::Fr::zero();
// check vector length first
assert_eq!(self.y.len(), message.len());
for i in 0 .. message.len() {
for i in 0..message.len() {
// s = s + (self.y[i] * message[i]);
let mut res_yi = self.y[i];
res_yi.mul_assign(&message[i]);
@ -143,7 +143,6 @@ impl<E: Engine> SecretKey<E> {
H1.mul_assign(r);
Signature { h: h1, H: H1 }
}
}
@ -186,7 +185,7 @@ impl<E: Engine> SecretKey<E> {
impl<E: Engine> PublicKey<E> {
pub fn from_secret(mpk: &PublicParams<E>, secret: &SecretKey<E>) -> Self {
let mut Y: Vec<E::G2> = Vec::new();
for i in 0 .. secret.y.len() {
for i in 0..secret.y.len() {
// Y[i] = g2 ^ y[i]
let mut g2 = mpk.g2;
g2.mul_assign(secret.y[i]);
@ -197,13 +196,13 @@ impl<E: Engine> PublicKey<E> {
X.mul_assign(secret.x);
PublicKey {
X: X,
Y: Y
Y: Y,
}
}
pub fn verify(&self, mpk: &PublicParams<E>, message: &Vec<E::Fr>, signature: &Signature<E>) -> bool {
let mut L = E::G2::zero();
for i in 0 .. self.Y.len() {
for i in 0..self.Y.len() {
// L = L + self.Y[i].mul(message[i]);
let mut Y = self.Y[i];
Y.mul_assign(message[i]); // Y_i ^ m_i
@ -218,7 +217,7 @@ impl<E: Engine> PublicKey<E> {
}
}
impl<E: Engine> BlindPublicKey<E> {
impl<E: Engine> BlindPublicKey<E> {
pub fn from_secret(mpk: &PublicParams<E>, secret: &SecretKey<E>) -> Self {
let mut Y1: Vec<E::G1> = Vec::new();
let mut Y2: Vec<E::G2> = Vec::new();
@ -241,7 +240,7 @@ impl<E: Engine> BlindPublicKey<E> {
X1: X1,
X2: X2,
Y1: Y1,
Y2: Y2
Y2: Y2,
}
}
@ -250,7 +249,7 @@ impl<E: Engine> BlindPublicKey<E> {
let l = self.Y2.len();
assert_eq!(message.len(), l + 1);
for i in 0 .. l {
for i in 0..l {
// L = L + self.Y[i].mul(message[i]);
let mut Y = self.Y2[i];
Y.mul_assign(message[i]); // Y_i ^ m_i
@ -288,11 +287,9 @@ impl<E: Engine> BlindPublicKey<E> {
g.mul_assign(&p.a);
gx == g
}
}
pub fn setup<R: Rng, E: Engine>(csprng: &mut R) -> PublicParams<E> {
let g1 = E::G1::rand(csprng);
let g2 = E::G2::rand(csprng);
@ -335,7 +332,7 @@ impl<E: Engine> BlindKeyPair<E> {
let mut com_bases = vec! {mpk.g1};
com_bases.append(&mut self.public.Y1.clone());
CSMultiParams { pub_bases: com_bases}
CSMultiParams { pub_bases: com_bases }
}
/// extract unblinded public key
@ -391,16 +388,19 @@ impl<E: Engine> BlindKeyPair<E> {
/// prove knowledge of a signature: commitment phase
/// returns the proof state, including commitment a and a blind signature blindSig
pub fn prove_commitment<R: Rng>(&self, rng: &mut R, mpk: &PublicParams<E>, signature: &Signature<E>) -> ProofState<E> {
pub fn prove_commitment<R: Rng>(&self, rng: &mut R, mpk: &PublicParams<E>, signature: &Signature<E>,
tOptional: Option<Vec<E::Fr>>, ttOptional: Option<E::Fr>) -> ProofState<E> {
let v = E::Fr::rand(rng);
let blindSig = self.blind(rng, &v, signature);
let s = E::Fr::rand(rng);
let mut t = Vec::<E::Fr>::with_capacity(self.public.Y2.len());
let tt = E::Fr::rand(rng);
let mut t = tOptional.unwrap_or(Vec::<E::Fr>::with_capacity(self.public.Y2.len()));
let tt = ttOptional.unwrap_or(E::Fr::rand(rng));
let mut gx = E::pairing(blindSig.h, self.public.X2);
gx = gx.pow(s.into_repr());
for j in 0..self.public.Y2.len() {
t.push(E::Fr::rand(rng));
if t.len() == j {
t.push(E::Fr::rand(rng));
}
let mut gy = E::pairing(blindSig.h, self.public.Y2[j]);
gy = gy.pow(t[j].into_repr());
gx.mul_assign(&gy);
@ -426,7 +426,7 @@ impl<E: Engine> BlindKeyPair<E> {
let mut vic = ps.v.clone();
vic.mul_assign(&challenge);
zv.add_assign(&vic);
SignatureProof {zsig, zx, zv, a: ps.a }
SignatureProof { zsig, zx, zv, a: ps.a }
}
}
@ -458,7 +458,7 @@ mod tests {
use ff::Rand;
use pairing::bls12_381::{Bls12, Fr};
use rand::{SeedableRng};
use rand::SeedableRng;
use rand_xorshift::XorShiftRng;
use ped92::CSMultiParams;
@ -475,8 +475,8 @@ mod tests {
println!("PUBLIC KEY => {}", keypair.public);
let mut message1 : Vec<Fr> = Vec::new();
let mut message2 : Vec<Fr> = Vec::new();
let mut message1: Vec<Fr> = Vec::new();
let mut message2: Vec<Fr> = Vec::new();
for i in 0..l {
message1.push(Fr::rand(&mut rng));
@ -499,8 +499,8 @@ mod tests {
let public_key = keypair.get_public_key(&mpk);
let mut message1 : Vec<Fr> = Vec::new();
let mut message2 : Vec<Fr> = Vec::new();
let mut message1: Vec<Fr> = Vec::new();
let mut message2: Vec<Fr> = Vec::new();
for i in 0..l {
message1.push(Fr::rand(&mut rng));
@ -512,15 +512,15 @@ mod tests {
assert_eq!(public_key.verify(&mpk, &message2, &sig), false);
let t = Fr::rand(&mut rng);
let blind_sig = keypair.blind(&mut rng, &t,&sig);
let blind_sig = keypair.blind(&mut rng, &t, &sig);
// pick another blinding factor
let t1 = Fr::rand(&mut rng);
// verify blind signatures and provide blinding factor as input
assert_eq!(keypair.verify(&mpk,&message1, &t,&blind_sig), true);
assert_eq!(keypair.verify(&mpk,&message2, &t,&blind_sig), false);
assert_eq!(keypair.verify(&mpk,&message1, &t1,&blind_sig), false);
assert_eq!(keypair.verify(&mpk, &message1, &t, &blind_sig), true);
assert_eq!(keypair.verify(&mpk, &message2, &t, &blind_sig), false);
assert_eq!(keypair.verify(&mpk, &message1, &t1, &blind_sig), false);
}
#[test]
@ -532,7 +532,7 @@ mod tests {
let mpk = setup(&mut rng);
let keypair = BlindKeyPair::<Bls12>::generate(&mut rng, &mpk, l);
let mut message1 : Vec<Fr> = Vec::new();
let mut message1: Vec<Fr> = Vec::new();
for i in 0..l {
message1.push(Fr::rand(&mut rng));
@ -559,8 +559,8 @@ mod tests {
let public_key = keypair.get_public_key(&mpk);
let mut message1 : Vec<Fr> = Vec::new();
let mut message2 : Vec<Fr> = Vec::new();
let mut message1: Vec<Fr> = Vec::new();
let mut message2: Vec<Fr> = Vec::new();
for i in 0..l {
message1.push(Fr::rand(&mut rng));
@ -577,11 +577,11 @@ mod tests {
let t1 = Fr::rand(&mut rng);
assert_eq!(keypair.get_public_key(&mpk).verify(&mpk,&message1, &unblinded_sig), true);
assert_eq!(keypair.verify(&mpk,&message1, &t, &signature), true);
assert_eq!(keypair.get_public_key(&mpk).verify(&mpk,&message2, &unblinded_sig), false);
assert_eq!(keypair.verify(&mpk,&message2, &t, &signature), false);
assert_eq!(keypair.verify(&mpk,&message1, &t1, &signature), false);
assert_eq!(keypair.get_public_key(&mpk).verify(&mpk, &message1, &unblinded_sig), true);
assert_eq!(keypair.verify(&mpk, &message1, &t, &signature), true);
assert_eq!(keypair.get_public_key(&mpk).verify(&mpk, &message2, &unblinded_sig), false);
assert_eq!(keypair.verify(&mpk, &message2, &t, &signature), false);
assert_eq!(keypair.verify(&mpk, &message1, &t1, &signature), false);
}
#[test]
@ -594,19 +594,18 @@ mod tests {
let public_key = keypair.get_public_key(&mpk);
let mut message1 : Vec<Fr> = Vec::new();
let mut message1: Vec<Fr> = Vec::new();
for i in 0..l {
message1.push(Fr::rand(&mut rng));
}
let sig = keypair.sign(&mut rng, &message1);
let proof_state = keypair.prove_commitment(rng, &mpk, &sig);
let proof_state = keypair.prove_commitment(rng, &mpk, &sig, None, None);
let challenge = Fr::rand(&mut rng);
let proof = keypair.prove_response(&proof_state.clone(), challenge, &mut message1);
assert_eq!(keypair.public.verify_proof(&mpk, proof_state.blindSig, proof, challenge), true);
}
}

View File

@ -55,9 +55,6 @@ impl<E: Engine> NIZKPublicParams<E> {
h.mul_assign(t2);
T.add_assign(&h);
//commit signature
let proofState = self.keypair.prove_commitment(rng, &self.mpk, &paymentToken);
//commit commitment
let mut D = E::G1::zero();
let mut t = Vec::<E::Fr>::with_capacity(self.comParams.pub_bases.len() - 1);
@ -69,6 +66,9 @@ impl<E: Engine> NIZKPublicParams<E> {
D.add_assign(&gt);
}
//commit signature
let proofState = self.keypair.prove_commitment(rng, &self.mpk, &paymentToken, Some(t[1..].to_vec()), Some(t[0].clone()));
//commit range proof
let rpStateBC = self.rpParamsBC.prove_commitment(rng, newWallet.bc.clone(), newWalletCom.clone(), 3);
let rpStateBM = self.rpParamsBM.prove_commitment(rng, newWallet.bm.clone(), newWalletCom.clone(), 4);

View File

@ -70,8 +70,8 @@ pub struct CommitmentProof<E: Engine> {
impl<E: Engine> CommitmentProof<E> {
pub fn new<R: Rng>(csprng: &mut R, com_params: &CSMultiParams<E>, com: &E::G1, wallet: &Vec<E::Fr>, r: &E::Fr) -> Self {
let mut Tvals = E::G1::zero();
let mut t = Vec::<E::Fr>::with_capacity(com_params.pub_bases1.len() - 1);
for g in com_params.pub_bases1.clone() {
let mut t = Vec::<E::Fr>::with_capacity(com_params.pub_bases.len() - 1);
for g in com_params.pub_bases.clone() {
let ti = E::Fr::rand(csprng);
t.push(ti);
let mut gt = g.clone();
@ -118,7 +118,7 @@ pub fn verify<E: Engine>(com_params: &CSMultiParams<E>, com: &E::G1, proof: &Com
let mut x = E::G1::zero();
for i in 0..proof.z.len() {
let mut base = com_params.pub_bases1[i].clone();
let mut base = com_params.pub_bases[i].clone();
base.mul_assign(proof.z[i].into_repr());
x.add_assign(&base);
}