diff --git a/libraries/chain/CMakeLists.txt b/libraries/chain/CMakeLists.txt index 8636af2f5d40ab683a249f55fe029350f27fb99b..a4949e1a0e8ada23acd3ebb7fb62410df314ede5 100644 --- a/libraries/chain/CMakeLists.txt +++ b/libraries/chain/CMakeLists.txt @@ -19,6 +19,7 @@ add_library( eosio_chain transaction_context.cpp eosio_contract.cpp eosio_contract_abi.cpp + chain_config.cpp # chain_config.cpp # block_trace.cpp diff --git a/libraries/chain/chain_config.cpp b/libraries/chain/chain_config.cpp new file mode 100644 index 0000000000000000000000000000000000000000..b62d4c177bb8ebb3868cb837217c52b0e1670ddc --- /dev/null +++ b/libraries/chain/chain_config.cpp @@ -0,0 +1,43 @@ +/** + * @file + * @copyright defined in eos/LICENSE.txt + */ + +#include +#include + +namespace eosio { namespace chain { + + void chain_config::validate()const { + EOS_ASSERT( target_block_net_usage_pct <= config::percent_100, action_validate_exception, + "target block net usage percentage cannot exceed 100%" ); + EOS_ASSERT( target_block_net_usage_pct >= config::percent_1/10, action_validate_exception, + "target block net usage percentage must be at least 0.1%" ); + EOS_ASSERT( target_block_cpu_usage_pct <= config::percent_100, action_validate_exception, + "target block cpu usage percentage cannot exceed 100%" ); + EOS_ASSERT( target_block_cpu_usage_pct >= config::percent_1/10, action_validate_exception, + "target block cpu usage percentage must be at least 0.1%" ); + + EOS_ASSERT( max_transaction_net_usage < max_block_net_usage, action_validate_exception, + "max transaction net usage must be less than max block net usage" ); + EOS_ASSERT( max_transaction_cpu_usage < max_block_cpu_usage, action_validate_exception, + "max transaction cpu usage must be less than max block cpu usage" ); + + EOS_ASSERT( base_per_transaction_net_usage < max_transaction_net_usage, action_validate_exception, + "base net usage per transaction must be less than the max transaction net usage" ); + EOS_ASSERT( (max_transaction_net_usage - base_per_transaction_net_usage) >= config::min_net_usage_delta_between_base_and_max_for_trx, + action_validate_exception, + "max transaction net usage must be at least ${delta} bytes larger than base net usage per transaction", + ("delta", config::min_net_usage_delta_between_base_and_max_for_trx) ); + EOS_ASSERT( context_free_discount_net_usage_den > 0, action_validate_exception, + "net usage discount ratio for context free data cannot have a 0 denominator" ); + EOS_ASSERT( context_free_discount_net_usage_num <= context_free_discount_net_usage_den, action_validate_exception, + "net usage discount ratio for context free data cannot exceed 1" ); + + EOS_ASSERT( min_transaction_cpu_usage <= max_transaction_cpu_usage, action_validate_exception, + "min transaction cpu usage cannot exceed max transaction cpu usage" ); + EOS_ASSERT( max_transaction_cpu_usage < (max_block_cpu_usage - min_transaction_cpu_usage), action_validate_exception, + "max transaction cpu usage must be at less than the difference between the max block cpu usage and the min transaction cpu usage" ); + } + +} } // namespace eosio::chain diff --git a/libraries/chain/controller.cpp b/libraries/chain/controller.cpp index 89137f7354f90a431f5cb75028d050642e23ca1e..bf8cb76da8c853be38102effc35c23a4c21e0f22 100644 --- a/libraries/chain/controller.cpp +++ b/libraries/chain/controller.cpp @@ -365,6 +365,7 @@ struct controller_impl { bs.block_id = head->id; }); + conf.genesis.initial_configuration.validate(); db.create([&](auto& gpo ){ gpo.configuration = conf.genesis.initial_configuration; }); diff --git a/libraries/chain/include/eosio/chain/chain_config.hpp b/libraries/chain/include/eosio/chain/chain_config.hpp index ab99ad6740228ceee5ec5fb299d59e8be19243bf..b41d9faa2772ab81927d6c1f8586d4bc48dba2fb 100644 --- a/libraries/chain/include/eosio/chain/chain_config.hpp +++ b/libraries/chain/include/eosio/chain/chain_config.hpp @@ -38,6 +38,8 @@ struct chain_config { uint16_t max_authority_depth; ///< recursion depth limit for checking if an authority is satisfied uint32_t max_generated_transaction_count; ///< the number of generated transactions per action (TODO: implement?) + void validate()const; + template friend Stream& operator << ( Stream& out, const chain_config& c ) { return out << "Max Block Net Usage: " << c.max_block_net_usage << ", " diff --git a/libraries/chain/include/eosio/chain/config.hpp b/libraries/chain/include/eosio/chain/config.hpp index e9f7c2a0d73ff5bbff3003a506c4241b8f54e4df..1f8cd67e49f7a36300c1b8936534d03adaf8378a 100644 --- a/libraries/chain/include/eosio/chain/config.hpp +++ b/libraries/chain/include/eosio/chain/config.hpp @@ -81,6 +81,10 @@ const static uint16_t default_max_inline_action_depth = 4; const static uint16_t default_max_auth_depth = 6; const static uint32_t default_max_gen_trx_count = 16; +const static uint32_t min_net_usage_delta_between_base_and_max_for_trx = 10*1024; +// Should be large enough to allow recovery from badly set blockchain parameters without a hard fork +// (unless net_usage_leeway is set to 0 and so are the net limits of all accounts that can help with resetting blockchain parameters). + const static uint32_t fixed_net_overhead_of_packed_trx = 16; // TODO: is this reasonable? const static uint32_t fixed_overhead_shared_vector_ram_bytes = 16; ///< overhead accounts for fixed portion of size of shared_vector field diff --git a/libraries/chain/wasm_interface.cpp b/libraries/chain/wasm_interface.cpp index 24736cc9f6a71b1e96494480ace57324171c19e4..c84d8254b68e0f85ccaf7676c29100102e1fdc5e 100644 --- a/libraries/chain/wasm_interface.cpp +++ b/libraries/chain/wasm_interface.cpp @@ -179,6 +179,7 @@ class privileged_api : public context_aware_api { datastream ds( packed_blockchain_parameters, datalen ); chain::chain_config cfg; fc::raw::unpack(ds, cfg); + cfg.validate(); context.db.modify( context.control.get_global_properties(), [&]( auto& gprops ) { gprops.configuration = cfg;