From 37734bb3a7234368f2c31d48265a079f7b3fa58d Mon Sep 17 00:00:00 2001 From: Thomas Plisson Date: Mon, 24 Jul 2023 10:59:29 +0200 Subject: [PATCH 1/4] Evm related interface function and eoa checker --- src/as_execution/abi.rs | 2 +- src/types.rs | 19 +++++++++++++++++-- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/src/as_execution/abi.rs b/src/as_execution/abi.rs index 938a64d1..cec4e740 100644 --- a/src/as_execution/abi.rs +++ b/src/as_execution/abi.rs @@ -661,7 +661,7 @@ pub(crate) fn assembly_script_evm_signature_verify( let public_key = read_buffer(memory, &ctx, public_key)?; Ok(env .get_interface() - .verify_evm_signature(&data, &signature, &public_key)? as i32) + .evm_signature_verify(&data, &signature, &public_key)? as i32) } /// converts a public key to an address diff --git a/src/types.rs b/src/types.rs index 81840e32..c1104ce2 100644 --- a/src/types.rs +++ b/src/types.rs @@ -310,13 +310,28 @@ pub trait Interface: Send + Sync + InterfaceClone { } // Verify EVM signature - fn verify_evm_signature( + fn evm_signature_verify( &self, message: &[u8], signature: &[u8], public_key: &[u8], ) -> Result { - unimplemented!("verify_evm_signature") + unimplemented!("evm_signature_verify") + } + + // Get address from public key (EVM) + fn evm_get_address_from_pubkey(public_key: &[u8]) -> Result> { + unimplemented!("evm_get_address_from_pubkey") + } + + // Get public key from signature (EVM) + fn evm_get_pubkey_from_signature(signature: &[u8]) -> Result> { + unimplemented!("evm_get_pubkey_from_signature") + } + + // Return true if the address is an User address, otherwise false if it is an SC address + fn is_address_eoa(&self, address: &str) -> Result { + unimplemented!("is_address_eoa") } // Convert a public key to an address From 02f3e4ff9bb90639dff850e4803025f312b7cced Mon Sep 17 00:00:00 2001 From: Thomas Plisson Date: Mon, 24 Jul 2023 13:34:21 +0200 Subject: [PATCH 2/4] fix self param issue --- src/types.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/types.rs b/src/types.rs index c1104ce2..eadfaeba 100644 --- a/src/types.rs +++ b/src/types.rs @@ -320,12 +320,12 @@ pub trait Interface: Send + Sync + InterfaceClone { } // Get address from public key (EVM) - fn evm_get_address_from_pubkey(public_key: &[u8]) -> Result> { + fn evm_get_address_from_pubkey(&self, public_key: &[u8]) -> Result> { unimplemented!("evm_get_address_from_pubkey") } // Get public key from signature (EVM) - fn evm_get_pubkey_from_signature(signature: &[u8]) -> Result> { + fn evm_get_pubkey_from_signature(&self, signature: &[u8]) -> Result> { unimplemented!("evm_get_pubkey_from_signature") } From d702a0a6d5a4d57f6858b4704df1e55fad56aac8 Mon Sep 17 00:00:00 2001 From: Thomas Plisson Date: Mon, 24 Jul 2023 15:20:08 +0200 Subject: [PATCH 3/4] evm_get_pubkey_from_signature proto update --- src/types.rs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/types.rs b/src/types.rs index fc4e9cd8..005e7135 100644 --- a/src/types.rs +++ b/src/types.rs @@ -310,7 +310,7 @@ pub trait Interface: Send + Sync + InterfaceClone { unimplemented!("signature_verify") } - // Verify EVM signature + // Verify signature (EVM) fn evm_signature_verify( &self, message: &[u8], @@ -326,7 +326,7 @@ pub trait Interface: Send + Sync + InterfaceClone { } // Get public key from signature (EVM) - fn evm_get_pubkey_from_signature(&self, signature: &[u8]) -> Result> { + fn evm_get_pubkey_from_signature(&self, hash: &[u8], signature: &[u8]) -> Result> { unimplemented!("evm_get_pubkey_from_signature") } From 67e26cb1bc1d1fd75ac36cbae1f73840f78db375 Mon Sep 17 00:00:00 2001 From: Thomas Plisson Date: Mon, 24 Jul 2023 16:04:47 +0200 Subject: [PATCH 4/4] Add abis --- src/as_execution/abi.rs | 49 +++++++++++++++++++++++++++++++++++++ src/as_execution/context.rs | 3 +++ src/types.rs | 25 +++++++++++++------ 3 files changed, 69 insertions(+), 8 deletions(-) diff --git a/src/as_execution/abi.rs b/src/as_execution/abi.rs index 96a16c2b..917516ae 100644 --- a/src/as_execution/abi.rs +++ b/src/as_execution/abi.rs @@ -664,6 +664,55 @@ pub(crate) fn assembly_script_evm_signature_verify( .evm_signature_verify(&data, &signature, &public_key)? as i32) } +/// Get address from public key (EVM) +#[named] +pub(crate) fn assembly_script_evm_get_address_from_pubkey( + mut ctx: FunctionEnvMut, + public_key: i32, +) -> ABIResult { + let env = get_env(&ctx)?; + sub_remaining_gas_abi(&env, &mut ctx, function_name!())?; + let memory = get_memory!(env); + let public_key = read_buffer(memory, &ctx, public_key)?; + let address = env + .get_interface() + .evm_get_address_from_pubkey(&public_key)?; + let ptr = pointer_from_bytearray(&env, &mut ctx, &address)?.offset(); + Ok(ptr as i32) +} + +/// Get public key from signature (EVM) +#[named] +pub(crate) fn assembly_script_evm_get_pubkey_from_signature( + mut ctx: FunctionEnvMut, + data: i32, + signature: i32, +) -> ABIResult { + let env = get_env(&ctx)?; + sub_remaining_gas_abi(&env, &mut ctx, function_name!())?; + let memory = get_memory!(env); + let data = read_buffer(memory, &ctx, data)?; + let signature = read_buffer(memory, &ctx, signature)?; + let public_key = env + .get_interface() + .evm_get_pubkey_from_signature(&data, &signature)?; + let ptr = pointer_from_bytearray(&env, &mut ctx, &public_key)?.offset(); + Ok(ptr as i32) +} + +#[named] +/// Return Ok(1) if the address is a User address, Ok(0) if it is an SC address +pub(crate) fn assembly_script_is_address_eoa( + mut ctx: FunctionEnvMut, + address: i32, +) -> ABIResult { + let env = get_env(&ctx)?; + sub_remaining_gas_abi(&env, &mut ctx, function_name!())?; + let memory = get_memory!(env); + let address = read_string(memory, &ctx, address)?; + Ok(env.get_interface().is_address_eoa(&address)? as i32) +} + /// converts a public key to an address #[named] pub(crate) fn assembly_script_address_from_public_key( diff --git a/src/as_execution/context.rs b/src/as_execution/context.rs index 236f0377..cefa0376 100644 --- a/src/as_execution/context.rs +++ b/src/as_execution/context.rs @@ -247,6 +247,9 @@ impl ASContext { "assembly_script_keccak256_hash" => Function::new_typed_with_env(store, &fenv, assembly_script_keccak256_hash), "assembly_script_signature_verify" => Function::new_typed_with_env(store, &fenv, assembly_script_signature_verify), "assembly_script_evm_signature_verify" => Function::new_typed_with_env(store, &fenv, assembly_script_evm_signature_verify), + "assembly_script_evm_get_address_from_pubkey" => Function::new_typed_with_env(store, &fenv, assembly_script_evm_get_address_from_pubkey), + "assembly_script_evm_get_pubkey_from_signature" => Function::new_typed_with_env(store, &fenv, assembly_script_evm_get_pubkey_from_signature), + "assembly_script_is_address_eoa" => Function::new_typed_with_env(store, &fenv, assembly_script_is_address_eoa), "assembly_script_address_from_public_key" => Function::new_typed_with_env(store, &fenv, assembly_script_address_from_public_key), "assembly_script_validate_address" => Function::new_typed_with_env(store, &fenv, assembly_script_validate_address), "assembly_script_unsafe_random" => Function::new_typed_with_env(store, &fenv, assembly_script_unsafe_random), diff --git a/src/types.rs b/src/types.rs index 005e7135..6f11f38c 100644 --- a/src/types.rs +++ b/src/types.rs @@ -112,6 +112,15 @@ impl Default for GasCosts { abi_costs.insert(String::from("assembly_script_set_data_for"), 165); abi_costs.insert(String::from("assembly_script_signature_verify"), 98); abi_costs.insert(String::from("assembly_script_evm_signature_verify"), 264); + abi_costs.insert( + String::from("assembly_script_evm_get_address_from_pubkey"), + 11, + ); + abi_costs.insert( + String::from("assembly_script_evm_get_pubkey_from_signature"), + 11, + ); + abi_costs.insert(String::from("assembly_script_is_address_eoa"), 11); abi_costs.insert(String::from("assembly_script_transfer_coins"), 62); abi_costs.insert(String::from("assembly_script_transfer_coins_for"), 102); abi_costs.insert(String::from("assembly_script_unsafe_random"), 11); @@ -300,17 +309,17 @@ pub trait Interface: Send + Sync + InterfaceClone { unimplemented!("caller_has_write_access") } - // Hash data + /// Hash data fn hash(&self, data: &[u8]) -> Result<[u8; 32]> { unimplemented!("hash") } - // Verify signature + /// Verify signature fn signature_verify(&self, data: &[u8], signature: &str, public_key: &str) -> Result { unimplemented!("signature_verify") } - // Verify signature (EVM) + /// Verify signature (EVM) fn evm_signature_verify( &self, message: &[u8], @@ -320,27 +329,27 @@ pub trait Interface: Send + Sync + InterfaceClone { unimplemented!("evm_signature_verify") } - // Get address from public key (EVM) + /// Get address from public key (EVM) fn evm_get_address_from_pubkey(&self, public_key: &[u8]) -> Result> { unimplemented!("evm_get_address_from_pubkey") } - // Get public key from signature (EVM) + /// Get public key from signature (EVM) fn evm_get_pubkey_from_signature(&self, hash: &[u8], signature: &[u8]) -> Result> { unimplemented!("evm_get_pubkey_from_signature") } - // Return true if the address is an User address, otherwise false if it is an SC address + /// Return true if the address is a User address, false if it is an SC address fn is_address_eoa(&self, address: &str) -> Result { unimplemented!("is_address_eoa") } - // Convert a public key to an address + /// Convert a public key to an address fn address_from_public_key(&self, public_key: &str) -> Result { unimplemented!("address_from_public_key") } - // Validate an address + /// Validate an address fn validate_address(&self, address: &str) -> Result { unimplemented!("validate_address") }