Skip to content

Commit

Permalink
Limiting the processing of a block in Runtime by delaying receipts (#…
Browse files Browse the repository at this point in the history
…1610)

Passing gas_limit from chunk_extra to the Runtime.
Processing receipts until the current total_burnt_gas doesn't reach or exceed the gas_limit.
Update balance checker to work with the delayed receipts.
Tests to cover this. Update challenge test partial state, cause we touch another key in the Runtime to check for delayed receipts.
  • Loading branch information
Evgeny Kuzyakov authored Nov 15, 2019
1 parent 5d4fda8 commit 4a68466
Show file tree
Hide file tree
Showing 16 changed files with 390 additions and 64 deletions.
1 change: 1 addition & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

5 changes: 5 additions & 0 deletions chain/chain/src/chain.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1985,6 +1985,7 @@ impl<'a> ChainUpdate<'a> {
&prev_chunk.transactions,
&prev_chunk.header.inner.validator_proposals,
prev_block.header.inner.gas_price,
prev_chunk.header.inner.gas_limit,
&challenges_result,
true,
)
Expand Down Expand Up @@ -2111,6 +2112,7 @@ impl<'a> ChainUpdate<'a> {
&chunk.transactions,
&chunk.header.inner.validator_proposals,
block.header.inner.gas_price,
chunk.header.inner.gas_limit,
&block.header.inner.challenges_result,
)
.map_err(|e| ErrorKind::Other(e.to_string()))?;
Expand Down Expand Up @@ -2169,6 +2171,7 @@ impl<'a> ChainUpdate<'a> {
&vec![],
&new_extra.validator_proposals,
block.header.inner.gas_price,
new_extra.gas_limit,
&block.header.inner.challenges_result,
)
.map_err(|e| ErrorKind::Other(e.to_string()))?;
Expand Down Expand Up @@ -2701,6 +2704,7 @@ impl<'a> ChainUpdate<'a> {
&chunk.transactions,
&chunk.header.inner.validator_proposals,
block_header.inner.gas_price,
chunk.header.inner.gas_limit,
&block_header.inner.challenges_result,
)?;

Expand Down Expand Up @@ -2779,6 +2783,7 @@ impl<'a> ChainUpdate<'a> {
&vec![],
&chunk_extra.validator_proposals,
block_header.inner.gas_price,
chunk_extra.gas_limit,
&block_header.inner.challenges_result,
)?;

