Implement verification.
This commit is contained in:
parent
d3b20d0f21
commit
d761316579
|
@ -1,7 +1,7 @@
|
|||
use thiserror::Error;
|
||||
|
||||
/// An error related to RedJubJub signatures.
|
||||
#[derive(Error, Debug)]
|
||||
#[derive(Error, Debug, Copy, Clone, Eq, PartialEq)]
|
||||
pub enum Error {
|
||||
/// The encoding of a secret key was malformed.
|
||||
#[error("Malformed secret key encoding.")]
|
||||
|
@ -9,4 +9,7 @@ pub enum Error {
|
|||
/// The encoding of a public key was malformed.
|
||||
#[error("Malformed public key encoding.")]
|
||||
MalformedPublicKey,
|
||||
/// Signature verification failed.
|
||||
#[error("Invalid signature.")]
|
||||
InvalidSignature,
|
||||
}
|
||||
|
|
|
@ -75,22 +75,50 @@ impl<T: SigType> PublicKey<T> {
|
|||
pub fn randomize(&self, randomizer: Randomizer) -> PublicKey<T> {
|
||||
unimplemented!();
|
||||
}
|
||||
}
|
||||
|
||||
impl PublicKey<Binding> {
|
||||
/// Verify a Zcash `BindingSig` over `msg` made by this public key.
|
||||
/// Verify a purported `signature` over `msg` made by this public key.
|
||||
// This is similar to impl signature::Verifier but without boxed errors
|
||||
pub fn verify(&self, msg: &[u8], signature: &Signature<Binding>) -> Result<(), Error> {
|
||||
// this lets us specialize the basepoint parameter, could call a verify_inner
|
||||
unimplemented!();
|
||||
}
|
||||
}
|
||||
use crate::HStar;
|
||||
|
||||
impl PublicKey<SpendAuth> {
|
||||
/// Verify a Zcash `SpendAuthSig` over `msg` made by this public key.
|
||||
// This is similar to impl signature::Verifier but without boxed errors
|
||||
pub fn verify(&self, msg: &[u8], signature: &Signature<SpendAuth>) -> Result<(), Error> {
|
||||
// this lets us specialize the basepoint parameter, could call a verify_inner
|
||||
unimplemented!();
|
||||
let r = {
|
||||
// XXX-jubjub: should not use CtOption here
|
||||
// XXX-jubjub: inconsistent ownership in from_bytes
|
||||
let maybe_point = jubjub::AffinePoint::from_bytes(signature.r_bytes);
|
||||
if maybe_point.is_some().into() {
|
||||
jubjub::ExtendedPoint::from(maybe_point.unwrap())
|
||||
} else {
|
||||
return Err(Error::InvalidSignature);
|
||||
}
|
||||
};
|
||||
|
||||
let s = {
|
||||
// XXX-jubjub: should not use CtOption here
|
||||
let maybe_scalar = Scalar::from_bytes(&signature.s_bytes);
|
||||
if maybe_scalar.is_some().into() {
|
||||
maybe_scalar.unwrap()
|
||||
} else {
|
||||
return Err(Error::InvalidSignature);
|
||||
}
|
||||
};
|
||||
|
||||
let c = HStar::default()
|
||||
.update(&signature.r_bytes[..])
|
||||
.update(&self.bytes.bytes[..]) // XXX ugly
|
||||
.update(msg)
|
||||
.finalize();
|
||||
|
||||
// XXX rewrite as normal double scalar mul
|
||||
// Verify check is h * ( - s * B + R + c * A) == 0
|
||||
// h * ( s * B - c * A - R) == 0
|
||||
let sB = &T::basepoint() * &s;
|
||||
let cA = &self.point * &c;
|
||||
let check = sB - cA - r;
|
||||
|
||||
if check.is_small_order().into() {
|
||||
Ok(())
|
||||
} else {
|
||||
Err(Error::InvalidSignature)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -13,6 +13,12 @@ pub struct SecretKey<T: SigType> {
|
|||
pk: PublicKey<T>,
|
||||
}
|
||||
|
||||
impl<'a, T: SigType> From<&'a SecretKey<T>> for PublicKey<T> {
|
||||
fn from(sk: &'a SecretKey<T>) -> PublicKey<T> {
|
||||
sk.pk.clone()
|
||||
}
|
||||
}
|
||||
|
||||
impl<T: SigType> From<SecretKey<T>> for [u8; 32] {
|
||||
fn from(sk: SecretKey<T>) -> [u8; 32] {
|
||||
sk.sk.to_bytes()
|
||||
|
@ -79,7 +85,7 @@ impl<T: SigType> SecretKey<T> {
|
|||
|
||||
let s_bytes = (&nonce + &(&c * &self.sk)).to_bytes();
|
||||
|
||||
Signature{
|
||||
Signature {
|
||||
r_bytes,
|
||||
s_bytes,
|
||||
_marker: PhantomData,
|
||||
|
|
|
@ -32,4 +32,3 @@ impl<T: SigType> From<Signature<T>> for [u8; 64] {
|
|||
bytes
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue