From 3c89c732b713829b618fa006f4e3c65ca1455b82 Mon Sep 17 00:00:00 2001 From: Rohit Narurkar Date: Sun, 15 Aug 2021 17:00:44 +0530 Subject: [PATCH] fix: signature fields should be U256 instead of H256 (#379) * fix: signature fields should be U256 instead of H256 * fix: relevant changes for aws and ledger signer --- ethers-core/src/types/signature.rs | 26 +++++++++++++++++--------- ethers-signers/src/aws/utils.rs | 6 +++--- ethers-signers/src/ledger/app.rs | 4 ++-- ethers-signers/src/wallet/mod.rs | 6 +++--- 4 files changed, 25 insertions(+), 17 deletions(-) diff --git a/ethers-core/src/types/signature.rs b/ethers-core/src/types/signature.rs index bf21b14b..959c0d33 100644 --- a/ethers-core/src/types/signature.rs +++ b/ethers-core/src/types/signature.rs @@ -1,6 +1,6 @@ // Code adapted from: https://github.com/tomusdrw/rust-web3/blob/master/src/api/accounts.rs use crate::{ - types::{Address, H256}, + types::{Address, H256, U256}, utils::hash_message, }; @@ -55,9 +55,9 @@ pub enum RecoveryMessage { /// An ECDSA signature pub struct Signature { /// R value - pub r: H256, + pub r: U256, /// S Value - pub s: H256, + pub s: U256, /// V value in 'Electrum' notation. pub v: u64, } @@ -118,8 +118,12 @@ impl Signature { fn as_signature(&self) -> Result<(RecoverableSignature, RecoveryId), SignatureError> { let recovery_id = self.recovery_id()?; let signature = { - let gar: &GenericArray = GenericArray::from_slice(self.r.as_bytes()); - let gas: &GenericArray = GenericArray::from_slice(self.s.as_bytes()); + let mut r_bytes = [0u8; 32]; + let mut s_bytes = [0u8; 32]; + self.r.to_big_endian(&mut r_bytes); + self.s.to_big_endian(&mut s_bytes); + let gar: &GenericArray = GenericArray::from_slice(&r_bytes); + let gas: &GenericArray = GenericArray::from_slice(&s_bytes); let sig = K256Signature::from_scalars(*gar, *gas)?; RecoverableSignature::new(&sig, recovery_id)? }; @@ -163,8 +167,8 @@ impl<'a> TryFrom<&'a [u8]> for Signature { } let v = bytes[64]; - let r = H256::from_slice(&bytes[0..32]); - let s = H256::from_slice(&bytes[32..64]); + let r = U256::from_big_endian(&bytes[0..32]); + let s = U256::from_big_endian(&bytes[32..64]); Ok(Signature { r, s, v: v.into() }) } @@ -183,8 +187,12 @@ impl FromStr for Signature { impl From<&Signature> for [u8; 65] { fn from(src: &Signature) -> [u8; 65] { let mut sig = [0u8; 65]; - sig[..32].copy_from_slice(src.r.as_bytes()); - sig[32..64].copy_from_slice(src.s.as_bytes()); + let mut r_bytes = [0u8; 32]; + let mut s_bytes = [0u8; 32]; + src.r.to_big_endian(&mut r_bytes); + src.s.to_big_endian(&mut s_bytes); + sig[..32].copy_from_slice(&r_bytes); + sig[32..64].copy_from_slice(&s_bytes); // TODO: What if we try to serialize a signature where // the `v` is not normalized? sig[64] = src.v as u8; diff --git a/ethers-signers/src/aws/utils.rs b/ethers-signers/src/aws/utils.rs index 149b66d7..7b98ec5a 100644 --- a/ethers-signers/src/aws/utils.rs +++ b/ethers-signers/src/aws/utils.rs @@ -13,7 +13,7 @@ use ethers_core::{ elliptic_curve::sec1::ToEncodedPoint, FieldBytes, }, - types::{Address, Signature as EthSig, H256}, + types::{Address, Signature as EthSig, U256}, utils::keccak256, }; use rusoto_kms::{GetPublicKeyResponse, SignResponse}; @@ -26,8 +26,8 @@ pub(super) fn rsig_to_ethsig(sig: &RSig) -> EthSig { let v = (v + 27) as u64; let r_bytes: FieldBytes = sig.r().into(); let s_bytes: FieldBytes = sig.s().into(); - let r = H256::from_slice(&r_bytes.as_slice()); - let s = H256::from_slice(&s_bytes.as_slice()); + let r = U256::from_big_endian(&r_bytes.as_slice()); + let s = U256::from_big_endian(&s_bytes.as_slice()); EthSig { r, s, v } } diff --git a/ethers-signers/src/ledger/app.rs b/ethers-signers/src/ledger/app.rs index 2579b3df..0a02294f 100644 --- a/ethers-signers/src/ledger/app.rs +++ b/ethers-signers/src/ledger/app.rs @@ -170,8 +170,8 @@ impl LedgerEthereum { } let v = result[0] as u64; - let r = H256::from_slice(&result[1..33]); - let s = H256::from_slice(&result[33..]); + let r = U256::from_big_endian(&result[1..33]); + let s = U256::from_big_endian(&result[33..]); Ok(Signature { r, s, v }) } diff --git a/ethers-signers/src/wallet/mod.rs b/ethers-signers/src/wallet/mod.rs index 53d3a294..bf4d0876 100644 --- a/ethers-signers/src/wallet/mod.rs +++ b/ethers-signers/src/wallet/mod.rs @@ -16,7 +16,7 @@ use ethers_core::{ elliptic_curve::FieldBytes, Secp256k1, }, - types::{transaction::eip2718::TypedTransaction, Address, Signature, H256}, + types::{transaction::eip2718::TypedTransaction, Address, Signature, H256, U256}, utils::hash_message, }; use hash::Sha256Proxy; @@ -116,8 +116,8 @@ impl> Wallet { let r_bytes: FieldBytes = recoverable_sig.r().into(); let s_bytes: FieldBytes = recoverable_sig.s().into(); - let r = H256::from_slice(r_bytes.as_slice()); - let s = H256::from_slice(s_bytes.as_slice()); + let r = U256::from_big_endian(r_bytes.as_slice()); + let s = U256::from_big_endian(s_bytes.as_slice()); Signature { r, s, v } }