Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(crypto): CRP-2609 Introduce master key ID variant for vetKD #2108

Merged
merged 16 commits into from
Oct 29, 2024
Merged
Show file tree
Hide file tree
Changes from 11 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
2 changes: 2 additions & 0 deletions rs/consensus/src/idkg/payload_builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1082,6 +1082,7 @@ mod tests {
signature: vec![2; 32],
})
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
},
);

Expand Down Expand Up @@ -1924,6 +1925,7 @@ mod tests {
&mut rng,
))
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
payload_0.available_pre_signatures.insert(
payload_0.uid_generator.next_pre_signature_id(),
Expand Down
24 changes: 18 additions & 6 deletions rs/consensus/src/idkg/payload_builder/pre_signatures.rs
Original file line number Diff line number Diff line change
Expand Up @@ -359,6 +359,12 @@ fn make_new_pre_signatures_if_needed_helper(
let Some(pre_signatures_to_create) = chain_key_config
.key_configs
.iter()
.filter(|key_config| {
matches!(
&key_config.key_id,
MasterPublicKeyId::Ecdsa(_) | MasterPublicKeyId::Schnorr(_)
)
})
.find(|key_config| &key_config.key_id == key_id)
.map(|key_config| key_config.pre_signatures_to_create_in_advance as usize)
else {
Expand All @@ -370,7 +376,7 @@ fn make_new_pre_signatures_if_needed_helper(
}

for _ in 0..(pre_signatures_to_create - unassigned_pre_signatures) {
let pre_signature = match key_id {
match key_id {
MasterPublicKeyId::Ecdsa(ecdsa_key_id) => {
let kappa_config = new_random_unmasked_config(
key_id,
Expand All @@ -380,11 +386,12 @@ fn make_new_pre_signatures_if_needed_helper(
);
let lambda_config =
new_random_config(key_id, subnet_nodes, registry_version, uid_generator);
PreSignatureInCreation::Ecdsa(QuadrupleInCreation::new(
let pre_signature = PreSignatureInCreation::Ecdsa(QuadrupleInCreation::new(
ecdsa_key_id.clone(),
kappa_config,
lambda_config,
))
));
new_pre_signatures.insert(uid_generator.next_pre_signature_id(), pre_signature);
}
MasterPublicKeyId::Schnorr(schnorr_key_id) => {
let blinder_config = new_random_unmasked_config(
Expand All @@ -393,13 +400,16 @@ fn make_new_pre_signatures_if_needed_helper(
registry_version,
uid_generator,
);
PreSignatureInCreation::Schnorr(TranscriptInCreation::new(
let pre_signature = PreSignatureInCreation::Schnorr(TranscriptInCreation::new(
schnorr_key_id.clone(),
blinder_config,
))
));
new_pre_signatures.insert(uid_generator.next_pre_signature_id(), pre_signature);
}
MasterPublicKeyId::VetKd(_vetkd_key_id) => {
// vetKD does not have pre-signatures
}
};
new_pre_signatures.insert(uid_generator.next_pre_signature_id(), pre_signature);
}

new_pre_signatures
Expand Down Expand Up @@ -495,6 +505,7 @@ pub(super) mod test_utils {
blinder_config_ref,
))
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
let configs = pre_signature
.iter_transcript_configs_in_creation()
Expand Down Expand Up @@ -709,6 +720,7 @@ pub(super) mod tests {
let expected_transcript_ids = match key_id {
MasterPublicKeyId::Ecdsa(_) => 2 * expected_pre_signatures_in_creation,
MasterPublicKeyId::Schnorr(_) => expected_pre_signatures_in_creation,
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
assert_eq!(transcript_ids.len(), expected_transcript_ids);
assert_eq!(
Expand Down
1 change: 1 addition & 0 deletions rs/consensus/src/idkg/payload_builder/signatures.rs
Original file line number Diff line number Diff line change
Expand Up @@ -311,6 +311,7 @@ mod tests {
signature: vec![i as u8; 32],
})
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
},
);
}
Expand Down
2 changes: 2 additions & 0 deletions rs/consensus/src/idkg/payload_verifier.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1043,6 +1043,7 @@ mod test {
MasterPublicKeyId::Schnorr(_) => {
SignWithSchnorrReply { signature: vec![] }.encode()
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
}),
));

Expand Down Expand Up @@ -1076,6 +1077,7 @@ mod test {
fake_schnorr_master_public_key_id(SchnorrAlgorithm::Ed25519)
}
MasterPublicKeyId::Schnorr(_) => fake_ecdsa_master_public_key_id(),
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
// Add a pre-signature for the "wrong_key_id"
insert_test_sig_inputs(
Expand Down
4 changes: 4 additions & 0 deletions rs/consensus/src/idkg/signer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1101,6 +1101,7 @@ mod tests {
fake_schnorr_master_public_key_id(SchnorrAlgorithm::Ed25519)
}
MasterPublicKeyId::Schnorr(_) => fake_ecdsa_master_public_key_id(),
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};

// Set up the signature requests
Expand Down Expand Up @@ -1288,6 +1289,7 @@ mod tests {
let expected_complaints_count = match key_id {
MasterPublicKeyId::Ecdsa(_) => requested_signatures_count * 5,
MasterPublicKeyId::Schnorr(_) => requested_signatures_count * 2,
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
let complaints = transcript_loader.returned_complaints();
assert_eq!(change_set.len(), complaints.len());
Expand Down Expand Up @@ -1368,6 +1370,7 @@ mod tests {
ThresholdSigInputs::Schnorr(inputs),
)
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
};
let crypto = env
.nodes
Expand Down Expand Up @@ -1548,6 +1551,7 @@ mod tests {
fake_schnorr_master_public_key_id(SchnorrAlgorithm::Ed25519)
}
MasterPublicKeyId::Schnorr(_) => fake_ecdsa_master_public_key_id(),
MasterPublicKeyId::VetKd(_) => fake_vetkd_master_public_key_id(),
eichhorl marked this conversation as resolved.
Show resolved Hide resolved
};
let message = create_signature_share(&key_id_wrong_scheme, NODE_2, id_2.clone());
let msg_id_2 = message.message_id();
Expand Down
16 changes: 15 additions & 1 deletion rs/consensus/src/idkg/test_utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,9 @@ use ic_crypto_tree_hash::{LabeledTree, MixedHashTree};
use ic_interfaces::idkg::{IDkgChangeAction, IDkgPool};
use ic_interfaces_state_manager::{CertifiedStateSnapshot, Labeled};
use ic_logger::ReplicaLogger;
use ic_management_canister_types::{EcdsaKeyId, MasterPublicKeyId, SchnorrAlgorithm, SchnorrKeyId};
use ic_management_canister_types::{
EcdsaKeyId, MasterPublicKeyId, SchnorrAlgorithm, SchnorrKeyId, VetKdKeyId,
};
use ic_metrics::MetricsRegistry;
use ic_replicated_state::metadata_state::subnet_call_context_manager::{
EcdsaArguments, IDkgDealingsContext, SchnorrArguments, SignWithThresholdContext,
Expand Down Expand Up @@ -97,6 +99,7 @@ fn fake_signature_request_args(key_id: MasterPublicKeyId) -> ThresholdArguments
key_id,
message: Arc::new(vec![1; 48]),
}),
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
}
}

