1use std::{collections::BTreeMap, convert::TryInto, path::PathBuf, sync::Arc};
6
7use cfx_rpc_builder::RpcModuleSelection;
8use lazy_static::*;
9use log::{error, warn};
10use parking_lot::RwLock;
11use rand::Rng;
12
13use cfx_addr::{cfx_addr_decode, Network};
14use cfx_executor::{machine::Machine, spec::CommonParams};
15use cfx_internal_common::{
16 ChainIdParams, ChainIdParamsInner, ChainIdParamsOneChainInner,
17};
18use cfx_parameters::{
19 block::DEFAULT_TARGET_BLOCK_GAS_LIMIT, tx_pool::TXPOOL_DEFAULT_NONCE_BITS,
20};
21use cfx_rpc_cfx_types::{
22 address::USE_SIMPLE_RPC_ADDRESS, apis::ApiSet, RpcImplConfiguration,
23};
24use cfx_storage::{
25 defaults::DEFAULT_DEBUG_SNAPSHOT_CHECKER_THREADS, storage_dir,
26 ConsensusParam, ProvideExtraSnapshotSyncConfig, StorageConfiguration,
27};
28use cfx_types::{
29 parse_hex_string, Address, AllChainID, Space, SpaceMap, H256, U256,
30};
31use cfxcore::{
32 block_data_manager::{DataManagerConfiguration, DbType},
33 block_parameters::*,
34 cache_config::{
35 DEFAULT_INVALID_BLOCK_HASH_CACHE_SIZE_IN_COUNT,
36 DEFAULT_LEDGER_CACHE_SIZE,
37 DEFAULT_TARGET_DIFFICULTIES_CACHE_SIZE_IN_COUNT,
38 },
39 consensus::{
40 consensus_inner::consensus_executor::ConsensusExecutionConfiguration,
41 pivot_hint::PivotHintConfig, ConsensusConfig, ConsensusInnerConfig,
42 },
43 consensus_internal_parameters::*,
44 consensus_parameters::*,
45 light_protocol::LightNodeConfiguration,
46 sync::{ProtocolConfiguration, StateSyncConfiguration, SyncGraphConfig},
47 sync_parameters::*,
48 transaction_pool::TxPoolConfig,
49 NodeType,
50};
51use diem_types::term_state::{
52 pos_state_config::PosStateConfig, IN_QUEUE_LOCKED_VIEWS,
53 OUT_QUEUE_LOCKED_VIEWS, ROUND_PER_TERM, TERM_ELECTED_SIZE, TERM_MAX_SIZE,
54};
55use jsonrpsee::server::ServerConfigBuilder;
56use metrics::MetricsConfiguration;
57use network::DiscoveryConfiguration;
58use primitives::block_header::CIP112_TRANSITION_HEIGHT;
59use txgen::TransactionGeneratorConfig;
60
61use crate::{HttpConfiguration, TcpConfiguration, WsConfiguration};
62
63lazy_static! {
64 pub static ref CHAIN_ID: RwLock<Option<ChainIdParams>> = Default::default();
65}
66const BLOCK_DB_DIR_NAME: &str = "blockchain_db";
67const NET_CONFIG_DB_DIR_NAME: &str = "net_config";
68
69build_config! {
87 {
88 (mode, (Option<String>), None)
113 (debug_invalid_state_root, (bool), false)
115 (debug_invalid_state_root_epoch, (Option<String>), None)
116 (debug_dump_dir_invalid_state_root, (String), "./storage_db/debug_dump_invalid_state_root/".to_string())
117 (dev_block_interval_ms, (Option<u64>), None)
120 (dev_pack_tx_immediately, (Option<bool>), None)
121 (enable_state_expose, (bool), false)
122 (generate_tx, (bool), false)
123 (generate_tx_period_us, (Option<u64>), Some(100_000))
124 (log_conf, (Option<String>), None)
125 (log_file, (Option<String>), None)
126 (max_block_size_in_bytes, (usize), MAX_BLOCK_SIZE_IN_BYTES)
127 (evm_transaction_block_ratio,(u64),EVM_TRANSACTION_BLOCK_RATIO)
128 (evm_transaction_gas_ratio,(u64),EVM_TRANSACTION_GAS_RATIO)
129 (metrics_enabled, (bool), false)
130 (metrics_influxdb_host, (Option<String>), None)
131 (metrics_influxdb_db, (String), "conflux".into())
132 (metrics_influxdb_username, (Option<String>), None)
133 (metrics_influxdb_password, (Option<String>), None)
134 (metrics_influxdb_node, (Option<String>), None)
135 (metrics_output_file, (Option<String>), None)
136 (metrics_report_interval_ms, (u64), 3_000)
137 (metrics_prometheus_listen_addr, (Option<String>), None)
138 (profiling_listen_addr, (Option<String>), None)
139 (rocksdb_disable_wal, (bool), false)
140 (txgen_account_count, (usize), 10)
141
142 (adaptive_weight_beta, (u64), ADAPTIVE_WEIGHT_DEFAULT_BETA)
144 (anticone_penalty_ratio, (u64), ANTICONE_PENALTY_RATIO)
145 (chain_id, (Option<u32>), None)
146 (evm_chain_id, (Option<u32>), None)
147 (execute_genesis, (bool), true)
148 (default_transition_time, (Option<u64>), None)
149 (dev_snapshot_epoch_count, (u32), SNAPSHOT_EPOCHS_CAPACITY)
152 (era_epoch_count, (u64), ERA_DEFAULT_EPOCH_COUNT)
153 (heavy_block_difficulty_ratio, (u64), HEAVY_BLOCK_DEFAULT_DIFFICULTY_RATIO)
154 (genesis_accounts, (Option<String>), None)
155 (genesis_evm_secrets, (Option<String>), None)
156 (genesis_secrets, (Option<String>), None)
157 (pivot_hint_path, (Option<String>), None)
158 (pivot_hint_checksum, (Option<String>), None)
159 (initial_difficulty, (Option<u64>), None)
160 (referee_bound, (usize), REFEREE_DEFAULT_BOUND)
161 (timer_chain_beta, (u64), TIMER_CHAIN_DEFAULT_BETA)
162 (timer_chain_block_difficulty_ratio, (u64), TIMER_CHAIN_BLOCK_DEFAULT_DIFFICULTY_RATIO)
163 (transaction_epoch_bound, (u64), TRANSACTION_DEFAULT_EPOCH_BOUND)
165
166
167 (tanzanite_transition_height, (u64), TANZANITE_HEIGHT)
170 (hydra_transition_number, (Option<u64>), None)
172 (hydra_transition_height, (Option<u64>), None)
173 (cip43_init_end_number, (Option<u64>), None)
174 (cip78_patch_transition_number,(Option<u64>),None)
175 (cip90_transition_height,(Option<u64>),None)
176 (cip90_transition_number,(Option<u64>),None)
177 (dao_vote_transition_number, (Option<u64>), None)
179 (dao_vote_transition_height, (Option<u64>), None)
180 (cip105_transition_number, (Option<u64>), None)
181 (params_dao_vote_period, (u64), DAO_PARAMETER_VOTE_PERIOD)
182 (sigma_fix_transition_number, (Option<u64>), None)
184 (cip107_transition_number, (Option<u64>), None)
186 (cip112_transition_height, (Option<u64>), None)
187 (cip118_transition_number, (Option<u64>), None)
188 (cip119_transition_number, (Option<u64>), None)
189 (base_fee_burn_transition_number, (Option<u64>), None)
191 (base_fee_burn_transition_height, (Option<u64>), None)
192 (cip1559_transition_height, (Option<u64>), None)
193 (cancun_opcodes_transition_number, (Option<u64>), None)
194 (min_native_base_price, (Option<u64>), None)
195 (min_eth_base_price, (Option<u64>), None)
196 (c2_fix_transition_height, (Option<u64>), None)
198 (eoa_code_transition_height, (Option<u64>), None)
200 (cip151_transition_height, (Option<u64>), None)
201 (cip645_transition_height, (Option<u64>), None)
202 (cip145_fix_transition_height, (Option<u64>), None)
203 (align_evm_transition_height, (u64), u64::MAX)
205 (cip166_transition_height, (Option<u64>), None)
207 (osaka_opcode_transition_height, (Option<u64>), None)
208
209
210
211 (mining_author, (Option<String>), None)
213 (mining_type, (Option<String>), None)
214 (stratum_listen_address, (String), "127.0.0.1".into())
215 (stratum_port, (u16), 32525)
216 (stratum_secret, (Option<String>), None)
217 (use_octopus_in_test_mode, (bool), false)
218 (pow_problem_window_size, (usize), 1)
219
220 (jsonrpc_local_tcp_port, (Option<u16>), None)
222 (jsonrpc_local_http_port, (Option<u16>), None)
223 (jsonrpc_local_ws_port, (Option<u16>), None)
224 (jsonrpc_ws_port, (Option<u16>), None)
225 (jsonrpc_tcp_port, (Option<u16>), None)
226 (jsonrpc_http_port, (Option<u16>), None)
227 (jsonrpc_http_threads, (Option<usize>), None)
228 (jsonrpc_cors, (Option<String>), None)
229 (jsonrpc_http_keep_alive, (bool), false)
230 (jsonrpc_ws_max_payload_bytes, (usize), 30 * 1024 * 1024)
231 (jsonrpc_http_eth_port, (Option<u16>), None)
232 (jsonrpc_ws_eth_port, (Option<u16>), None)
233 (jsonrpc_max_request_body_size, (u32), 10 * 1024 * 1024)
234 (jsonrpc_max_response_body_size, (u32), 10 * 1024 * 1024)
235 (jsonrpc_max_connections, (u32), 100)
236 (jsonrpc_max_subscriptions_per_connection, (u32), 1024)
237 (jsonrpc_message_buffer_capacity, (u32), 1024)
238 (network_id, (Option<u64>), None)
243 (rpc_enable_metrics, (bool), false)
244 (tcp_port, (u16), 32323)
245 (public_tcp_port, (Option<u16>), None)
246 (public_address, (Option<String>), None)
247 (udp_port, (Option<u16>), Some(32323))
248 (max_estimation_gas_limit, (Option<u64>), None)
249 (rpc_address_simple_mode, (bool), false)
250
251 (blocks_request_timeout_ms, (u64), 20_000)
253 (check_request_period_ms, (u64), 1_000)
254 (chunk_size_byte, (u64), DEFAULT_CHUNK_SIZE)
255 (demote_peer_for_timeout, (bool), false)
256 (dev_allow_phase_change_without_peer, (bool), false)
257 (egress_queue_capacity, (usize), 256)
258 (egress_min_throttle, (usize), 10)
259 (egress_max_throttle, (usize), 64)
260 (expire_block_gc_period_s, (u64), 900)
261 (headers_request_timeout_ms, (u64), 10_000)
262 (heartbeat_period_interval_ms, (u64), 30_000)
263 (heartbeat_timeout_ms, (u64), 180_000)
264 (inflight_pending_tx_index_maintain_timeout_ms, (u64), 30_000)
265 (max_allowed_timeout_in_observing_period, (u64), 10)
266 (max_chunk_number_in_manifest, (usize), 500)
267 (max_downloading_chunks, (usize), 8)
268 (max_downloading_chunk_attempts, (usize), 5)
269 (max_downloading_manifest_attempts, (usize), 5)
270 (max_handshakes, (usize), 64)
271 (max_incoming_peers, (usize), 64)
272 (max_inflight_request_count, (u64), 64)
273 (max_outgoing_peers, (usize), 8)
274 (max_outgoing_peers_archive, (Option<usize>), None)
275 (max_peers_tx_propagation, (usize), 128)
276 (max_unprocessed_block_size_mb, (usize), (128))
277 (min_peers_tx_propagation, (usize), 8)
278 (min_phase_change_normal_peer_count, (usize), 3)
279 (received_tx_index_maintain_timeout_ms, (u64), 300_000)
280 (request_block_with_public, (bool), false)
281 (send_tx_period_ms, (u64), 1300)
282 (snapshot_candidate_request_timeout_ms, (u64), 10_000)
283 (snapshot_chunk_request_timeout_ms, (u64), 30_000)
284 (snapshot_manifest_request_timeout_ms, (u64), 30_000)
285 (sync_expire_block_timeout_s, (u64), 7200)
286 (throttling_conf, (Option<String>), None)
287 (timeout_observing_period_s, (u64), 600)
288 (transaction_request_timeout_ms, (u64), 30_000)
289 (tx_maintained_for_peer_timeout_ms, (u64), 600_000)
290
291 (bootnodes, (Option<String>), None)
293 (discovery_discover_node_count, (u32), 16)
294 (discovery_expire_time_s, (u64), 20)
295 (discovery_fast_refresh_timeout_ms, (u64), 10_000)
296 (discovery_find_node_timeout_ms, (u64), 2_000)
297 (discovery_housekeeping_timeout_ms, (u64), 1_000)
298 (discovery_max_nodes_ping, (usize), 32)
299 (discovery_ping_timeout_ms, (u64), 2_000)
300 (discovery_round_timeout_ms, (u64), 500)
301 (discovery_throttling_interval_ms, (u64), 1_000)
302 (discovery_throttling_limit_ping, (usize), 20)
303 (discovery_throttling_limit_find_nodes, (usize), 10)
304 (enable_discovery, (bool), true)
305 (netconf_dir, (Option<String>), None)
306 (net_key, (Option<String>), None)
307 (node_table_timeout_s, (u64), 300)
308 (node_table_promotion_timeout_s, (u64), 3 * 24 * 3600)
309 (session_ip_limits, (String), "1,8,4,2".into())
310 (subnet_quota, (usize), 128)
311
312 (tx_cache_index_maintain_timeout_ms, (u64), 300_000)
314 (tx_pool_size, (usize), 50_000)
315 (tx_pool_min_native_tx_gas_price, (Option<u64>), None)
316 (tx_pool_min_eth_tx_gas_price, (Option<u64>), None)
317 (tx_pool_nonce_bits, (usize), TXPOOL_DEFAULT_NONCE_BITS)
318 (tx_pool_allow_gas_over_half_block, (bool), false)
319 (max_packing_batch_gas_limit, (u64), 3_000_000)
320 (max_packing_batch_size, (usize), 50)
321 (packing_pool_degree, (u8), 4)
322
323
324 (additional_maintained_snapshot_count, (u32), 1)
326 (additional_maintained_block_body_epoch_count, (Option<usize>), None)
328 (additional_maintained_execution_result_epoch_count, (Option<usize>), None)
329 (additional_maintained_reward_epoch_count, (Option<usize>), None)
330 (additional_maintained_trace_epoch_count, (Option<usize>), None)
331 (additional_maintained_transaction_index_epoch_count, (Option<usize>), None)
332 (block_cache_gc_period_ms, (u64), 5_000)
333 (block_db_dir, (Option<String>), None)
334 (block_db_type, (String), "rocksdb".to_string())
335 (checkpoint_gc_time_in_era_count, (f64), 0.5)
336 (conflux_data_dir, (String), "./blockchain_data".to_string())
338 (enable_single_mpt_storage, (bool), false)
339 (ledger_cache_size, (usize), DEFAULT_LEDGER_CACHE_SIZE)
340 (invalid_block_hash_cache_size_in_count, (usize), DEFAULT_INVALID_BLOCK_HASH_CACHE_SIZE_IN_COUNT)
341 (rocksdb_cache_size, (Option<usize>), Some(128))
342 (rocksdb_compaction_profile, (Option<String>), None)
343 (storage_delta_mpts_cache_recent_lfu_factor, (f64), cfx_storage::defaults::DEFAULT_DELTA_MPTS_CACHE_RECENT_LFU_FACTOR)
344 (storage_delta_mpts_cache_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_CACHE_SIZE)
345 (storage_delta_mpts_cache_start_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_CACHE_START_SIZE)
346 (storage_delta_mpts_node_map_vec_size, (u32), cfx_storage::defaults::MAX_CACHED_TRIE_NODES_R_LFU_COUNTER)
347 (storage_delta_mpts_slab_idle_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_SLAB_IDLE_SIZE)
348 (storage_single_mpt_cache_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_CACHE_SIZE * 2)
349 (storage_single_mpt_cache_start_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_CACHE_START_SIZE * 2)
350 (storage_single_mpt_slab_idle_size, (u32), cfx_storage::defaults::DEFAULT_DELTA_MPTS_SLAB_IDLE_SIZE * 2)
351 (storage_max_open_snapshots, (u16), cfx_storage::defaults::DEFAULT_MAX_OPEN_SNAPSHOTS)
352 (storage_max_open_mpt_count, (u32), cfx_storage::defaults::DEFAULT_MAX_OPEN_MPT)
353 (strict_tx_index_gc, (bool), true)
354 (sync_state_starting_epoch, (Option<u64>), None)
355 (sync_state_epoch_gap, (Option<u64>), None)
356 (target_difficulties_cache_size_in_count, (usize), DEFAULT_TARGET_DIFFICULTIES_CACHE_SIZE_IN_COUNT)
357
358 (account_provider_refresh_time_ms, (u64), 1000)
360 (check_phase_change_period_ms, (u64), 1000)
361 (enable_optimistic_execution, (bool), true)
362 (future_block_buffer_capacity, (usize), 32768)
363 (get_logs_filter_max_limit, (Option<usize>), None)
364 (get_logs_filter_max_epoch_range, (Option<u64>), None)
365 (get_logs_filter_max_block_number_range, (Option<u64>), None)
366 (get_logs_epoch_batch_size, (usize), 32)
367 (max_trans_count_received_in_catch_up, (u64), 60_000)
368 (persist_tx_index, (bool), false)
369 (persist_block_number_index, (bool), true)
370 (print_memory_usage_period_s, (Option<u64>), None)
371 (target_block_gas_limit, (u64), DEFAULT_TARGET_BLOCK_GAS_LIMIT)
372 (executive_trace, (bool), false)
373 (check_status_genesis, (bool), true)
374 (packing_gas_limit_block_count, (u64), 10)
375 (poll_lifetime_in_seconds, (Option<u32>), None)
376
377 (is_consortium, (bool), false)
379 (pos_config_path, (Option<String>), Some("./pos_config/pos_config.yaml".to_string()))
380 (pos_genesis_pivot_decision, (Option<H256>), None)
381 (vrf_proposal_threshold, (U256), U256::from_str("1111111111111100000000000000000000000000000000000000000000000000").unwrap())
382 (pos_pivot_decision_defer_epoch_count, (u64), 50)
384 (cip113_pivot_decision_defer_epoch_count, (u64), 20)
385 (cip113_transition_height, (u64), u64::MAX)
386 (pos_reference_enable_height, (u64), u64::MAX)
387 (pos_initial_nodes_path, (String), "./pos_config/initial_nodes.json".to_string())
388 (pos_private_key_path, (String), "./pos_config/pos_key".to_string())
389 (pos_round_per_term, (u64), ROUND_PER_TERM)
390 (pos_term_max_size, (usize), TERM_MAX_SIZE)
391 (pos_term_elected_size, (usize), TERM_ELECTED_SIZE)
392 (pos_in_queue_locked_views, (u64), IN_QUEUE_LOCKED_VIEWS)
393 (pos_out_queue_locked_views, (u64), OUT_QUEUE_LOCKED_VIEWS)
394 (pos_cip99_transition_view, (u64), u64::MAX)
395 (pos_cip99_in_queue_locked_views, (u64), IN_QUEUE_LOCKED_VIEWS)
396 (pos_cip99_out_queue_locked_views, (u64), OUT_QUEUE_LOCKED_VIEWS)
397 (nonce_limit_transition_view, (u64), u64::MAX)
398 (pos_cip136_transition_view, (u64), u64::MAX)
399 (pos_cip136_in_queue_locked_views, (u64), IN_QUEUE_LOCKED_VIEWS)
400 (pos_cip136_out_queue_locked_views, (u64), OUT_QUEUE_LOCKED_VIEWS)
401 (pos_cip136_round_per_term, (u64), ROUND_PER_TERM)
402 (pos_cip156_transition_view, (u64), u64::MAX)
403 (pos_cip156_dispute_locked_views, (u64), 6 * 30 * 24 * 60 * 2)
405 (dev_pos_private_key_encryption_password, (Option<String>), None)
406 (pos_started_as_voter, (bool), true)
407
408 (ln_epoch_request_batch_size, (Option<usize>), None)
410 (ln_epoch_request_timeout_sec, (Option<u64>), None)
411 (ln_header_request_batch_size, (Option<usize>), None)
412 (ln_header_request_timeout_sec, (Option<u64>), None)
413 (ln_max_headers_in_flight, (Option<usize>), None)
414 (ln_max_parallel_epochs_to_request, (Option<usize>), None)
415 (ln_num_epochs_to_request, (Option<usize>), None)
416 (ln_num_waiting_headers_threshold, (Option<usize>), None)
417 (keep_snapshot_before_stable_checkpoint, (bool), true)
418 (force_recompute_height_during_construct_pivot, (Option<u64>), None)
419
420 (use_isolated_db_for_mpt_table, (bool), false)
423 (use_isolated_db_for_mpt_table_height, (Option<u64>), None)
427 (recovery_latest_mpt_snapshot, (bool), false)
429 (keep_era_genesis_snapshot, (bool), true)
430
431 (backup_mpt_snapshot, (bool), true)
433 }
434 {
435 (
437 log_level, (LevelFilter), LevelFilter::Info, |l| {
438 LevelFilter::from_str(l)
439 .map_err(|_| format!("Invalid log level: {}", l))
440 }
441 )
442
443 (chain_id_params, (Option<ChainIdParamsOneChainInner>), None,
447 ChainIdParamsOneChainInner::parse_config_str)
448
449 (provide_more_snapshot_for_sync,
451 (Vec<ProvideExtraSnapshotSyncConfig>),
452 vec![ProvideExtraSnapshotSyncConfig::StableCheckpoint],
453 ProvideExtraSnapshotSyncConfig::parse_config_list)
454 (node_type, (Option<NodeType>), None, NodeType::from_str)
455 (public_rpc_apis, (ApiSet), ApiSet::Safe, ApiSet::from_str)
456 (public_evm_rpc_apis, (RpcModuleSelection), RpcModuleSelection::Evm, RpcModuleSelection::from_str)
457 (single_mpt_space, (Option<Space>), None, Space::from_str)
458 }
459}
460
461#[derive(Debug, Clone)]
462pub struct Configuration {
463 pub raw_conf: RawConfiguration,
464}
465
466impl Default for Configuration {
467 fn default() -> Self {
468 Configuration {
469 raw_conf: Default::default(),
470 }
471 }
472}
473
474impl Configuration {
475 pub fn parse(matches: &clap::ArgMatches) -> Result<Configuration, String> {
476 let mut config = Configuration::default();
477 config.raw_conf = RawConfiguration::parse(matches)?;
478
479 if matches.get_flag("archive") {
480 config.raw_conf.node_type = Some(NodeType::Archive);
481 } else if matches.get_flag("full") {
482 config.raw_conf.node_type = Some(NodeType::Full);
483 } else if matches.get_flag("light") {
484 config.raw_conf.node_type = Some(NodeType::Light);
485 }
486
487 CIP112_TRANSITION_HEIGHT
488 .set(config.raw_conf.cip112_transition_height.unwrap_or(u64::MAX))
489 .expect("called once");
490
491 USE_SIMPLE_RPC_ADDRESS
492 .set(config.raw_conf.rpc_address_simple_mode)
493 .expect("called once");
494
495 Ok(config)
496 }
497
498 pub fn from_file(config_path: &str) -> Result<Configuration, String> {
499 Ok(Configuration {
500 raw_conf: RawConfiguration::from_file(config_path)?,
501 })
502 }
503
504 fn network_id(&self) -> u64 {
505 match self.raw_conf.network_id {
506 Some(x) => x,
507 None => {
510 self.chain_id_params()
511 .read()
512 .get_chain_id(0)
513 .in_native_space() as u64
514 }
515 }
516 }
517
518 pub fn net_config(&self) -> Result<NetworkConfiguration, String> {
519 let mut network_config = NetworkConfiguration::new_with_port(
520 self.network_id(),
521 self.raw_conf.tcp_port,
522 self.discovery_protocol(),
523 );
524
525 network_config.is_consortium = self.raw_conf.is_consortium;
526 network_config.discovery_enabled = self.raw_conf.enable_discovery;
527 network_config.boot_nodes = to_bootnodes(&self.raw_conf.bootnodes)
528 .map_err(|e| format!("failed to parse bootnodes: {}", e))?;
529 network_config.config_path = Some(match &self.raw_conf.netconf_dir {
530 Some(dir) => dir.clone(),
531 None => Path::new(&self.raw_conf.conflux_data_dir)
532 .join(NET_CONFIG_DB_DIR_NAME)
533 .into_os_string()
534 .into_string()
535 .unwrap(),
536 });
537 network_config.use_secret =
538 self.raw_conf.net_key.as_ref().map(|sec_str| {
539 parse_hex_string(sec_str)
540 .expect("net_key is not a valid secret string")
541 });
542 if let Some(addr) = self.raw_conf.public_address.clone() {
543 let addr_ip = if let Some(idx) = addr.find(":") {
544 warn!("Public address configuration should not contain port! (val = {}). Content after ':' is ignored.", &addr);
545 (&addr[0..idx]).to_string()
546 } else {
547 addr
548 };
549 let addr_with_port = match self.raw_conf.public_tcp_port {
550 Some(port) => addr_ip + ":" + &port.to_string(),
551 None => addr_ip + ":" + &self.raw_conf.tcp_port.to_string(),
552 };
553 network_config.public_address =
554 match addr_with_port.to_socket_addrs().map(|mut i| i.next()) {
555 Ok(sock_addr) => sock_addr,
556 Err(_e) => {
557 warn!("public_address in config is invalid");
558 None
559 }
560 };
561 }
562 network_config.node_table_timeout =
563 Duration::from_secs(self.raw_conf.node_table_timeout_s);
564 network_config.connection_lifetime_for_promotion =
565 Duration::from_secs(self.raw_conf.node_table_promotion_timeout_s);
566 network_config.test_mode = self.is_test_mode();
567 network_config.subnet_quota = self.raw_conf.subnet_quota;
568 network_config.session_ip_limit_config =
569 self.raw_conf.session_ip_limits.clone().try_into().map_err(
570 |e| format!("failed to parse session ip limit config: {}", e),
571 )?;
572 network_config.fast_discovery_refresh_timeout = Duration::from_millis(
573 self.raw_conf.discovery_fast_refresh_timeout_ms,
574 );
575 network_config.discovery_round_timeout =
576 Duration::from_millis(self.raw_conf.discovery_round_timeout_ms);
577 network_config.housekeeping_timeout = Duration::from_millis(
578 self.raw_conf.discovery_housekeeping_timeout_ms,
579 );
580 network_config.max_handshakes = self.raw_conf.max_handshakes;
581 network_config.max_incoming_peers = self.raw_conf.max_incoming_peers;
582 network_config.max_outgoing_peers = self.raw_conf.max_outgoing_peers;
583 network_config.max_outgoing_peers_archive =
584 self.raw_conf.max_outgoing_peers_archive.unwrap_or(0);
585 Ok(network_config)
586 }
587
588 pub fn cache_config(&self) -> CacheConfig {
589 let mut cache_config = CacheConfig::default();
590 cache_config.ledger = self.raw_conf.ledger_cache_size;
591 cache_config.invalid_block_hashes_cache_size_in_count =
592 self.raw_conf.invalid_block_hash_cache_size_in_count;
593 cache_config.target_difficulties_cache_size_in_count =
594 self.raw_conf.target_difficulties_cache_size_in_count;
595 cache_config
596 }
597
598 pub fn db_config(&self) -> (PathBuf, DatabaseConfig) {
599 let db_dir: PathBuf = match &self.raw_conf.block_db_dir {
600 Some(dir) => dir.into(),
601 None => Path::new(&self.raw_conf.conflux_data_dir)
602 .join(BLOCK_DB_DIR_NAME),
603 };
604 if let Err(e) = fs::create_dir_all(&db_dir) {
605 panic!("Error creating database directory: {:?}", e);
606 }
607
608 let compact_profile =
609 match self.raw_conf.rocksdb_compaction_profile.as_ref() {
610 Some(p) => db::DatabaseCompactionProfile::from_str(p).unwrap(),
611 None => db::DatabaseCompactionProfile::default(),
612 };
613 let db_config = db::db_config(
614 &db_dir,
615 self.raw_conf.rocksdb_cache_size.clone(),
616 compact_profile,
617 NUM_COLUMNS.clone(),
618 self.raw_conf.rocksdb_disable_wal,
619 );
620 (db_dir, db_config)
621 }
622
623 pub fn chain_id_params(&self) -> ChainIdParams {
624 if CHAIN_ID.read().is_none() {
625 let mut to_init = CHAIN_ID.write();
626 if to_init.is_none() {
627 if let Some(_chain_id_params) = &self.raw_conf.chain_id_params {
628 unreachable!("Upgradable ChainId is not ready.")
629 } else {
633 let chain_id = self
634 .raw_conf
635 .chain_id
636 .unwrap_or_else(|| rand::rng().random());
637 let evm_chain_id =
638 self.raw_conf.evm_chain_id.unwrap_or(chain_id);
639 *to_init = Some(ChainIdParamsInner::new_simple(
640 AllChainID::new(chain_id, evm_chain_id),
641 ));
642 }
643 }
644 }
645 CHAIN_ID.read().as_ref().unwrap().clone()
646 }
647
648 pub fn consensus_config(&self) -> ConsensusConfig {
649 let enable_optimistic_execution = if DEFERRED_STATE_EPOCH_COUNT <= 1 {
650 false
651 } else {
652 self.raw_conf.enable_optimistic_execution
653 };
654 let pivot_hint_conf = match (
655 &self.raw_conf.pivot_hint_path,
656 &self.raw_conf.pivot_hint_checksum,
657 ) {
658 (Some(path), Some(checksum)) => {
659 let checksum = H256::from_str(checksum)
660 .expect("Cannot parse `pivot_hint_checksum` as hex string");
661 Some(PivotHintConfig::new(path, checksum))
662 }
663 (None, None) => None,
664 _ => {
665 panic!("`pivot_hint_path` and `pivot_hint_checksum` must be both set or both unset");
666 }
667 };
668 let mut conf = ConsensusConfig {
669 chain_id: self.chain_id_params(),
670 inner_conf: ConsensusInnerConfig {
671 adaptive_weight_beta: self.raw_conf.adaptive_weight_beta,
672 heavy_block_difficulty_ratio: self
673 .raw_conf
674 .heavy_block_difficulty_ratio,
675 timer_chain_block_difficulty_ratio: self
676 .raw_conf
677 .timer_chain_block_difficulty_ratio,
678 timer_chain_beta: self.raw_conf.timer_chain_beta,
679 era_epoch_count: self.raw_conf.era_epoch_count,
680 enable_optimistic_execution,
681 enable_state_expose: self.raw_conf.enable_state_expose,
682 pos_pivot_decision_defer_epoch_count: self.raw_conf.pos_pivot_decision_defer_epoch_count,
683 cip113_pivot_decision_defer_epoch_count: self.raw_conf.cip113_pivot_decision_defer_epoch_count,
684 cip113_transition_height: self.raw_conf.cip113_transition_height,
685 debug_dump_dir_invalid_state_root: if self
686 .raw_conf
687 .debug_invalid_state_root
688 {
689 Some(
690 self.raw_conf.debug_dump_dir_invalid_state_root.clone(),
691 )
692 } else {
693 None
694 },
695
696 debug_invalid_state_root_epoch: match &self
697 .raw_conf
698 .debug_invalid_state_root_epoch
699 {
700 Some(epoch_hex) => {
701 Some(H256::from_str(&epoch_hex).expect("debug_invalid_state_root_epoch byte length is incorrect."))
702 }
703 None => None,
704 },
705 force_recompute_height_during_construct_pivot: self.raw_conf.force_recompute_height_during_construct_pivot,
706 recovery_latest_mpt_snapshot: self.raw_conf.recovery_latest_mpt_snapshot,
707 use_isolated_db_for_mpt_table: self.raw_conf.use_isolated_db_for_mpt_table,
708 },
709 bench_mode: false,
710 transaction_epoch_bound: self.raw_conf.transaction_epoch_bound,
711 referee_bound: self.raw_conf.referee_bound,
712 get_logs_epoch_batch_size: self.raw_conf.get_logs_epoch_batch_size,
713 get_logs_filter_max_epoch_range: self.raw_conf.get_logs_filter_max_epoch_range,
714 get_logs_filter_max_block_number_range: self.raw_conf.get_logs_filter_max_block_number_range,
715 get_logs_filter_max_limit: self.raw_conf.get_logs_filter_max_limit,
716 sync_state_starting_epoch: self.raw_conf.sync_state_starting_epoch,
717 sync_state_epoch_gap: self.raw_conf.sync_state_epoch_gap,
718 pivot_hint_conf,
719 };
720 match self.raw_conf.node_type {
721 Some(NodeType::Archive) => {
722 if conf.sync_state_starting_epoch.is_none() {
723 conf.sync_state_starting_epoch = Some(0);
724 }
725 }
726 _ => {
727 if conf.sync_state_epoch_gap.is_none() {
728 conf.sync_state_epoch_gap =
729 Some(CATCH_UP_EPOCH_LAG_THRESHOLD);
730 }
731 }
732 }
733 conf
734 }
735
736 pub fn pow_config(&self) -> ProofOfWorkConfig {
737 let stratum_secret =
738 self.raw_conf.stratum_secret.as_ref().map(|hex_str| {
739 parse_hex_string(hex_str)
740 .expect("Stratum secret should be 64-digit hex string")
741 });
742
743 ProofOfWorkConfig::new(
744 self.is_test_or_dev_mode(),
745 self.raw_conf.use_octopus_in_test_mode,
746 self.raw_conf.mining_type.as_ref().map_or_else(
747 || {
748 if self.raw_conf.mining_author.is_some() {
750 "stratum"
751 } else {
752 "disable"
753 }
754 },
755 |s| s.as_str(),
756 ),
757 self.raw_conf.initial_difficulty,
758 self.raw_conf.stratum_listen_address.clone(),
759 self.raw_conf.stratum_port,
760 stratum_secret,
761 self.raw_conf.pow_problem_window_size,
762 self.common_params().transition_heights.cip86,
763 )
764 }
765
766 pub fn verification_config(
767 &self, machine: Arc<Machine>,
768 ) -> VerificationConfig {
769 VerificationConfig::new(
770 self.is_test_mode(),
771 self.raw_conf.referee_bound,
772 self.raw_conf.max_block_size_in_bytes,
773 self.raw_conf.transaction_epoch_bound,
774 self.raw_conf.tx_pool_nonce_bits,
775 self.raw_conf.pos_reference_enable_height,
776 machine,
777 )
778 }
779
780 pub fn tx_gen_config(&self) -> Option<TransactionGeneratorConfig> {
781 if self.is_test_or_dev_mode() &&
782 self.raw_conf.genesis_secrets.is_some()
784 {
785 Some(TransactionGeneratorConfig::new(
786 self.raw_conf.generate_tx,
787 self.raw_conf.generate_tx_period_us.expect("has default"),
788 self.raw_conf.txgen_account_count,
789 ))
790 } else {
791 None
792 }
793 }
794
795 pub fn storage_config(&self, node_type: &NodeType) -> StorageConfiguration {
796 let conflux_data_path = Path::new(&self.raw_conf.conflux_data_dir);
797 StorageConfiguration {
798 additional_maintained_snapshot_count: self
799 .raw_conf
800 .additional_maintained_snapshot_count,
801 consensus_param: ConsensusParam {
802 snapshot_epoch_count: if self.is_test_mode() {
803 self.raw_conf.dev_snapshot_epoch_count
804 } else {
805 SNAPSHOT_EPOCHS_CAPACITY
806 },
807 era_epoch_count: self.raw_conf.era_epoch_count,
808 },
809 debug_snapshot_checker_threads:
810 DEFAULT_DEBUG_SNAPSHOT_CHECKER_THREADS,
811 delta_mpts_cache_recent_lfu_factor: self
812 .raw_conf
813 .storage_delta_mpts_cache_recent_lfu_factor,
814 delta_mpts_cache_size: self.raw_conf.storage_delta_mpts_cache_size,
815 delta_mpts_cache_start_size: self
816 .raw_conf
817 .storage_delta_mpts_cache_start_size,
818 delta_mpts_node_map_vec_size: self
819 .raw_conf
820 .storage_delta_mpts_node_map_vec_size,
821 delta_mpts_slab_idle_size: self
822 .raw_conf
823 .storage_delta_mpts_slab_idle_size,
824 single_mpt_cache_start_size: self
825 .raw_conf
826 .storage_single_mpt_cache_start_size,
827 single_mpt_cache_size: self.raw_conf.storage_single_mpt_cache_size,
828 single_mpt_slab_idle_size: self
829 .raw_conf
830 .storage_single_mpt_slab_idle_size,
831 max_open_snapshots: self.raw_conf.storage_max_open_snapshots,
832 path_delta_mpts_dir: conflux_data_path
833 .join(&*storage_dir::DELTA_MPTS_DIR),
834 path_snapshot_dir: conflux_data_path
835 .join(&*storage_dir::SNAPSHOT_DIR),
836 path_snapshot_info_db: conflux_data_path
837 .join(&*storage_dir::SNAPSHOT_INFO_DB_PATH),
838 path_storage_dir: conflux_data_path
839 .join(&*storage_dir::STORAGE_DIR),
840 provide_more_snapshot_for_sync: self
841 .raw_conf
842 .provide_more_snapshot_for_sync
843 .clone(),
844 max_open_mpt_count: self.raw_conf.storage_max_open_mpt_count,
845 enable_single_mpt_storage: match node_type {
846 NodeType::Archive => self.raw_conf.enable_single_mpt_storage,
847 _ => {
848 if self.raw_conf.enable_single_mpt_storage {
849 error!("enable_single_mpt_storage is only supported for Archive nodes!")
850 }
851 false
852 }
853 },
854 single_mpt_space: self.raw_conf.single_mpt_space.clone(),
855 cip90a: self
856 .raw_conf
857 .cip90_transition_height
858 .unwrap_or(self.raw_conf.hydra_transition_height.unwrap_or(0)),
859 keep_snapshot_before_stable_checkpoint: self
860 .raw_conf
861 .keep_snapshot_before_stable_checkpoint,
862 use_isolated_db_for_mpt_table: self
863 .raw_conf
864 .use_isolated_db_for_mpt_table,
865 use_isolated_db_for_mpt_table_height: self
866 .raw_conf
867 .use_isolated_db_for_mpt_table_height,
868 keep_era_genesis_snapshot: self.raw_conf.keep_era_genesis_snapshot,
869 backup_mpt_snapshot: self.raw_conf.backup_mpt_snapshot,
870 }
871 }
872
873 pub fn protocol_config(&self) -> ProtocolConfiguration {
874 ProtocolConfiguration {
875 is_consortium: self.raw_conf.is_consortium,
876 send_tx_period: Duration::from_millis(
877 self.raw_conf.send_tx_period_ms,
878 ),
879 check_request_period: Duration::from_millis(
880 self.raw_conf.check_request_period_ms,
881 ),
882 check_phase_change_period: Duration::from_millis(
883 self.raw_conf.check_phase_change_period_ms,
884 ),
885 heartbeat_period_interval: Duration::from_millis(
886 self.raw_conf.heartbeat_period_interval_ms,
887 ),
888 block_cache_gc_period: Duration::from_millis(
889 self.raw_conf.block_cache_gc_period_ms,
890 ),
891 expire_block_gc_period: Duration::from_secs(
892 self.raw_conf.expire_block_gc_period_s,
893 ),
894 headers_request_timeout: Duration::from_millis(
895 self.raw_conf.headers_request_timeout_ms,
896 ),
897 blocks_request_timeout: Duration::from_millis(
898 self.raw_conf.blocks_request_timeout_ms,
899 ),
900 transaction_request_timeout: Duration::from_millis(
901 self.raw_conf.transaction_request_timeout_ms,
902 ),
903 tx_maintained_for_peer_timeout: Duration::from_millis(
904 self.raw_conf.tx_maintained_for_peer_timeout_ms,
905 ),
906 max_inflight_request_count: self
907 .raw_conf
908 .max_inflight_request_count,
909 request_block_with_public: self.raw_conf.request_block_with_public,
910 received_tx_index_maintain_timeout: Duration::from_millis(
911 self.raw_conf.received_tx_index_maintain_timeout_ms,
912 ),
913 inflight_pending_tx_index_maintain_timeout: Duration::from_millis(
914 self.raw_conf.inflight_pending_tx_index_maintain_timeout_ms,
915 ),
916 max_trans_count_received_in_catch_up: self
917 .raw_conf
918 .max_trans_count_received_in_catch_up,
919 min_peers_tx_propagation: self.raw_conf.min_peers_tx_propagation,
920 max_peers_tx_propagation: self.raw_conf.max_peers_tx_propagation,
921 max_downloading_chunks: self.raw_conf.max_downloading_chunks,
922 max_downloading_chunk_attempts: self
923 .raw_conf
924 .max_downloading_chunk_attempts,
925 test_mode: self.is_test_mode(),
926 dev_mode: self.is_dev_mode(),
927 throttling_config_file: self.raw_conf.throttling_conf.clone(),
928 snapshot_candidate_request_timeout: Duration::from_millis(
929 self.raw_conf.snapshot_candidate_request_timeout_ms,
930 ),
931 snapshot_manifest_request_timeout: Duration::from_millis(
932 self.raw_conf.snapshot_manifest_request_timeout_ms,
933 ),
934 snapshot_chunk_request_timeout: Duration::from_millis(
935 self.raw_conf.snapshot_chunk_request_timeout_ms,
936 ),
937 chunk_size_byte: self.raw_conf.chunk_size_byte,
938 max_chunk_number_in_manifest: self
939 .raw_conf
940 .max_chunk_number_in_manifest,
941 timeout_observing_period_s: self
942 .raw_conf
943 .timeout_observing_period_s,
944 max_allowed_timeout_in_observing_period: self
945 .raw_conf
946 .max_allowed_timeout_in_observing_period,
947 demote_peer_for_timeout: self.raw_conf.demote_peer_for_timeout,
948 heartbeat_timeout: Duration::from_millis(
949 self.raw_conf.heartbeat_timeout_ms,
950 ),
951 max_unprocessed_block_size: self
952 .raw_conf
953 .max_unprocessed_block_size_mb
954 * 1_000_000,
955 sync_expire_block_timeout: Duration::from_secs(
956 self.raw_conf.sync_expire_block_timeout_s,
957 ),
958 allow_phase_change_without_peer: if self.is_dev_mode() {
959 true
960 } else {
961 self.raw_conf.dev_allow_phase_change_without_peer
962 },
963 min_phase_change_normal_peer_count: self
964 .raw_conf
965 .min_phase_change_normal_peer_count,
966 pos_genesis_pivot_decision: self
967 .raw_conf
968 .pos_genesis_pivot_decision
969 .expect("set to genesis if none"),
970 check_status_genesis: self.raw_conf.check_status_genesis,
971 pos_started_as_voter: self.raw_conf.pos_started_as_voter,
972 }
973 }
974
975 pub fn state_sync_config(&self) -> StateSyncConfiguration {
976 StateSyncConfiguration {
977 max_downloading_chunks: self.raw_conf.max_downloading_chunks,
978 candidate_request_timeout: Duration::from_millis(
979 self.raw_conf.snapshot_candidate_request_timeout_ms,
980 ),
981 chunk_request_timeout: Duration::from_millis(
982 self.raw_conf.snapshot_chunk_request_timeout_ms,
983 ),
984 manifest_request_timeout: Duration::from_millis(
985 self.raw_conf.snapshot_manifest_request_timeout_ms,
986 ),
987 max_downloading_manifest_attempts: self
988 .raw_conf
989 .max_downloading_manifest_attempts,
990 }
991 }
992
993 pub fn data_mananger_config(&self) -> DataManagerConfiguration {
994 let mut conf = DataManagerConfiguration {
995 persist_tx_index: self.raw_conf.persist_tx_index,
996 persist_block_number_index: self
997 .raw_conf
998 .persist_block_number_index,
999 tx_cache_index_maintain_timeout: Duration::from_millis(
1000 self.raw_conf.tx_cache_index_maintain_timeout_ms,
1001 ),
1002 db_type: match self.raw_conf.block_db_type.as_str() {
1003 "rocksdb" => DbType::Rocksdb,
1004 "sqlite" => DbType::Sqlite,
1005 _ => panic!("Invalid block_db_type parameter!"),
1006 },
1007 additional_maintained_block_body_epoch_count: self
1008 .raw_conf
1009 .additional_maintained_block_body_epoch_count,
1010 additional_maintained_execution_result_epoch_count: self
1011 .raw_conf
1012 .additional_maintained_execution_result_epoch_count,
1013 additional_maintained_reward_epoch_count: self
1014 .raw_conf
1015 .additional_maintained_reward_epoch_count,
1016 additional_maintained_trace_epoch_count: self
1017 .raw_conf
1018 .additional_maintained_trace_epoch_count,
1019 additional_maintained_transaction_index_epoch_count: self
1020 .raw_conf
1021 .additional_maintained_transaction_index_epoch_count,
1022 checkpoint_gc_time_in_epoch_count: (self
1023 .raw_conf
1024 .checkpoint_gc_time_in_era_count
1025 * self.raw_conf.era_epoch_count as f64)
1026 as usize,
1027 strict_tx_index_gc: self.raw_conf.strict_tx_index_gc,
1028 };
1029
1030 if !matches!(self.raw_conf.node_type, Some(NodeType::Archive)) {
1033 if conf.additional_maintained_block_body_epoch_count.is_none() {
1034 conf.additional_maintained_block_body_epoch_count = Some(0);
1035 }
1036 if conf
1037 .additional_maintained_execution_result_epoch_count
1038 .is_none()
1039 {
1040 conf.additional_maintained_execution_result_epoch_count =
1041 Some(0);
1042 }
1043 if conf
1044 .additional_maintained_transaction_index_epoch_count
1045 .is_none()
1046 {
1047 conf.additional_maintained_transaction_index_epoch_count =
1048 Some(0);
1049 }
1050 if conf.additional_maintained_reward_epoch_count.is_none() {
1051 conf.additional_maintained_reward_epoch_count = Some(0);
1052 }
1053 if conf.additional_maintained_trace_epoch_count.is_none() {
1054 conf.additional_maintained_trace_epoch_count = Some(0);
1055 }
1056 }
1057 if conf.additional_maintained_transaction_index_epoch_count != Some(0) {
1058 conf.persist_tx_index = true;
1059 }
1060 conf
1061 }
1062
1063 pub fn sync_graph_config(&self) -> SyncGraphConfig {
1064 SyncGraphConfig {
1065 future_block_buffer_capacity: self
1066 .raw_conf
1067 .future_block_buffer_capacity,
1068 enable_state_expose: self.raw_conf.enable_state_expose,
1069 is_consortium: self.raw_conf.is_consortium,
1070 }
1071 }
1072
1073 pub fn metrics_config(&self) -> MetricsConfiguration {
1074 MetricsConfiguration {
1075 enabled: self.raw_conf.metrics_enabled,
1076 report_interval: Duration::from_millis(
1077 self.raw_conf.metrics_report_interval_ms,
1078 ),
1079 file_report_output: self.raw_conf.metrics_output_file.clone(),
1080 influxdb_report_host: self.raw_conf.metrics_influxdb_host.clone(),
1081 influxdb_report_db: self.raw_conf.metrics_influxdb_db.clone(),
1082 influxdb_report_username: self
1083 .raw_conf
1084 .metrics_influxdb_username
1085 .clone(),
1086 influxdb_report_password: self
1087 .raw_conf
1088 .metrics_influxdb_password
1089 .clone(),
1090 influxdb_report_node: self.raw_conf.metrics_influxdb_node.clone(),
1091 prometheus_listen_addr: self
1092 .raw_conf
1093 .metrics_prometheus_listen_addr
1094 .clone(),
1095 }
1096 }
1097
1098 pub fn txpool_config(&self) -> TxPoolConfig {
1099 let (min_native_tx_price_default, min_eth_tx_price_default) =
1100 if self.is_test_or_dev_mode() {
1101 (1, 1)
1102 } else {
1103 (ONE_GDRIP_IN_DRIP, 20 * ONE_GDRIP_IN_DRIP)
1104 };
1105 TxPoolConfig {
1106 capacity: self.raw_conf.tx_pool_size,
1107 half_block_gas_limit: RwLock::new(U256::from(
1108 DEFAULT_TARGET_BLOCK_GAS_LIMIT / 2,
1109 )),
1110 min_native_tx_price: self
1111 .raw_conf
1112 .tx_pool_min_native_tx_gas_price
1113 .unwrap_or(min_native_tx_price_default),
1114 allow_gas_over_half_block: self
1115 .raw_conf
1116 .tx_pool_allow_gas_over_half_block,
1117 target_block_gas_limit: self.raw_conf.target_block_gas_limit,
1118 min_eth_tx_price: self
1119 .raw_conf
1120 .tx_pool_min_eth_tx_gas_price
1121 .unwrap_or(min_eth_tx_price_default),
1122 max_packing_batch_gas_limit: self
1123 .raw_conf
1124 .max_packing_batch_gas_limit,
1125 max_packing_batch_size: self.raw_conf.max_packing_batch_size,
1126 packing_pool_degree: self.raw_conf.packing_pool_degree,
1127 }
1128 }
1129
1130 pub fn rpc_impl_config(&self) -> RpcImplConfiguration {
1131 RpcImplConfiguration {
1132 get_logs_filter_max_limit: self.raw_conf.get_logs_filter_max_limit,
1133 dev_pack_tx_immediately: self
1134 .raw_conf
1135 .dev_pack_tx_immediately
1136 .unwrap_or_else(|| {
1137 self.is_dev_mode()
1138 && self.raw_conf.dev_block_interval_ms.is_none()
1139 }),
1140 max_payload_bytes: self.raw_conf.jsonrpc_ws_max_payload_bytes,
1141 enable_metrics: self.raw_conf.rpc_enable_metrics,
1142 poll_lifetime_in_seconds: self.raw_conf.poll_lifetime_in_seconds,
1143 max_estimation_gas_limit: self
1144 .raw_conf
1145 .max_estimation_gas_limit
1146 .map(U256::from),
1147 }
1148 }
1149
1150 pub fn local_http_config(&self) -> HttpConfiguration {
1151 HttpConfiguration::new(
1152 Some((127, 0, 0, 1)),
1153 self.raw_conf.jsonrpc_local_http_port,
1154 self.raw_conf.jsonrpc_cors.clone(),
1155 self.raw_conf.jsonrpc_http_keep_alive,
1156 self.raw_conf.jsonrpc_http_threads,
1157 )
1158 }
1159
1160 pub fn http_config(&self) -> HttpConfiguration {
1161 HttpConfiguration::new(
1162 None,
1163 self.raw_conf.jsonrpc_http_port,
1164 self.raw_conf.jsonrpc_cors.clone(),
1165 self.raw_conf.jsonrpc_http_keep_alive,
1166 self.raw_conf.jsonrpc_http_threads,
1167 )
1168 }
1169
1170 pub fn eth_http_config(&self) -> HttpConfiguration {
1171 HttpConfiguration::new(
1172 None,
1173 self.raw_conf.jsonrpc_http_eth_port,
1174 self.raw_conf.jsonrpc_cors.clone(),
1175 self.raw_conf.jsonrpc_http_keep_alive,
1176 self.raw_conf.jsonrpc_http_threads,
1177 )
1178 }
1179
1180 pub fn eth_ws_config(&self) -> WsConfiguration {
1181 WsConfiguration::new(
1182 None,
1183 self.raw_conf.jsonrpc_ws_eth_port,
1184 self.raw_conf.jsonrpc_ws_max_payload_bytes,
1185 )
1186 }
1187
1188 pub fn local_tcp_config(&self) -> TcpConfiguration {
1189 TcpConfiguration::new(
1190 Some((127, 0, 0, 1)),
1191 self.raw_conf.jsonrpc_local_tcp_port,
1192 )
1193 }
1194
1195 pub fn tcp_config(&self) -> TcpConfiguration {
1196 TcpConfiguration::new(None, self.raw_conf.jsonrpc_tcp_port)
1197 }
1198
1199 pub fn jsonrpsee_server_builder(&self) -> ServerConfigBuilder {
1200 let builder = ServerConfigBuilder::default()
1201 .max_request_body_size(self.raw_conf.jsonrpc_max_request_body_size)
1202 .max_response_body_size(
1203 self.raw_conf.jsonrpc_max_response_body_size,
1204 )
1205 .max_connections(self.raw_conf.jsonrpc_max_connections)
1206 .max_subscriptions_per_connection(
1207 self.raw_conf.jsonrpc_max_subscriptions_per_connection,
1208 )
1209 .set_message_buffer_capacity(
1210 self.raw_conf.jsonrpc_message_buffer_capacity,
1211 );
1212
1213 builder
1214 }
1215
1216 pub fn local_ws_config(&self) -> WsConfiguration {
1217 WsConfiguration::new(
1218 Some((127, 0, 0, 1)),
1219 self.raw_conf.jsonrpc_local_ws_port,
1220 self.raw_conf.jsonrpc_ws_max_payload_bytes,
1221 )
1222 }
1223
1224 pub fn ws_config(&self) -> WsConfiguration {
1225 WsConfiguration::new(
1226 None,
1227 self.raw_conf.jsonrpc_ws_port,
1228 self.raw_conf.jsonrpc_ws_max_payload_bytes,
1229 )
1230 }
1231
1232 pub fn execution_config(&self) -> ConsensusExecutionConfiguration {
1233 ConsensusExecutionConfiguration {
1234 executive_trace: self.raw_conf.executive_trace,
1235 }
1236 }
1237
1238 pub fn discovery_protocol(&self) -> DiscoveryConfiguration {
1239 DiscoveryConfiguration {
1240 discover_node_count: self.raw_conf.discovery_discover_node_count,
1241 expire_time: Duration::from_secs(
1242 self.raw_conf.discovery_expire_time_s,
1243 ),
1244 find_node_timeout: Duration::from_millis(
1245 self.raw_conf.discovery_find_node_timeout_ms,
1246 ),
1247 max_nodes_ping: self.raw_conf.discovery_max_nodes_ping,
1248 ping_timeout: Duration::from_millis(
1249 self.raw_conf.discovery_ping_timeout_ms,
1250 ),
1251 throttling_interval: Duration::from_millis(
1252 self.raw_conf.discovery_throttling_interval_ms,
1253 ),
1254 throttling_limit_ping: self
1255 .raw_conf
1256 .discovery_throttling_limit_ping,
1257 throttling_limit_find_nodes: self
1258 .raw_conf
1259 .discovery_throttling_limit_find_nodes,
1260 }
1261 }
1262
1263 pub fn is_test_mode(&self) -> bool {
1264 match self.raw_conf.mode.as_ref().map(|s| s.as_str()) {
1265 Some("test") => true,
1266 _ => false,
1267 }
1268 }
1269
1270 pub fn is_dev_mode(&self) -> bool {
1271 match self.raw_conf.mode.as_ref().map(|s| s.as_str()) {
1272 Some("dev") => true,
1273 _ => false,
1274 }
1275 }
1276
1277 pub fn is_test_or_dev_mode(&self) -> bool {
1278 match self.raw_conf.mode.as_ref().map(|s| s.as_str()) {
1279 Some("dev") | Some("test") => true,
1280 _ => false,
1281 }
1282 }
1283
1284 pub fn is_consortium(&self) -> bool { self.raw_conf.is_consortium }
1285
1286 pub fn light_node_config(&self) -> LightNodeConfiguration {
1287 LightNodeConfiguration {
1288 epoch_request_batch_size: self.raw_conf.ln_epoch_request_batch_size,
1289 epoch_request_timeout: self
1290 .raw_conf
1291 .ln_epoch_request_timeout_sec
1292 .map(Duration::from_secs),
1293 header_request_batch_size: self
1294 .raw_conf
1295 .ln_header_request_batch_size,
1296 header_request_timeout: self
1297 .raw_conf
1298 .ln_header_request_timeout_sec
1299 .map(Duration::from_secs),
1300 max_headers_in_flight: self.raw_conf.ln_max_headers_in_flight,
1301 max_parallel_epochs_to_request: self
1302 .raw_conf
1303 .ln_max_parallel_epochs_to_request,
1304 num_epochs_to_request: self.raw_conf.ln_num_epochs_to_request,
1305 num_waiting_headers_threshold: self
1306 .raw_conf
1307 .ln_num_waiting_headers_threshold,
1308 }
1309 }
1310
1311 pub fn common_params(&self) -> CommonParams {
1312 let mut params = CommonParams::default();
1313
1314 if self.is_test_or_dev_mode() {
1315 params.early_set_internal_contracts_states = true;
1316 }
1317
1318 let non_test_default = SpaceMap::new(
1319 INITIAL_1559_CORE_BASE_PRICE,
1320 INITIAL_1559_ETH_BASE_PRICE,
1321 );
1322 let test_default = SpaceMap::new(1u64, 1);
1323 let config = SpaceMap::new(
1324 self.raw_conf.min_native_base_price,
1325 self.raw_conf.min_eth_base_price,
1326 );
1327 let base_price = SpaceMap::zip3(non_test_default, test_default, config)
1328 .map_all(|(non_test, test, config)| {
1329 if let Some(x) = config {
1330 x
1331 } else if self.is_test_or_dev_mode() {
1332 test
1333 } else {
1334 non_test
1335 }
1336 });
1337 params.min_base_price = base_price.map_all(U256::from);
1338
1339 params.chain_id = self.chain_id_params();
1340 params.anticone_penalty_ratio = self.raw_conf.anticone_penalty_ratio;
1341 params.evm_transaction_block_ratio =
1342 self.raw_conf.evm_transaction_block_ratio;
1343 params.evm_transaction_gas_ratio =
1344 self.raw_conf.evm_transaction_gas_ratio;
1345
1346 params.params_dao_vote_period = self.raw_conf.params_dao_vote_period;
1347
1348 self.set_cips(&mut params);
1349
1350 params
1351 }
1352
1353 pub fn node_type(&self) -> NodeType {
1354 self.raw_conf.node_type.unwrap_or(NodeType::Full)
1355 }
1356
1357 pub fn pos_state_config(&self) -> PosStateConfig {
1358 assert_eq!(self.raw_conf.pos_round_per_term % 2, 0);
1361 PosStateConfig::new(
1362 self.raw_conf.pos_round_per_term,
1363 self.raw_conf.pos_term_max_size,
1364 self.raw_conf.pos_term_elected_size,
1365 self.raw_conf.pos_in_queue_locked_views,
1366 self.raw_conf.pos_out_queue_locked_views,
1367 self.raw_conf.pos_cip99_transition_view,
1368 self.raw_conf.pos_cip99_in_queue_locked_views,
1369 self.raw_conf.pos_cip99_out_queue_locked_views,
1370 self.raw_conf.nonce_limit_transition_view,
1371 20_000, self.raw_conf.pos_cip136_transition_view,
1373 self.raw_conf.pos_cip136_in_queue_locked_views,
1374 self.raw_conf.pos_cip136_out_queue_locked_views,
1375 self.raw_conf.pos_cip136_round_per_term,
1376 self.raw_conf.pos_cip156_transition_view,
1377 self.raw_conf.pos_cip156_dispute_locked_views,
1378 )
1379 }
1380
1381 fn set_cips(&self, params: &mut CommonParams) {
1382 let default_transition_time =
1383 if let Some(num) = self.raw_conf.default_transition_time {
1384 num
1385 } else if self.is_test_or_dev_mode() {
1386 0u64
1387 } else {
1388 u64::MAX
1389 };
1390
1391 let non_genesis_default_transition_time =
1394 match self.raw_conf.default_transition_time {
1395 Some(num) if num > 0 => num,
1396 _ => {
1397 if self.is_test_or_dev_mode() {
1398 1u64
1399 } else {
1400 u64::MAX
1401 }
1402 }
1403 };
1404
1405 params.transition_heights.cip40 =
1409 self.raw_conf.tanzanite_transition_height;
1410 let mut base_block_rewards = BTreeMap::new();
1411 base_block_rewards.insert(0, INITIAL_BASE_MINING_REWARD_IN_UCFX.into());
1412 base_block_rewards.insert(
1413 params.transition_heights.cip40,
1414 MINING_REWARD_TANZANITE_IN_UCFX.into(),
1415 );
1416 params.base_block_rewards = base_block_rewards;
1417
1418 set_conf!(
1422 self.raw_conf.hydra_transition_number.unwrap_or(default_transition_time);
1423 params.transition_numbers => { cip43a, cip64, cip71, cip78a, cip92 }
1424 );
1425 set_conf!(
1426 self.raw_conf.hydra_transition_height.unwrap_or(default_transition_time);
1427 params.transition_heights => { cip76, cip86 }
1428 );
1429 params.transition_numbers.cip43b =
1430 self.raw_conf.cip43_init_end_number.unwrap_or(
1431 if self.is_test_or_dev_mode() {
1432 u64::MAX
1433 } else {
1434 params.transition_numbers.cip43a
1435 },
1436 );
1437 params.transition_numbers.cip62 = if self.is_test_or_dev_mode() {
1438 0u64
1439 } else {
1440 BN128_ENABLE_NUMBER
1441 };
1442 params.transition_numbers.cip78b = self
1443 .raw_conf
1444 .cip78_patch_transition_number
1445 .unwrap_or(params.transition_numbers.cip78a);
1446 params.transition_heights.cip90a = self
1447 .raw_conf
1448 .cip90_transition_height
1449 .or(self.raw_conf.hydra_transition_height)
1450 .unwrap_or(default_transition_time);
1451 params.transition_numbers.cip90b = self
1452 .raw_conf
1453 .cip90_transition_number
1454 .or(self.raw_conf.hydra_transition_number)
1455 .unwrap_or(default_transition_time);
1456
1457 set_conf!(
1461 self.raw_conf.dao_vote_transition_number.unwrap_or(default_transition_time);
1462 params.transition_numbers => { cip97, cip98 }
1463 );
1464 params.transition_numbers.cip94n = self
1465 .raw_conf
1466 .dao_vote_transition_number
1467 .unwrap_or(non_genesis_default_transition_time);
1468 params.transition_heights.cip94h = self
1469 .raw_conf
1470 .dao_vote_transition_height
1471 .unwrap_or(non_genesis_default_transition_time);
1472 params.transition_numbers.cip105 = self
1473 .raw_conf
1474 .cip105_transition_number
1475 .or(self.raw_conf.dao_vote_transition_number)
1476 .unwrap_or(default_transition_time);
1477
1478 params.transition_numbers.cip_sigma_fix = self
1482 .raw_conf
1483 .sigma_fix_transition_number
1484 .unwrap_or(default_transition_time);
1485
1486 params.transition_numbers.cip107 = self
1490 .raw_conf
1491 .cip107_transition_number
1492 .unwrap_or(default_transition_time);
1493 params.transition_heights.cip112 =
1494 *CIP112_TRANSITION_HEIGHT.get().expect("initialized");
1495 params.transition_numbers.cip118 = self
1496 .raw_conf
1497 .cip118_transition_number
1498 .unwrap_or(default_transition_time);
1499 params.transition_numbers.cip119 = self
1500 .raw_conf
1501 .cip119_transition_number
1502 .unwrap_or(default_transition_time);
1503
1504 set_conf!(
1508 self.raw_conf.base_fee_burn_transition_number.unwrap_or(default_transition_time);
1509 params.transition_numbers => { cip131, cip132, cip133b, cip137, cip144, cip145 }
1510 );
1511 set_conf!(
1512 self.raw_conf.base_fee_burn_transition_height.unwrap_or(default_transition_time);
1513 params.transition_heights => { cip130, cip133e }
1514 );
1515 params.transition_heights.cip1559 = self
1517 .raw_conf
1518 .cip1559_transition_height
1519 .or(self.raw_conf.base_fee_burn_transition_height)
1520 .unwrap_or(non_genesis_default_transition_time);
1521 params.transition_numbers.cancun_opcodes = self
1522 .raw_conf
1523 .cancun_opcodes_transition_number
1524 .or(self.raw_conf.base_fee_burn_transition_number)
1525 .unwrap_or(default_transition_time);
1526
1527 if params.transition_heights.cip1559
1528 < self.raw_conf.pos_reference_enable_height
1529 {
1530 panic!("1559 can not be activated earlier than pos reference: 1559 (epoch {}), pos (epoch {})", params.transition_heights.cip1559, self.raw_conf.pos_reference_enable_height);
1531 }
1532
1533 params.transition_heights.cip_c2_fix = self
1537 .raw_conf
1538 .c2_fix_transition_height
1539 .unwrap_or(default_transition_time);
1540
1541 set_conf!(
1545 self.raw_conf.eoa_code_transition_height.unwrap_or(default_transition_time);
1546 params.transition_heights => { cip150, cip151, cip152, cip154, cip7702, cip645, eip2537, eip2935, eip7623, cip145_fix }
1547 );
1548 if let Some(x) = self.raw_conf.cip151_transition_height {
1549 params.transition_heights.cip151 = x;
1550 }
1551 if let Some(x) = self.raw_conf.cip645_transition_height {
1552 params.transition_heights.cip645 = x;
1553 }
1554 if let Some(x) = self.raw_conf.cip145_fix_transition_height {
1555 params.transition_heights.cip145_fix = x;
1556 }
1557 params.transition_heights.align_evm =
1558 self.raw_conf.align_evm_transition_height;
1559
1560 set_conf!(
1562 self.raw_conf.osaka_opcode_transition_height.unwrap_or(default_transition_time);
1563 params.transition_heights => { cip166 }
1564 );
1565 if let Some(x) = self.raw_conf.cip166_transition_height {
1566 params.transition_heights.cip166 = x;
1567 }
1568 }
1569}
1570
1571pub fn to_bootnodes(bootnodes: &Option<String>) -> Result<Vec<String>, String> {
1573 match *bootnodes {
1574 Some(ref x) if !x.is_empty() => x
1575 .split(',')
1576 .filter(|s| !s.is_empty())
1578 .map(|s| match validate_node_url(s).map(Into::into) {
1579 None => Ok(s.to_owned()),
1580 Some(network::Error::AddressResolve(_)) => Err(format!(
1581 "Failed to resolve hostname of a boot node: {}",
1582 s
1583 )),
1584 Some(e) => Err(format!(
1585 "Invalid node address format given for a boot node: {} err={:?}",
1586 s, e
1587 )),
1588 })
1589 .collect(),
1590 Some(_) => Ok(vec![]),
1591 None => Ok(vec![]),
1592 }
1593}
1594
1595pub fn parse_config_address_string(
1596 addr: &str, network: &Network,
1597) -> Result<Address, String> {
1598 let base32_err = match cfx_addr_decode(addr) {
1599 Ok(address) => {
1600 return if address.network != *network {
1601 Err(format!(
1602 "address in configuration has unmatching network id: expected network={},\
1603 address.network={}",
1604 network,
1605 address.network
1606 ))
1607 } else {
1608 address
1609 .hex_address
1610 .ok_or("decoded address has wrong byte length".into())
1611 };
1612 }
1613 Err(e) => e,
1614 };
1615 let hex_err = match parse_hex_string(addr) {
1616 Ok(address) => return Ok(address),
1617 Err(e) => e,
1618 };
1619 Err(format!("Address from configuration should be a valid base32 address or a 40-digit hex string!
1621 base32_err={:?}
1622 hex_err={:?}",
1623 base32_err, hex_err))
1624}
1625
1626#[cfg(test)]
1627mod tests {
1628 use cfx_addr::Network;
1629
1630 use crate::configuration::parse_config_address_string;
1631
1632 #[test]
1633 fn test_config_address_string() {
1634 let addr = parse_config_address_string(
1635 "0x1a2f80341409639ea6a35bbcab8299066109aa55",
1636 &Network::Main,
1637 )
1638 .unwrap();
1639 assert_eq!(
1641 addr,
1642 parse_config_address_string(
1643 "1a2f80341409639ea6a35bbcab8299066109aa55",
1644 &Network::Main,
1645 )
1646 .unwrap()
1647 );
1648 assert_eq!(
1650 addr,
1651 parse_config_address_string(
1652 "cfx:aarc9abycue0hhzgyrr53m6cxedgccrmmyybjgh4xg",
1653 &Network::Main,
1654 )
1655 .unwrap()
1656 );
1657 assert_eq!(
1659 addr,
1660 parse_config_address_string(
1661 "cfx:type.user:aarc9abycue0hhzgyrr53m6cxedgccrmmyybjgh4xg",
1662 &Network::Main,
1663 )
1664 .unwrap()
1665 );
1666 }
1667}