mithril_stm/aggregate_signature/
signature.rs1use blake2::digest::{Digest, FixedOutput};
2
3use serde::{Deserialize, Serialize};
4
5use crate::bls_multi_signature::{BlsSignature, BlsVerificationKey};
6use crate::key_registration::RegisteredParty;
7use crate::merkle_tree::MerkleBatchPath;
8use crate::{
9 AggregateVerificationKey, BasicVerifier, Parameters, SingleSignatureWithRegisteredParty,
10 StmAggregateSignatureError,
11};
12
13#[derive(Debug, Clone, Serialize, Deserialize)]
17#[serde(bound(
18 serialize = "MerkleBatchPath<D>: Serialize",
19 deserialize = "MerkleBatchPath<D>: Deserialize<'de>"
20))]
21pub struct AggregateSignature<D: Clone + Digest + FixedOutput> {
22 pub(crate) signatures: Vec<SingleSignatureWithRegisteredParty>,
23 pub batch_proof: MerkleBatchPath<D>,
25}
26
27impl<D: Clone + Digest + FixedOutput + Send + Sync> AggregateSignature<D> {
28 fn preliminary_verify(
35 &self,
36 msg: &[u8],
37 avk: &AggregateVerificationKey<D>,
38 parameters: &Parameters,
39 ) -> Result<(Vec<BlsSignature>, Vec<BlsVerificationKey>), StmAggregateSignatureError<D>> {
40 let msgp = avk.get_merkle_tree_batch_commitment().concatenate_with_message(msg);
41 BasicVerifier::preliminary_verify(
42 &avk.get_total_stake(),
43 &self.signatures,
44 parameters,
45 &msgp,
46 )?;
47
48 let leaves = self
49 .signatures
50 .iter()
51 .map(|r| r.reg_party)
52 .collect::<Vec<RegisteredParty>>();
53
54 avk.get_merkle_tree_batch_commitment()
55 .verify_leaves_membership_from_batch_path(&leaves, &self.batch_proof)?;
56
57 Ok(BasicVerifier::collect_signatures_verification_keys(
58 &self.signatures,
59 ))
60 }
61
62 pub fn verify(
69 &self,
70 msg: &[u8],
71 avk: &AggregateVerificationKey<D>,
72 parameters: &Parameters,
73 ) -> Result<(), StmAggregateSignatureError<D>> {
74 let msgp = avk.get_merkle_tree_batch_commitment().concatenate_with_message(msg);
75 let (sigs, vks) = self.preliminary_verify(msg, avk, parameters)?;
76
77 BlsSignature::verify_aggregate(msgp.as_slice(), &vks, &sigs)?;
78 Ok(())
79 }
80
81 pub fn batch_verify(
83 stm_signatures: &[Self],
84 msgs: &[Vec<u8>],
85 avks: &[AggregateVerificationKey<D>],
86 parameters: &[Parameters],
87 ) -> Result<(), StmAggregateSignatureError<D>> {
88 let batch_size = stm_signatures.len();
89 assert_eq!(
90 batch_size,
91 msgs.len(),
92 "Number of messages should correspond to size of the batch"
93 );
94 assert_eq!(
95 batch_size,
96 avks.len(),
97 "Number of avks should correspond to size of the batch"
98 );
99 assert_eq!(
100 batch_size,
101 parameters.len(),
102 "Number of parameters should correspond to size of the batch"
103 );
104
105 let mut aggr_sigs = Vec::with_capacity(batch_size);
106 let mut aggr_vks = Vec::with_capacity(batch_size);
107 for (idx, sig_group) in stm_signatures.iter().enumerate() {
108 sig_group.preliminary_verify(&msgs[idx], &avks[idx], ¶meters[idx])?;
109 let grouped_sigs: Vec<BlsSignature> =
110 sig_group.signatures.iter().map(|sig_reg| sig_reg.sig.sigma).collect();
111 let grouped_vks: Vec<BlsVerificationKey> = sig_group
112 .signatures
113 .iter()
114 .map(|sig_reg| sig_reg.reg_party.0)
115 .collect();
116
117 let (aggr_vk, aggr_sig) = BlsSignature::aggregate(&grouped_vks, &grouped_sigs).unwrap();
118 aggr_sigs.push(aggr_sig);
119 aggr_vks.push(aggr_vk);
120 }
121
122 let concat_msgs: Vec<Vec<u8>> = msgs
123 .iter()
124 .zip(avks.iter())
125 .map(|(msg, avk)| avk.get_merkle_tree_batch_commitment().concatenate_with_message(msg))
126 .collect();
127
128 BlsSignature::batch_verify_aggregates(&concat_msgs, &aggr_vks, &aggr_sigs)?;
129 Ok(())
130 }
131
132 pub fn to_bytes(&self) -> Vec<u8> {
139 let mut out = Vec::new();
140 let proof_type: u8 = 0;
144 out.extend_from_slice(&proof_type.to_be_bytes());
145 out.extend_from_slice(&u64::try_from(self.signatures.len()).unwrap().to_be_bytes());
146 for sig_reg in &self.signatures {
147 out.extend_from_slice(&u64::try_from(sig_reg.to_bytes().len()).unwrap().to_be_bytes());
148 out.extend_from_slice(&sig_reg.to_bytes());
149 }
150 let proof = &self.batch_proof;
151 out.extend_from_slice(&proof.to_bytes());
152
153 out
154 }
155
156 pub fn from_bytes(
158 bytes: &[u8],
159 ) -> Result<AggregateSignature<D>, StmAggregateSignatureError<D>> {
160 let mut u8_bytes = [0u8; 1];
161 let mut bytes_index = 0;
162
163 u8_bytes
164 .copy_from_slice(bytes.get(..1).ok_or(StmAggregateSignatureError::SerializationError)?);
165 bytes_index += 1;
166 let proof_type = u8::from_be_bytes(u8_bytes);
167 if proof_type != 0 {
168 return Err(StmAggregateSignatureError::SerializationError);
169 }
170
171 let mut u64_bytes = [0u8; 8];
172 u64_bytes.copy_from_slice(
173 bytes
174 .get(bytes_index..bytes_index + 8)
175 .ok_or(StmAggregateSignatureError::SerializationError)?,
176 );
177 let total_sigs = usize::try_from(u64::from_be_bytes(u64_bytes))
178 .map_err(|_| StmAggregateSignatureError::SerializationError)?;
179 bytes_index += 8;
180
181 let mut sig_reg_list = Vec::with_capacity(total_sigs);
182 for _ in 0..total_sigs {
183 u64_bytes.copy_from_slice(
184 bytes
185 .get(bytes_index..bytes_index + 8)
186 .ok_or(StmAggregateSignatureError::SerializationError)?,
187 );
188 let sig_reg_size = usize::try_from(u64::from_be_bytes(u64_bytes))
189 .map_err(|_| StmAggregateSignatureError::SerializationError)?;
190 let sig_reg = SingleSignatureWithRegisteredParty::from_bytes::<D>(
191 bytes
192 .get(bytes_index + 8..bytes_index + 8 + sig_reg_size)
193 .ok_or(StmAggregateSignatureError::SerializationError)?,
194 )?;
195 bytes_index += 8 + sig_reg_size;
196 sig_reg_list.push(sig_reg);
197 }
198
199 let batch_proof = MerkleBatchPath::from_bytes(
200 bytes
201 .get(bytes_index..)
202 .ok_or(StmAggregateSignatureError::SerializationError)?,
203 )?;
204
205 Ok(AggregateSignature {
206 signatures: sig_reg_list,
207 batch_proof,
208 })
209 }
210}