Expand Down Expand Up @@ -1152,6 +1155,7 @@ pub(crate) fn create_sig_inputs_with_args(
MasterPublicKeyId::Schnorr(key_id) => {
create_schnorr_sig_inputs_with_args(caller, receivers, key_unmasked, height, key_id)
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
}
}

Expand Down Expand Up @@ -1356,6 +1360,7 @@ pub(crate) fn create_signature_share_with_nonce(
sig_share_raw: vec![nonce],
},
}),
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
}
}

Expand Down Expand Up @@ -1617,6 +1622,7 @@ pub(crate) fn key_id_with_name(key_id: &MasterPublicKeyId, name: &str) -> Master
match key_id {
MasterPublicKeyId::Ecdsa(ref mut key_id) => key_id.name = name.into(),
MasterPublicKeyId::Schnorr(ref mut key_id) => key_id.name = name.into(),
MasterPublicKeyId::VetKd(ref mut key_id) => key_id.name = name.into(),
}
key_id
}
Expand Down Expand Up @@ -1648,6 +1654,14 @@ pub(crate) fn schnorr_algorithm(algorithm: AlgorithmId) -> SchnorrAlgorithm {
}
}

pub(crate) fn fake_vetkd_key_id() -> VetKdKeyId {
VetKdKeyId::from_str("Bls12_381:some_key").unwrap()
}

pub(crate) fn fake_vetkd_master_public_key_id() -> MasterPublicKeyId {
MasterPublicKeyId::VetKd(fake_vetkd_key_id())
}

