Skip to content

Commit f644f26

Browse files
committed
refactor code
1 parent ae60405 commit f644f26

File tree

5 files changed

+67
-111
lines changed

5 files changed

+67
-111
lines changed

runtime/src/precompiles/balance_transfer.rs

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,12 @@
1-
use frame_system::RawOrigin;
21
use pallet_evm::{
32
BalanceConverter, ExitError, ExitSucceed, PrecompileHandle, PrecompileOutput, PrecompileResult,
43
};
54
use sp_runtime::traits::UniqueSaturatedInto;
65
use sp_std::vec;
76

8-
use crate::precompiles::{get_method_id, get_pubkey, get_slice, try_dispatch_runtime_call};
7+
use crate::precompiles::{
8+
contract_to_origin, get_method_id, get_pubkey, get_slice, try_dispatch_runtime_call,
9+
};
910
use crate::Runtime;
1011

1112
pub const BALANCE_TRANSFER_INDEX: u64 = 2048;
@@ -47,15 +48,13 @@ impl BalanceTransferPrecompile {
4748
}
4849

4950
let address_bytes_dst = get_slice(txdata, 4, 36)?;
50-
let (account_id_src, _) = get_pubkey(&CONTRACT_ADDRESS_SS58)?;
5151
let (account_id_dst, _) = get_pubkey(address_bytes_dst)?;
5252

5353
let call = pallet_balances::Call::<Runtime>::transfer_allow_death {
5454
dest: account_id_dst.into(),
5555
value: amount_sub.unique_saturated_into(),
5656
};
57-
let origin = RawOrigin::Signed(account_id_src);
5857

59-
try_dispatch_runtime_call(handle, call, origin)
58+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
6059
}
6160
}

runtime/src/precompiles/mod.rs

Lines changed: 22 additions & 85 deletions
Original file line numberDiff line numberDiff line change
@@ -6,9 +6,8 @@ use core::marker::PhantomData;
66
use frame_support::dispatch::{GetDispatchInfo, Pays};
77

88
use pallet_evm::{
9-
AddressMapping, BalanceConverter, ExitError, ExitSucceed, GasWeightMapping,
10-
HashedAddressMapping, IsPrecompileResult, Precompile, PrecompileFailure, PrecompileHandle,
11-
PrecompileOutput, PrecompileResult, PrecompileSet,
9+
ExitError, ExitSucceed, GasWeightMapping, IsPrecompileResult, Precompile, PrecompileFailure,
10+
PrecompileHandle, PrecompileOutput, PrecompileResult, PrecompileSet,
1211
};
1312
use pallet_evm_precompile_modexp::Modexp;
1413
use pallet_evm_precompile_sha3fips::Sha3FIPS256;
@@ -20,10 +19,6 @@ use crate::{Runtime, RuntimeCall};
2019

2120
use frame_system::RawOrigin;
2221

23-
use sp_core::crypto::Ss58Codec;
24-
use sp_core::U256;
25-
use sp_runtime::traits::{BlakeTwo256, UniqueSaturatedInto};
26-
2722
use sp_std::vec;
2823

2924
// Include custom precompiles
@@ -147,84 +142,6 @@ pub fn get_slice(data: &[u8], from: usize, to: usize) -> Result<&[u8], Precompil
147142
}
148143
}
149144