Expand Down
8 changes: 6 additions & 2 deletions chain/chain/src/test_utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,8 @@ use near_primitives::transaction::{
TransferAction,
};
use near_primitives::types::{
AccountId, Balance, BlockIndex, EpochId, MerkleHash, Nonce, ShardId, StateRoot, ValidatorStake,
AccountId, Balance, BlockIndex, EpochId, Gas, MerkleHash, Nonce, ShardId, StateRoot,
ValidatorStake,
};
use near_primitives::views::QueryResponse;
use near_store::test_utils::create_test_store;
Expand Down Expand Up @@ -445,7 +446,8 @@ impl RuntimeAdapter for KeyValueRuntime {
&self,
_block_index: u64,
_block_timestamp: u64,
_gas_price: u128,
_gas_price: Balance,
_gas_limit: Gas,
_state_root: StateRoot,
transactions: Vec<SignedTransaction>,
) -> Vec<SignedTransaction> {
Expand Down Expand Up @@ -491,6 +493,7 @@ impl RuntimeAdapter for KeyValueRuntime {
transactions: &[SignedTransaction],
_last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
_gas_limit: Gas,
_challenges: &ChallengesResult,
generate_storage_proof: bool,
) -> Result<ApplyTransactionResult, Error> {
Expand Down Expand Up @@ -682,6 +685,7 @@ impl RuntimeAdapter for KeyValueRuntime {
_transactions: &[SignedTransaction],
_last_validator_proposals: &[ValidatorStake],
_gas_price: Balance,
_gas_limit: Gas,
_challenges: &ChallengesResult,
) -> Result<ApplyTransactionResult, Error> {
unimplemented!();
Expand Down
5 changes: 5 additions & 0 deletions chain/chain/src/types.rs
Original file line number Diff line number Diff line change
Expand Up @@ -164,6 +164,7 @@ pub trait RuntimeAdapter: Send + Sync {
block_index: BlockIndex,
block_timestamp: u64,
gas_price: Balance,
gas_limit: Gas,
state_root: StateRoot,
transactions: Vec<SignedTransaction>,
) -> Vec<SignedTransaction>;
Expand Down Expand Up @@ -317,6 +318,7 @@ pub trait RuntimeAdapter: Send + Sync {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges_result: &ChallengesResult,
) -> Result<ApplyTransactionResult, Error> {
self.apply_transactions_with_optional_storage_proof(
Expand All @@ -330,6 +332,7 @@ pub trait RuntimeAdapter: Send + Sync {
transactions,
last_validator_proposals,
gas_price,
gas_limit,
challenges_result,
false,
)
Expand All @@ -347,6 +350,7 @@ pub trait RuntimeAdapter: Send + Sync {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges_result: &ChallengesResult,
generate_storage_proof: bool,
) -> Result<ApplyTransactionResult, Error>;
Expand All @@ -364,6 +368,7 @@ pub trait RuntimeAdapter: Send + Sync {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges_result: &ChallengesResult,
) -> Result<ApplyTransactionResult, Error>;

Expand Down
3 changes: 2 additions & 1 deletion chain/chain/src/validate.rs
Original file line number Diff line number Diff line change
Expand Up @@ -233,7 +233,8 @@ fn validate_chunk_state_challenge(
&chunk_state.prev_chunk.receipts,
&chunk_state.prev_chunk.transactions,
&[],
0,
prev_block_header.inner.gas_price,
chunk_state.prev_chunk.header.inner.gas_limit,
&ChallengesResult::default(),
)
.map_err(|_| Error::from(ErrorKind::MaliciousChallenge))?;
Expand Down
1 change: 1 addition & 0 deletions chain/client/src/client.rs
Original file line number Diff line number Diff line change
Expand Up @@ -428,6 +428,7 @@ impl Client {
next_height,
prev_block_timestamp,
block_header.inner.gas_price,
chunk_extra.gas_limit,
chunk_extra.state_root.clone(),
transactions,
);
Expand Down
22 changes: 16 additions & 6 deletions chain/client/tests/challenges.rs
Original file line number Diff line number Diff line change
Expand Up @@ -288,12 +288,22 @@ fn test_verify_chunk_invalid_state_challenge() {
assert_eq!(prev_merkle_proofs[0], challenge_body.prev_merkle_proof);
assert_eq!(merkle_proofs[0], challenge_body.merkle_proof);
assert_eq!(
vec![vec![
3, 1, 0, 0, 0, 16, 54, 106, 135, 107, 146, 249, 30, 224, 4, 250, 77, 43, 107, 71,
32, 36, 160, 74, 172, 80, 43, 254, 111, 201, 245, 124, 145, 98, 123, 210, 44, 242,
167, 124, 2, 0, 0, 0, 0, 0,
]],
challenge_body.partial_state
challenge_body.partial_state,
vec![
vec![
1, 7, 0, 227, 6, 86, 139, 125, 37, 242, 104, 89, 182, 115, 113, 193, 120, 119,
33, 26, 201, 6, 127, 176, 76, 7, 26, 49, 95, 52, 178, 159, 143, 117, 52, 30,
175, 188, 91, 174, 142, 135, 98, 116, 150, 226, 129, 204, 53, 64, 77, 100, 76,
30, 35, 91, 181, 116, 222, 89, 72, 223, 126, 155, 43, 85, 154, 123, 65, 104,
88, 146, 81, 64, 114, 10, 155, 246, 47, 39, 58, 223, 4, 22, 25, 219, 175, 9,
240, 3, 80, 88, 189, 162, 254, 21, 231, 234, 116, 125, 124, 2, 0, 0, 0, 0, 0
],
vec![
3, 1, 0, 0, 0, 16, 54, 106, 135, 107, 146, 249, 30, 224, 4, 250, 77, 43, 107,
71, 32, 36, 160, 74, 172, 80, 43, 254, 111, 201, 245, 124, 145, 98, 123, 210,
44, 242, 167, 124, 2, 0, 0, 0, 0, 0
]
],
);
}
let challenge =
Expand Down
8 changes: 8 additions & 0 deletions core/primitives/src/errors.rs
Original file line number Diff line number Diff line change
Expand Up @@ -173,10 +173,12 @@ pub struct BalanceMismatchError {
pub incoming_validator_rewards: Balance,
pub initial_accounts_balance: Balance,
pub incoming_receipts_balance: Balance,
pub processed_delayed_receipts_balance: Balance,
pub initial_postponed_receipts_balance: Balance,
// Output balances
pub final_accounts_balance: Balance,
pub outgoing_receipts_balance: Balance,
pub new_delayed_receipts_balance: Balance,
pub final_postponed_receipts_balance: Balance,
pub total_rent_paid: Balance,
pub total_validator_reward: Balance,
Expand All @@ -191,10 +193,12 @@ impl Display for BalanceMismatchError {
.incoming_validator_rewards
.saturating_add(self.initial_accounts_balance)
.saturating_add(self.incoming_receipts_balance)
.saturating_add(self.processed_delayed_receipts_balance)
.saturating_add(self.initial_postponed_receipts_balance);
let final_balance = self
.final_accounts_balance
.saturating_add(self.outgoing_receipts_balance)
.saturating_add(self.new_delayed_receipts_balance)
.saturating_add(self.final_postponed_receipts_balance)
.saturating_add(self.total_rent_paid)
.saturating_add(self.total_validator_reward)
Expand All @@ -207,10 +211,12 @@ impl Display for BalanceMismatchError {
\tIncoming validator rewards sum: {}\n\
\tInitial accounts balance sum: {}\n\
\tIncoming receipts balance sum: {}\n\
\tProcessed delayed receipts balance sum: {}\n\
\tInitial postponed receipts balance sum: {}\n\
Outputs:\n\
\tFinal accounts balance sum: {}\n\
\tOutgoing receipts balance sum: {}\n\
\tNew delayed receipts balance sum: {}\n\
\tFinal postponed receipts balance sum: {}\n\
\tTotal rent paid: {}\n\
\tTotal validators reward: {}\n\
Expand All @@ -221,9 +227,11 @@ impl Display for BalanceMismatchError {
self.incoming_validator_rewards,
self.initial_accounts_balance,
self.incoming_receipts_balance,
self.processed_delayed_receipts_balance,
self.initial_postponed_receipts_balance,
self.final_accounts_balance,
self.outgoing_receipts_balance,
self.new_delayed_receipts_balance,
self.final_postponed_receipts_balance,
self.total_rent_paid,
self.total_validator_reward,
Expand Down
8 changes: 8 additions & 0 deletions core/primitives/src/utils.rs
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@ pub mod col {
pub const POSTPONED_RECEIPT_ID: &[u8] = &[4];
pub const PENDING_DATA_COUNT: &[u8] = &[5];
pub const POSTPONED_RECEIPT: &[u8] = &[6];
pub const DELAYED_RECEIPT_INDICES: &[u8] = &[7];
pub const DELAYED_RECEIPT: &[u8] = &[8];
}

fn key_for_column_account_id(column: &[u8], account_key: &AccountId) -> Vec<u8> {
Expand Down Expand Up @@ -100,6 +102,12 @@ pub fn key_for_postponed_receipt(account_id: &AccountId, receipt_id: &CryptoHash
key
}

pub fn key_for_delayed_receipt(index: u64) -> Vec<u8> {
let mut key = col::DELAYED_RECEIPT.to_vec();
key.extend_from_slice(&index.to_le_bytes());
key
}

pub fn create_nonce_with_nonce(base: &CryptoHash, salt: u64) -> CryptoHash {
let mut nonce: Vec<u8> = base.as_ref().to_owned();
nonce.append(&mut index_to_bytes(salt));
Expand Down
26 changes: 22 additions & 4 deletions near/src/runtime.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ use near_primitives::serialize::from_base64;
use near_primitives::sharding::ShardChunkHeader;
use near_primitives::transaction::SignedTransaction;
use near_primitives::types::{
AccountId, Balance, BlockIndex, EpochId, MerkleHash, ShardId, StateRoot, ValidatorStake,
AccountId, Balance, BlockIndex, EpochId, Gas, MerkleHash, ShardId, StateRoot, ValidatorStake,
};
use near_primitives::utils::{prefix_for_access_key, ACCOUNT_DATA_SEPARATOR};
use near_primitives::views::{
Expand Down Expand Up @@ -211,6 +211,7 @@ impl NightshadeRuntime {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges_result: &ChallengesResult,
) -> Result<ApplyTransactionResult, Error> {
let validator_accounts_update = {
Expand Down Expand Up @@ -278,6 +279,7 @@ impl NightshadeRuntime {
epoch_length: self.genesis_config.epoch_length,
gas_price,
block_timestamp,
gas_limit: Some(gas_limit),
};

let apply_result = self
Expand Down Expand Up @@ -644,6 +646,8 @@ impl RuntimeAdapter for NightshadeRuntime {
epoch_length: self.genesis_config.epoch_length,
gas_price,
block_timestamp,
// NOTE: verify transaction doesn't use gas limit
gas_limit: None,
};

if let Err(err) = self.runtime.verify_and_charge_transaction(
Expand All @@ -662,6 +666,7 @@ impl RuntimeAdapter for NightshadeRuntime {
block_index: BlockIndex,
block_timestamp: u64,
gas_price: Balance,
gas_limit: Gas,
state_root: StateRoot,
transactions: Vec<SignedTransaction>,
) -> Vec<SignedTransaction> {
Expand All @@ -671,6 +676,7 @@ impl RuntimeAdapter for NightshadeRuntime {
epoch_length: self.genesis_config.epoch_length,
gas_price,
block_timestamp,
gas_limit: Some(gas_limit),
};
transactions
.into_iter()
Expand Down Expand Up @@ -736,6 +742,7 @@ impl RuntimeAdapter for NightshadeRuntime {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges: &ChallengesResult,
generate_storage_proof: bool,
) -> Result<ApplyTransactionResult, Error> {
Expand All @@ -755,6 +762,7 @@ impl RuntimeAdapter for NightshadeRuntime {
transactions,
last_validator_proposals,
gas_price,
gas_limit,
challenges,
) {
Ok(result) => Ok(result),
Expand All @@ -780,6 +788,7 @@ impl RuntimeAdapter for NightshadeRuntime {
transactions: &[SignedTransaction],
last_validator_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges: &ChallengesResult,
) -> Result<ApplyTransactionResult, Error> {
let trie = Arc::new(Trie::from_recorded_storage(partial_storage));
Expand All @@ -794,6 +803,7 @@ impl RuntimeAdapter for NightshadeRuntime {
transactions,
last_validator_proposals,
gas_price,
gas_limit,
challenges,
)
}
Expand Down Expand Up @@ -1045,7 +1055,7 @@ mod test {
Action, CreateAccountAction, SignedTransaction, StakeAction,
};
use near_primitives::types::{
AccountId, Balance, BlockIndex, EpochId, Nonce, ShardId, StateRoot, ValidatorStake,
AccountId, Balance, BlockIndex, EpochId, Gas, Nonce, ShardId, StateRoot, ValidatorStake,
};
use near_primitives::views::{AccountView, EpochValidatorInfo, QueryResponse};
use near_store::create_store;
Expand Down Expand Up @@ -1091,6 +1101,7 @@ mod test {
transactions: &[SignedTransaction],
last_proposals: &[ValidatorStake],
gas_price: Balance,
gas_limit: Gas,
challenges: &ChallengesResult,
) -> (StateRoot, Vec<ValidatorStake>, ReceiptResult) {
let result = self
Expand All @@ -1105,6 +1116,7 @@ mod test {
transactions,
last_proposals,
gas_price,
gas_limit,
challenges,
)
.unwrap();
Expand Down Expand Up @@ -1212,6 +1224,7 @@ mod test {
&transactions[i as usize],
self.last_shard_proposals.get(&i).unwrap_or(&vec![]),
self.runtime.genesis_config.gas_price,
u64::max_value(),
&challenges_result,
);
self.state_roots[i as usize] = state_root;
Expand Down Expand Up @@ -1956,8 +1969,13 @@ mod test {
10,
CryptoHash::default(),
);
let apply_state =
ApplyState { block_index: 1, epoch_length: 2, gas_price: 10, block_timestamp: 100 };
let apply_state = ApplyState {
block_index: 1,
epoch_length: 2,
gas_price: 10,
block_timestamp: 100,
gas_limit: None,
};
let mut prefixes = HashSet::new();
prefixes.insert(prefix);
let apply_result = env
Expand Down
1 change: 1 addition & 0 deletions runtime/runtime-params-estimator/src/testbed.rs
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,7 @@ impl RuntimeTestbed {
epoch_length: 4,
gas_price: 1,
block_timestamp: 0,
gas_limit: None,
};
Self { workdir, trie, root, runtime, prev_receipts, apply_state }
}
Expand Down
1 change: 1 addition & 0 deletions runtime/runtime/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -40,5 +40,6 @@ rayon = "1.1"
assert_matches = "1.3.0"

testlib = { path = "../../test-utils/testlib" }
near = { path = "../../near" }

genesis-populate = { path = "../../genesis-tools/genesis-populate"}
Loading

0 comments on commit 4a68466

Please sign in to comment.