eichhorl marked this conversation as resolved.
Show resolved Hide resolved
pub(crate) fn fake_master_public_key_ids_for_all_algorithms() -> Vec<MasterPublicKeyId> {
AlgorithmId::iter()
.flat_map(|alg| match alg {
Expand Down
5 changes: 4 additions & 1 deletion rs/consensus/src/idkg/utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ use ic_interfaces::consensus_pool::ConsensusBlockChain;
use ic_interfaces::idkg::{IDkgChangeAction, IDkgChangeSet, IDkgPool};
use ic_interfaces_registry::RegistryClient;
use ic_logger::{warn, ReplicaLogger};
use ic_management_canister_types::{EcdsaCurve, MasterPublicKeyId, SchnorrAlgorithm};
use ic_management_canister_types::{EcdsaCurve, MasterPublicKeyId, SchnorrAlgorithm, VetKdCurve};
use ic_protobuf::registry::subnet::v1 as pb;
use ic_registry_client_helpers::subnet::SubnetRegistry;
use ic_registry_subnet_features::ChainKeyConfig;
Expand Down Expand Up @@ -443,6 +443,9 @@ pub(crate) fn algorithm_for_key_id(key_id: &MasterPublicKeyId) -> AlgorithmId {
SchnorrAlgorithm::Bip340Secp256k1 => AlgorithmId::ThresholdSchnorrBip340,
SchnorrAlgorithm::Ed25519 => AlgorithmId::ThresholdEd25519,
},
MasterPublicKeyId::VetKd(vetkd_key_id) => match vetkd_key_id.curve {
VetKdCurve::Bls12_381_G2 => AlgorithmId::Placeholder,
},
}
}

Expand Down
2 changes: 2 additions & 0 deletions rs/consensus/utils/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -860,6 +860,7 @@ mod tests {
MasterPublicKeyId::Schnorr(key_id) => {
PreSignatureRef::Schnorr(fake_schnorr_transcript(id, key_id.clone()))
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
}
}

Expand All @@ -880,6 +881,7 @@ mod tests {
key_id: key_id.clone(),
})
}
MasterPublicKeyId::VetKd(_) => panic!("not applicable to vetKD"),
},
derivation_path: vec![],
pseudo_random_id: [0; 32],
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -140,6 +140,7 @@ mod tests {
key_id: key_id.clone(),
message: Arc::new(vec![1; 64]),
}),
MasterPublicKeyId::VetKd(_) => panic!("vetKD does not have pre-signatures"),
};
let context = SignWithThresholdContext {
request: RequestBuilder::new().build(),
Expand Down
11 changes: 11 additions & 0 deletions rs/protobuf/def/registry/crypto/v1/crypto.proto
Original file line number Diff line number Diff line change
Expand Up @@ -80,9 +80,20 @@ message SchnorrKeyId {
string name = 2;
}

enum VetKdCurve {
VETKD_CURVE_UNSPECIFIED = 0;
VETKD_CURVE_BLS12_381_G2 = 1;
}

message VetKdKeyId {
VetKdCurve curve = 1;
string name = 2;
}

message MasterPublicKeyId {
oneof key_id {
EcdsaKeyId ecdsa = 1;
SchnorrKeyId schnorr = 2;
VetKdKeyId vetkd = 3;
maksymar marked this conversation as resolved.
Show resolved Hide resolved
}
}
49 changes: 48 additions & 1 deletion rs/protobuf/src/gen/crypto/registry.crypto.v1.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,15 @@ pub struct SchnorrKeyId {
pub name: ::prost::alloc::string::String,
}
#[derive(serde::Serialize, serde::Deserialize, Clone, PartialEq, ::prost::Message)]
pub struct VetKdKeyId {
#[prost(enumeration = "VetKdCurve", tag = "1")]
pub curve: i32,
#[prost(string, tag = "2")]
pub name: ::prost::alloc::string::String,
}
#[derive(serde::Serialize, serde::Deserialize, Clone, PartialEq, ::prost::Message)]
pub struct MasterPublicKeyId {
#[prost(oneof = "master_public_key_id::KeyId", tags = "1, 2")]
#[prost(oneof = "master_public_key_id::KeyId", tags = "1, 2, 3")]
pub key_id: ::core::option::Option<master_public_key_id::KeyId>,
}
/// Nested message and enum types in `MasterPublicKeyId`.
Expand All @@ -61,6 +68,8 @@ pub mod master_public_key_id {
Ecdsa(super::EcdsaKeyId),
#[prost(message, tag = "2")]
Schnorr(super::SchnorrKeyId),
#[prost(message, tag = "3")]
Vetkd(super::VetKdKeyId),
}
}
/// An algorithm ID. This is used to specify the signature algorithm associated with a public key.
Expand Down Expand Up @@ -237,3 +246,41 @@ impl SchnorrAlgorithm {
}
}
}
#[derive(
serde::Serialize,
serde::Deserialize,
Clone,
Copy,
Debug,
PartialEq,
Eq,
Hash,
PartialOrd,
Ord,
::prost::Enumeration,
)]
#[repr(i32)]
pub enum VetKdCurve {
VetkdCurveUnspecified = 0,
VetkdCurveBls12381G2 = 1,
}
impl VetKdCurve {
/// String value of the enum field names used in the ProtoBuf definition.
///
/// The values are not transformed in any way and thus are considered stable
/// (if the ProtoBuf definition does not change) and safe for programmatic use.
pub fn as_str_name(&self) -> &'static str {
match self {
Self::VetkdCurveUnspecified => "VETKD_CURVE_UNSPECIFIED",
Self::VetkdCurveBls12381G2 => "VETKD_CURVE_BLS12_381_G2",
}
}
/// Creates an enum from field names used in the ProtoBuf definition.
pub fn from_str_name(value: &str) -> ::core::option::Option<Self> {
match value {
"VETKD_CURVE_UNSPECIFIED" => Some(Self::VetkdCurveUnspecified),
"VETKD_CURVE_BLS12_381_G2" => Some(Self::VetkdCurveBls12381G2),
_ => None,
}
}
}
Loading