From 2eaf9c71df4c2d453faf26a7695938add670bfdb Mon Sep 17 00:00:00 2001 From: greged93 <82421016+greged93@users.noreply.github.com> Date: Thu, 12 Oct 2023 10:24:46 +0200 Subject: [PATCH] feat: balance verification sender (#526) * remove ef-tests feature * subtract transaction cost to sender balance * use `and_then` instead of map * add additional failing tests * remove kakarot submodule * update skipped tests + gitignore * update based on comment --- .env.example | 2 -- .gitignore | 4 +-- Makefile | 8 +++-- blockchain-tests-skip.yml | 11 +++++++ crates/ef-testing/Cargo.toml | 3 -- crates/ef-testing/src/models/case.rs | 43 +++++++++++++++++++------- crates/ef-testing/src/models/result.rs | 13 +++----- crates/ef-testing/src/traits/mod.rs | 2 +- crates/ef-testing/tests/tests.rs | 2 -- lib/kakarot | 1 - 10 files changed, 55 insertions(+), 34 deletions(-) delete mode 100644 .env.example delete mode 160000 lib/kakarot diff --git a/.env.example b/.env.example deleted file mode 100644 index fc3a03fb..00000000 --- a/.env.example +++ /dev/null @@ -1,2 +0,0 @@ -# Github token -GITHUB_TOKEN= diff --git a/.gitignore b/.gitignore index b970d529..a56d82d2 100644 --- a/.gitignore +++ b/.gitignore @@ -17,5 +17,5 @@ broadcast # Ignore the ef-tests /crates/ef-testing/ethereum-tests -# Ignore Katana -.katana +# Ignore compiled Kakarot contracts +lib/kakarot diff --git a/Makefile b/Makefile index cd6b40de..a3224869 100644 --- a/Makefile +++ b/Makefile @@ -35,10 +35,14 @@ clean-kakarot: rm -rf lib/kakarot mkdir -p lib/kakarot/build +# Runs all tests but integration tests +unit: + cargo test --lib + # Runs the repo tests tests: - cargo nextest run --all-features + cargo nextest run # Runs ef tests only ef-test: - cargo nextest run --package ef-testing --test tests --features ef-tests + cargo nextest run --package ef-testing --test tests diff --git a/blockchain-tests-skip.yml b/blockchain-tests-skip.yml index f2f7ca1b..ec71b252 100644 --- a/blockchain-tests-skip.yml +++ b/blockchain-tests-skip.yml @@ -140,6 +140,7 @@ filename: - callcodecallcodecallcode_111_SuicideMiddle.json # ef-tests #485 - callcodecallcodecall_110_SuicideMiddle.json # ef-tests #485 - callcodecallcode_11_SuicideEnd.json # ef-tests #485 + - touchAndGo.json # ef-tests #527 stCallCreateCallCodeTest: - Call1024BalanceTooLow.json # ef-tests #493 - CallcodeLoseGasOOG.json # ef-tests #493 @@ -173,6 +174,7 @@ filename: - createInitFailUndefinedInstruction.json # ef-tests #493 - createInitFail_OOGduringInit2.json # ef-tests #497 - callOutput3partialFail.json # ef-tests #493 + - createNameRegistratorPerTxsNotEnoughGas.json # ef-tests #529 stCallDelegateCodesCallCodeHomestead: - callcallcallcode_001.json # ef-tests #330 - callcallcallcode_001_OOGE.json # ef-tests #330 @@ -298,6 +300,7 @@ filename: - codesizeValid.json # ef-tests #263 - create2CodeSizeLimit.json # ef-tests #264 - createCodeSizeLimit.json # ef-tests #265 + - codesizeOOGInvalidSize.json # ef-tests #528 stCreate2: - RevertDepthCreate2OOG.json # ef-tests #334 - RevertDepthCreate2OOGBerlin.json # ef-tests #334 @@ -772,6 +775,7 @@ filename: - randomStatetest628.json # ef-tests #395 - randomStatetest636.json # ef-tests #395 - randomStatetest506.json # ef-tests #395 + - randomStatetest642.json # ef-tests #533 stRefundTest: - refundFF.json # ef-tests #405 - refundMax.json # ef-tests #405 @@ -1207,6 +1211,9 @@ filename: - CallToNameRegistratorNotMuchMemory0.json # ef-test #490 - CallToNameRegistratorAddressTooBigLeft.json # ef-test #490 - CallToNameRegistratorTooMuchMemory2.json # ef-test #523 + - suicideCaller.json # ef-test #530 + - suicideCallerAddresTooBigLeft.json # ef-test #530 + - suicideOrigin.json # ef-test #530 stStaticFlagEnabled: - CallcodeToPrecompileFromCalledContract.json # ef-test #443 - CallcodeToPrecompileFromContractInitialization.json # ef-test #443 @@ -1227,6 +1234,10 @@ filename: - walletExecuteOverDailyLimitOnlyOneOwner.json # ef-test #430 - walletExecuteOverDailyLimitOnlyOneOwnerNew.json # ef-test #430 - walletExecuteUnderDailyLimit.json # ef-test #430 + - dayLimitConstructionOOG.json # ef-test #531 + - walletConstructionOOG.json # ef-test #531 + - multiOwnedConstructionNotEnoughGasPartial.json # ef-test #531 + - walletKill.json # ef-test #531 stStaticCall: - StaticcallToPrecompileFromContractInitialization.json # ef-tests #421 - static_CallContractToCreateContractAndCallItOOG.json # ef-tests #421 diff --git a/crates/ef-testing/Cargo.toml b/crates/ef-testing/Cargo.toml index 6d153170..b315248b 100644 --- a/crates/ef-testing/Cargo.toml +++ b/crates/ef-testing/Cargo.toml @@ -48,6 +48,3 @@ zip = { workspace = true, optional = true } [dev-dependencies] tracing-subscriber = { workspace = true } - -[features] -ef-tests = [] diff --git a/crates/ef-testing/src/models/case.rs b/crates/ef-testing/src/models/case.rs index 5087f7b2..e265c487 100644 --- a/crates/ef-testing/src/models/case.rs +++ b/crates/ef-testing/src/models/case.rs @@ -158,6 +158,25 @@ impl BlockchainTestCase { LocalWallet::from_bytes(&sk.0).map_err(|err| RunnerError::Other(err.to_string()))?; let sender_address = wallet.address().to_fixed_bytes(); + // Get gas used from block header + let maybe_block = test.blocks.first(); + let maybe_block_header = maybe_block.and_then(|block| block.block_header.as_ref()); + let gas_used = maybe_block_header + .map(|block_header| block_header.gas_used.0) + .unwrap_or_default(); + + // Get gas price from transaction + let maybe_transaction = maybe_block.and_then(|block| { + block + .transactions + .as_ref() + .and_then(|transactions| transactions.first()) + }); + let gas_price = maybe_transaction + .and_then(|transaction| transaction.gas_price.map(|gas_price| gas_price.0)) + .unwrap_or_default(); + let transaction_cost = gas_price * gas_used; + let post_state = match test.post_state.clone().ok_or_else(|| { RunnerError::Other(format!("missing post state for {}", test_case_name)) })? { @@ -174,8 +193,8 @@ impl BlockchainTestCase { let actual = sequencer.get_storage_at(address, k.0)?; if actual != v.0 { return Err(RunnerError::Other(format!( - "storage mismatch for {:#20x} at {:#32x}: expected {:#32x}, got {:#32x}", - address, k.0, v.0, actual + "{} storage mismatch for {:#20x} at {:#32x}: expected {:#32x}, got {:#32x}", + test_case_name, address, k.0, v.0, actual ))); } } @@ -183,28 +202,28 @@ impl BlockchainTestCase { let actual = sequencer.get_nonce_at(address)?; if actual != expected_state.nonce.0 { return Err(RunnerError::Other(format!( - "nonce mismatch for {:#20x}: expected {:#32x}, got {:#32x}", - address, expected_state.nonce.0, actual + "{} nonce mismatch for {:#20x}: expected {:#32x}, got {:#32x}", + test_case_name, address, expected_state.nonce.0, actual ))); } // Bytecode let actual = sequencer.get_code_at(address)?; if actual != expected_state.code { return Err(RunnerError::Other(format!( - "code mismatch for {:#20x}: expected {:#x}, got {:#x}", - address, expected_state.code, actual + "{} code mismatch for {:#20x}: expected {:#x}, got {:#x}", + test_case_name, address, expected_state.code, actual ))); } - // Skip sender address because of the difference in gas cost + // Balance + let mut actual = sequencer.get_balance_at(address)?; + // Subtract transaction cost to sender balance if address.0 == sender_address { - continue; + actual -= transaction_cost; } - // Balance - let actual = sequencer.get_balance_at(address)?; if actual != expected_state.balance.0 { return Err(RunnerError::Other(format!( - "balance mismatch for {:#20x}: expected {:#32x}, got {:#32x}", - address, expected_state.balance.0, actual + "{} balance mismatch for {:#20x}: expected {:#32x}, got {:#32x}", + test_case_name, address, expected_state.balance.0, actual ))); } } diff --git a/crates/ef-testing/src/models/result.rs b/crates/ef-testing/src/models/result.rs index d6f91e1a..aa878e6f 100644 --- a/crates/ef-testing/src/models/result.rs +++ b/crates/ef-testing/src/models/result.rs @@ -29,10 +29,10 @@ impl CaseResult { } /// Assert that all the given tests passed and print the results to stdout. -pub(crate) fn assert_tests_pass(suite_name: &str, results: &[CaseResult]) { +pub(crate) fn assert_tests_pass(results: &[CaseResult]) { let failed = categorize_results(results); - print_results(suite_name, &failed); + print_results(&failed); assert!(failed.is_empty(), "Some tests failed (see above)"); } @@ -53,16 +53,11 @@ pub(crate) fn categorize_results(results: &[CaseResult]) -> Vec<&CaseResult> { } /// Display the given test results to stdout. -pub(crate) fn print_results(suite_name: &str, failed: &[&CaseResult]) { +pub(crate) fn print_results(failed: &[&CaseResult]) { for case in failed { match &case.result { Ok(_) => unreachable!(), - Err(err) => println!( - "[!] Suite {} Case {} failed:\n{}", - suite_name, - case.path.display(), - err, - ), + Err(err) => println!("[!] Case {} failed:\n{}", case.path.display(), err,), } } } diff --git a/crates/ef-testing/src/traits/mod.rs b/crates/ef-testing/src/traits/mod.rs index 5ef82e54..26b47e83 100644 --- a/crates/ef-testing/src/traits/mod.rs +++ b/crates/ef-testing/src/traits/mod.rs @@ -59,7 +59,7 @@ pub trait Suite { let results = Cases { test_cases }.run().await; - assert_tests_pass(&self.suite_name(), &results); + assert_tests_pass(&results); } } diff --git a/crates/ef-testing/tests/tests.rs b/crates/ef-testing/tests/tests.rs index 2fd7f048..773fcc53 100644 --- a/crates/ef-testing/tests/tests.rs +++ b/crates/ef-testing/tests/tests.rs @@ -1,5 +1,3 @@ -#![cfg(feature = "ef-tests")] - use ef_testing::models::suite::BlockchainTestSuite; use ef_testing::traits::Suite; use std::format; diff --git a/lib/kakarot b/lib/kakarot deleted file mode 160000 index b41e2590..00000000 --- a/lib/kakarot +++ /dev/null @@ -1 +0,0 @@ -Subproject commit b41e2590bb4eadbd027cff9d02a2acc22c38c6c8