Skip to content

Commit

Permalink
add support to tapyrus setup to sign xfield
Browse files Browse the repository at this point in the history
add test for xfield signature generation
  • Loading branch information
Naviabheeman committed Dec 4, 2023
1 parent b3e4b51 commit 883059f
Show file tree
Hide file tree
Showing 8 changed files with 514 additions and 56 deletions.
190 changes: 172 additions & 18 deletions src/cli/setup/compute_sig.rs

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion src/cli/setup/create_block_vss.rs
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ impl<'a> CreateBlockVssCommand {
.long("threshold")
.required(true)
.takes_value(true)
.help("the minimum number of signers required to sign block"),
.help("the minimum number of signers required to sign block/xfield change"),
])
}
}
Expand Down
179 changes: 165 additions & 14 deletions src/cli/setup/sign.rs

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion src/crypto/multi_party_schnorr.rs
Original file line number Diff line number Diff line change
Expand Up @@ -256,7 +256,7 @@ impl LocalSig {
}
}

#[derive(Clone, Serialize, Deserialize)]
#[derive(Clone, Debug, Serialize, Deserialize, PartialEq)]
pub struct Signature {
pub sigma: FE,
pub v: GE,
Expand Down
171 changes: 154 additions & 17 deletions src/crypto/vss.rs
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ use std::collections::BTreeMap;
use std::fmt;
use std::io;
use std::str::FromStr;
use tapyrus::blockdata::block::Block;
use tapyrus::blockdata::block::{Block, XField};
use tapyrus::consensus::encode::{self, *};
use tapyrus::util::prime::jacobi;
use tapyrus::{PrivateKey, PublicKey};
Expand Down Expand Up @@ -119,6 +119,32 @@ impl Vss {
}

pub fn create_local_sig_from_shares(
_priv_shared_keys: &SharedKeys,
index: usize,
shared_block_secrets: &BidirectionalSharedSecretMap,
local_sig_for_positive: &LocalSig,
local_sig_for_negative: &LocalSig,
) -> Result<(bool, SharedKeys, LocalSig), Error> {
let shared_keys_for_positive =
Sign::verify_vss_and_construct_key(&shared_block_secrets.for_positive(), &index)?;

let shared_keys_for_negative =
Sign::verify_vss_and_construct_key(&shared_block_secrets.for_negative(), &index)?;

let y = shared_keys_for_positive
.y
.y_coor()
.expect("can not get y_coor");
let is_positive = jacobi(&Converter::to_vec(&y)) == 1;
let (shared_keys, local_sig) = if is_positive {
(shared_keys_for_positive, local_sig_for_positive)
} else {
(shared_keys_for_negative, local_sig_for_negative)
};
Ok((is_positive, shared_keys, local_sig.clone()))
}

pub fn create_local_sig_from_shares_for_block(
priv_shared_keys: &SharedKeys,
index: usize,
shared_block_secrets: &BidirectionalSharedSecretMap,
Expand All @@ -139,22 +165,47 @@ impl Vss {
&priv_shared_keys,
block.header.signature_hash(),
);
Self::create_local_sig_from_shares(
priv_shared_keys,
index,
shared_block_secrets,
&local_sig_for_positive,
&local_sig_for_negative,
)
}

let y = shared_keys_for_positive
.y
.y_coor()
.expect("can not get y_coor");
let is_positive = jacobi(&Converter::to_vec(&y)) == 1;
let (shared_keys, local_sig) = if is_positive {
(shared_keys_for_positive, local_sig_for_positive)
} else {
(shared_keys_for_negative, local_sig_for_negative)
};
Ok((is_positive, shared_keys, local_sig))
pub fn create_local_sig_from_shares_for_xfield(
priv_shared_keys: &SharedKeys,
index: usize,
shared_block_secrets: &BidirectionalSharedSecretMap,
xfield: &XField,
) -> Result<(bool, SharedKeys, LocalSig), Error> {
let shared_keys_for_positive =
Sign::verify_vss_and_construct_key(&shared_block_secrets.for_positive(), &index)?;
let local_sig_for_positive = Sign::sign_xfield(
&shared_keys_for_positive,
&priv_shared_keys,
xfield.signature_hash()?,
);

let shared_keys_for_negative =
Sign::verify_vss_and_construct_key(&shared_block_secrets.for_negative(), &index)?;
let local_sig_for_negative = Sign::sign_xfield(
&shared_keys_for_negative,
&priv_shared_keys,
xfield.signature_hash()?,
);
Self::create_local_sig_from_shares(
priv_shared_keys,
index,
shared_block_secrets,
&local_sig_for_positive,
&local_sig_for_negative,
)
}

pub fn aggregate_and_verify_signature(
block: &Block,
hash: &[u8],
signatures: BTreeMap<SignerID, (FE, FE)>,
pubkey_list: &Vec<PublicKey>,
shared_secrets: &SharedSecretMap,
Expand Down Expand Up @@ -189,7 +240,6 @@ impl Vss {
block_shared_keys.unwrap().2,
);
let public_key = priv_shared_keys.y;
let hash = block.header.signature_hash();
signature.verify(&hash[..], &public_key)?;
Ok(signature)
}
Expand Down Expand Up @@ -544,9 +594,13 @@ mod tests {
})
.collect();