150-
/// The function return the token to smart contract
151-
fn transfer_back_to_caller(
152-
smart_contract_address: &str,
153-
account_id: &AccountId32,
154-
amount: U256,
155-
) -> Result<(), PrecompileFailure> {
156-
// this is staking smart contract's(0x0000000000000000000000000000000000000801) sr25519 address
157-
let smart_contract_account_id = match AccountId32::from_ss58check(smart_contract_address) {
158-
// match AccountId32::from_ss58check("5CwnBK9Ack1mhznmCnwiibCNQc174pYQVktYW3ayRpLm4K2X") {
159-
Ok(addr) => addr,
160-
Err(_) => {
161-
return Err(PrecompileFailure::Error {
162-
exit_status: ExitError::Other("Invalid SS58 address".into()),
163-
});
164-
}
165-
};
166-
let amount_sub =
167-
<Runtime as pallet_evm::Config>::BalanceConverter::into_substrate_balance(amount)
168-
.ok_or(ExitError::OutOfFund)?;
169-
170-
// Create a transfer call from the smart contract to the caller
171-
let transfer_call =
172-
RuntimeCall::Balances(pallet_balances::Call::<Runtime>::transfer_allow_death {
173-
dest: account_id.clone().into(),
174-
value: amount_sub.unique_saturated_into(),
175-
});
176-
177-
// Execute the transfer
178-
let transfer_result =
179-
transfer_call.dispatch(RawOrigin::Signed(smart_contract_account_id).into());
180-
181-
if let Err(dispatch_error) = transfer_result {
182-
log::error!(
183-
"Transfer back to caller failed. Error: {:?}",
184-
dispatch_error
185-
);
186-
return Err(PrecompileFailure::Error {
187-
exit_status: ExitError::Other("Transfer back to caller failed".into()),
188-
});
189-
}
190-
191-
Ok(())
192-
}
193-
194-
fn dispatch(
195-
handle: &mut impl PrecompileHandle,
196-
call: RuntimeCall,
197-
smart_contract_address: &str,
198-
) -> PrecompileResult {
199-
let account_id =
200-
<HashedAddressMapping<BlakeTwo256> as AddressMapping<AccountId32>>::into_account_id(
201-
handle.context().caller,
202-
);
203-
204-
// Transfer the amount back to the caller before executing the staking operation
205-
// let caller = handle.context().caller;
206-
let amount = handle.context().apparent_value;
207-
208-
if !amount.is_zero() {
209-
transfer_back_to_caller(smart_contract_address, &account_id, amount)?;
210-
}
211-
212-
let result = call.dispatch(RawOrigin::Signed(account_id.clone()).into());
213-
match &result {
214-
Ok(post_info) => log::info!("Dispatch succeeded. Post info: {:?}", post_info),
215-
Err(dispatch_error) => log::error!("Dispatch failed. Error: {:?}", dispatch_error),
216-
}
217-
match result {
218-
Ok(_) => Ok(PrecompileOutput {
219-
exit_status: ExitSucceed::Returned,
220-
output: vec![],
221-
}),
222-
Err(_) => Err(PrecompileFailure::Error {
223-
exit_status: ExitError::Other("Subtensor call failed".into()),
224-
}),
225-
}
226-
}
227-
228145
pub fn get_pubkey(data: &[u8]) -> Result<(AccountId32, vec::Vec<u8>), PrecompileFailure> {
229146
let mut pubkey = [0u8; 32];
230147
pubkey.copy_from_slice(get_slice(data, 0, 32)?);
@@ -235,6 +152,26 @@ pub fn get_pubkey(data: &[u8]) -> Result<(AccountId32, vec::Vec<u8>), Precompile
235152
.map_or_else(vec::Vec::new, |slice| slice.to_vec()),
236153
))
237154
}
155+
156+
fn parse_netuid(data: &[u8], offset: usize) -> Result<u16, PrecompileFailure> {
157+
if data.len() < offset + 2 {
158+
return Err(PrecompileFailure::Error {
159+
exit_status: ExitError::InvalidRange,
160+
});
161+
}
162+
163+
let mut netuid_bytes = [0u8; 2];
164+
netuid_bytes.copy_from_slice(get_slice(data, offset, offset + 2)?);
165+
let netuid: u16 = netuid_bytes[1] as u16 | ((netuid_bytes[0] as u16) << 8u16);
166+
167+
Ok(netuid)
168+
}
169+
170+
fn contract_to_origin(contract: &[u8; 32]) -> Result<RawOrigin<AccountId32>, PrecompileFailure> {
171+
let (account_id, _) = get_pubkey(contract)?;
172+
Ok(RawOrigin::Signed(account_id))
173+
}
174+
238175
/// Dispatches a runtime call, but also checks and records the gas costs.
239176
fn try_dispatch_runtime_call(
240177
handle: &mut impl PrecompileHandle,

runtime/src/precompiles/neuron.rs

Lines changed: 12 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,15 +1,21 @@
11
use pallet_evm::{ExitError, PrecompileFailure, PrecompileHandle, PrecompileResult};
22

3-
use crate::precompiles::{dispatch, get_method_id, get_pubkey, get_slice};
3+
use crate::precompiles::{
4+
contract_to_origin, get_method_id, get_pubkey, get_slice, parse_netuid,
5+
try_dispatch_runtime_call,
6+
};
47
use sp_runtime::AccountId32;
58
use sp_std::vec;
69

710
use crate::{Runtime, RuntimeCall};
811
pub const NEURON_PRECOMPILE_INDEX: u64 = 2052;
912

10-
// this is neuron smart contract's(0x0000000000000000000000000000000000000804) sr25519 address
11-
pub const NEURON_CONTRACT_ADDRESS: &str = "5GKZiUUgTnWSz3BgiVBMehEKkLszsG4ZXnvgWpWFUFKqrqyn";
12-
13+
// ss58 public key i.e., the contract sends funds it received to the destination address from the
14+
// method parameter.
15+
const CONTRACT_ADDRESS_SS58: [u8; 32] = [
16+
0xbc, 0x46, 0x35, 0x79, 0xbc, 0x99, 0xf9, 0xee, 0x7c, 0x59, 0xed, 0xee, 0x20, 0x61, 0xa3, 0x09,
17+
0xd2, 0x1e, 0x68, 0xd5, 0x39, 0xb6, 0x40, 0xec, 0x66, 0x46, 0x90, 0x30, 0xab, 0x74, 0xc1, 0xdb,
18+
];
1319
pub struct NeuronPrecompile;
1420

1521
impl NeuronPrecompile {
@@ -38,7 +44,7 @@ impl NeuronPrecompile {
3844
netuid,
3945
hotkey,
4046
});
41-
dispatch(handle, call, NEURON_CONTRACT_ADDRESS)
47+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
4248
}
4349

