Skip to content

Commit

Permalink
extract Signature into conditional traits
Browse files Browse the repository at this point in the history
  • Loading branch information
grandima committed Oct 28, 2024
1 parent fe3fcd6 commit e9d3a60
Show file tree
Hide file tree
Showing 4 changed files with 92 additions and 40 deletions.
73 changes: 40 additions & 33 deletions crates/primitives/src/signature/ecdsa_sig.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ use crate::{
};
use alloc::vec::Vec;
use core::str::FromStr;
use crate::signature::super_signature::{ArbitrarySuperSig, K256SuperSig, RlpSuperSig, SerdeSuperSig};

/// The order of the secp256k1 curve
const SECP256K1N_ORDER: U256 =
Expand All @@ -21,46 +22,62 @@ pub struct EcdsaSignature {
}

impl EcdsaSignature {
/// Returns the recovery ID.
#[cfg(feature = "k256")]
#[inline]
const fn recid(&self) -> k256::ecdsa::RecoveryId {
self.v.recid()
}

#[cfg(feature = "k256")]
#[doc(hidden)]
#[deprecated(note = "use `Signature::recid` instead")]
pub const fn recovery_id(&self) -> k256::ecdsa::RecoveryId {
self.recid()
}

#[doc(hidden)]
fn test_signature() -> Self {
Self::from_scalars_and_parity(
b256!("840cfc572845f5786e702984c2a582528cad4b49b2a10b9db1be7fca90058565"),
b256!("25e7109ceb98168d95b09b18bbf6b685130e0562f233877d492b94eee0c5b6d1"),
false,
)
.unwrap()
}
}

impl RlpSuperSig for EcdsaSignature {}

impl K256SuperSig for EcdsaSignature {}

impl SerdeSuperSig for EcdsaSignature {}

impl ArbitrarySuperSig for EcdsaSignature {}

impl Signature for EcdsaSignature {
/// Instantiate a new signature from `r`, `s`, and `v` values.
#[allow(clippy::missing_const_for_fn)]
pub fn new(r: U256, s: U256, v: Parity) -> Self {
fn new(r: U256, s: U256, v: Parity) -> Self {
Self { r, s, v }
}

/// Returns the `r` component of this signature.
#[inline]
pub const fn r(&self) -> U256 {
fn r(&self) -> U256 {
self.r
}

/// Returns the `s` component of this signature.
#[inline]
pub const fn s(&self) -> U256 {
fn s(&self) -> U256 {
self.s
}

/// Returns the recovery ID as a `u8`.
#[inline]
pub const fn v(&self) -> Parity {
fn v(&self) -> Parity {
self.v
}

/// Returns the recovery ID.
#[cfg(feature = "k256")]
#[inline]
const fn recid(&self) -> k256::ecdsa::RecoveryId {
self.v.recid()
}

#[cfg(feature = "k256")]
#[doc(hidden)]
#[deprecated(note = "use `Signature::recid` instead")]
pub const fn recovery_id(&self) -> k256::ecdsa::RecoveryId {
self.recid()
}
}

impl Signature<'_> for EcdsaSignature {
#[cfg(feature = "rlp")]
fn decode_rlp_vrs(buf: &mut &[u8]) -> Result<Self, alloy_rlp::Error> {
use alloy_rlp::Decodable;
Expand All @@ -73,16 +90,6 @@ impl Signature<'_> for EcdsaSignature {
.map_err(|_| alloy_rlp::Error::Custom("attempted to decode invalid field element"))
}

#[doc(hidden)]
fn test_signature() -> Self {
Self::from_scalars_and_parity(
b256!("840cfc572845f5786e702984c2a582528cad4b49b2a10b9db1be7fca90058565"),
b256!("25e7109ceb98168d95b09b18bbf6b685130e0562f233877d492b94eee0c5b6d1"),
false,
)
.unwrap()
}

/// Returns the byte-array representation of this signature.
///
/// The first 32 bytes are the `r` value, the second 32 bytes the `s` value
Expand Down Expand Up @@ -385,7 +392,7 @@ impl serde::Serialize for EcdsaSignature {
where
S: serde::Serializer,
{
// if the serializer is human readable, serialize as a map, otherwise as a tuple
// if the serializer is human-readable, serialize as a map, otherwise as a tuple
if serializer.is_human_readable() {
use serde::ser::SerializeMap;

Expand Down
2 changes: 2 additions & 0 deletions crates/primitives/src/signature/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ pub use ecdsa_sig::EcdsaSignature;
mod utils;

mod sig;
mod super_signature;

pub use sig::Signature;

pub use utils::to_eip155_v;
27 changes: 20 additions & 7 deletions crates/primitives/src/signature/sig.rs
Original file line number Diff line number Diff line change
@@ -1,21 +1,34 @@
use crate::{Parity, SignatureError, U256};
use core::str::FromStr;
use crate::signature::super_signature::{ArbitrarySuperSig, K256SuperSig, RlpSuperSig, SerdeSuperSig};

/// An Ethereum Generic signature.
pub trait Signature<'a>:
TryFrom<&'a [u8], Error = SignatureError> + FromStr<Err = SignatureError>
pub trait Signature:
for<'a> TryFrom<&'a [u8], Error = SignatureError>
+ FromStr<Err = SignatureError>
+ RlpSuperSig
+ K256SuperSig
+ SerdeSuperSig
+ ArbitrarySuperSig
{
/// Instantiate a new signature from `r`, `s`, and `v` values.
fn new(r: U256, s: U256, v: Parity) -> Self;

/// Returns the `r` component of this signature.
fn r(&self) -> U256;

/// Returns the `s` component of this signature.
fn s(&self) -> U256;

/// Returns the recovery ID as a `u8`.
fn v(&self) -> Parity;

/// Decode an RLP-encoded VRS signature.
#[cfg(feature = "rlp")]
fn decode_rlp_vrs(buf: &mut &[u8]) -> Result<Self, alloy_rlp::Error>
where
Self: Sized;

#[doc(hidden)]
fn test_signature() -> Self
where
Self: Sized;

/// Returns the byte-array representation of this signature.
fn as_bytes(&self) -> [u8; 65];

Expand Down
30 changes: 30 additions & 0 deletions crates/primitives/src/signature/super_signature.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
use crate::{Parity, U256};

#[cfg(not(feature = "rlp"))]
pub trait RlpSuperSig {}

#[cfg(feature = "rlp")]
pub trait RlpSuperSig: alloy_rlp::Encodable + alloy_rlp::Decodable {}

#[cfg(not(feature = "k256"))]
pub trait K256SuperSig {}

#[cfg(feature = "k256")]
pub trait K256SuperSig: From<(k256::ecdsa::Signature, k256::ecdsa::RecoveryId)> {}

#[cfg(not(feature = "serde"))]
pub trait SerdeSuperSig {}

#[cfg(feature = "serde")]
pub trait SerdeSuperSig: serde::Serialize + serde::Deserialize {}

#[cfg(not(feature = "arbitrary"))]
pub trait ArbitrarySuperSig {}

#[cfg(feature = "arbitrary")]
pub trait ArbitrarySuperSig:
arbitrary::Arbitrary
+ proptest::arbitrary::Arbitrary<Parameters=(),Strategy=proptest::strategy::FilterMap<
<(U256, U256, Parity) as proptest::arbitrary::Arbitrary>::Strategy,
fn((U256, U256, Parity)) -> Option<Self>,
>> {}

0 comments on commit e9d3a60

Please sign in to comment.