let (is_positive, key, local_sig) =
Vss::create_local_sig_from_shares(&priv_shared_keys, 1, &shared_block_secrets, &block)
.expect("error occurred in Vss::create_local_sig_from_shares");
let (is_positive, key, local_sig) = Vss::create_local_sig_from_shares_for_block(
&priv_shared_keys,
1,
&shared_block_secrets,
&block,
)
.expect("error occurred in Vss::create_local_sig_from_shares");

let expected_localsig = to_local_sig(&v["expected_localsig"]).unwrap();
let expected_block_shared_keys =
Expand All @@ -557,4 +611,87 @@ mod tests {
assert_eq!(key.x_i, expected_block_shared_keys.1);
assert_eq!(key.y, expected_block_shared_keys.2);
}

#[test]
fn test_create_local_sig_from_shares_xfield1() {
let contents = load_test_vector("./tests/resources/vss.json").unwrap();
let v: Value =
serde_json::from_value(contents["create_local_sig_from_shares_successfully"].clone())
.unwrap();
let priv_shared_keys: SharedKeys =
serde_json::from_value(v["priv_shared_key"].clone()).unwrap();
let xfield: XField = XField::AggregatePublicKey(
PublicKey::from_str(
"025700236c2890233592fcef262f4520d22af9160e3d9705855140eb2aa06c35d3",
)
.unwrap(),
);
let shared_block_secrets = v["shared_block_secrets"]
.as_object()
.unwrap()
.iter()
.map(|(k, value)| {
(
to_signer_id(k),
(to_shared_secret(&value[0]), to_shared_secret(&value[1])),
)
})
.collect();

let (is_positive, key, local_sig) = Vss::create_local_sig_from_shares_for_xfield(
&priv_shared_keys,
1,
&shared_block_secrets,
&xfield,
)
.expect("error occurred in Vss::create_local_sig_from_shares");

let expected_localsig = to_local_sig(&v["expected_localsig"]).unwrap();
let expected_block_shared_keys =
to_block_shared_keys(&v["expected_block_shared_keys"]).unwrap();

assert_eq!(false, is_positive);
assert_eq!(key.x_i, expected_block_shared_keys.1);
assert_eq!(key.y, expected_block_shared_keys.2);
//TODO : check signature
}

