From c44a8e94dce1cf60d012721b22f4a35dd13d5624 Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 14:28:01 -0500 Subject: [PATCH 1/8] added bunch of things --- src/cost_estimates/mod.rs | 14 ++++++++++--- src/cost_estimates/pessimistic.rs | 35 +++++++++++++++++++++---------- src/net/rpc.rs | 25 +++++++++++----------- 3 files changed, 47 insertions(+), 27 deletions(-) diff --git a/src/cost_estimates/mod.rs b/src/cost_estimates/mod.rs index 129cfd05ab..f5bf5b0ee3 100644 --- a/src/cost_estimates/mod.rs +++ b/src/cost_estimates/mod.rs @@ -21,6 +21,7 @@ pub mod pessimistic; pub mod tests; use crate::chainstate::stacks::StacksTransaction; +use core::StacksEpochId; use self::metrics::CostMetric; pub use self::pessimistic::PessimisticEstimator; @@ -128,12 +129,15 @@ pub trait CostEstimator: Send { tx: &TransactionPayload, actual_cost: &ExecutionCost, block_limit: &ExecutionCost, +evaluated_epoch: &StacksEpochId ) -> Result<(), EstimatorError>; /// This method is used by a stacks-node to obtain an estimate for a given transaction payload. /// If the estimator cannot provide an accurate estimate for a given payload, it should return /// `EstimatorError::NoEstimateAvailable` - fn estimate_cost(&self, tx: &TransactionPayload) -> Result; + fn estimate_cost(&self, tx: &TransactionPayload, +evaluated_epoch: &StacksEpochId + ) -> Result; /// This method is invoked by the `stacks-node` to notify the estimator of all the transaction /// receipts in a given block. @@ -225,11 +229,12 @@ impl CostEstimator for () { _tx: &TransactionPayload, _actual_cost: &ExecutionCost, _block_limit: &ExecutionCost, + _evaluated_epoch: &StacksEpochId ) -> Result<(), EstimatorError> { Ok(()) } - fn estimate_cost(&self, _tx: &TransactionPayload) -> Result { + fn estimate_cost(&self, _tx: &TransactionPayload, _evaluated_epoch: &StacksEpochId) -> Result { Err(EstimatorError::NoEstimateAvailable) } } @@ -261,11 +266,14 @@ impl CostEstimator for UnitEstimator { _tx: &TransactionPayload, _actual_cost: &ExecutionCost, _block_limit: &ExecutionCost, +_evaluated_epoch: &StacksEpochId ) -> Result<(), EstimatorError> { Ok(()) } - fn estimate_cost(&self, _tx: &TransactionPayload) -> Result { + fn estimate_cost(&self, _tx: &TransactionPayload, +_evaluated_epoch: &StacksEpochId + ) -> Result { Ok(ExecutionCost { write_length: 1, write_count: 1, diff --git a/src/cost_estimates/pessimistic.rs b/src/cost_estimates/pessimistic.rs index 13478276dd..4860c71074 100644 --- a/src/cost_estimates/pessimistic.rs +++ b/src/cost_estimates/pessimistic.rs @@ -18,6 +18,8 @@ use crate::util::db::sql_pragma; use crate::util::db::table_exists; use crate::util::db::tx_begin_immediate_sqlite; +use crate::core::StacksEpochId; + use super::{CostEstimator, EstimatorError}; /// This struct pessimistically estimates the `ExecutionCost` of transaction payloads. @@ -215,11 +217,19 @@ impl PessimisticEstimator { Ok(()) } - fn get_estimate_key(tx: &TransactionPayload, field: &CostField) -> String { + fn get_estimate_key(tx: &TransactionPayload, field: &CostField, evaluated_epoch: &StacksEpochId) -> String { let tx_descriptor = match tx { TransactionPayload::TokenTransfer(..) => "stx-transfer".to_string(), TransactionPayload::ContractCall(cc) => { - format!("cc:{}.{}", cc.contract_name, cc.function_name) + let epoch_marker = match evaluated_epoch { + StacksEpochId::Epoch10 => "", + StacksEpochId::Epoch20 => "", + StacksEpochId::Epoch2_05 => ":2.05", + }; + format!( + "cc{}:{}.{}", + epoch_marker, cc.contract_name, cc.function_name + ) } TransactionPayload::SmartContract(_sc) => "contract-publish".to_string(), TransactionPayload::PoisonMicroblock(_, _) => "poison-ublock".to_string(), @@ -242,6 +252,7 @@ impl CostEstimator for PessimisticEstimator { tx: &TransactionPayload, actual_cost: &ExecutionCost, block_limit: &ExecutionCost, +evaluated_epoch: &StacksEpochId ) -> Result<(), EstimatorError> { if self.log_error { // only log the estimate error if an estimate could be constructed @@ -251,14 +262,14 @@ impl CostEstimator for PessimisticEstimator { let actual_scalar = actual_cost.proportion_dot_product(&block_limit, PROPORTION_RESOLUTION); info!("PessimisticEstimator received event"; - "key" => %PessimisticEstimator::get_estimate_key(tx, &CostField::RuntimeCost), + "key" => %PessimisticEstimator::get_estimate_key(tx, &CostField::RuntimeCost, evaluated_epoch), "estimate" => estimated_scalar, "actual" => actual_scalar, "estimate_err" => (estimated_scalar as i64 - actual_scalar as i64), "estimate_err_pct" => (estimated_scalar as i64 - actual_scalar as i64)/(cmp::max(1, actual_scalar as i64)),); for field in CostField::ALL.iter() { info!("New data event received"; - "key" => %PessimisticEstimator::get_estimate_key(tx, field), + "key" => %PessimisticEstimator::get_estimate_key(tx, field, evaluated_epoch), "value" => field.select_key(actual_cost)); } } @@ -266,7 +277,7 @@ impl CostEstimator for PessimisticEstimator { let sql_tx = tx_begin_immediate_sqlite(&mut self.db)?; for field in CostField::ALL.iter() { - let key = PessimisticEstimator::get_estimate_key(tx, field); + let key = PessimisticEstimator::get_estimate_key(tx, field, evaluated_epoch); let field_cost = field.select_key(actual_cost); let mut current_sample = Samples::get_sqlite(&sql_tx, &key); current_sample.update_with(field_cost); @@ -276,30 +287,32 @@ impl CostEstimator for PessimisticEstimator { Ok(()) } - fn estimate_cost(&self, tx: &TransactionPayload) -> Result { + fn estimate_cost(&self, tx: &TransactionPayload, +evaluated_epoch: &StacksEpochId + ) -> Result { let runtime = Samples::get_estimate_sqlite( &self.db, - &PessimisticEstimator::get_estimate_key(tx, &CostField::RuntimeCost), + &PessimisticEstimator::get_estimate_key(tx, &CostField::RuntimeCost, evaluated_epoch), ) .ok_or_else(|| EstimatorError::NoEstimateAvailable)?; let read_count = Samples::get_estimate_sqlite( &self.db, - &PessimisticEstimator::get_estimate_key(tx, &CostField::ReadCount), + &PessimisticEstimator::get_estimate_key(tx, &CostField::ReadCount, evaluated_epoch), ) .ok_or_else(|| EstimatorError::NoEstimateAvailable)?; let read_length = Samples::get_estimate_sqlite( &self.db, - &PessimisticEstimator::get_estimate_key(tx, &CostField::ReadLength), + &PessimisticEstimator::get_estimate_key(tx, &CostField::ReadLength, evaluated_epoch), ) .ok_or_else(|| EstimatorError::NoEstimateAvailable)?; let write_count = Samples::get_estimate_sqlite( &self.db, - &PessimisticEstimator::get_estimate_key(tx, &CostField::WriteCount), + &PessimisticEstimator::get_estimate_key(tx, &CostField::WriteCount, evaluated_epoch), ) .ok_or_else(|| EstimatorError::NoEstimateAvailable)?; let write_length = Samples::get_estimate_sqlite( &self.db, - &PessimisticEstimator::get_estimate_key(tx, &CostField::WriteLength), + &PessimisticEstimator::get_estimate_key(tx, &CostField::WriteLength, evaluated_epoch), ) .ok_or_else(|| EstimatorError::NoEstimateAvailable)?; diff --git a/src/net/rpc.rs b/src/net/rpc.rs index 160d017fed..a5b22e8b27 100644 --- a/src/net/rpc.rs +++ b/src/net/rpc.rs @@ -1609,19 +1609,6 @@ impl ConversationHttp { estimated_len: u64, ) -> Result<(), net_error> { let response_metadata = HttpResponseMetadata::from(req); - if let Some((cost_estimator, fee_estimator, metric)) = handler_args.get_estimators_ref() { - let estimated_cost = match cost_estimator.estimate_cost(tx) { - Ok(x) => x, - Err(e) => { - debug!( - "Estimator RPC endpoint failed to estimate tx: {}", - tx.name() - ); - return HttpResponseType::BadRequestJSON(response_metadata, e.into_json()) - .send(http, fd); - } - }; - let tip = SortitionDB::get_canonical_burn_chain_tip(sortdb.conn())?; let stacks_epoch = sortdb .index_conn() @@ -1633,6 +1620,18 @@ impl ConversationHttp { ); net_error::ChainstateError("Could not load Stacks epoch for canonical burn height".into()) })?; + if let Some((cost_estimator, fee_estimator, metric)) = handler_args.get_estimators_ref() { + let estimated_cost = match cost_estimator.estimate_cost(tx, &stacks_epoch.epoch_id) { + Ok(x) => x, + Err(e) => { + debug!( + "Estimator RPC endpoint failed to estimate tx: {}", + tx.name() + ); + return HttpResponseType::BadRequestJSON(response_metadata, e.into_json()) + .send(http, fd); + } + }; let scalar_cost = metric.from_cost_and_len(&estimated_cost, &stacks_epoch.block_limit, estimated_len); From 4b65e0a7e1980fe0570f7010f5b01149d22f96ae Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 15:24:00 -0500 Subject: [PATCH 2/8] moving the stuff --- src/chainstate/coordinator/mod.rs | 2 +- src/chainstate/stacks/miner.rs | 25 +++++++++++++++++++++++-- src/core/mempool.rs | 7 +++++++ src/cost_estimates/mod.rs | 7 ++++--- src/cost_estimates/pessimistic.rs | 2 +- src/net/p2p.rs | 1 + src/net/rpc.rs | 1 + 7 files changed, 38 insertions(+), 7 deletions(-) diff --git a/src/chainstate/coordinator/mod.rs b/src/chainstate/coordinator/mod.rs index eedb5ce1c7..7997d296be 100644 --- a/src/chainstate/coordinator/mod.rs +++ b/src/chainstate/coordinator/mod.rs @@ -775,7 +775,7 @@ impl< .get_stacks_epoch_by_epoch_id(&block_receipt.evaluated_epoch) .expect("Could not find a stacks epoch."); estimator - .notify_block(&block_receipt.tx_receipts, &stacks_epoch.block_limit); + .notify_block(&block_receipt.tx_receipts, &stacks_epoch.block_limit, &stacks_epoch.epoch_id); } if let Some(ref mut estimator) = self.fee_estimator { diff --git a/src/chainstate/stacks/miner.rs b/src/chainstate/stacks/miner.rs index bc36f115f0..8c4d2735e3 100644 --- a/src/chainstate/stacks/miner.rs +++ b/src/chainstate/stacks/miner.rs @@ -470,10 +470,11 @@ impl<'a> StacksMicroblockBuilder<'a> { let deadline = get_epoch_time_ms() + (self.settings.max_miner_time_ms as u128); mem_pool.reset_last_known_nonces()?; + let stacks_epoch_id = clarity_tx.get_epoch(); let block_limit = clarity_tx .block_limit() .expect("No block limit found for clarity_tx."); - mem_pool.estimate_tx_rates(100, &block_limit)?; + mem_pool.estimate_tx_rates(100, &block_limit, &stacks_epoch_id)?; debug!( "Microblock transaction selection begins (child of {}), bytes so far: {}", @@ -514,6 +515,7 @@ impl<'a> StacksMicroblockBuilder<'a> { &mempool_tx.tx.payload, &receipt.execution_cost, &block_limit, + &stacks_epoch_id, ) { warn!("Error updating estimator"; "txid" => %mempool_tx.metadata.txid, @@ -1492,6 +1494,8 @@ impl StacksBlockBuilder { let mut epoch_tx = builder.epoch_begin(&mut chainstate, burn_dbconn)?; + let stacks_epoch_id = epoch_tx.get_epoch(); + let block_limit = epoch_tx .block_limit() .expect("Failed to obtain block limit from miner's block connection"); @@ -1500,7 +1504,7 @@ impl StacksBlockBuilder { mempool.reset_last_known_nonces()?; - mempool.estimate_tx_rates(100, &block_limit)?; + mempool.estimate_tx_rates(100, &block_limit, &stacks_epoch_id)?; let mut considered = HashSet::new(); // txids of all transactions we looked at let mut mined_origin_nonces: HashMap = HashMap::new(); // map addrs of mined transaction origins to the nonces we used @@ -1572,6 +1576,7 @@ impl StacksBlockBuilder { &txinfo.tx.payload, &tx_receipt.execution_cost, &block_limit, + &stacks_epoch_id, ) { warn!("Error updating estimator"; "txid" => %txinfo.metadata.txid, @@ -6588,6 +6593,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -6728,6 +6734,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -6865,6 +6872,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -6889,6 +6897,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -7036,6 +7045,7 @@ pub mod test { &tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -7238,6 +7248,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -7258,6 +7269,7 @@ pub mod test { &contract_tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -7277,6 +7289,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -7431,6 +7444,7 @@ pub mod test { &contract_tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -7588,6 +7602,7 @@ pub mod test { &contract_tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -7723,6 +7738,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -7749,6 +7765,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -8094,6 +8111,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -8121,6 +8139,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -8156,6 +8175,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -8183,6 +8203,7 @@ pub mod test { &parent_header_hash, contract_tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); diff --git a/src/core/mempool.rs b/src/core/mempool.rs index 550d53099d..4f0b0b9d72 100644 --- a/src/core/mempool.rs +++ b/src/core/mempool.rs @@ -42,6 +42,7 @@ use chainstate::stacks::{ use core::ExecutionCost; use core::FIRST_BURNCHAIN_CONSENSUS_HASH; use core::FIRST_STACKS_BLOCK_HASH; +use core::StacksEpochId; use monitoring::increment_stx_mempool_gc; use std::time::Instant; use util::db::query_row_columns; @@ -661,6 +662,7 @@ impl MemPoolDB { &mut self, max_updates: u32, block_limit: &ExecutionCost, + stacks_epoch_id: &StacksEpochId, ) -> Result { let sql_tx = tx_begin_immediate(&mut self.db)?; let txs: Vec = query_rows( @@ -677,6 +679,7 @@ impl MemPoolDB { self.cost_estimator.as_ref(), self.metric.as_ref(), block_limit, + stacks_epoch_id, ); let fee_rate_f64 = match estimator_result { Ok(x) => Some(x), @@ -1232,12 +1235,14 @@ impl MemPoolDB { tx: &StacksTransaction, event_observer: Option<&dyn MemPoolEventDispatcher>, block_limit: &ExecutionCost, + stacks_epoch_id: &StacksEpochId, ) -> Result<(), MemPoolRejection> { let estimator_result = cost_estimates::estimate_fee_rate( tx, self.cost_estimator.as_ref(), self.metric.as_ref(), block_limit, + stacks_epoch_id, ); let mut mempool_tx = self.tx_begin().map_err(MemPoolRejection::DBError)?; @@ -1277,6 +1282,7 @@ impl MemPoolDB { block_hash: &BlockHeaderHash, tx_bytes: Vec, block_limit: &ExecutionCost, + stacks_epoch_id:&StacksEpochId, ) -> Result<(), MemPoolRejection> { let tx = StacksTransaction::consensus_deserialize(&mut &tx_bytes[..]) .map_err(MemPoolRejection::DeserializationFailure)?; @@ -1286,6 +1292,7 @@ impl MemPoolDB { self.cost_estimator.as_ref(), self.metric.as_ref(), block_limit, + stacks_epoch_id, ); let mut mempool_tx = self.tx_begin().map_err(MemPoolRejection::DBError)?; diff --git a/src/cost_estimates/mod.rs b/src/cost_estimates/mod.rs index f5bf5b0ee3..2c7c56d5ba 100644 --- a/src/cost_estimates/mod.rs +++ b/src/cost_estimates/mod.rs @@ -107,8 +107,9 @@ pub fn estimate_fee_rate( estimator: &CE, metric: &CM, block_limit: &ExecutionCost, + stacks_epoch_id: &StacksEpochId, ) -> Result { - let cost_estimate = estimator.estimate_cost(&tx.payload)?; + let cost_estimate = estimator.estimate_cost(&tx.payload, stacks_epoch_id)?; let metric_estimate = metric.from_cost_and_len(&cost_estimate, block_limit, tx.tx_len()); Ok(tx.get_tx_fee() as f64 / metric_estimate as f64) } @@ -144,7 +145,7 @@ evaluated_epoch: &StacksEpochId /// /// A default implementation is provided to implementing structs that processes the transaction /// receipts by feeding them into `CostEstimator::notify_event()` - fn notify_block(&mut self, receipts: &[StacksTransactionReceipt], block_limit: &ExecutionCost) { + fn notify_block(&mut self, receipts: &[StacksTransactionReceipt], block_limit: &ExecutionCost, stacks_epoch_id:&StacksEpochId) { // iterate over receipts, and for all the tx receipts, notify the event for current_receipt in receipts.iter() { let current_txid = match current_receipt.transaction { @@ -157,7 +158,7 @@ evaluated_epoch: &StacksEpochId }; if let Err(e) = - self.notify_event(tx_payload, ¤t_receipt.execution_cost, block_limit) + self.notify_event(tx_payload, ¤t_receipt.execution_cost, block_limit, stacks_epoch_id) { info!("CostEstimator failed to process event"; "txid" => %current_txid, diff --git a/src/cost_estimates/pessimistic.rs b/src/cost_estimates/pessimistic.rs index 4860c71074..106ca2eb15 100644 --- a/src/cost_estimates/pessimistic.rs +++ b/src/cost_estimates/pessimistic.rs @@ -256,7 +256,7 @@ evaluated_epoch: &StacksEpochId ) -> Result<(), EstimatorError> { if self.log_error { // only log the estimate error if an estimate could be constructed - if let Ok(estimated_cost) = self.estimate_cost(tx) { + if let Ok(estimated_cost) = self.estimate_cost(tx, evaluated_epoch) { let estimated_scalar = estimated_cost.proportion_dot_product(&block_limit, PROPORTION_RESOLUTION); let actual_scalar = diff --git a/src/net/p2p.rs b/src/net/p2p.rs index 077cfeae5e..a7477dcce5 100644 --- a/src/net/p2p.rs +++ b/src/net/p2p.rs @@ -4416,6 +4416,7 @@ impl PeerNetwork { &tx, event_observer, &stacks_epoch.block_limit, + &stacks_epoch.epoch_id, ) { warn!("Transaction rejected from mempool, {}", &e.into_json(&txid)); return false; diff --git a/src/net/rpc.rs b/src/net/rpc.rs index a5b22e8b27..06f63b47f1 100644 --- a/src/net/rpc.rs +++ b/src/net/rpc.rs @@ -1726,6 +1726,7 @@ impl ConversationHttp { &tx, event_observer, &stacks_epoch.block_limit, + &stacks_epoch.epoch_id, ) { Ok(_) => { debug!("Mempool accepted POSTed transaction {}", &txid); From 3c05b52b0c94e507fc78c92fb28e040f1a354b74 Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 16:21:25 -0500 Subject: [PATCH 3/8] test compiles --- src/chainstate/coordinator/mod.rs | 7 +- src/chainstate/stacks/miner.rs | 12 ++- src/core/mempool.rs | 4 +- src/cost_estimates/mod.rs | 44 ++++++---- src/cost_estimates/pessimistic.rs | 16 ++-- src/cost_estimates/tests/cost_estimators.rs | 93 +++++++++++++++++---- src/net/rpc.rs | 4 +- 7 files changed, 135 insertions(+), 45 deletions(-) diff --git a/src/chainstate/coordinator/mod.rs b/src/chainstate/coordinator/mod.rs index 7997d296be..4fd0700fc3 100644 --- a/src/chainstate/coordinator/mod.rs +++ b/src/chainstate/coordinator/mod.rs @@ -774,8 +774,11 @@ impl< .index_conn() .get_stacks_epoch_by_epoch_id(&block_receipt.evaluated_epoch) .expect("Could not find a stacks epoch."); - estimator - .notify_block(&block_receipt.tx_receipts, &stacks_epoch.block_limit, &stacks_epoch.epoch_id); + estimator.notify_block( + &block_receipt.tx_receipts, + &stacks_epoch.block_limit, + &stacks_epoch.epoch_id, + ); } if let Some(ref mut estimator) = self.fee_estimator { diff --git a/src/chainstate/stacks/miner.rs b/src/chainstate/stacks/miner.rs index 8c4d2735e3..9b8765127f 100644 --- a/src/chainstate/stacks/miner.rs +++ b/src/chainstate/stacks/miner.rs @@ -6872,7 +6872,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), - &StacksEpochId::Epoch20, + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -6897,7 +6897,7 @@ pub mod test { &stx_transfer, None, &ExecutionCost::max_value(), - &StacksEpochId::Epoch20, + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -7045,7 +7045,7 @@ pub mod test { &tx, None, &ExecutionCost::max_value(), - &StacksEpochId::Epoch20, + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -8470,6 +8470,7 @@ pub mod test { &parent_header_hash, tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -8801,6 +8802,7 @@ pub mod test { &parent_header_hash, tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -8875,6 +8877,7 @@ pub mod test { &parent_header_hash, tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -8906,6 +8909,7 @@ pub mod test { &parent_header_hash, tx_bytes, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -9281,6 +9285,7 @@ pub mod test { &tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap() } @@ -9305,6 +9310,7 @@ pub mod test { &tx, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap() } diff --git a/src/core/mempool.rs b/src/core/mempool.rs index 4f0b0b9d72..b8c2b52abc 100644 --- a/src/core/mempool.rs +++ b/src/core/mempool.rs @@ -40,9 +40,9 @@ use chainstate::stacks::{ Error as ChainstateError, StacksTransaction, }; use core::ExecutionCost; +use core::StacksEpochId; use core::FIRST_BURNCHAIN_CONSENSUS_HASH; use core::FIRST_STACKS_BLOCK_HASH; -use core::StacksEpochId; use monitoring::increment_stx_mempool_gc; use std::time::Instant; use util::db::query_row_columns; @@ -1282,7 +1282,7 @@ impl MemPoolDB { block_hash: &BlockHeaderHash, tx_bytes: Vec, block_limit: &ExecutionCost, - stacks_epoch_id:&StacksEpochId, + stacks_epoch_id: &StacksEpochId, ) -> Result<(), MemPoolRejection> { let tx = StacksTransaction::consensus_deserialize(&mut &tx_bytes[..]) .map_err(MemPoolRejection::DeserializationFailure)?; diff --git a/src/cost_estimates/mod.rs b/src/cost_estimates/mod.rs index 2c7c56d5ba..fd481de13c 100644 --- a/src/cost_estimates/mod.rs +++ b/src/cost_estimates/mod.rs @@ -130,22 +130,29 @@ pub trait CostEstimator: Send { tx: &TransactionPayload, actual_cost: &ExecutionCost, block_limit: &ExecutionCost, -evaluated_epoch: &StacksEpochId + evaluated_epoch: &StacksEpochId, ) -> Result<(), EstimatorError>; /// This method is used by a stacks-node to obtain an estimate for a given transaction payload. /// If the estimator cannot provide an accurate estimate for a given payload, it should return /// `EstimatorError::NoEstimateAvailable` - fn estimate_cost(&self, tx: &TransactionPayload, -evaluated_epoch: &StacksEpochId - ) -> Result; + fn estimate_cost( + &self, + tx: &TransactionPayload, + evaluated_epoch: &StacksEpochId, + ) -> Result; /// This method is invoked by the `stacks-node` to notify the estimator of all the transaction /// receipts in a given block. /// /// A default implementation is provided to implementing structs that processes the transaction /// receipts by feeding them into `CostEstimator::notify_event()` - fn notify_block(&mut self, receipts: &[StacksTransactionReceipt], block_limit: &ExecutionCost, stacks_epoch_id:&StacksEpochId) { + fn notify_block( + &mut self, + receipts: &[StacksTransactionReceipt], + block_limit: &ExecutionCost, + stacks_epoch_id: &StacksEpochId, + ) { // iterate over receipts, and for all the tx receipts, notify the event for current_receipt in receipts.iter() { let current_txid = match current_receipt.transaction { @@ -157,9 +164,12 @@ evaluated_epoch: &StacksEpochId TransactionOrigin::Stacks(ref tx) => &tx.payload, }; - if let Err(e) = - self.notify_event(tx_payload, ¤t_receipt.execution_cost, block_limit, stacks_epoch_id) - { + if let Err(e) = self.notify_event( + tx_payload, + ¤t_receipt.execution_cost, + block_limit, + stacks_epoch_id, + ) { info!("CostEstimator failed to process event"; "txid" => %current_txid, "error" => %e, @@ -230,12 +240,16 @@ impl CostEstimator for () { _tx: &TransactionPayload, _actual_cost: &ExecutionCost, _block_limit: &ExecutionCost, - _evaluated_epoch: &StacksEpochId + _evaluated_epoch: &StacksEpochId, ) -> Result<(), EstimatorError> { Ok(()) } - fn estimate_cost(&self, _tx: &TransactionPayload, _evaluated_epoch: &StacksEpochId) -> Result { + fn estimate_cost( + &self, + _tx: &TransactionPayload, + _evaluated_epoch: &StacksEpochId, + ) -> Result { Err(EstimatorError::NoEstimateAvailable) } } @@ -267,14 +281,16 @@ impl CostEstimator for UnitEstimator { _tx: &TransactionPayload, _actual_cost: &ExecutionCost, _block_limit: &ExecutionCost, -_evaluated_epoch: &StacksEpochId + _evaluated_epoch: &StacksEpochId, ) -> Result<(), EstimatorError> { Ok(()) } - fn estimate_cost(&self, _tx: &TransactionPayload, -_evaluated_epoch: &StacksEpochId - ) -> Result { + fn estimate_cost( + &self, + _tx: &TransactionPayload, + _evaluated_epoch: &StacksEpochId, + ) -> Result { Ok(ExecutionCost { write_length: 1, write_count: 1, diff --git a/src/cost_estimates/pessimistic.rs b/src/cost_estimates/pessimistic.rs index 106ca2eb15..2fbb72144c 100644 --- a/src/cost_estimates/pessimistic.rs +++ b/src/cost_estimates/pessimistic.rs @@ -217,7 +217,11 @@ impl PessimisticEstimator { Ok(()) } - fn get_estimate_key(tx: &TransactionPayload, field: &CostField, evaluated_epoch: &StacksEpochId) -> String { + fn get_estimate_key( + tx: &TransactionPayload, + field: &CostField, + evaluated_epoch: &StacksEpochId, + ) -> String { let tx_descriptor = match tx { TransactionPayload::TokenTransfer(..) => "stx-transfer".to_string(), TransactionPayload::ContractCall(cc) => { @@ -252,7 +256,7 @@ impl CostEstimator for PessimisticEstimator { tx: &TransactionPayload, actual_cost: &ExecutionCost, block_limit: &ExecutionCost, -evaluated_epoch: &StacksEpochId + evaluated_epoch: &StacksEpochId, ) -> Result<(), EstimatorError> { if self.log_error { // only log the estimate error if an estimate could be constructed @@ -287,9 +291,11 @@ evaluated_epoch: &StacksEpochId Ok(()) } - fn estimate_cost(&self, tx: &TransactionPayload, -evaluated_epoch: &StacksEpochId - ) -> Result { + fn estimate_cost( + &self, + tx: &TransactionPayload, + evaluated_epoch: &StacksEpochId, + ) -> Result { let runtime = Samples::get_estimate_sqlite( &self.db, &PessimisticEstimator::get_estimate_key(tx, &CostField::RuntimeCost, evaluated_epoch), diff --git a/src/cost_estimates/tests/cost_estimators.rs b/src/cost_estimates/tests/cost_estimators.rs index d8cfb56c49..67b5f0bdb3 100644 --- a/src/cost_estimates/tests/cost_estimators.rs +++ b/src/cost_estimates/tests/cost_estimators.rs @@ -67,7 +67,7 @@ fn test_empty_pessimistic_estimator() { let estimator = instantiate_test_db(); assert_eq!( estimator - .estimate_cost(&make_dummy_transfer_payload()) + .estimate_cost(&make_dummy_transfer_payload(), &StacksEpochId::Epoch20) .expect_err("Empty pessimistic estimator should error."), EstimatorError::NoEstimateAvailable ); @@ -191,11 +191,14 @@ fn test_cost_estimator_notify_block() { }, ), ]; - estimator.notify_block(&block, &BLOCK_LIMIT_MAINNET_20); + estimator.notify_block(&block, &BLOCK_LIMIT_MAINNET_20, &StacksEpochId::Epoch20); assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20 + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 10, @@ -227,12 +230,16 @@ fn test_pessimistic_cost_estimator_declining_average() { runtime: 10, }, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20 + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 10, @@ -254,12 +261,16 @@ fn test_pessimistic_cost_estimator_declining_average() { runtime: 1, }, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 5, @@ -290,12 +301,16 @@ fn test_pessimistic_cost_estimator() { runtime: 1, }, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 1, @@ -319,12 +334,16 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 5, @@ -340,6 +359,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -349,7 +369,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 2 + 1 = 7 / 3 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 6, @@ -365,6 +388,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -374,7 +398,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 3 + 1 = 10 / 4 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 7, @@ -390,6 +417,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -399,7 +427,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 4 + 1 = 13 / 5 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 7, @@ -415,6 +446,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -424,7 +456,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 5 + 1 = 16 / 6 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 7, @@ -440,6 +475,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -449,7 +485,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 6 + 1 = 19 / 7 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 7, @@ -465,6 +504,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -474,7 +514,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 7 + 1 = 22 / 8 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 8, @@ -490,6 +533,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -499,7 +543,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 8 + 1 = 25 / 9 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 8, @@ -515,6 +562,7 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -524,7 +572,10 @@ fn test_pessimistic_cost_estimator() { // 3 * 9 + 1 = 28 / 10 assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 8, @@ -543,13 +594,17 @@ fn test_pessimistic_cost_estimator() { &make_dummy_cc_payload("contract-1", "func1"), &repeated_cost, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); // should just be equal to the repeated cost, because all of the costs in the window are equal assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 9, @@ -571,6 +626,7 @@ fn test_pessimistic_cost_estimator() { runtime: 1, }, &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, ) .expect("Should be able to process event"); @@ -578,7 +634,10 @@ fn test_pessimistic_cost_estimator() { // by the pessimistic estimator assert_eq!( estimator - .estimate_cost(&make_dummy_cc_payload("contract-1", "func1")) + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20, + ) .expect("Should be able to provide cost estimate now"), ExecutionCost { write_length: 9, diff --git a/src/net/rpc.rs b/src/net/rpc.rs index 06f63b47f1..b0beb981c7 100644 --- a/src/net/rpc.rs +++ b/src/net/rpc.rs @@ -1609,8 +1609,8 @@ impl ConversationHttp { estimated_len: u64, ) -> Result<(), net_error> { let response_metadata = HttpResponseMetadata::from(req); - let tip = SortitionDB::get_canonical_burn_chain_tip(sortdb.conn())?; - let stacks_epoch = sortdb + let tip = SortitionDB::get_canonical_burn_chain_tip(sortdb.conn())?; + let stacks_epoch = sortdb .index_conn() .get_stacks_epoch(tip.block_height as u32) .ok_or_else(|| { From 91e704f005e5c71843dfd10b52f47ac3ebb3aa9b Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 16:56:37 -0500 Subject: [PATCH 4/8] added a test --- src/cost_estimates/pessimistic.rs | 1 + src/cost_estimates/tests/cost_estimators.rs | 53 +++++++++++++++++++++ 2 files changed, 54 insertions(+) diff --git a/src/cost_estimates/pessimistic.rs b/src/cost_estimates/pessimistic.rs index 2fbb72144c..06a31ff587 100644 --- a/src/cost_estimates/pessimistic.rs +++ b/src/cost_estimates/pessimistic.rs @@ -225,6 +225,7 @@ impl PessimisticEstimator { let tx_descriptor = match tx { TransactionPayload::TokenTransfer(..) => "stx-transfer".to_string(), TransactionPayload::ContractCall(cc) => { + // Epoch key is "" before Epoch2_05 for backwards compatibility. let epoch_marker = match evaluated_epoch { StacksEpochId::Epoch10 => "", StacksEpochId::Epoch20 => "", diff --git a/src/cost_estimates/tests/cost_estimators.rs b/src/cost_estimates/tests/cost_estimators.rs index 67b5f0bdb3..9506f05e83 100644 --- a/src/cost_estimates/tests/cost_estimators.rs +++ b/src/cost_estimates/tests/cost_estimators.rs @@ -648,3 +648,56 @@ fn test_pessimistic_cost_estimator() { } ); } + +/// Test that we forget the "learnings" from previous Stacks epoch on next epoch. +#[test] +fn test_cost_estimator_forget_previous() { + // Setup: Do "notify" in Epoch20. + let mut estimator = instantiate_test_db(); + let block = vec![ + make_dummy_coinbase_tx(), + make_dummy_transfer_tx(), + make_dummy_transfer_tx(), + make_dummy_cc_tx( + "contract-1", + "func1", + ExecutionCost { + write_length: 10, + write_count: 10, + read_length: 10, + read_count: 10, + runtime: 10, + }, + ), + ]; + estimator.notify_block(&block, &BLOCK_LIMIT_MAINNET_20, &StacksEpochId::Epoch20); + + // Test 1: We should get *non-zero* estimates back when we test in Epoch20. + assert_eq!( + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20 + ) + .expect("Should be able to provide cost estimate now"), + ExecutionCost { + write_length: 10, + write_count: 10, + read_length: 10, + read_count: 10, + runtime: 10, + } + ); + + // Test 2: We should get *zero* estimates back when we test in Epoch20. + assert_eq!( + error, + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch2_05 + ) + .unwrap_err(), + EstimatorError::NoEstimateAvailable + ); +} From 7f6649f214c4138b747afd09bdd3a3ad284caf6c Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 17:33:24 -0500 Subject: [PATCH 5/8] fixed typo --- src/cost_estimates/tests/cost_estimators.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/cost_estimates/tests/cost_estimators.rs b/src/cost_estimates/tests/cost_estimators.rs index 9506f05e83..1f07a548eb 100644 --- a/src/cost_estimates/tests/cost_estimators.rs +++ b/src/cost_estimates/tests/cost_estimators.rs @@ -689,7 +689,7 @@ fn test_cost_estimator_forget_previous() { } ); - // Test 2: We should get *zero* estimates back when we test in Epoch20. + // Test 2: We should get *zero* estimates back when we test in Epoch2_05. assert_eq!( error, estimator From 608ec8baeea95264ec97c51cb7e316218c988bbb Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Thu, 11 Nov 2021 20:39:21 -0500 Subject: [PATCH 6/8] added two tests --- src/cost_estimates/tests/cost_estimators.rs | 142 +++++++++++++++++--- 1 file changed, 125 insertions(+), 17 deletions(-) diff --git a/src/cost_estimates/tests/cost_estimators.rs b/src/cost_estimates/tests/cost_estimators.rs index 1f07a548eb..d6e7203cd3 100644 --- a/src/cost_estimates/tests/cost_estimators.rs +++ b/src/cost_estimates/tests/cost_estimators.rs @@ -654,22 +654,17 @@ fn test_pessimistic_cost_estimator() { fn test_cost_estimator_forget_previous() { // Setup: Do "notify" in Epoch20. let mut estimator = instantiate_test_db(); - let block = vec![ - make_dummy_coinbase_tx(), - make_dummy_transfer_tx(), - make_dummy_transfer_tx(), - make_dummy_cc_tx( - "contract-1", - "func1", - ExecutionCost { - write_length: 10, - write_count: 10, - read_length: 10, - read_count: 10, - runtime: 10, - }, - ), - ]; + let block = vec![make_dummy_cc_tx( + "contract-1", + "func1", + ExecutionCost { + write_length: 10, + write_count: 10, + read_length: 10, + read_count: 10, + runtime: 10, + }, + )]; estimator.notify_block(&block, &BLOCK_LIMIT_MAINNET_20, &StacksEpochId::Epoch20); // Test 1: We should get *non-zero* estimates back when we test in Epoch20. @@ -691,7 +686,6 @@ fn test_cost_estimator_forget_previous() { // Test 2: We should get *zero* estimates back when we test in Epoch2_05. assert_eq!( - error, estimator .estimate_cost( &make_dummy_cc_payload("contract-1", "func1"), @@ -701,3 +695,117 @@ fn test_cost_estimator_forget_previous() { EstimatorError::NoEstimateAvailable ); } + +/// Test that data from a later epoch doesn't affect an earlier one. +#[test] +fn test_cost_estimator_dont_affect_previous() { + // Setup: Do "notify" in Epoch2_05. + let mut estimator = instantiate_test_db(); + let block = vec![make_dummy_cc_tx( + "contract-1", + "func1", + ExecutionCost { + write_length: 10, + write_count: 10, + read_length: 10, + read_count: 10, + runtime: 10, + }, + )]; + estimator.notify_block(&block, &BLOCK_LIMIT_MAINNET_20, &StacksEpochId::Epoch2_05); + + // Test 1: We should get *non-zero* estimates back when we test in Epoch2_05. + assert_eq!( + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch2_05 + ) + .expect("Should be able to provide cost estimate now"), + ExecutionCost { + write_length: 10, + write_count: 10, + read_length: 10, + read_count: 10, + runtime: 10, + } + ); + + // Test 2: We should get *zero* estimates back when we test in Epoch20. + assert_eq!( + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20 + ) + .unwrap_err(), + EstimatorError::NoEstimateAvailable + ); +} + +/// Test that updates to Stacks 2.0 and Stacks 2.05 can be recorded and recovered independently. +#[test] +fn test_cost_estimator_epochs_independent() { + let contract_name = "contract-1"; + let func_name = "func1"; + let cost_200 = ExecutionCost { + write_length: 200, + write_count: 200, + read_length: 200, + read_count: 200, + runtime: 200, + }; + let cost_205 = ExecutionCost { + write_length: 205, + write_count: 205, + read_length: 205, + read_count: 205, + runtime: 205, + }; + let mut estimator = instantiate_test_db(); + + // Setup: "notify" cost_200 in Epoch20. + estimator.notify_block( + &vec![make_dummy_cc_tx( + &contract_name, + &func_name, + cost_200.clone(), + )], + &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch20, + ); + + // Setup: "notify" cost_205 in Epoch2_05. + estimator.notify_block( + &vec![ + make_dummy_coinbase_tx(), + make_dummy_transfer_tx(), + make_dummy_transfer_tx(), + make_dummy_cc_tx(&contract_name, &func_name, cost_205.clone()), + ], + &BLOCK_LIMIT_MAINNET_20, + &StacksEpochId::Epoch2_05, + ); + + // Check: We get back cost_200 for Epoch20. + assert_eq!( + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch20 + ) + .expect("Should be able to provide cost estimate now"), + cost_200.clone(), + ); + + // Check: We get back cost_205 for Epoch2_05. + assert_eq!( + estimator + .estimate_cost( + &make_dummy_cc_payload("contract-1", "func1"), + &StacksEpochId::Epoch2_05 + ) + .expect("Should be able to provide cost estimate now"), + cost_205.clone(), + ); +} From d36b44044b44bd2e0b7c696c7c2ee69a824e43c6 Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Mon, 15 Nov 2021 09:50:12 -0500 Subject: [PATCH 7/8] updated code/tests in stacks-node --- testnet/stacks-node/src/neon_node.rs | 1 + testnet/stacks-node/src/node.rs | 6 +++- .../stacks-node/src/tests/bitcoin_regtest.rs | 16 +++++++---- testnet/stacks-node/src/tests/integrations.rs | 25 +++++++++++++++++ testnet/stacks-node/src/tests/mempool.rs | 6 ++++ testnet/stacks-node/src/tests/mod.rs | 28 +++++++++++++------ 6 files changed, 67 insertions(+), 15 deletions(-) diff --git a/testnet/stacks-node/src/neon_node.rs b/testnet/stacks-node/src/neon_node.rs index e0a21663a0..cc22227304 100644 --- a/testnet/stacks-node/src/neon_node.rs +++ b/testnet/stacks-node/src/neon_node.rs @@ -1848,6 +1848,7 @@ impl InitializedNeonNode { &poison_microblock_tx, Some(event_observer), &stacks_epoch.block_limit, + &stacks_epoch.epoch_id, ) { warn!( "Detected but failed to mine poison-microblock transaction: {:?}", diff --git a/testnet/stacks-node/src/node.rs b/testnet/stacks-node/src/node.rs index 0853a46b30..ee3a2c0fcb 100644 --- a/testnet/stacks-node/src/node.rs +++ b/testnet/stacks-node/src/node.rs @@ -884,7 +884,11 @@ impl Node { .get_stacks_epoch_by_epoch_id(&processed_block.evaluated_epoch) .expect("Could not find a stacks epoch."); if let Some(estimator) = cost_estimator.as_mut() { - estimator.notify_block(&processed_block.tx_receipts, &stacks_epoch.block_limit); + estimator.notify_block( + &processed_block.tx_receipts, + &stacks_epoch.block_limit, + &stacks_epoch.epoch_id, + ); } if let Some(estimator) = fee_estimator.as_mut() { diff --git a/testnet/stacks-node/src/tests/bitcoin_regtest.rs b/testnet/stacks-node/src/tests/bitcoin_regtest.rs index 17db2ac45e..b13d07fa81 100644 --- a/testnet/stacks-node/src/tests/bitcoin_regtest.rs +++ b/testnet/stacks-node/src/tests/bitcoin_regtest.rs @@ -9,6 +9,7 @@ use stacks::chainstate::burn::operations::BlockstackOperationType::{ LeaderBlockCommit, LeaderKeyRegister, }; use stacks::chainstate::stacks::StacksPrivateKey; +use stacks::core::StacksEpochId; use stacks::util::hash::hex_bytes; use super::PUBLISH_CONTRACT; @@ -328,7 +329,8 @@ fn bitcoind_integration_test() { // ./blockstack-cli --testnet publish 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 0 0 store /tmp/out.clar let header_hash = chain_tip.block.block_hash(); let consensus_hash = chain_tip.metadata.consensus_hash; - tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash, PUBLISH_CONTRACT.to_owned(), &ExecutionCost::max_value()).unwrap(); + tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash, PUBLISH_CONTRACT.to_owned(), &ExecutionCost::max_value(), + &StacksEpochId::Epoch20,).unwrap(); }, 2 => { // On round 2, publish a "get:foo" transaction @@ -336,7 +338,8 @@ fn bitcoind_integration_test() { let header_hash = chain_tip.block.block_hash(); let consensus_hash = chain_tip.metadata.consensus_hash; let get_foo = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000001000000000000000a0100b7ff8b6c20c427b4f4f09c1ad7e50027e2b076b2ddc0ab55e64ef5ea3771dd4763a79bc5a2b1a79b72ce03dd146ccf24b84942d675a815819a8b85aa8065dfaa030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; - tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), &ExecutionCost::max_value()).unwrap(); + tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), &ExecutionCost::max_value(), + &StacksEpochId::Epoch20,).unwrap(); }, 3 => { // On round 3, publish a "set:foo=bar" transaction @@ -344,7 +347,8 @@ fn bitcoind_integration_test() { let header_hash = chain_tip.block.block_hash(); let consensus_hash = chain_tip.metadata.consensus_hash; let set_foo_bar = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000002000000000000000a010142a01caf6a32b367664869182f0ebc174122a5a980937ba259d44cc3ebd280e769a53dd3913c8006ead680a6e1c98099fcd509ce94b0a4e90d9f4603b101922d030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265097365742d76616c7565000000020d00000003666f6f0d00000003626172"; - tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(set_foo_bar).unwrap().to_vec(), &ExecutionCost::max_value()).unwrap(); + tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(set_foo_bar).unwrap().to_vec(), &ExecutionCost::max_value(), + &StacksEpochId::Epoch20,).unwrap(); }, 4 => { // On round 4, publish a "get:foo" transaction @@ -352,7 +356,8 @@ fn bitcoind_integration_test() { let header_hash = chain_tip.block.block_hash(); let consensus_hash = chain_tip.metadata.consensus_hash; let get_foo = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000003000000000000000a010046c2c1c345231443fef9a1f64fccfef3e1deacc342b2ab5f97612bb3742aa799038b20aea456789aca6b883e52f84a31adfee0bc2079b740464877af8f2f87d2030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; - tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), &ExecutionCost::max_value()).unwrap(); + tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), &ExecutionCost::max_value(), + &StacksEpochId::Epoch20,).unwrap(); }, 5 => { // On round 5, publish a stacks transaction @@ -360,7 +365,8 @@ fn bitcoind_integration_test() { let header_hash = chain_tip.block.block_hash(); let consensus_hash = chain_tip.metadata.consensus_hash; let transfer_1000_stx = "80800000000400b71a091b4b8b7661a661c620966ab6573bc2dcd30000000000000000000000000000000a0000393810832bacd44cfc4024980876135de6b95429bdb610d5ce96a92c9ee9bfd81ec77ea0f1748c8515fc9a1589e51d8b92bf028e3e84ade1249682c05271d5b803020000000000051a525b8a36ef8a73548cd0940c248d3b71ecf4a45100000000000003e800000000000000000000000000000000000000000000000000000000000000000000"; - tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(transfer_1000_stx).unwrap().to_vec(), &ExecutionCost::max_value()).unwrap(); + tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(transfer_1000_stx).unwrap().to_vec(), &ExecutionCost::max_value(), + &StacksEpochId::Epoch20,).unwrap(); }, _ => {} }; diff --git a/testnet/stacks-node/src/tests/integrations.rs b/testnet/stacks-node/src/tests/integrations.rs index c671f1afba..c67ee23c38 100644 --- a/testnet/stacks-node/src/tests/integrations.rs +++ b/testnet/stacks-node/src/tests/integrations.rs @@ -218,6 +218,7 @@ fn integration_test_get_info() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); let publish_tx = @@ -230,6 +231,7 @@ fn integration_test_get_info() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); let publish_tx = @@ -242,6 +244,7 @@ fn integration_test_get_info() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 2 { @@ -262,6 +265,7 @@ fn integration_test_get_info() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round >= 3 { @@ -284,6 +288,7 @@ fn integration_test_get_info() { &header_hash, tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -304,6 +309,7 @@ fn integration_test_get_info() { &header_hash, tx_xfer, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -1065,6 +1071,7 @@ fn contract_stx_transfer() { &header_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 2 { @@ -1079,6 +1086,7 @@ fn contract_stx_transfer() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 3 { @@ -1098,6 +1106,7 @@ fn contract_stx_transfer() { block_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -1118,6 +1127,7 @@ fn contract_stx_transfer() { &header_hash, tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 4 { @@ -1142,6 +1152,7 @@ fn contract_stx_transfer() { &xfer_to_contract, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -1159,6 +1170,7 @@ fn contract_stx_transfer() { &xfer_to_contract, None, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap_err() { @@ -1375,6 +1387,7 @@ fn mine_transactions_out_of_order() { &header_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 2 { @@ -1388,6 +1401,7 @@ fn mine_transactions_out_of_order() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 3 { @@ -1401,6 +1415,7 @@ fn mine_transactions_out_of_order() { &header_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 4 { @@ -1414,6 +1429,7 @@ fn mine_transactions_out_of_order() { &header_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -1516,6 +1532,7 @@ fn mine_contract_twice() { block_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -1611,6 +1628,7 @@ fn bad_contract_tx_rollback() { block_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round == 2 { @@ -1628,6 +1646,7 @@ fn bad_contract_tx_rollback() { block_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -1641,6 +1660,7 @@ fn bad_contract_tx_rollback() { block_hash, xfer_to_contract, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -1654,6 +1674,7 @@ fn bad_contract_tx_rollback() { block_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -1667,6 +1688,7 @@ fn bad_contract_tx_rollback() { block_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -1869,6 +1891,7 @@ fn block_limit_runtime_test() { block_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } else if round > 1 { @@ -1897,6 +1920,7 @@ fn block_limit_runtime_test() { block_hash, tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } @@ -1982,6 +2006,7 @@ fn mempool_errors() { &header_hash, publish_tx, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } diff --git a/testnet/stacks-node/src/tests/mempool.rs b/testnet/stacks-node/src/tests/mempool.rs index 24f2d6888a..ba917a72cb 100644 --- a/testnet/stacks-node/src/tests/mempool.rs +++ b/testnet/stacks-node/src/tests/mempool.rs @@ -26,6 +26,7 @@ use stacks::{address::AddressHashMode, chainstate::stacks::TransactionAnchorMode use crate::helium::RunLoop; use crate::Keychain; +use stacks::core::StacksEpochId; use stacks::vm::costs::ExecutionCost; use super::{ @@ -123,6 +124,7 @@ fn mempool_setup_chainstate() { &header_hash, publish_tx1, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -136,6 +138,7 @@ fn mempool_setup_chainstate() { &header_hash, publish_tx2, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -154,6 +157,7 @@ fn mempool_setup_chainstate() { &header_hash, publish_tx3, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -172,6 +176,7 @@ fn mempool_setup_chainstate() { &header_hash, publish_tx4, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); @@ -190,6 +195,7 @@ fn mempool_setup_chainstate() { &header_hash, publish_tx4, &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ) .unwrap(); } diff --git a/testnet/stacks-node/src/tests/mod.rs b/testnet/stacks-node/src/tests/mod.rs index 95b601455c..e45d4eccd0 100644 --- a/testnet/stacks-node/src/tests/mod.rs +++ b/testnet/stacks-node/src/tests/mod.rs @@ -25,6 +25,7 @@ use stacks::vm::{ClarityName, ContractName, Value}; use stacks::{address::AddressHashMode, util::hash::to_hex}; use crate::helium::RunLoop; +use stacks::core::StacksEpochId; use super::burnchains::bitcoin_regtest_controller::ParsedUTXO; use super::Config; @@ -441,7 +442,8 @@ fn should_succeed_mining_valid_txs() { 1 => { // On round 1, publish the KV contract tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash, PUBLISH_CONTRACT.to_owned(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 2 => { @@ -449,7 +451,8 @@ fn should_succeed_mining_valid_txs() { // ./blockstack-cli --testnet contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 1 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store get-value -e \"foo\" let get_foo = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000001000000000000000a0100b7ff8b6c20c427b4f4f09c1ad7e50027e2b076b2ddc0ab55e64ef5ea3771dd4763a79bc5a2b1a79b72ce03dd146ccf24b84942d675a815819a8b85aa8065dfaa030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 3 => { @@ -457,7 +460,8 @@ fn should_succeed_mining_valid_txs() { // ./blockstack-cli --testnet contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 2 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store set-value -e \"foo\" -e \"bar\" let set_foo_bar = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000002000000000000000a010142a01caf6a32b367664869182f0ebc174122a5a980937ba259d44cc3ebd280e769a53dd3913c8006ead680a6e1c98099fcd509ce94b0a4e90d9f4603b101922d030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265097365742d76616c7565000000020d00000003666f6f0d00000003626172"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(set_foo_bar).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 4 => { @@ -465,7 +469,8 @@ fn should_succeed_mining_valid_txs() { // ./blockstack-cli --testnet contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 3 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store get-value -e \"foo\" let get_foo = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000003000000000000000a010046c2c1c345231443fef9a1f64fccfef3e1deacc342b2ab5f97612bb3742aa799038b20aea456789aca6b883e52f84a31adfee0bc2079b740464877af8f2f87d2030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 5 => { @@ -473,7 +478,8 @@ fn should_succeed_mining_valid_txs() { // ./blockstack-cli --testnet token-transfer b1cf9cee5083f421c84d7cb53be5edf2801c3c78d63d53917aee0bdc8bd160ee01 10 0 ST195Q2HPXY576N4CT2A0R94D7DRYSX54A5X3YZTH 1000 let transfer_1000_stx = "80800000000400b71a091b4b8b7661a661c620966ab6573bc2dcd30000000000000000000000000000000a0000393810832bacd44cfc4024980876135de6b95429bdb610d5ce96a92c9ee9bfd81ec77ea0f1748c8515fc9a1589e51d8b92bf028e3e84ade1249682c05271d5b803020000000000051a525b8a36ef8a73548cd0940c248d3b71ecf4a45100000000000003e800000000000000000000000000000000000000000000000000000000000000000000"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(transfer_1000_stx).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, _ => {} @@ -730,7 +736,8 @@ fn should_succeed_handling_malformed_and_valid_txs() { let contract_sk = StacksPrivateKey::from_hex(SK_1).unwrap(); let publish_contract = make_contract_publish(&contract_sk, 0, 10, "store", STORE_CONTRACT); tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,publish_contract, - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 2 => { @@ -739,7 +746,8 @@ fn should_succeed_handling_malformed_and_valid_txs() { // ./blockstack-cli contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 1 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store get-value -e \"foo\" let get_foo = "0000000001040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000001000000000000000a0101ef2b00e7e55ee5cb7684d5313c7c49680c97e60cb29f0166798e6ffabd984a030cf0a7b919bcf5fa052efd5d9efd96b927213cb3af1cfb8d9c5a0be0fccda64d030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 3 => { @@ -748,7 +756,8 @@ fn should_succeed_handling_malformed_and_valid_txs() { // ./blockstack-cli --testnet contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 1 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store set-value -e \"foo\" -e \"bar\" let set_foo_bar = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000001000000000000000a010093f733efcebe2b239bb22e2e1ed25612547403af66b29282ed1f6fdfbbbf8f7f6ef107256d07947cbb72e165d723af99c447d6e25e7fbb6a92fd9a51c5ef7ee9030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265097365742d76616c7565000000020d00000003666f6f0d00000003626172"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(set_foo_bar).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, 4 => { @@ -756,7 +765,8 @@ fn should_succeed_handling_malformed_and_valid_txs() { // ./blockstack-cli --testnet contract-call 043ff5004e3d695060fa48ac94c96049b8c14ef441c50a184a6a3875d2a000f3 10 1 STGT7GSMZG7EA0TS6MVSKT5JC1DCDFGZWJJZXN8A store get-value -e \"foo\" let get_foo = "8080000000040021a3c334fc0ee50359353799e8b2605ac6be1fe40000000000000001000000000000000a0100b7ff8b6c20c427b4f4f09c1ad7e50027e2b076b2ddc0ab55e64ef5ea3771dd4763a79bc5a2b1a79b72ce03dd146ccf24b84942d675a815819a8b85aa8065dfaa030200000000021a21a3c334fc0ee50359353799e8b2605ac6be1fe40573746f7265096765742d76616c7565000000010d00000003666f6f"; tenure.mem_pool.submit_raw(&mut chainstate_copy, &consensus_hash, &header_hash,hex_bytes(get_foo).unwrap().to_vec(), - &ExecutionCost::max_value() + &ExecutionCost::max_value(), + &StacksEpochId::Epoch20, ).unwrap(); }, _ => {} From 94d8855e61017c5a09ed4528bca715e9b655072e Mon Sep 17 00:00:00 2001 From: Gregory Coppola <60008382+gregorycoppola@users.noreply.github.com> Date: Mon, 15 Nov 2021 18:42:21 -0500 Subject: [PATCH 8/8] replaced indexed conn with unindexed one --- src/net/rpc.rs | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/src/net/rpc.rs b/src/net/rpc.rs index b0beb981c7..8af14bed49 100644 --- a/src/net/rpc.rs +++ b/src/net/rpc.rs @@ -1610,9 +1610,7 @@ impl ConversationHttp { ) -> Result<(), net_error> { let response_metadata = HttpResponseMetadata::from(req); let tip = SortitionDB::get_canonical_burn_chain_tip(sortdb.conn())?; - let stacks_epoch = sortdb - .index_conn() - .get_stacks_epoch(tip.block_height as u32) + let stacks_epoch = SortitionDB::get_stacks_epoch(sortdb.conn(), tip.block_height)? .ok_or_else(|| { warn!( "Failed to get fee rate estimate because could not load Stacks epoch for canonical burn height = {}",