4450
fn parse_netuid_hotkey_parameter(data: &[u8]) -> Result<(u16, AccountId32), PrecompileFailure> {
@@ -47,9 +53,7 @@ impl NeuronPrecompile {
4753
exit_status: ExitError::InvalidRange,
4854
});
4955
}
50-
let mut netuid_vec = [0u8; 2];
51-
netuid_vec.copy_from_slice(get_slice(data, 30, 32)?);
52-
let netuid = u16::from_be_bytes(netuid_vec);
56+
let netuid = parse_netuid(data, 30)?;
5357

5458
let (hotkey, _) = get_pubkey(get_slice(data, 32, 64)?)?;
5559

runtime/src/precompiles/staking.rs

Lines changed: 19 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,10 @@
2525
// - Precompile checks the result of do_remove_stake and, in case of a failure, reverts the transaction.
2626
//
2727

28-
use crate::precompiles::{dispatch, get_method_id, get_pubkey, get_slice};
28+
use crate::precompiles::{
29+
contract_to_origin, get_method_id, get_pubkey, get_slice, parse_netuid,
30+
try_dispatch_runtime_call,
31+
};
2932
use crate::{ProxyType, Runtime, RuntimeCall};
3033
use pallet_evm::{
3134
BalanceConverter, ExitError, ExitSucceed, PrecompileFailure, PrecompileHandle,
@@ -36,8 +39,14 @@ use sp_runtime::traits::{StaticLookup, UniqueSaturatedInto};
3639
use sp_std::vec;
3740

3841
pub const STAKING_PRECOMPILE_INDEX: u64 = 2049;
39-
// this is staking smart contract's(0x0000000000000000000000000000000000000801) sr25519 address
40-
pub const STAKING_CONTRACT_ADDRESS: &str = "5CwnBK9Ack1mhznmCnwiibCNQc174pYQVktYW3ayRpLm4K2X";
42+
43+
// ss58 public key i.e., the contract sends funds it received to the destination address from the
44+
// method parameter.
45+
const CONTRACT_ADDRESS_SS58: [u8; 32] = [
46+
0x26, 0xf4, 0x10, 0x1e, 0x52, 0xb7, 0x57, 0x34, 0x33, 0x24, 0x5b, 0xc3, 0x0a, 0xe1, 0x8b, 0x63,
47+
0x99, 0x53, 0xd8, 0x41, 0x79, 0x33, 0x03, 0x61, 0x4d, 0xfa, 0xcf, 0xf0, 0x37, 0xf7, 0x12, 0x94,
48+
];
49+
4150
pub struct StakingPrecompile;
4251

4352
impl StakingPrecompile {
@@ -74,14 +83,16 @@ impl StakingPrecompile {
7483
<Runtime as pallet_evm::Config>::BalanceConverter::into_substrate_balance(amount)
7584
.ok_or(ExitError::OutOfFund)?;
7685

86+
// let (account_id_src, _) = get_pubkey(&CONTRACT_ADDRESS_SS58)?;
7787
// Create the add_stake call
7888
let call = RuntimeCall::SubtensorModule(pallet_subtensor::Call::<Runtime>::add_stake {
7989
hotkey,
8090
netuid,
8191
amount_staked: amount_sub.unique_saturated_into(),
8292
});
93+
// let origin = RawOrigin::Signed(account_id_src);
8394
// Dispatch the add_stake call
84-
dispatch(handle, call, STAKING_CONTRACT_ADDRESS)
95+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
8596
}
8697

8798
fn remove_stake(handle: &mut impl PrecompileHandle, data: &[u8]) -> PrecompileResult {
@@ -104,7 +115,7 @@ impl StakingPrecompile {
104115
netuid,
105116
amount_unstaked: amount_sub.unique_saturated_into(),
106117
});
107-
dispatch(handle, call, STAKING_CONTRACT_ADDRESS)
118+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
108119
}
109120

110121
fn add_proxy(handle: &mut impl PrecompileHandle, data: &[u8]) -> PrecompileResult {
@@ -116,7 +127,7 @@ impl StakingPrecompile {
116127
delay: 0,
117128
});
118129

119-
dispatch(handle, call, STAKING_CONTRACT_ADDRESS)
130+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
120131
}
121132

