aurora_engine_precompiles/
account_ids.rs1use aurora_engine_sdk::env::Env;
2use aurora_engine_types::account_id::AccountId;
3use aurora_evm::{Context, ExitError};
4
5use super::{EvmPrecompileResult, Precompile};
6use crate::prelude::types::{Address, EthGas, make_address};
7use crate::{PrecompileOutput, utils};
8
9mod costs {
10 use crate::prelude::types::EthGas;
11
12 pub(super) const PREDECESSOR_ACCOUNT_GAS: EthGas = EthGas::new(0);
14 #[allow(dead_code)]
16 pub(super) const CURRENT_ACCOUNT_GAS: EthGas = EthGas::new(0);
17}
18
19pub struct PredecessorAccount<'a, E> {
20 env: &'a E,
21}
22
23pub mod predecessor_account {
24 use aurora_engine_types::types::{Address, make_address};
25
26 pub const ADDRESS: Address = make_address(0x723ffbab, 0xa940e75e7bf5f6d61dcbf8d9a4de0fd7);
31}
32
33impl<'a, E> PredecessorAccount<'a, E> {
34 pub const fn new(env: &'a E) -> Self {
35 Self { env }
36 }
37}
38
39impl<E: Env> Precompile for PredecessorAccount<'_, E> {
40 fn required_gas(_input: &[u8]) -> Result<EthGas, ExitError> {
41 Ok(costs::PREDECESSOR_ACCOUNT_GAS)
42 }
43
44 fn run(
45 &self,
46 input: &[u8],
47 target_gas: Option<EthGas>,
48 context: &Context,
49 _is_static: bool,
50 ) -> EvmPrecompileResult {
51 utils::validate_no_value_attached_to_precompile(context.apparent_value)?;
52 let cost = Self::required_gas(input)?;
53 if let Some(target_gas) = target_gas {
54 if cost > target_gas {
55 return Err(ExitError::OutOfGas);
56 }
57 }
58
59 let predecessor_account_id = self.env.predecessor_account_id();
60 Ok(PrecompileOutput::without_logs(
61 cost,
62 predecessor_account_id.as_bytes().to_vec(),
63 ))
64 }
65}
66
67pub struct CurrentAccount {
68 current_account_id: AccountId,
69}
70
71impl CurrentAccount {
72 pub const ADDRESS: Address = make_address(0xfefae79e, 0x4180eb0284f261205e3f8cea737aff56);
77
78 #[must_use]
79 pub const fn new(current_account_id: AccountId) -> Self {
80 Self { current_account_id }
81 }
82}
83
84impl Precompile for CurrentAccount {
85 fn required_gas(_input: &[u8]) -> Result<EthGas, ExitError> {
86 Ok(costs::PREDECESSOR_ACCOUNT_GAS)
87 }
88
89 fn run(
90 &self,
91 input: &[u8],
92 target_gas: Option<EthGas>,
93 context: &Context,
94 _is_static: bool,
95 ) -> EvmPrecompileResult {
96 utils::validate_no_value_attached_to_precompile(context.apparent_value)?;
97 let cost = Self::required_gas(input)?;
98 if let Some(target_gas) = target_gas {
99 if cost > target_gas {
100 return Err(ExitError::OutOfGas);
101 }
102 }
103
104 Ok(PrecompileOutput::without_logs(
105 cost,
106 self.current_account_id.as_bytes().to_vec(),
107 ))
108 }
109}
110
111#[cfg(test)]
112mod tests {
113 use crate::account_ids::{CurrentAccount, predecessor_account};
114 use crate::prelude::sdk::types::near_account_to_evm_address;
115
116 #[test]
117 fn test_predecessor_account_precompile_id() {
118 assert_eq!(
119 predecessor_account::ADDRESS,
120 near_account_to_evm_address(b"predecessorAccountId")
121 );
122 }
123
124 #[test]
125 fn test_current_account_precompile_id() {
126 assert_eq!(
127 CurrentAccount::ADDRESS,
128 near_account_to_evm_address(b"currentAccountId")
129 );
130 }
131}