|
1 | 1 | use borsh::BorshSerialize;
|
2 |
| -use rayon::iter::{IntoParallelRefIterator as _, ParallelIterator as _}; |
| 2 | +use rayon::{ |
| 3 | + iter::{IntoParallelRefIterator as _, ParallelIterator as _}, |
| 4 | + slice::ParallelSlice as _, |
| 5 | +}; |
3 | 6 | use serde::{Deserialize, Serialize};
|
4 | 7 | use utoipa::ToSchema;
|
5 | 8 |
|
@@ -99,12 +102,6 @@ pub fn get_address(verifying_key: &VerifyingKey) -> Address {
|
99 | 102 | Address(output)
|
100 | 103 | }
|
101 | 104 |
|
102 |
| -struct Package<'a> { |
103 |
| - messages: Vec<&'a [u8]>, |
104 |
| - signatures: Vec<Signature>, |
105 |
| - verifying_keys: Vec<VerifyingKey>, |
106 |
| -} |
107 |
| - |
108 | 105 | pub fn verify_authorized_transaction(
|
109 | 106 | transaction: &AuthorizedTransaction,
|
110 | 107 | ) -> Result<(), Error> {
|
@@ -155,55 +152,19 @@ pub fn verify_authorizations(body: &Body) -> Result<(), Error> {
|
155 | 152 | std::iter::repeat_n(tx.as_slice(), *n_inputs)
|
156 | 153 | });
|
157 | 154 | let pairs = body.authorizations.iter().zip(messages).collect::<Vec<_>>();
|
158 |
| - |
159 |
| - let num_threads = rayon::current_num_threads(); |
160 |
| - let num_authorizations = body.authorizations.len(); |
161 |
| - let package_size = num_authorizations / num_threads; |
162 |
| - let mut packages: Vec<Package> = Vec::with_capacity(num_threads); |
163 |
| - for i in 0..num_threads { |
164 |
| - let mut package = Package { |
165 |
| - messages: Vec::with_capacity(package_size), |
166 |
| - signatures: Vec::with_capacity(package_size), |
167 |
| - verifying_keys: Vec::with_capacity(package_size), |
168 |
| - }; |
169 |
| - for (authorization, message) in |
170 |
| - &pairs[i * package_size..(i + 1) * package_size] |
171 |
| - { |
172 |
| - package.messages.push(*message); |
173 |
| - package.signatures.push(authorization.signature); |
174 |
| - package.verifying_keys.push(authorization.verifying_key); |
175 |
| - } |
176 |
| - packages.push(package); |
177 |
| - } |
178 |
| - for (authorization, message) in &pairs[num_threads * package_size..] { |
179 |
| - packages[num_threads - 1].messages.push(*message); |
180 |
| - packages[num_threads - 1] |
181 |
| - .signatures |
182 |
| - .push(authorization.signature); |
183 |
| - packages[num_threads - 1] |
184 |
| - .verifying_keys |
185 |
| - .push(authorization.verifying_key); |
186 |
| - } |
187 |
| - assert_eq!( |
188 |
| - packages.iter().map(|p| p.signatures.len()).sum::<usize>(), |
189 |
| - body.authorizations.len() |
190 |
| - ); |
191 |
| - packages |
192 |
| - .par_iter() |
193 |
| - .map( |
194 |
| - |Package { |
195 |
| - messages, |
196 |
| - signatures, |
197 |
| - verifying_keys, |
198 |
| - }| { |
199 |
| - ed25519_dalek::verify_batch( |
200 |
| - messages, |
201 |
| - signatures, |
202 |
| - verifying_keys, |
203 |
| - ) |
204 |
| - }, |
205 |
| - ) |
206 |
| - .collect::<Result<(), SignatureError>>()?; |
| 155 | + assert_eq!(pairs.len(), body.authorizations.len()); |
| 156 | + const CHUNK_SIZE: usize = 1 << 14; |
| 157 | + pairs.par_chunks(CHUNK_SIZE).try_for_each(|chunk| { |
| 158 | + let (signatures, verifying_keys, messages): ( |
| 159 | + Vec<Signature>, |
| 160 | + Vec<VerifyingKey>, |
| 161 | + Vec<&[u8]>, |
| 162 | + ) = chunk |
| 163 | + .iter() |
| 164 | + .map(|(auth, msg)| (auth.signature, auth.verifying_key, msg)) |
| 165 | + .collect(); |
| 166 | + ed25519_dalek::verify_batch(&messages, &signatures, &verifying_keys) |
| 167 | + })?; |
207 | 168 | Ok(())
|
208 | 169 | }
|
209 | 170 |
|
|
0 commit comments