frontier_template_runtime/
precompiles.rs

1use core::marker::PhantomData;
2use pallet_evm::{
3	IsPrecompileResult, Precompile, PrecompileHandle, PrecompileResult, PrecompileSet,
4};
5use sp_core::H160;
6
7use pallet_evm_precompile_curve25519 as curve25519_precompile;
8use pallet_evm_precompile_modexp::Modexp;
9use pallet_evm_precompile_sha3fips::Sha3FIPS256;
10use pallet_evm_precompile_simple::{ECRecover, ECRecoverPublicKey, Identity, Ripemd160, Sha256};
11
12pub struct FrontierPrecompiles<R>(PhantomData<R>);
13
14impl<R> FrontierPrecompiles<R>
15where
16	R: pallet_evm::Config,
17{
18	pub fn new() -> Self {
19		Self(Default::default())
20	}
21	pub fn used_addresses() -> [H160; 9] {
22		[
23			hash(1),
24			hash(2),
25			hash(3),
26			hash(4),
27			hash(5),
28			hash(1024),
29			hash(1025),
30			hash(1026),
31			hash(1027),
32		]
33	}
34}
35impl<R> PrecompileSet for FrontierPrecompiles<R>
36where
37	R: pallet_evm::Config + frame_system::Config,
38{
39	fn execute(&self, handle: &mut impl PrecompileHandle) -> Option<PrecompileResult> {
40		match handle.code_address() {
41			// Ethereum precompiles :
42			a if a == hash(1) => Some(ECRecover::execute(handle)),
43			a if a == hash(2) => Some(Sha256::execute(handle)),
44			a if a == hash(3) => Some(Ripemd160::execute(handle)),
45			a if a == hash(4) => Some(Identity::execute(handle)),
46			a if a == hash(5) => Some(Modexp::execute(handle)),
47			// Non-Frontier specific nor Ethereum precompiles :
48			a if a == hash(1024) => Some(Sha3FIPS256::<
49				R,
50				crate::weights::pallet_evm_precompile_sha3fips::WeightInfo<R>,
51			>::execute(handle)),
52			a if a == hash(1025) => Some(ECRecoverPublicKey::execute(handle)),
53			// Curve25519 precompiles
54			a if a == hash(1026) => Some(curve25519_precompile::Curve25519Add::<
55				R,
56				crate::weights::pallet_evm_precompile_curve25519::WeightInfo<R>,
57			>::execute(handle)),
58			a if a == hash(1027) => Some(curve25519_precompile::Curve25519ScalarMul::<
59				R,
60				crate::weights::pallet_evm_precompile_curve25519::WeightInfo<R>,
61			>::execute(handle)),
62			_ => None,
63		}
64	}
65
66	fn is_precompile(&self, address: H160, _gas: u64) -> IsPrecompileResult {
67		IsPrecompileResult::Answer {
68			is_precompile: Self::used_addresses().contains(&address),
69			extra_cost: 0,
70		}
71	}
72}
73
74fn hash(a: u64) -> H160 {
75	H160::from_low_u64_be(a)
76}