@@ -10,6 +10,23 @@ pub(crate) fn bytes_to_binary<'env>(env: Env<'env>, bytes: &[u8]) -> Binary<'env
1010 binary. into ( )
1111}
1212
13+ // Deserialize a PublicKey from a slice of bytes.
14+ // Faster than PublicKey::deserialize() as it doesn't validate the key
15+ // Returns Error on invalid BLST encoding or on Infinity Public Key.
16+ fn fast_public_key_deserialize ( pk : & [ u8 ] ) -> Result < PublicKey , String > {
17+ if pk == & bls:: INFINITY_PUBLIC_KEY [ ..] {
18+ Err ( "Infinity public Key" . to_owned ( ) )
19+ } else {
20+ bls:: impls:: blst:: types:: PublicKey :: from_bytes ( pk)
21+ . map_err ( |err| format ! ( "BlstError({:?})" , err) )
22+ . and_then ( |pk| {
23+ PublicKey :: deserialize_uncompressed ( pk. serialize ( ) . as_slice ( ) )
24+ // This should never be an error as the pk is obtained from an uncompressed valid key
25+ . map_err ( |e| format ! ( "Deserialization error: {:?}" , e) )
26+ } )
27+ }
28+ }
29+
1330#[ rustler:: nif]
1431fn sign < ' env > (
1532 env : Env < ' env > ,
@@ -59,7 +76,7 @@ fn verify<'env>(public_key: Binary, message: Binary, signature: Binary) -> Resul
5976 }
6077 let sig = Signature :: deserialize ( signature. as_slice ( ) ) . map_err ( |err| format ! ( "{:?}" , err) ) ?;
6178 let pubkey =
62- PublicKey :: deserialize ( public_key. as_slice ( ) ) . map_err ( |err| format ! ( "{:?}" , err) ) ?;
79+ fast_public_key_deserialize ( public_key. as_slice ( ) ) . map_err ( |err| format ! ( "{:?}" , err) ) ?;
6380
6481 Ok ( sig. verify ( & pubkey, Hash256 :: from_slice ( message. as_slice ( ) ) ) )
6582}
@@ -74,7 +91,7 @@ fn aggregate_verify<'env>(
7491 . map_err ( |err| format ! ( "{:?}" , err) ) ?;
7592 let pubkeys_result = public_keys
7693 . iter ( )
77- . map ( |pkb| PublicKey :: deserialize ( pkb. as_slice ( ) ) )
94+ . map ( |pkb| fast_public_key_deserialize ( pkb. as_slice ( ) ) )
7895 . collect :: < Result < Vec < PublicKey > , _ > > ( ) ;
7996 let pubkeys = pubkeys_result. map_err ( |err| format ! ( "{:?}" , err) ) ?;
8097
@@ -86,7 +103,7 @@ fn aggregate_verify<'env>(
86103 Ok ( aggregate_sig. aggregate_verify ( & msgs, & pubkey_refs) )
87104}
88105
89- #[ rustler:: nif]
106+ #[ rustler:: nif( schedule = "DirtyCpu" ) ]
90107fn fast_aggregate_verify < ' env > (
91108 public_keys : Vec < Binary > ,
92109 message : Binary ,
@@ -99,7 +116,8 @@ fn fast_aggregate_verify<'env>(
99116 . map_err ( |err| format ! ( "{:?}" , err) ) ?;
100117 let pubkeys_result = public_keys
101118 . iter ( )
102- . map ( |pkb| PublicKey :: deserialize ( pkb. as_slice ( ) ) )
119+ . map ( |pkb| fast_public_key_deserialize ( pkb. as_slice ( ) ) )
120+ //.map(|pkb| PublicKey::deserialize(pkb.as_slice()))
103121 . collect :: < Result < Vec < PublicKey > , _ > > ( ) ;
104122 let pubkeys = pubkeys_result. map_err ( |err| format ! ( "{:?}" , err) ) ?;
105123
@@ -120,7 +138,7 @@ fn eth_fast_aggregate_verify<'env>(
120138 . map_err ( |err| format ! ( "{:?}" , err) ) ?;
121139 let pubkeys_result = public_keys
122140 . iter ( )
123- . map ( |pkb| PublicKey :: deserialize ( pkb. as_slice ( ) ) )
141+ . map ( |pkb| fast_public_key_deserialize ( pkb. as_slice ( ) ) )
124142 . collect :: < Result < Vec < PublicKey > , _ > > ( ) ;
125143 let pubkeys = pubkeys_result. map_err ( |err| format ! ( "{:?}" , err) ) ?;
126144
@@ -139,7 +157,7 @@ fn eth_aggregate_pubkeys<'env>(
139157 _ => {
140158 let pubkeys_result = public_keys
141159 . iter ( )
142- . map ( |pkb| PublicKey :: deserialize ( pkb. as_slice ( ) ) )
160+ . map ( |pkb| fast_public_key_deserialize ( pkb. as_slice ( ) ) )
143161 . collect :: < Result < Vec < PublicKey > , _ > > ( ) ;
144162
145163 let pubkeys = pubkeys_result. map_err ( |err| format ! ( "{:?}" , err) ) ?;
@@ -156,8 +174,7 @@ fn eth_aggregate_pubkeys<'env>(
156174}
157175#[ rustler:: nif]
158176fn key_validate < ' env > ( public_key : Binary ) -> Result < bool , String > {
159- let _pubkey =
160- PublicKey :: deserialize ( public_key. as_slice ( ) ) . map_err ( |err| format ! ( "{:?}" , err) ) ?;
177+ let _pubkey = fast_public_key_deserialize ( public_key. as_slice ( ) ) ?;
161178
162179 Ok ( true )
163180}
@@ -173,17 +190,4 @@ fn derive_pubkey<'env>(env: Env<'env>, private_key: Binary) -> Result<Binary<'en
173190 Ok ( bytes_to_binary ( env, & public_key_bytes) )
174191}
175192
176- rustler:: init!(
177- "Elixir.Bls" ,
178- [
179- sign,
180- aggregate,
181- aggregate_verify,
182- fast_aggregate_verify,
183- eth_fast_aggregate_verify,
184- eth_aggregate_pubkeys,
185- verify,
186- key_validate,
187- derive_pubkey
188- ]
189- ) ;
193+ rustler:: init!( "Elixir.Bls" ) ;
0 commit comments