122133
fn remove_proxy(handle: &mut impl PrecompileHandle, data: &[u8]) -> PrecompileResult {
@@ -128,13 +139,13 @@ impl StakingPrecompile {
128139
delay: 0,
129140
});
130141

131-
dispatch(handle, call, STAKING_CONTRACT_ADDRESS)
142+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
132143
}
133144

134145
fn get_stake(data: &[u8]) -> PrecompileResult {
135146
let (hotkey, left_data) = get_pubkey(data)?;
136147
let (coldkey, _) = get_pubkey(&left_data)?;
137-
let netuid = Self::parse_netuid(data, 0x5E)?;
148+
let netuid = parse_netuid(data, 0x5E)?;
138149

139150
let stake = pallet_subtensor::Pallet::<Runtime>::get_stake_for_hotkey_and_coldkey_on_subnet(
140151
&hotkey, &coldkey, netuid,

runtime/src/precompiles/subnet.rs

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
1-
use crate::precompiles::{dispatch, get_method_id, get_pubkey, get_slice};
1+
use crate::precompiles::{
2+
contract_to_origin, get_method_id, get_pubkey, get_slice, try_dispatch_runtime_call,
3+
};
24
use crate::{Runtime, RuntimeCall};
35
use pallet_evm::{ExitError, PrecompileFailure, PrecompileHandle, PrecompileResult};
46
use sp_runtime::AccountId32;
@@ -8,9 +10,12 @@ pub const SUBNET_PRECOMPILE_INDEX: u64 = 2051;
810
// three bytes with max lenght 1K
911
pub const MAX_PARAMETER_SIZE: usize = 3 * 1024;
1012

11-
// this is staking smart contract's(0x0000000000000000000000000000000000000803) sr25519 address
12-
pub const STAKING_CONTRACT_ADDRESS: &str = "5DPSUCb5mZFfizvBDSnRoAqmxV5Bmov2CS3xV773qU6VP1w2";
13-
13+
// ss58 public key i.e., the contract sends funds it received to the destination address from the
14+
// method parameter.
15+
const CONTRACT_ADDRESS_SS58: [u8; 32] = [
16+
0x3a, 0x86, 0x18, 0xfb, 0xbb, 0x1b, 0xbc, 0x47, 0x86, 0x64, 0xff, 0x53, 0x46, 0x18, 0x0c, 0x35,
17+
0xd0, 0x9f, 0xac, 0x26, 0xf2, 0x02, 0x70, 0x85, 0xb3, 0x1c, 0x56, 0xc1, 0x06, 0x3c, 0x1c, 0xd3,
18+
];
1419
pub struct SubnetPrecompile;
1520

1621
impl SubnetPrecompile {
@@ -79,7 +84,7 @@ impl SubnetPrecompile {
7984
};
8085

8186
// Dispatch the register_network call
82-
dispatch(handle, call, STAKING_CONTRACT_ADDRESS)
87+
try_dispatch_runtime_call(handle, call, contract_to_origin(&CONTRACT_ADDRESS_SS58)?)
8388
}
8489

8590
fn parse_register_network_parameters(

0 commit comments

Comments
 (0)