#[test]
fn test_create_local_sig_from_shares_xfield2() {
let contents = load_test_vector("./tests/resources/vss.json").unwrap();
let v: Value =
serde_json::from_value(contents["create_local_sig_from_shares_successfully"].clone())
.unwrap();
let priv_shared_keys: SharedKeys =
serde_json::from_value(v["priv_shared_key"].clone()).unwrap();
let xfield: XField = XField::MaxBlockSize(100);
let shared_block_secrets = v["shared_block_secrets"]
.as_object()
.unwrap()
.iter()
.map(|(k, value)| {
(
to_signer_id(k),
(to_shared_secret(&value[0]), to_shared_secret(&value[1])),
)
})
.collect();

let (is_positive, key, local_sig) = Vss::create_local_sig_from_shares_for_xfield(
&priv_shared_keys,
1,
&shared_block_secrets,
&xfield,
)
.expect("error occurred in Vss::create_local_sig_from_shares");

let expected_localsig = to_local_sig(&v["expected_localsig"]).unwrap();
let expected_block_shared_keys =
to_block_shared_keys(&v["expected_block_shared_keys"]).unwrap();

assert_eq!(false, is_positive);
assert_eq!(key.x_i, expected_block_shared_keys.1);
assert_eq!(key.y, expected_block_shared_keys.2);
//TODO : check signature
}
}
10 changes: 10 additions & 0 deletions src/sign.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ use curv::arithmetic::traits::*;
use curv::cryptographic_primitives::secret_sharing::feldman_vss::VerifiableSS;
use curv::elliptic::curves::traits::*;
use curv::{BigInt, FE, GE};
use tapyrus::XFieldHash;

use crate::errors::Error;
use crate::signer_node::SharedSecretMap;
Expand Down Expand Up @@ -78,6 +79,15 @@ impl Sign {
local_sig
}

pub fn sign_xfield(
eph_shared_keys: &SharedKeys,
priv_shared_keys: &SharedKeys,
message: XFieldHash,
) -> LocalSig {
let local_sig = LocalSig::compute(&message[..], &eph_shared_keys, &priv_shared_keys);
local_sig
}

pub fn aggregate(
vss_sum: &VerifiableSS,
local_sigs: &Vec<LocalSig>,
Expand Down
2 changes: 1 addition & 1 deletion src/signer_node/message_processor/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -131,7 +131,7 @@ where
let block_height = prev_state.block_height();
let federation = params.get_federation_by_block_height(block_height);

Vss::create_local_sig_from_shares(
Vss::create_local_sig_from_shares_for_block(
&federation.node_secret_share(),
params.self_node_index(block_height) + 1,
shared_block_secrets,
Expand Down
14 changes: 10 additions & 4 deletions src/signer_node/message_processor/process_blocksig.rs
Original file line number Diff line number Diff line change
Expand Up @@ -132,7 +132,7 @@ where
let federation = params.get_federation_by_block_height(block_height);

let signature = match Vss::aggregate_and_verify_signature(
candidate_block,
&candidate_block.header.signature_hash(),
new_signatures,
&params.pubkey_list(block_height),
&federation.node_shared_secrets(),
Expand Down Expand Up @@ -415,7 +415,9 @@ mod tests {
0,
Some(dump.threshold as u8),
Some(dump.node_vss.clone()),
dump.aggregated_public_key,
XField::AggregatePublicKey(dump.aggregated_public_key),
None,
None,
)];
let federations = Federations::new(federations);
let params = NodeParametersBuilder::new()
Expand Down Expand Up @@ -459,7 +461,9 @@ mod tests {
0,
Some(dump.threshold as u8),
Some(dump.node_vss.clone()),
dump.aggregated_public_key,
XField::AggregatePublicKey(dump.aggregated_public_key),
None,
None,
)];
let federations = Federations::new(federations);
let params = NodeParametersBuilder::new()
Expand Down Expand Up @@ -505,7 +509,9 @@ mod tests {
0,
Some(dump.threshold as u8),
Some(dump.node_vss.clone()),
dump.aggregated_public_key,
XField::AggregatePublicKey(dump.aggregated_public_key),
None,
None,
)];
let federations = Federations::new(federations);
let params = NodeParametersBuilder::new()
Expand Down

0 comments on commit 883059f

Please sign in to comment.