diff --git a/ethcore/res/ethereum/frontier.json b/ethcore/res/ethereum/frontier.json index be473237c..b951973f8 100644 --- a/ethcore/res/ethereum/frontier.json +++ b/ethcore/res/ethereum/frontier.json @@ -134,7 +134,8 @@ "eip155Transition": "0x7fffffffffffffff", "eip160Transition": "0x7fffffffffffffff", "eip161abcTransition": "0x7fffffffffffffff", - "eip161dTransition": "0x7fffffffffffffff" + "eip161dTransition": "0x7fffffffffffffff", + "maxCodeSize": 24576 } } }, diff --git a/ethcore/src/client/test_client.rs b/ethcore/src/client/test_client.rs index 434edd3e8..ea220fb1c 100644 --- a/ethcore/src/client/test_client.rs +++ b/ethcore/src/client/test_client.rs @@ -315,7 +315,7 @@ pub fn get_temp_state_db() -> GuardedTempResult { impl MiningBlockChainClient for TestBlockChainClient { fn latest_schedule(&self) -> Schedule { - Schedule::new_post_eip150(true, true, true) + Schedule::new_post_eip150(24576, true, true, true) } fn prepare_open_block(&self, author: Address, gas_range_target: (U256, U256), extra_data: Bytes) -> OpenBlock { diff --git a/ethcore/src/engines/instant_seal.rs b/ethcore/src/engines/instant_seal.rs index 75fae4d81..3dc78d1a2 100644 --- a/ethcore/src/engines/instant_seal.rs +++ b/ethcore/src/engines/instant_seal.rs @@ -55,7 +55,7 @@ impl Engine for InstantSeal { } fn schedule(&self, _env_info: &EnvInfo) -> Schedule { - Schedule::new_post_eip150(false, false, false) + Schedule::new_post_eip150(usize::max_value(), false, false, false) } fn is_sealer(&self, _author: &Address) -> Option { Some(true) } diff --git a/ethcore/src/ethereum/ethash.rs b/ethcore/src/ethereum/ethash.rs index 6436e3531..de2a85942 100644 --- a/ethcore/src/ethereum/ethash.rs +++ b/ethcore/src/ethereum/ethash.rs @@ -73,7 +73,9 @@ pub struct EthashParams { /// Number of first block where ECIP-1010 begins. pub ecip1010_pause_transition: u64, /// Number of first block where ECIP-1010 ends. - pub ecip1010_continue_transition: u64 + pub ecip1010_continue_transition: u64, + /// Maximum amount of code that can be deploying into a contract. + pub max_code_size: u64, } impl From for EthashParams { @@ -87,19 +89,20 @@ impl From for EthashParams { block_reward: p.block_reward.into(), registrar: p.registrar.map_or_else(Address::new, Into::into), homestead_transition: p.homestead_transition.map_or(0, Into::into), - dao_hardfork_transition: p.dao_hardfork_transition.map_or(0x7fffffffffffffff, Into::into), + dao_hardfork_transition: p.dao_hardfork_transition.map_or(u64::max_value(), Into::into), dao_hardfork_beneficiary: p.dao_hardfork_beneficiary.map_or_else(Address::new, Into::into), dao_hardfork_accounts: p.dao_hardfork_accounts.unwrap_or_else(Vec::new).into_iter().map(Into::into).collect(), - difficulty_hardfork_transition: p.difficulty_hardfork_transition.map_or(0x7fffffffffffffff, Into::into), + difficulty_hardfork_transition: p.difficulty_hardfork_transition.map_or(u64::max_value(), Into::into), difficulty_hardfork_bound_divisor: p.difficulty_hardfork_bound_divisor.map_or(p.difficulty_bound_divisor.into(), Into::into), - bomb_defuse_transition: p.bomb_defuse_transition.map_or(0x7fffffffffffffff, Into::into), + bomb_defuse_transition: p.bomb_defuse_transition.map_or(u64::max_value(), Into::into), eip150_transition: p.eip150_transition.map_or(0, Into::into), eip155_transition: p.eip155_transition.map_or(0, Into::into), eip160_transition: p.eip160_transition.map_or(0, Into::into), eip161abc_transition: p.eip161abc_transition.map_or(0, Into::into), - eip161d_transition: p.eip161d_transition.map_or(0x7fffffffffffffff, Into::into), - ecip1010_pause_transition: p.ecip1010_pause_transition.map_or(0x7fffffffffffffff, Into::into), - ecip1010_continue_transition: p.ecip1010_continue_transition.map_or(0x7fffffffffffffff, Into::into), + eip161d_transition: p.eip161d_transition.map_or(u64::max_value(), Into::into), + ecip1010_pause_transition: p.ecip1010_pause_transition.map_or(u64::max_value(), Into::into), + ecip1010_continue_transition: p.ecip1010_continue_transition.map_or(u64::max_value(), Into::into), + max_code_size: p.max_code_size.map_or(u64::max_value(), Into::into), } } } @@ -152,6 +155,7 @@ impl Engine for Ethash { Schedule::new_homestead() } else { Schedule::new_post_eip150( + self.ethash_params.max_code_size as usize, env_info.number >= self.ethash_params.eip160_transition, env_info.number >= self.ethash_params.eip161abc_transition, env_info.number >= self.ethash_params.eip161d_transition diff --git a/ethcore/src/evm/schedule.rs b/ethcore/src/evm/schedule.rs index b68f6acb5..773708956 100644 --- a/ethcore/src/evm/schedule.rs +++ b/ethcore/src/evm/schedule.rs @@ -70,6 +70,8 @@ pub struct Schedule { pub quad_coeff_div: usize, /// Cost for contract length when executing `CREATE` pub create_data_gas: usize, + /// Maximum code size when creating a contract. + pub create_data_limit: usize, /// Transaction cost pub tx_gas: usize, /// `CREATE` transaction cost @@ -111,7 +113,7 @@ impl Schedule { } /// Schedule for the post-EIP-150-era of the Ethereum main net. - pub fn new_post_eip150(fix_exp: bool, no_empty: bool, kill_empty: bool) -> Schedule { + pub fn new_post_eip150(max_code_size: usize, fix_exp: bool, no_empty: bool, kill_empty: bool) -> Schedule { Schedule { exceptional_failed_code_deposit: true, have_delegate_call: true, @@ -139,6 +141,7 @@ impl Schedule { memory_gas: 3, quad_coeff_div: 512, create_data_gas: 200, + create_data_limit: max_code_size, tx_gas: 21000, tx_create_gas: 53000, tx_data_zero_gas: 4, @@ -183,6 +186,7 @@ impl Schedule { memory_gas: 3, quad_coeff_div: 512, create_data_gas: 200, + create_data_limit: usize::max_value(), tx_gas: 21000, tx_create_gas: tcg, tx_data_zero_gas: 4, diff --git a/ethcore/src/externalities.rs b/ethcore/src/externalities.rs index df1b64e67..3704ead67 100644 --- a/ethcore/src/externalities.rs +++ b/ethcore/src/externalities.rs @@ -242,7 +242,7 @@ impl<'a, T, V> Ext for Externalities<'a, T, V> where T: 'a + Tracer, V: 'a + VMT }, OutputPolicy::InitContract(ref mut copy) => { let return_cost = U256::from(data.len()) * U256::from(self.schedule.create_data_gas); - if return_cost > *gas { + if return_cost > *gas || data.len() > self.schedule.create_data_limit { return match self.schedule.exceptional_failed_code_deposit { true => Err(evm::Error::OutOfGas), false => Ok(*gas) diff --git a/ethcore/src/tests/helpers.rs b/ethcore/src/tests/helpers.rs index 96d5f8366..adfb4f096 100644 --- a/ethcore/src/tests/helpers.rs +++ b/ethcore/src/tests/helpers.rs @@ -433,18 +433,19 @@ pub fn get_default_ethash_params() -> EthashParams{ block_reward: U256::from(0), registrar: "0000000000000000000000000000000000000001".into(), homestead_transition: 1150000, - dao_hardfork_transition: 0x7fffffffffffffff, + dao_hardfork_transition: u64::max_value(), dao_hardfork_beneficiary: "0000000000000000000000000000000000000001".into(), dao_hardfork_accounts: vec![], - difficulty_hardfork_transition: 0x7fffffffffffffff, + difficulty_hardfork_transition: u64::max_value(), difficulty_hardfork_bound_divisor: U256::from(0), - bomb_defuse_transition: 0x7fffffffffffffff, - eip150_transition: 0x7fffffffffffffff, - eip155_transition: 0x7fffffffffffffff, - eip160_transition: 0x7fffffffffffffff, - eip161abc_transition: 0x7fffffffffffffff, - eip161d_transition: 0x7fffffffffffffff, - ecip1010_pause_transition: 0x7fffffffffffffff, - ecip1010_continue_transition: 0x7fffffffffffffff + bomb_defuse_transition: u64::max_value(), + eip150_transition: u64::max_value(), + eip155_transition: u64::max_value(), + eip160_transition: u64::max_value(), + eip161abc_transition: u64::max_value(), + eip161d_transition: u64::max_value(), + ecip1010_pause_transition: u64::max_value(), + ecip1010_continue_transition: u64::max_value(), + max_code_size: u64::max_value(), } } diff --git a/json/src/spec/ethash.rs b/json/src/spec/ethash.rs index 10f0c6293..752d6853e 100644 --- a/json/src/spec/ethash.rs +++ b/json/src/spec/ethash.rs @@ -92,6 +92,11 @@ pub struct EthashParams { /// See main EthashParams docs. #[serde(rename="ecip1010ContinueTransition")] pub ecip1010_continue_transition: Option, + + /// See main EthashParams docs. + #[serde(rename="maxCodeSize")] + pub max_code_size: Option, + } /// Ethash engine deserialization.