diff --git a/All.lean b/All.lean index 2245d5ca..43ce68a5 100644 --- a/All.lean +++ b/All.lean @@ -1,21 +1,243 @@ -import Generated.peano.Peano.addk -import Generated.peano.Peano.addk_user -import Generated.peano.Peano.expk_user -import Generated.peano.Peano.mulk_user +import Generated.erc20shim.ERC20Shim.fun_transfer_gen +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256_gen +import Generated.erc20shim.ERC20Shim.fun_approve_420_user +import Generated.erc20shim.ERC20Shim.fun_msgSender_gen +import Generated.erc20shim.ERC20Shim.fun__approve_gen +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 +import Generated.erc20shim.ERC20Shim.fun__approve +import Generated.erc20shim.ERC20Shim.fun_decimals_user +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr +import Generated.erc20shim.ERC20Shim.abi_encode_address_gen +import Generated.erc20shim.ERC20Shim.fun_transferFrom_gen +import Generated.erc20shim.ERC20Shim.fun__transfer +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256_gen +import Generated.erc20shim.ERC20Shim.fun_symbol_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint8 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.fun_allowance_user +import Generated.erc20shim.ERC20Shim.extract_byte_array_length_gen +import Generated.erc20shim.ERC20Shim.panic_error_0x11 +import Generated.erc20shim.ERC20Shim.extract_byte_array_length_user +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_user +import Generated.erc20shim.ERC20Shim.abi_encode_bool_user +import Generated.erc20shim.ERC20Shim.fun_symbol +import Generated.erc20shim.ERC20Shim.fun_transfer_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_user +import Generated.erc20shim.ERC20Shim.fun_allowance_gen +import Generated.erc20shim.ERC20Shim.abi_decode_address_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8_user +import Generated.erc20shim.ERC20Shim.abi_encode_bool +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256 +import Generated.erc20shim.ERC20Shim.abi_encode_bool_gen +import Generated.erc20shim.ERC20Shim.checked_add_uint256_gen +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup_user +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool +import Generated.erc20shim.ERC20Shim.panic_error_0x11_user +import Generated.erc20shim.ERC20Shim.validator_revert_address +import Generated.erc20shim.ERC20Shim.abi_encode_string +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string_gen +import Generated.erc20shim.ERC20Shim.fun_totalSupply_user +import Generated.erc20shim.ERC20Shim.fun_approve +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack_user +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb +import Generated.erc20shim.ERC20Shim.abi_encode_address_user +import Generated.erc20shim.ERC20Shim.fun_decimals_gen +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen +import Generated.erc20shim.ERC20Shim.fun_symbol_gen +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift_user +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address_user +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256 +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr_user +import Generated.erc20shim.ERC20Shim.fun_update_gen +import Generated.erc20shim.ERC20Shim.fun_name_gen +import Generated.erc20shim.ERC20Shim.fun_totalSupply +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_gen +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.panic_error_0x11_gen +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_user +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup +import Generated.erc20shim.ERC20Shim.abi_decode_uint256_user +import Generated.erc20shim.ERC20Shim.fun_spendAllowance +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_user +import Generated.erc20shim.ERC20Shim.finalize_allocation_gen +import Generated.erc20shim.ERC20Shim.fun_transferFrom +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool_user +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256_gen +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup_gen +import Generated.erc20shim.ERC20Shim.abi_decode +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256_user +import Generated.erc20shim.ERC20Shim.fun__approve_user +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.checked_add_uint256 +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256_user +import Generated.erc20shim.ERC20Shim.fun_allowance +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_gen +import Generated.erc20shim.ERC20Shim.panic_error_0x41 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_user +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address_gen +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr_gen +import Generated.erc20shim.ERC20Shim.fun_decimals +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string_user +import Generated.erc20shim.ERC20Shim.panic_error_0x22_gen +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256_user +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address_user +import Generated.erc20shim.ERC20Shim.abi_decode_address_gen +import Generated.erc20shim.ERC20Shim.checked_add_uint256_user +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage_gen +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256_gen +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun_name_user +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address_gen +import Generated.erc20shim.ERC20Shim.fun_balanceOf_gen +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string +import Generated.erc20shim.ERC20Shim.fun_spendAllowance_gen +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage_user +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool_gen +import Generated.erc20shim.ERC20Shim.fun_name +import Generated.erc20shim.ERC20Shim.finalize_allocation_user +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_user +import Generated.erc20shim.ERC20Shim.abi_decode_user +import Generated.erc20shim.ERC20Shim.fun_approve_user +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage +import Generated.erc20shim.ERC20Shim.validator_revert_address_gen +import Generated.erc20shim.ERC20Shim.validator_revert_address_user +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen +import Generated.erc20shim.ERC20Shim.fun_approve_gen +import Generated.erc20shim.ERC20Shim.fun_msgSender_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8_gen +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen +import Generated.erc20shim.ERC20Shim.fun_update_user +import Generated.erc20shim.ERC20Shim.validator_revert_uint256_gen +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.panic_error_0x22_user +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack_gen +import Generated.erc20shim.ERC20Shim.abi_encode_string_gen +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift_gen +import Generated.erc20shim.ERC20Shim.extract_byte_array_length +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address_user +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 +import Generated.erc20shim.ERC20Shim.validator_revert_uint256 +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address_gen +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage_gen +import Generated.erc20shim.ERC20Shim.validator_revert_uint256_user +import Generated.erc20shim.ERC20Shim.abi_encode_address +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256_user +import Generated.erc20shim.ERC20Shim.fun_totalSupply_gen +import Generated.erc20shim.ERC20Shim.fun_approve_420 +import Generated.erc20shim.ERC20Shim.panic_error_0x22 +import Generated.erc20shim.ERC20Shim.abi_decode_gen +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string +import Generated.erc20shim.ERC20Shim.fun_transfer +import Generated.erc20shim.ERC20Shim.fun_spendAllowance_user +import Generated.erc20shim.ERC20Shim.fun_approve_420_gen +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_user +import Generated.erc20shim.ERC20Shim.fun_balanceOf +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256_gen +import Generated.erc20shim.ERC20Shim.fun__transfer_user +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage +import Generated.erc20shim.ERC20Shim.fun_balanceOf_user +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_gen +import Generated.erc20shim.ERC20Shim.finalize_allocation +import Generated.erc20shim.ERC20Shim.panic_error_0x41_user +import Generated.erc20shim.ERC20Shim.abi_encode_string_user +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage_user +import Generated.erc20shim.ERC20Shim.fun_transferFrom_user +import Generated.erc20shim.ERC20Shim.panic_error_0x41_gen +import Generated.erc20shim.ERC20Shim.abi_decode_uint256_gen +import Generated.erc20shim.ERC20Shim.fun_update +import Generated.erc20shim.ERC20Shim.fun__transfer_gen +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address_user +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_gen +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229 +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933 +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657_gen +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657_user +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831_gen +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506_user +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919_user +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_gen +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189_gen +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899 +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326 +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734 +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473_user +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942_gen +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473 +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685_user +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734_gen +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453 +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040_user +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506 +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172 +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933_user +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326_user +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453_user +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189 +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335_gen +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348_gen +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189_user +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172_gen +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685 +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473_gen +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040_gen +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919 +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831_user +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225 +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335 +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225_gen +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941 +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040 +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453_gen +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225_user +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229_user +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_user +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734_user +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348_user +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326_gen +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942 +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172_user +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919_gen +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899_gen +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335_user +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348 +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942_user +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657 +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229_gen +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933_gen +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506_gen +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685_gen +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899_user +import Generated.peano.Peano.expk_gen import Generated.peano.Peano.mulk import Generated.peano.Peano.expk +import Generated.peano.Peano.addk_user +import Generated.peano.Peano.expk_user +import Generated.peano.Peano.addk import Generated.peano.Peano.mulk_gen -import Generated.peano.Peano.expk_gen +import Generated.peano.Peano.mulk_user import Generated.peano.Peano.addk_gen -import Generated.peano.Peano.Common.for_84821961910748561 -import Generated.peano.Peano.Common.if_6183625948864629624_gen -import Generated.peano.Peano.Common.for_4806375509446804985_gen -import Generated.peano.Peano.Common.for_727972558926940900_gen +import Generated.peano.Peano.Common.for_4806375509446804985_user +import Generated.peano.Peano.Common.for_84821961910748561_gen import Generated.peano.Peano.Common.for_84821961910748561_user import Generated.peano.Peano.Common.if_6183625948864629624_user -import Generated.peano.Peano.Common.for_727972558926940900_user -import Generated.peano.Peano.Common.for_727972558926940900 import Generated.peano.Peano.Common.for_4806375509446804985 -import Generated.peano.Peano.Common.for_84821961910748561_gen -import Generated.peano.Peano.Common.for_4806375509446804985_user +import Generated.peano.Peano.Common.for_4806375509446804985_gen +import Generated.peano.Peano.Common.for_84821961910748561 import Generated.peano.Peano.Common.if_6183625948864629624 +import Generated.peano.Peano.Common.if_6183625948864629624_gen +import Generated.peano.Peano.Common.for_727972558926940900_user +import Generated.peano.Peano.Common.for_727972558926940900_gen +import Generated.peano.Peano.Common.for_727972558926940900 diff --git a/Clear/Abstraction.lean b/Clear/Abstraction.lean index d7111c7c..57bb45dd 100644 --- a/Clear/Abstraction.lean +++ b/Clear/Abstraction.lean @@ -3,6 +3,7 @@ import Clear.ExecLemmas import Clear.OutOfFuelLemmas import Clear.JumpLemmas import Clear.YulNotation +import Clear.Wheels namespace Clear.Abstraction @@ -18,7 +19,7 @@ variable {s s₀ s₁ sEnd : State} -- | General form for relational specs (concrete and abstract). @[aesop safe 0 unfold (rule_sets := [Clear.aesop_spec])] -def Spec (R : State → State → Prop) (s₀ s₁ : State) : Prop := +def Spec (R : State → State → Prop) (s₀ s₁ : State) := match s₀ with | OutOfFuel => ❓ s₁ | Checkpoint c => s₁.isJump c @@ -31,6 +32,30 @@ lemma Spec_ok_unfold {P : State → State → Prop} : unfold Spec aesop +-- -- | Specs that are somewhat pure +-- @[aesop safe 0 unfold (rule_sets := [Clear.aesop_spec])] +-- def PureSpec (R : State → State → Prop) : State → State → Prop := +-- Spec (R ∩ (preserved on evm)) + +-- lemma PureSpec_ok_unfold {P : State → State → Prop} : +-- ∀ {s s' : State}, s.isOk → ¬ ❓ s' → PureSpec P s s' → (P ∩ (preserved on evm)) s s' := by +-- intros s s' h h' +-- unfold PureSpec Spec +-- aesop + +-- -- | Specs for code that might result in hash collision +-- @[aesop safe 0 unfold (rule_sets := [Clear.aesop_spec])] +-- def CollidingSpec (R : State → State → Prop) (s₀ s₁ : State) : Prop := +-- if s₀.evm.hash_collision +-- then ❓ s₁ +-- else ¬ s₁.evm.hash_collision → Spec R s₀ s₁ + +-- lemma CollidingSpec_ok_unfold {P : State → State → Prop} : +-- ∀ {s s' : State}, s.isOk → ¬ ❓ s' → ¬ s'.evm.hash_collision → CollidingSpec P s s' → P s s' := by +-- intros s s' h h' h'' +-- unfold CollidingSpec Spec +-- aesop + open Lean Elab Tactic in elab "clr_spec" "at" h:ident : tactic => do evalTactic <| ← `(tactic| ( @@ -46,6 +71,12 @@ lemma not_isOutOfFuel_Spec (spec : Spec R s₀ s₁) (h : ¬ isOutOfFuel s₁) : intros hs₀ aesop_spec +-- | No hash collision propagates backwards through specs. +-- lemma not_hashCollision_Spec +-- (spec : CollidingSpec R s₀ s₁) (h : ¬ s₁.evm.hasHashCollision) : ¬ s₀.evm.hasHashCollision := by +-- intros hs₀ +-- aesop_spec + -- ============================================================================ -- TACTICS -- ============================================================================ @@ -97,6 +128,34 @@ end Clear.Abstraction namespace Clear +/-- Looking at the code of fun_transfer : + + ``` def fun_transfer : FunctionDefinition := var + +{ + let _1 := fun_msgSender() + fun__transfer(_1, var_to, var_value) + var := 1 +} + +> +``` +Should return 0 (var = 0) in case +`fun__transfer` reverts. As such, it would appear that `var := 1` +must not execute in case `fun_transfer` reverts. This would entail +that modelling revert would necessitate changing the evaluation function, +which is not straightforward! + +Thus, EGREGIOUS_HACK_REVERTED was born :o + +TODO: +- FIX THIS + + -/ +lemma EGREGIOUS_HACK_REVERTED (s₀ s₉ : State) {s : State} (h : s.evm.reverted = true) : + s₀ = s₉ := sorry + open Abstraction State lemma spec_of_ok {s₀ s₉ : State} {S₁ S₂ : State → State → Prop} @@ -107,7 +166,7 @@ lemma spec_of_ok {s₀ s₉ : State} {S₁ S₂ : State → State → Prop} lemma isOutOfFuel_iff_s_eq_OutOfFuel {s : State} : ❓ s ↔ (s = OutOfFuel) := by unfold isOutOfFuel; aesop @[simp] -lemma setBreak_OutOfFuel_eq_OutOfFuel : 💔OutOfFuel = OutOfFuel := rfl +lemma setBreak_OutOfFuel_eq_OutOfFuel : 💔OutOfFuel = OutOfFuel := rfl @[aesop norm 100 simp (rule_sets := [Clear.aesop_spec])] lemma setBreak_ok_eq_checkpoint {evm : EVM} {varstore : VarStore} : @@ -151,7 +210,7 @@ elab "clr_funargs" "at" h:ident : tactic => do simp only [multifill_cons, multifill_nil', isOk_insert, isOk_Ok, isOutOfFuel_Ok, not_false_eq_true, imp_false, Ok.injEq, and_imp, forall_apply_eq_imp_iff₂, forall_apply_eq_imp_iff] at $h:ident - repeat (rw [←State.insert] at $h:ident) + repeat (rw [←State.insert] at $h:ident) )) end Clear diff --git a/Clear/EVMState.lean b/Clear/EVMState.lean index 96f10925..0532c3a6 100644 --- a/Clear/EVMState.lean +++ b/Clear/EVMState.lean @@ -1,8 +1,16 @@ import Mathlib.Data.Finmap import Mathlib.Data.Fin.Basic +import Mathlib.Data.List.Intervals import Clear.Ast import Clear.Instr import Clear.UInt256 +import Clear.Wheels + +set_option linter.setOption false +set_option pp.coercions false + +set_option maxHeartbeats 700000 +set_option maxRecDepth 800 open Clear Instr UInt256 @@ -28,19 +36,118 @@ def ByteArray.byteArrayToUInt256 (μ₀ : UInt256) (size : ℕ) (Id : ByteArray) let r : (ℕ × UInt256) := Array.foldl step ((size - 1) * 8, 0) arr1 r.2 - namespace Clear --- 2^160 https://www.wolframalpha.com/input?i=2%5E160 -def Address.size : Nat := 1461501637330902918203684832716283019655932542976 - +def Address.size : Nat := 2 ^ 160 abbrev Address : Type := Fin Address.size instance : Inhabited Address := ⟨Fin.ofNat 0⟩ +instance : NeZero Address.size := ⟨by decide⟩ + +namespace Address + +def top : ℕ := (⊤ : Address).val + +lemma top_def : top = 2 ^ 160 - 1 := by + unfold top + rw [Fin.top_eq_last] + simp + +lemma top_def' : top = 1461501637330902918203684832716283019655932542975 := by + rw [top_def]; simp + +lemma size_def : size = 1461501637330902918203684832716283019655932542976 := by + unfold size; simp + +def ofNat (n : ℕ) : Address := Fin.ofNat n +def ofUInt256 (u : UInt256) : Address := Fin.ofNat (u.val % size) + +instance {n : Nat} : OfNat Address n := ⟨ofNat n⟩ +instance : NeZero top := ⟨by decide⟩ + +lemma zero_lt_top : 0 < top := by decide +lemma zero_le_top : 0 ≤ top := le_of_lt zero_lt_top + +lemma zero_lt_size : 0 < size := by decide +lemma zero_le_size : 0 ≤ size := le_of_lt zero_lt_size + +lemma one_lt_top : 1 < top := by decide +lemma one_le_top : 1 ≤ top := le_of_lt one_lt_top + +lemma one_lt_size : 1 < size := by decide +lemma one_le_size : 1 ≤ size := le_of_lt one_lt_size + +lemma top_eq_pred_size : top = size - 1 := by + unfold size top + rw [Fin.top_eq_last] + simp + +lemma top_eq_pred_size_ofUInt256 : top.toUInt256 = size.toUInt256 - 1 := by + unfold size top + rw [Fin.top_eq_last] + simp + decide + +lemma succ_top_eq_size : top + 1 = size := by + rw [top_eq_pred_size, Nat.sub_add_cancel (le_of_lt one_lt_size)] + +lemma top_lt_size : top < size := by + rw [← succ_top_eq_size]; simp + +lemma top_le_size : top ≤ size := le_of_lt top_lt_size + +lemma size_lt_UInt256_size : size < UInt256.size := by decide +lemma size_le_UInt256_size : size ≤ UInt256.size := le_of_lt size_lt_UInt256_size + +lemma top_lt_UInt256_size : top < UInt256.size := by decide +lemma top_le_UInt256_size : top ≤ UInt256.size := le_of_lt top_lt_UInt256_size -def Address.ofNat {n : ℕ} : Address := Fin.ofNat n -def Address.ofUInt256 (v : UInt256) : Address := Fin.ofNat (v.val % Address.size) -instance {n : Nat} : OfNat Address n := ⟨Fin.ofNat n⟩ +lemma val_lt_UInt256_size : ∀ {u : Address}, u.val < UInt256.size := by + intro u + trans size + · exact u.2 + · exact size_lt_UInt256_size + +lemma val_le_UInt256_size : ∀ {u : Address}, u.val ≤ UInt256.size := le_of_lt val_lt_UInt256_size + +lemma ofUInt256_lt_UInt256_size {u : UInt256} : ↑(ofUInt256 u) < UInt256.size := by + unfold ofUInt256 Fin.ofNat + simp; rw [← size_def]; simp + simp_rw [← UInt256.size_def] + trans size + · exact Nat.mod_lt u (LT.lt.gt zero_lt_size) + · exact size_lt_UInt256_size + +lemma ofUInt256_eq_mod (u : UInt256) : ↑(ofUInt256 u) = u.val % size := by + unfold ofUInt256 Fin.ofNat + simp_rw [← top_def', succ_top_eq_size] + simp + +lemma and_size_eq_ofUInt256 {u : UInt256} + : Fin.land u (size.toUInt256 - 1) = ofUInt256 u := by + rw [ Fin.natCast_def ] + simp_rw [ Nat.mod_eq_of_lt ofUInt256_lt_UInt256_size ] + + rw [← top_eq_pred_size_ofUInt256] + unfold Fin.land + simp [-UInt256.size]; rw [← UInt256.size_def] + -- this ought to be in mathlib... + have Nat.land_eq_and (p q : Nat) : p.land q = p &&& q := rfl + rw [ Nat.land_eq_and u.val + , Nat.mod_eq_of_lt top_lt_UInt256_size + , top_def + , Nat.and_pow_two_is_mod u.val 160 + , ← size + ] + have : u.val % size < UInt256.size := by + trans size + · apply Nat.mod_lt u.val + exact LT.lt.gt zero_lt_size + · exact size_lt_UInt256_size + simp_rw [Nat.mod_eq_of_lt this] + symm; exact ofUInt256_eq_mod u + +end Address instance byteArrayDecEq : DecidableEq ByteArray := λ xs ys => by { rcases xs with ⟨ xs1 ⟩ ; rcases ys with ⟨ ys1 ⟩ @@ -69,8 +176,10 @@ def Account.updateStorage (act : Account) (k v : UInt256) : Account := -- definition of the machine state +abbrev Memory := Finmap (λ _ : UInt256 ↦ UInt8) + structure MachineState : Type where - memory : Finmap (λ _ : UInt256 => UInt8) + memory : Memory max_address : UInt256 gas_available : UInt256 return_data : List UInt256 @@ -80,21 +189,172 @@ instance : Inhabited MachineState := ⟨ MachineState.mk ∅ 0 0 [] ⟩ -- @langfield: Nit, but definitions should be camelCase. -def UInt256.offsets : List UInt256 := +def UInt256.offsets : List ℕ := [0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16, 17,18,19,20,21,22,23,24,25,26,27,28,29,30,31] +lemma UInt256.offsets_def : offsets = List.range 32 := by + repeat rw [ List.range_succ_eq_map ] + unfold offsets + simp + +lemma max_of_offsets_lt_32 : offsets.maximum < 32 := by decide +lemma min_of_offsets_eq_0 : offsets.minimum = 0 := by decide + +lemma mem_offsets : ∀ {n}, n ∈ offsets ↔ n < 32 := by + intro n + rw [offsets_def] + simp + +@[simp] +lemma mem_offsets_of_lt_32 : ∀ {n}, n < 32 → n ∈ offsets := + mem_offsets.mpr + +lemma lt_32_of_mem_offsets : ∀ {n}, n ∈ offsets → n < 32 := + mem_offsets.mp + +-- List.Ico not yet in mathlib +lemma UInt256.offsets_eq_Ico : offsets = List.Ico 0 32 := by + unfold List.Ico + rw [ List.range'_eq_map_range, offsets_def ] + simp + +-- lemma UInt256.offsets_at_addr : +-- ∀ (addr : UInt256), +-- offsets.map (addr + ↑·) = List.Ico addr.val (addr.val + 32) := by +-- intro addr +-- rw [offsets_eq_Ico, List.Ico.map_add 0 32 addr, zero_add, add_comm] + +lemma UInt256.mem_offsets_iff_mem_Ico : ∀ {n}, n ∈ offsets ↔ n ∈ Set.Ico 0 32 := by + intro n + apply Iff.intro + · intro mem + simp + exact mem_offsets.mp mem + · intro mem + simp at mem + exact mem_offsets.mpr mem + +lemma UInt256.offsetted_addresses (addr : UInt256) : ∀ {n}, + (h : n ∈ offsets) → addr + ↑n ∈ offsets.map (addr + ↑·) := by + intro n h + exact List.mem_map_of_mem (addr + ↑·) h + +-- lemma UInt256.word_addresses (addr : UInt256) : +-- Set.MapsTo (addr + ↑·) (Set.Ico 0 32) (Set.Ico addr (addr + 32)) := by +-- have : (addr + ↑·) '' (Set.Ico 0 32) = Set.Ico addr (addr + 32) := by +-- dsimp [Set.image] +-- conv => rhs; rw [← Set.Ico_def] + +-- sorry + +-- rw [← this] +-- exact Set.mapsTo_image (addr + ↑·) (Set.Ico 0 32) + + +-- lemma UInt256.same_address_of_offsetted_addresses (addr addr': UInt256) {n} : +-- (h : n ∈ offsets) → +-- addr' + ↑n ∈ offsets.map (addr + ↑·) → +-- addr' = addr := by +-- intro h mem +-- simp at mem +-- sorry + +-- lemma UInt256.addresses_of (addr : UInt256) {a} : +-- a ∈ offsets.map (addr + ↑·) ↔ a ∈ Set.Ico addr (addr + 32) := by +-- sorry + +namespace UInt256 + +def range' (start : UInt256) (len : ℕ) (step : UInt256 := 1) : List UInt256 := + match start, len with + | _, 0 => [] + | s, n + 1 => s :: range' (s + step) n step + +@[simp] +lemma range'_zero {s step : UInt256} : range' s 0 step = [] := by + unfold range' + rfl + +@[simp] +lemma range'_one {s step : UInt256} : range' s 1 step = [s] := by + unfold range' + simp + +lemma range'_succ (start : UInt256) (len : ℕ) (step : UInt256) : + range' start (len + 1) step = + start :: range' (start + step) len step := by + conv => + lhs + unfold range' + simp + +-- lemma range'_succ' (start : UInt256) (len : ℕ) (step : UInt256) (k : ℕ) [NeZero k] : +-- range' start (len + k) step = +-- start :: range' (start + step) (len + k - 1) step := by +-- admit + +lemma map_add_range' (a) : ∀ s n step, + List.map (a + ·) (range' s n step) = + range' (a + s) n step + | _, 0, _ => by simp + | s, n+1, step => by + unfold range' + simp [map_add_range', add_assoc] + +def offsets_at (addr : UInt256) : List UInt256 := + range' addr 32 1 + +def words_at (addr : UInt256) (n : ℕ) : List UInt256 := + range' addr n 32 + +end UInt256 + +lemma splice_toBytes! (v : UInt256) : toBytes! v = + [ (toBytes! v)[0], (toBytes! v)[1], (toBytes! v)[2], (toBytes! v)[3] + , (toBytes! v)[4], (toBytes! v)[5], (toBytes! v)[6], (toBytes! v)[7] + , (toBytes! v)[8], (toBytes! v)[9], (toBytes! v)[10], (toBytes! v)[11] + , (toBytes! v)[12], (toBytes! v)[13], (toBytes! v)[14], (toBytes! v)[15] + , (toBytes! v)[16], (toBytes! v)[17], (toBytes! v)[18], (toBytes! v)[19] + , (toBytes! v)[20], (toBytes! v)[21], (toBytes! v)[22], (toBytes! v)[23] + , (toBytes! v)[24], (toBytes! v)[25], (toBytes! v)[26], (toBytes! v)[27] + , (toBytes! v)[28], (toBytes! v)[29], (toBytes! v)[30], (toBytes! v)[31] + ] := by + apply List.ext_get + · simp + · intro n h₁ h₂ + simp at h₂ + have h_offset := mem_offsets_of_lt_32 h₂ + fin_cases h_offset + all_goals aesop + +abbrev Entry := UInt256 × UInt8 + +@[simp] +def memInsert (entry : Entry) (mem : Memory) : Memory := + Function.uncurry mem.insert entry + +@[simp] +def mkEntries (addr data : UInt256) : List Entry := + let addrs := offsets.map (addr + ↑·) + addrs.zip (UInt256.toBytes! data) + +def Memory.maxWords := 3618502788666131106986593281521497120414687020801267626233049500247285301247 + +def Memory.maxWords_def : Memory.maxWords = (⊤ : UInt256) / 32 := by + rw [maxWords, Fin.top_eq_last] + simp + def MachineState.updateMemory (m : MachineState) (addr v : UInt256) : MachineState := - {m with memory := let offsets := List.range 32 - let addrs := offsets.map (·+addr) - let inserts := addrs.zipWith Finmap.insert (UInt256.toBytes! v) - inserts.foldl (init := m.memory) (flip id) + {m with memory := List.foldr (init := m.memory) memInsert <| mkEntries addr v max_address := max addr m.max_address } -lemma cheeky_proof {a b : Int} : (if a > b then a else b) = max a b := by rw [max_comm, max_def_lt] +def Memory.lookupByte (m : Memory) (addr : UInt256) : UInt8 := + (m.lookup addr).get! -def MachineState.lookupMemory (m : MachineState) (addr : UInt256) : UInt256 := - UInt256.fromBytes! (List.map (fun i => (m.memory.lookup (addr + i)).get!) UInt256.offsets) +def Memory.lookupWord (m : Memory) (addr : UInt256) : UInt256 := +-- UInt256.fromBytes! (offsets.map λ i ↦ (m.memory.lookup (addr + i)).get!) + UInt256.fromBytes! $ offsets.map $ m.lookupByte ∘ (addr + ↑·) def MachineState.setReturnData (m : MachineState) (r : List UInt256) : MachineState := {m with return_data := r} @@ -102,7 +362,6 @@ def MachineState.setReturnData (m : MachineState) (r : List UInt256) : MachineSt def MachineState.msize (m : MachineState) : UInt256 := m.max_address - -- definition of the blocks structure BlockHeader : Type where @@ -142,6 +401,21 @@ instance : Inhabited ExecutionEnv := -- definition of the evm state +@[simp] +def keccak_prod : (Σ _ : List UInt256, UInt256) → List UInt256 × UInt256 := + (Equiv.sigmaEquivProd (List UInt256) UInt256).toFun + +@[simp] +def keccak_key : (Σ _ : List UInt256, UInt256) → List UInt256 := + Prod.fst ∘ keccak_prod + +@[simp] +def keccak_val : (Σ _ : List UInt256, UInt256) → UInt256 := + Prod.snd ∘ keccak_prod + +lemma snd_eq_keccak_val {a : (Σ _ : List UInt256, UInt256)} : a.snd = keccak_val a := by + simp + structure EVMState : Type where -- account map account_map : Finmap (λ _ : Address => Account) @@ -156,23 +430,120 @@ structure EVMState : Type where -- blocks blocks : List EVMBlock hash_collision : Bool + -- reversion + reverted : Bool + -- props + -- keccak_inj : ∀ {a b}, + -- (a ∈ keccak_map.keys) → keccak_map.lookup a = keccak_map.lookup b → a = b + -- keccak_used_range : (keccak_map.entries.toList.map keccak_val).toFinset ⊆ used_range deriving DecidableEq instance : Inhabited EVMState := - ⟨ ∅ , default, default , ∅ , default, ∅ , default , False ⟩ + ⟨ ∅ , default, default , ∅ , default, ∅ , default , false, false⟩ abbrev EVM := EVMState +instance instPreorderFinmap : Preorder (Finmap (λ _ : List UInt256 ↦ UInt256)) where + le a b := a.keys ⊆ b.keys ∧ ∀ {key}, key ∈ a → a.lookup key = b.lookup key + le_refl := by aesop + le_trans := by aesop (add safe forward subset_trans) + +lemma lt_of_insert {map : Finmap (λ _ : List UInt256 ↦ UInt256)} {key} (val : UInt256) : + (h : key ∉ map) → map ≤ map.insert key val := by + intro key_ne_mem_map + dsimp [(· ≤ ·)] + apply And.intro + rw [Finset.subset_iff] + intro _ mem_prev + rw [Finmap.mem_keys, Finmap.mem_insert] + right; exact Finmap.mem_keys.mp mem_prev + + intro prev prev_mem + rw [Finmap.lookup_insert_of_ne] + by_contra h + rw [h] at prev_mem + exact key_ne_mem_map prev_mem + +structure Preserved (a : EVMState) (b : EVMState) : Prop where + account_map : (Eq on EVMState.account_map) a b + hash_collision : (Eq on EVMState.hash_collision) a b + execution_env : (Eq on EVMState.execution_env) a b + keccak_map : a.keccak_map ≤ b.keccak_map + +lemma Preserved_def {σ₀ σ₁ : EVM} : Preserved σ₀ σ₁ = + (σ₀.account_map = σ₁.account_map ∧ + σ₀.hash_collision = σ₁.hash_collision ∧ + σ₀.execution_env = σ₁.execution_env ∧ + σ₀.keccak_map ≤ σ₁.keccak_map) := by + ext + apply Iff.intro + · intro h + obtain ⟨_,_,_,_,_⟩ := h + tauto + · intro h + obtain ⟨a,b,c,d,e⟩ := h + exact ⟨a,b,c,d,e⟩ + +namespace Preserved + +@[simp] +lemma refl {e : EVM} : Preserved e e := by + constructor + all_goals simp + +lemma trans {e₀ e₁ e₂ : EVM} : + Preserved e₀ e₁ → Preserved e₁ e₂ → Preserved e₀ e₂ := by + intro h₀ h₁ + have acc := Eq.trans h₀.account_map h₁.account_map + have col := Eq.trans h₀.hash_collision h₁.hash_collision + have env := Eq.trans h₀.execution_env h₁.execution_env + have kec := le_trans h₀.keccak_map h₁.keccak_map + constructor <;> assumption + +end Preserved + +instance instPreorderEVMState : Preorder EVMState where + le := Preserved + le_refl := @Preserved.refl + le_trans := @Preserved.trans + -- functions for querying balance namespace EVMState +def isKeccakInjective (σ : EVMState) : Prop := ∀ {a b}, + (a ∈ σ.keccak_map.keys) → σ.keccak_map.lookup a = σ.keccak_map.lookup b → a = b + +def isKeccakUsedRange (σ : EVMState) : Prop := + (σ.keccak_map.entries.toList.map keccak_val).toFinset ⊆ σ.used_range + +def isEVMState (σ : EVMState) := σ.isKeccakInjective ∧ σ.isKeccakUsedRange + +abbrev IsEVMState := Subtype isEVMState + +instance : Inhabited IsEVMState := + ⟨ default + , ⟨ by dsimp [Inhabited.default]; unfold isKeccakInjective; aesop + , by dsimp [Inhabited.default]; unfold isKeccakUsedRange + have : (∅ : Finmap (λ _ : List UInt256 ↦ UInt256)) = ⟨∅, Multiset.nodup_zero⟩ := by rfl + rw [this] + dsimp + simp [Multiset.empty_toList] + ⟩ + ⟩ + section open Array ByteArray -- | Add an error to the EVMState indicating that we hit a hash collision in `keccak256`. -def addHashCollision (σ : EVMState) : EVMState := { σ with hash_collision := True } +def addHashCollision (σ : EVMState) : EVMState := { σ with hash_collision := true } + +lemma hash_collision_of_addHashCollision : + ∀ (σ : EVMState), σ.addHashCollision.hash_collision := by + intro evm + unfold addHashCollision + simp only [] def lookupAccount (σ : EVMState) (addr : Address) : Option Account := σ.account_map.lookup addr @@ -202,23 +573,284 @@ def calldatacopy (σ : EVMState) (mstart datastart s : UInt256) : EVMState := let r := arr.foldl (λ (sa , j) i => (EVMState.updateMemory sa j i.val, j + 1)) (σ , mstart) r.1 -def mkInterval (ms : MachineState) (p n : UInt256) : List UInt256 := - let i : ℕ := p.val - let f : ℕ := n.val - let m := (List.range' i f).map Fin.ofNat - m.map ms.lookupMemory +def mkInterval (ms : Memory) (p : UInt256) (n : ℕ) : List UInt256 := + (words_at p n).map ms.lookupWord + +def mkInterval' (ms : Memory) (start last : UInt256) : List UInt8 := + List.map ms.lookupByte <| range' start (last - start) + +lemma interval'_eq_interval {ms} {start last} (d : ℕ) : + (d_ne_zero : d ≠ 0) → (div : (d * 32) * Fin.div (last - start) (Nat.toUInt256 d * 32) = last - start) → + List.map (Nat.toUInt256 ∘ fromBytes!) (List.toChunks 32 (mkInterval' ms start last)) = + mkInterval ms start d := by + sorry + +lemma mem_sigma_proj {α} {β} {l : List (Σ _ : α, β)} : + ∀ {a : Σ _ : α, β}, a ∈ l → a.2 ∈ l.map (Prod.snd ∘ (Equiv.sigmaEquivProd α β).toFun) := by + intro ⟨a, b⟩ mem + simp only [ Equiv.toFun_as_coe, List.mem_map, Function.comp_apply + , Equiv.sigmaEquivProd_apply, Sigma.exists, exists_eq_right ] + use a, mem + +theorem filter_cons {α} {p : α → Bool} {x} {xs} : + (x :: xs : List α).filter p = if p x then x :: (xs.filter p) else xs.filter p := by + split <;> simp [*] + +@[simp] theorem filter_eq_nil_iff {α} {p : α → Bool} {l} : List.filter p l = [] ↔ ∀ a, a ∈ l → ¬p a := by + simp only [List.eq_nil_iff_forall_not_mem, List.mem_filter, not_and] + +theorem filter_eq_cons_iff {α} {p : α → Bool} {l} {a} {as} : + List.filter p l = a :: as ↔ + ∃ l₁ l₂, l = l₁ ++ a :: l₂ ∧ (∀ x, x ∈ l₁ → ¬p x) ∧ p a ∧ List.filter p l₂ = as := by + constructor + · induction l with + | nil => simp + | cons x l ih => + intro h + simp only [filter_cons] at h + split at h <;> rename_i w + · simp only [List.cons.injEq] at h + obtain ⟨rfl, rfl⟩ := h + refine ⟨[], l, ?_⟩ + simp [w] + · specialize ih h + obtain ⟨l₁, l₂, rfl, w₁, w₂, w₃⟩ := ih + refine ⟨x :: l₁, l₂, ?_⟩ + simp_all + · rintro ⟨l₁, l₂, rfl, h₁, h, h₂⟩ + simp [h₂, filter_cons, filter_eq_nil_iff.mpr h₁, h] + +-- def updated_keccak_map {interval} {r} {rs} {σ : EVMState} +-- (h_int : interval ∉ σ.keccak_map) +-- (h_filter : σ.keccak_range.filter (· ∉ σ.used_range) = r :: rs) +-- -- (h_head : r ∉ σ.used_range) +-- -- (h_rest : rs ⊆ σ.keccak_range) -- .filter (· ∉ σ.used_range) +-- : +-- EVMState := +-- have := filter_eq_cons_iff.mp h_filter +-- have r_ne_used : r ∈ σ.keccak_range.filter (· ∉ σ.used_range) := +-- by aesop +-- have r_mem_range := List.mem_filter.mp r_ne_used +-- have r_ne_mem_used : r ∉ σ.used_range := +-- by aesop +-- {σ with +-- keccak_map := σ.keccak_map.insert interval r, +-- keccak_range := rs, +-- used_range := {r} ∪ σ.used_range +-- keccak_used_range := by +-- intro r' r'_mem +-- have subset := Finset.subset_iff.mp σ.keccak_used_range +-- rw [ List.mem_toFinset, List.mem_map +-- , Finmap.insert_entries_of_neg h_int +-- ] at r'_mem +-- obtain ⟨a, ⟨a_mem, a_val_eq_r'⟩⟩ := r'_mem +-- rw [Multiset.mem_toList, Multiset.mem_cons] at a_mem +-- rcases a_mem with a_eq_interval_r | a_mem_prev +-- rw [a_eq_interval_r] at a_val_eq_r' +-- simp only [ keccak_val, keccak_prod +-- , Equiv.toFun_as_coe, Function.comp_apply +-- , Equiv.sigmaEquivProd_apply ] at a_val_eq_r' +-- rw [a_val_eq_r'] +-- simp + +-- rw [← Multiset.mem_toList] at a_mem_prev +-- apply mem_sigma_proj at a_mem_prev +-- rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset +-- , snd_eq_keccak_val, a_val_eq_r' +-- ] at a_mem_prev +-- have := subset a_mem_prev +-- simp only [Finset.mem_union, Finset.mem_singleton] +-- right; exact this + +-- keccak_inj := by +-- intro a b mem h_lookup +-- rcases Finmap.mem_insert.mp mem with a_eq_interval | a_mem_prev + +-- have b_lookup_eq_some_r := by +-- rw [a_eq_interval] at h_lookup +-- symm at h_lookup +-- simp at h_lookup +-- exact h_lookup +-- have b_mem : b ∈ Finmap.insert interval r σ.keccak_map := +-- Finmap.mem_iff.mpr ⟨r, b_lookup_eq_some_r⟩ +-- by_contra a_ne_b + +-- rw [ ← a_eq_interval, Finmap.lookup_insert_of_ne _ (Ne.symm a_ne_b) +-- , Finmap.lookup_eq_some_iff, ← Multiset.mem_toList ] at b_lookup_eq_some_r +-- apply mem_sigma_proj at b_lookup_eq_some_r +-- rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset] at b_lookup_eq_some_r +-- simp only [] at b_lookup_eq_some_r + +-- have r_mem_used := σ.keccak_used_range b_lookup_eq_some_r +-- exact r_ne_mem_used r_mem_used + +-- have a_ne_interval : a ≠ interval := by aesop +-- by_cases b_ne_interval : b ≠ interval +-- rw [ Finmap.lookup_insert_of_ne _ a_ne_interval +-- , Finmap.lookup_insert_of_ne _ b_ne_interval ] at h_lookup +-- exact σ.keccak_inj a_mem_prev h_lookup + +-- have b_eq_interval : b = interval := by aesop +-- rw [ b_eq_interval, Finmap.lookup_insert +-- , Finmap.lookup_insert_of_ne _ a_ne_interval ] at h_lookup + +-- rw [ Finmap.lookup_eq_some_iff, ← Multiset.mem_toList ] at h_lookup +-- apply mem_sigma_proj at h_lookup +-- rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset] at h_lookup +-- simp only [] at h_lookup + +-- have r_mem_used := σ.keccak_used_range h_lookup +-- contradiction +-- } def keccak256 (σ : EVMState) (p n : UInt256) : Option (UInt256 × EVMState) := - let interval : List UInt256 := mkInterval σ.machine_state p n + let interval : List UInt256 := List.map (Nat.toUInt256 ∘ fromBytes!) (List.toChunks 32 (mkInterval' σ.machine_state.memory p n)) match Finmap.lookup interval σ.keccak_map with | .some val => .some (val, σ) | .none => - match σ.keccak_range.partition (λ x => x ∈ σ.used_range) with - | (_,(r :: rs)) => - .some (r, {σ with keccak_map := σ.keccak_map.insert interval r, - keccak_range := rs, - used_range := {r} ∪ σ.used_range }) - | (_, []) => .none + match σ.keccak_range.filter (· ∉ σ.used_range) with + | r :: rs => .some ( r, { σ with + keccak_map := σ.keccak_map.insert interval r, + keccak_range := rs, + used_range := {r} ∪ σ.used_range + } ) + | [] => .none + +lemma Preserved_of_keccek256 + {σ} {res : UInt256 × EVMState} {p n} + (h : σ.keccak256 p n = some res) : Preserved σ res.2 := by + unfold keccak256 at h + generalize interval_def : + List.map + (Nat.toUInt256 ∘ fromBytes!) + (List.toChunks (OfNat.ofNat 32) (mkInterval' σ.machine_state.memory p n)) = interval at h + unfold_let at h + split at h + case h_1 r x h_filter => + rw [Option.some_inj] at h + rw [← h]; simp only [] + exact Preserved.refl + case h_2 a h_filter => + split at h + swap; contradiction + next r _ _ => + rw [Option.some_inj] at h + rw [← h] + constructor <;> simp only [] + refine lt_of_insert r ?_ + exact Finmap.lookup_eq_none.mp h_filter + +lemma keccak256_preserves_structure (σ : IsEVMState) {p n} : + (keccak256 ↑σ p n).elim' True (isEVMState ∘ Prod.snd) := by + unfold keccak256 + unfold_let + split + simp [σ.property] + split + swap; simp + + case _ heq _ r rs h => + have r_ne_used : r ∈ σ.val.keccak_range.filter (· ∉ σ.val.used_range) := + by aesop + have r_mem_range := List.mem_filter.mp r_ne_used + have r_ne_mem_used : r ∉ σ.val.used_range := + by aesop + simp only [Option.elim', Function.comp_apply] + unfold isEVMState isKeccakInjective isKeccakUsedRange + simp only [] + generalize interval_def : + List.map + (Nat.toUInt256 ∘ fromBytes!) + (List.toChunks (OfNat.ofNat 32) (mkInterval' σ.val.machine_state.memory p n)) = interval + rw [interval_def] at heq + have interval_ne_mem_map : interval ∉ σ.val.keccak_map := Finmap.lookup_eq_none.mp heq + apply And.intro + + -- injective + intro a b mem h_lookup' + rcases Finmap.mem_insert.mp mem with a_eq_interval | a_mem_prev + + have b_lookup_eq_some_r := by + rw [a_eq_interval] at h_lookup' + symm at h_lookup' + simp at h_lookup' + exact h_lookup' + have b_mem : b ∈ Finmap.insert interval r σ.val.keccak_map := + Finmap.mem_iff.mpr ⟨r, b_lookup_eq_some_r⟩ + by_contra a_ne_b + + rw [ ← a_eq_interval, Finmap.lookup_insert_of_ne _ (Ne.symm a_ne_b) + , Finmap.lookup_eq_some_iff, ← Multiset.mem_toList ] at b_lookup_eq_some_r + apply mem_sigma_proj at b_lookup_eq_some_r + rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset] at b_lookup_eq_some_r + simp only [] at b_lookup_eq_some_r + + have r_mem_used := σ.property.2 b_lookup_eq_some_r + exact r_ne_mem_used r_mem_used + + have a_ne_interval : a ≠ interval := by + have := Finmap.lookup_eq_none.mp heq + aesop + by_cases b_ne_interval : b ≠ interval + rw [ Finmap.lookup_insert_of_ne _ a_ne_interval + , Finmap.lookup_insert_of_ne _ b_ne_interval ] at h_lookup' + exact σ.property.1 a_mem_prev h_lookup' + + have b_eq_interval : b = interval := by aesop + rw [ b_eq_interval, Finmap.lookup_insert + , Finmap.lookup_insert_of_ne _ a_ne_interval ] at h_lookup' + + rw [ Finmap.lookup_eq_some_iff, ← Multiset.mem_toList ] at h_lookup' + apply mem_sigma_proj at h_lookup' + rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset] at h_lookup' + simp only [] at h_lookup' + + have r_mem_used := σ.property.2 h_lookup' + contradiction + + -- keccak_used_range + intro r' r'_mem + have subset := Finset.subset_iff.mp σ.property.2 + rw [ List.mem_toFinset, List.mem_map + , Finmap.insert_entries_of_neg interval_ne_mem_map + ] at r'_mem + obtain ⟨a, ⟨a_mem, a_val_eq_r'⟩⟩ := r'_mem + rw [Multiset.mem_toList, Multiset.mem_cons] at a_mem + rcases a_mem with a_eq_interval_r | a_mem_prev + rw [a_eq_interval_r] at a_val_eq_r' + simp only [ keccak_val, keccak_prod + , Equiv.toFun_as_coe, Function.comp_apply + , Equiv.sigmaEquivProd_apply ] at a_val_eq_r' + rw [a_val_eq_r'] + simp + + rw [← Multiset.mem_toList] at a_mem_prev + apply mem_sigma_proj at a_mem_prev + rw [← keccak_prod, ← keccak_val, ← List.mem_toFinset + , snd_eq_keccak_val, a_val_eq_r' + ] at a_mem_prev + have := subset a_mem_prev + simp only [Finset.mem_union, Finset.mem_singleton] + right; exact this + +lemma isEVMState_of_keccak256 {σ : IsEVMState} {σ'} {r} {p n} (h : keccak256 ↑σ p n = some ⟨r, σ'⟩) : + σ'.isEVMState := by + have := keccak256_preserves_structure σ (p := p) (n := n) + rw [h, Option.elim'_some] at this + exact this + +lemma keccak_map_lookup_eq_of_Preserved_of_lookup {σ₀ σ₁} {addr} {b} + (p : Preserved σ₀ σ₁) (h : Finmap.lookup addr σ₀.keccak_map = some b) : + σ₀.keccak_map.lookup addr = σ₁.keccak_map.lookup addr := by + apply p.keccak_map.2 + rw [Finmap.mem_iff] + use b + +lemma hash_collision_of_keccak256_eq_some {σ σ' : EVMState} {p n} {r} + (h : keccak256 σ p n = some ⟨r, σ'⟩) : + σ'.hash_collision = σ.hash_collision := by + unfold keccak256 at h + aesop -- code copy @@ -289,8 +921,13 @@ def selfbalance (σ : EVMState) : UInt256 := -- memory and storage operations +def storage (σ : EVMState) : Finmap (λ _ : UInt256 ↦ UInt256) := + match σ.lookupAccount σ.execution_env.code_owner with + | .some act => act.storage + | .none => ∅ + def mload (σ : EVMState) (spos : UInt256) : UInt256 := - σ.machine_state.lookupMemory spos + σ.machine_state.memory.lookupWord spos def mstore (σ : EVMState) (spos sval : UInt256) : EVMState := σ.updateMemory spos sval @@ -308,6 +945,10 @@ def sstore (σ : EVMState) (spos sval : UInt256) : EVMState := | .some act => let σ' := σ.updateAccount σ.execution_env.code_owner (act.updateStorage spos sval) {σ' with used_range := {spos} ∪ σ'.used_range} + -- keccak_used_range := + -- by trans σ'.used_range + -- · exact σ'.keccak_used_range + -- · exact Finset.subset_union_right | .none => σ def msize (σ : EVMState) : UInt256 := @@ -337,8 +978,1381 @@ def evm_return (σ : EVMState) (mstart s : UInt256) : EVMState := {σ with machine_state := σ.machine_state.setReturnData vals.data} def evm_revert (σ : EVMState) (mstart s : UInt256) : EVMState := - σ.evm_return mstart s + {(σ.evm_return mstart s) with reverted := true} + +lemma mstore_preserved {σ} {pos val} : Preserved σ (σ.mstore pos val) := by + unfold mstore updateMemory + rw [Preserved_def] + simp + +lemma hash_collision_of_mstore {σ : EVMState} {pos val} : + (σ.mstore pos val).hash_collision = σ.hash_collision := by + unfold mstore updateMemory + simp only [] + +lemma sload_eq_of_preserved {σ₀ σ₁} {pos} (h : Preserved σ₀ σ₁) : + sload σ₀ pos = sload σ₁ pos := by + unfold sload lookupAccount + rw [ h.account_map + , h.execution_env + ] + +lemma storage_eq_of_preserved {σ₀ σ₁} (h : Preserved σ₀ σ₁) : + σ₀.storage = σ₁.storage := by + unfold storage lookupAccount + rw [h.account_map, h.execution_env] + +lemma sload_of_not_mem_dom {evm : EVMState} : + ∀ {addr}, addr ∉ evm.storage.keys → evm.sload addr = 0 := by + intros addr h + unfold sload Account.lookupStorage + unfold storage at h + generalize act_def : evm.lookupAccount evm.execution_env.code_owner = mact + rw [act_def] at h + match mact with + | none => simp only + | some act => + simp only at h ⊢ + rw [Finmap.mem_keys, Iff.symm Finmap.lookup_eq_none] at h + rw [h] end +section Memory + +variable {addr addr' : UInt256} +variable {ms : MachineState} +variable {val val' : UInt256} +variable {entry : Entry} +variable {es es' : List Entry} + +@[simp] +lemma frontflip : (λ b a ↦ memInsert a b) = flip memInsert := by + unfold flip + ext + simp + +@[simp] +lemma backflip : (λ b a ↦ flip memInsert a b) = memInsert := by + unfold flip + ext + simp + +lemma foldr_mem_nil {init : Memory} : + List.foldr memInsert (List.foldr memInsert init []) [] = init := by + simp + +lemma memInsert_memInsert {m : Memory} {a b : UInt8} : + memInsert ⟨addr, a⟩ (memInsert ⟨addr, b⟩ m) = + memInsert ⟨addr, a⟩ m := by + simp + +lemma memInsert_memInsert_of_ne {m : Memory} {a b : UInt8} : + (h : addr' ≠ addr) → + memInsert ⟨addr, a⟩ (memInsert ⟨addr', b⟩ m) = + memInsert ⟨addr', b⟩ (memInsert ⟨addr, a⟩ m) := by + intro h + simp + exact Finmap.insert_insert_of_ne m h + +lemma foldr_memInsert_reverse {init : Memory} : + List.foldr memInsert init (mkEntries addr val) = + List.foldr memInsert init (mkEntries addr val).reverse := by + simp only [mkEntries] + rw [ splice_toBytes! val ] + unfold offsets + + simp only [List.map, List.zip, List.zipWith, List.reverse, List.reverseAux] + simp only [Nat.cast_ofNat, Nat.cast_one, Nat.cast_zero] + rw [List.foldr_cons] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[1]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[2]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[2]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[3]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[3]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[3]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[4]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[4]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[4]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[4]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[5]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[5]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[5]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[5]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[5]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[6]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[7]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[8]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[9]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[10]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[11]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[12]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[13]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[14]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[15]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[16]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[17]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[18]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[19]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[20]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[21]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[22]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[23]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[24]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[25]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[26]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[27]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[28]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[29]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[30]) (by simp) + ] + rw [ List.foldr_cons + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + , memInsert_memInsert_of_ne (b := (toBytes! val)[31]) (by simp) + ] + rw [ ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + , ← List.foldr_cons (f := memInsert), ← List.foldr_cons (f := memInsert) + ] + +lemma foldl_memInsert_reverse {init : Memory} : + List.foldl (flip memInsert) init (mkEntries addr val) = + List.foldl (flip memInsert) init (mkEntries addr val).reverse := by + rw [ List.foldl_reverse, backflip, foldr_memInsert_reverse, List.foldr_reverse, frontflip] + +lemma foldr_memInsert_eq_foldl_memInsert {init : Memory} : + List.foldr memInsert init (mkEntries addr val) = + List.foldl (flip memInsert) init (mkEntries addr val) := by + rw [ foldr_memInsert_reverse, List.foldr_reverse, frontflip] + +end Memory + +section MachineState + +variable {addr addr' : UInt256} +variable {ms : MachineState} +variable {val val' : UInt256} +variable {entry : Entry} +variable {es es' : List Entry} + +lemma update_update : + (ms.updateMemory addr val).updateMemory addr val' = ms.updateMemory addr val' := by + unfold MachineState.updateMemory + simp + + rw [ ← mkEntries, ← mkEntries ] + rw [ foldr_memInsert_eq_foldl_memInsert ] + + conv => rhs; rw [ foldr_memInsert_eq_foldl_memInsert, foldl_memInsert_reverse ] + rw [ mkEntries, mkEntries ] + + rw [ splice_toBytes! val, splice_toBytes! val' ] + unfold offsets + + unfold flip + simp only [List.map, List.zip, List.zipWith] + simp only [Nat.cast_ofNat, Nat.cast_one, Nat.cast_zero] + + rw [ List.foldr_cons, List.foldl_cons, memInsert_memInsert] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 2) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 3) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 3) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 4) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 4) (by simp), memInsert_memInsert_of_ne (addr := addr + 4) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 5) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 5) (by simp), memInsert_memInsert_of_ne (addr := addr + 5) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 5) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 6) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 6) (by simp), memInsert_memInsert_of_ne (addr := addr + 6) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 6) (by simp), memInsert_memInsert_of_ne (addr := addr + 6) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 7) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 7) (by simp), memInsert_memInsert_of_ne (addr := addr + 7) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 7) (by simp), memInsert_memInsert_of_ne (addr := addr + 7) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 7) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 8) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 8) (by simp), memInsert_memInsert_of_ne (addr := addr + 8) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 8) (by simp), memInsert_memInsert_of_ne (addr := addr + 8) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 8) (by simp), memInsert_memInsert_of_ne (addr := addr + 8) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 9) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 9) (by simp), memInsert_memInsert_of_ne (addr := addr + 9) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 9) (by simp), memInsert_memInsert_of_ne (addr := addr + 9) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 9) (by simp), memInsert_memInsert_of_ne (addr := addr + 9) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 9) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 10) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 10) (by simp), memInsert_memInsert_of_ne (addr := addr + 10) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 10) (by simp), memInsert_memInsert_of_ne (addr := addr + 10) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 10) (by simp), memInsert_memInsert_of_ne (addr := addr + 10) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 10) (by simp), memInsert_memInsert_of_ne (addr := addr + 10) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 11) (by simp), memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 11) (by simp), memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 11) (by simp), memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 11) (by simp), memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 11) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 12) (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 12) (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 12) (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 12) (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 12) (by simp), memInsert_memInsert_of_ne (addr := addr + 12) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp), memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 13) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 14) (by simp), memInsert_memInsert_of_ne (addr := addr + 14) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp), memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 15) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 16) (by simp), memInsert_memInsert_of_ne (addr := addr + 16) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp), memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 17) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 18) (by simp), memInsert_memInsert_of_ne (addr := addr + 18) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp), memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 19) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 20) (by simp), memInsert_memInsert_of_ne (addr := addr + 20) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp), memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 21) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 22) (by simp), memInsert_memInsert_of_ne (addr := addr + 22) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp), memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 23) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 24) (by simp), memInsert_memInsert_of_ne (addr := addr + 24) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp), memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 25) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 26) (by simp), memInsert_memInsert_of_ne (addr := addr + 26) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp), memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 27) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 28) (by simp), memInsert_memInsert_of_ne (addr := addr + 28) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp), memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 29) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 30) (by simp), memInsert_memInsert_of_ne (addr := addr + 30) (by simp) + , memInsert_memInsert ] + rw [ List.foldr_cons, List.foldl_cons + , memInsert_memInsert_of_ne (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp), memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert_of_ne (addr := addr + 31) (by simp) + , memInsert_memInsert ] + + rw [List.foldr_nil] + repeat rw [← List.foldl_cons] + simp only [List.reverse, List.reverseAux] + +lemma update_update_of_ne : + (h : ∀ {a}, a ∈ offsets_at addr' → a ∉ offsets_at addr) → + (ms.updateMemory addr val).updateMemory addr' val' = + (ms.updateMemory addr' val').updateMemory addr val := by + intro h + unfold MachineState.updateMemory + simp + apply And.intro + + swap + rw [← max_assoc, max_comm addr' addr, max_assoc] + + rw [ ← mkEntries, ← mkEntries ] + sorry + +lemma lt_toBytes_length_of_mem_offset : + ∀ {offset}, (v : UInt256) → (offset ∈ offsets) → offset < (toBytes! v).length := by + unfold offsets + simp + +lemma lookupBytes_nil : + ∀ {addr}, + [].map (ms.memory.lookupByte ∘ (addr + ↑·)) = [] := by + simp + +lemma lookupBytes_cons : + ∀ {addr} {offset : ℕ} {os : List ℕ}, + (offset :: os).map ((ms.updateMemory addr val).memory.lookupByte ∘ (addr + ↑·)) = + (ms.updateMemory addr val).memory.lookupByte (addr + ↑offset) + :: os.map ((ms.updateMemory addr val).memory.lookupByte ∘ (addr + ↑·)) := by + intro addr offset os + exact List.map_cons + ((ms.updateMemory addr val).memory.lookupByte ∘ (addr + ↑·)) + offset + os + +-- TODO: in newer mathlib +@[simp] theorem get!_some {α} [Inhabited α] {a : α} : (some a).get! = a := rfl + +-- lemma lookupByte_updateMemory : +-- ∀ {addr}, +-- (ms.updateMemory addr val).memory.lookupByte addr = +-- (UInt256.toBytes! val)[0] := by +-- intro addr +-- unfold MachineState.updateMemory Memory.lookupByte +-- simp +-- rw [ List.zipWith_foldl_eq_zip_foldl ] +-- conv => lhs; rw [splice_toBytes! val] +-- unfold offsets +-- simp only [List.map, List.zip, List.zipWith, List.foldl, flip, id] +-- norm_cast +-- rw [ Fin.add_zero addr ] +-- simp + +lemma lookupByte_update_of_ne : + ∀ {addr addr' : UInt256}, + (h : addr' ∉ offsets.map (addr + ↑·)) → + (ms.updateMemory addr val).memory.lookupByte addr' = + ms.memory.lookupByte addr' := by + intro addr addr' h + unfold MachineState.updateMemory Memory.lookupByte + simp + rw [splice_toBytes! val] + unfold offsets + simp [memInsert, List.foldr] + + unfold offsets at h + simp at h + repeat rw [← ne_eq] at h + let ⟨_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_,_⟩ := h + + rw [ Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + , Finmap.lookup_insert_of_ne, Finmap.lookup_insert_of_ne + ] + + all_goals assumption + +lemma lookupByte_at_offset_update : + ∀ {addr} {n}, (mem: n ∈ offsets) → + (ms.updateMemory addr val).memory.lookupByte (addr + ↑n) = + (UInt256.toBytes! val)[n]'(lt_toBytes_length_of_mem_offset val mem) := by + intro addr n mem + unfold MachineState.updateMemory Memory.lookupByte + simp + conv => lhs; rw [splice_toBytes! val] + unfold offsets + simp only [List.foldr] + norm_cast + fin_cases mem + · rw [ Nat.cast_zero, Fin.add_zero addr ] + simp + · rw [ Nat.cast_one ] + simp + all_goals simp only [ Nat.cast_ofNat, memInsert, Fin.isValue, List.getElem_eq_get + , Function.uncurry_apply_pair, add_zero, ne_eq, add_right_eq_self + , Fin.reduceEq, not_false_eq_true, Finmap.lookup_insert_of_ne + , add_right_inj, Finmap.lookup_insert, get!_some + ] + +lemma lookupByte_at_offset_update_of_ne {addr addr' : UInt256} : + ∀ {n}, (mem: n ∈ offsets) → + (h : addr' + ↑n ∉ offsets.map (addr + ↑·)) → + (ms.updateMemory addr val).memory.lookupByte (addr' + ↑n) = + ms.memory.lookupByte (addr' + ↑n) := by + intro n _ _ + apply lookupByte_update_of_ne (addr' := addr' + ↑n) + assumption + +lemma lookupWord_update : ∀ {addr}, + (ms.updateMemory addr val).memory.lookupWord addr = val := by + intro addr + unfold Memory.lookupWord offsets + repeat rw [ lookupBytes_cons, lookupByte_at_offset_update (by simp) ] + rw [ List.map_nil + , ← splice_toBytes! + , fromBytes!_toBytes! + ] + +lemma lookupWord_update_of_ne {addr addr' : UInt256} : + (h : ∀ {n}, (mem: n ∈ offsets) → addr' + ↑n ∉ offsets.map (addr + ↑·)) → + (ms.updateMemory addr val).memory.lookupWord addr' = ms.memory.lookupWord addr' := by + intro h + + unfold Memory.lookupWord + + rw [ ← List.map_comp_map + , Function.comp_apply + , ← List.map_comp_map + , Function.comp_apply + ] + simp only [List.map] + + rw [ lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + , lookupByte_at_offset_update_of_ne (by simp) (h (by simp)) + ] + +lemma lookupWord_update_of_next {addr : UInt256} : + (ms.updateMemory addr val).memory.lookupWord (addr + 32) = ms.memory.lookupWord (addr + 32) := by + refine lookupWord_update_of_ne (addr := addr) (addr' := addr + 32) ?h + intro n mem + fin_cases mem <;> (norm_cast; simp; intro x x_mem) + · fin_cases x_mem <;> norm_cast + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + · fin_cases x_mem <;> (norm_cast; try rw [add_assoc]; simp) + +lemma addr_no_overlap : ∀ {k : ℕ}, + (h : k < Memory.maxWords) → + addr + (k + 1) * 32 ∉ offsets.map (addr + ↑·) := by + intro k h + simp + intro x x_mem + apply ne_of_lt + norm_cast + + apply lt_of_le_of_lt (b := Nat.cast 31) + · rw [Fin.natCast_le_natCast (by linarith [lt_32_of_mem_offsets x_mem]) (by simp)] + apply Nat.le_of_lt_succ + exact lt_32_of_mem_offsets x_mem + · have succ_k_words_lt_size : + (k + 1) * 32 ≤ 115792089237316195423570985008687907853269984665640564039457584007913129639935 := by + trans Memory.maxWords * 32 + · simp + rw [Nat.succ_le] + exact h + · rw [Memory.maxWords] + simp + rw [Fin.natCast_lt_natCast (by simp) succ_k_words_lt_size] + apply Nat.lt_of_lt_of_le + · show (31 < 32); simp + · linarith + +end MachineState + +variable {addr addr' p : UInt256} +variable {evm : EVM} +variable {val val' : UInt256} + +lemma mstore_mstore : + mstore (mstore evm p val) p val' = mstore evm p val' := by + unfold mstore updateMemory + simp + exact update_update + +lemma mstore_mstore_of_ne : + (h : ∀ {a}, a ∈ offsets_at addr' → a ∉ offsets_at addr) → + mstore (mstore evm addr val) addr' val' = + mstore (mstore evm addr' val') addr val := by + intros h + unfold mstore updateMemory + simp + exact update_update_of_ne h + +lemma lookup_mstore : + (mstore evm p val).machine_state.memory.lookupWord p = val := by + unfold mstore updateMemory + simp + rw [lookupWord_update] + +lemma lookup_mstore_of_ne {addr addr' : UInt256} : + (h : ∀ {n}, (mem: n ∈ offsets) → addr' + ↑n ∉ offsets.map (addr + ↑·)) → + (mstore evm addr val).machine_state.memory.lookupWord addr' = + evm.machine_state.memory.lookupWord addr' := by + intro h + unfold mstore updateMemory + rw [lookupWord_update_of_ne h] + +lemma lookup_mstore_of_next : + ∀ {k}, (h : k < Memory.maxWords) → + (mstore evm p val).machine_state.memory.lookupWord (p + (k + 1) * 32) = + evm.machine_state.memory.lookupWord (p + (k + 1) * 32) := by + sorry + +lemma mstore_preserves_keccak_map : + (mstore evm addr val).keccak_map = evm.keccak_map := by + unfold mstore + unfold updateMemory + simp + +lemma mstore_preserves_used_range : + (mstore evm addr val).used_range = evm.used_range := by + unfold mstore + unfold updateMemory + simp + +section Interval + +variable {p : UInt256} +variable {n : ℕ} +variable {evm : EVM} +variable {ms : MachineState} +variable {val : UInt256} + +lemma interval_of_0_eq_nil : + mkInterval ms.memory p 0 = [] := by + unfold mkInterval words_at + simp + +lemma interval_eq_lookup_cons : ∀ {n}, + mkInterval ms.memory p (n + 1) = + ms.memory.lookupWord p :: mkInterval ms.memory (p + 32) n := by + intro n + unfold mkInterval words_at + rw [range'_succ p n, List.map_cons] + +-- theorem List.range'_succ (s n step) : +-- List.range' s (n + 1) step = s :: List.range' (s + step) n step := by +-- simp [List.range', Nat.add_succ, Nat.mul_succ] + +-- lemma out_of_range : +-- ∀ {n}, (h : n ≤ Memory.maxWords) → +-- mkInterval (mstore evm p val).machine_state.memory (p + 32) n = +-- mkInterval evm.machine_state.memory (p + 32) n := by +-- intro n h +-- induction n generalizing p with +-- | zero => rw [interval_of_0_eq_nil, interval_of_0_eq_nil] +-- | succ n' ih => +-- have : (2 : UInt256) * 32 = (1 + 1) * 32 := sorry +-- rw [ interval_eq_lookup_cons +-- , ← one_mul 32, ← zero_add 1, ← Nat.cast_zero +-- , lookup_mstore_of_next (p := p) (k := 0) (by simp [Memory.maxWords]) +-- , Nat.cast_zero, zero_add 1, one_mul 32 +-- , add_assoc, ← two_mul 32 +-- , this ] +-- rw (config := {occs := .pos [1]}) [ ← Nat.cast_one ] +-- rw [ +-- ] + +lemma interval_of_mstore_eq_val_cons : + mkInterval (mstore evm p val).machine_state.memory p (n + 1) = + val :: mkInterval (mstore evm p val).machine_state.memory (p + 32) n := by + rw [ interval_eq_lookup_cons, lookup_mstore ] + +lemma interval_of_mstore_eq_val_cons' : + ∀ {n}, (h : n < Memory.maxWords) → + mkInterval (mstore evm p val).machine_state.memory p (n + 1) = + val :: mkInterval evm.machine_state.memory (p + 32) n := by + sorry + -- intro n h + -- induction n generalizing p with + -- | zero => admit + -- | succ n' => + -- rw [ interval_eq_lookup_cons, lookup_mstore, out_of_range (le_of_lt h) ] + +end Interval + end Clear.EVMState diff --git a/Clear/PrimOps.lean b/Clear/PrimOps.lean index 319934aa..12ff0d46 100644 --- a/Clear/PrimOps.lean +++ b/Clear/PrimOps.lean @@ -50,12 +50,12 @@ def primCall (s : State) : PrimOp → List Literal → State × List Literal | .Sar, [a,b] => (s, [UInt256.sar a b]) | .Keccak256, [a,b] => match s.evm.keccak256 a b with - | .some (val, evm') => (s.setEvm evm', [val]) + | .some a => (s.setEvm a.snd, [a.fst]) -- This is the hash collision case. It's essentially an unrecoverable -- error, and we model it similar to how we model infinite loops, except we -- put the error in the EVM instead, so we don't have to bother with it in -- the interpreter. - | _ => (s.setEvm s.evm.addHashCollision, [0]) + | .none => (s.setEvm s.evm.addHashCollision, [0]) | .Address, [] => (s, [s.evm.execution_env.code_owner]) | .Balance, [a] => (s, [s.evm.balanceOf a]) | .Origin, [] => (s, [s.evm.execution_env.sender]) @@ -129,7 +129,7 @@ lemma EVMByte' : primCall s .Byte [a,b] = (s, [UInt lemma EVMShl' : primCall s .Shl [a,b] = (s, [Fin.shiftLeft b a]) := rfl lemma EVMShr' : primCall s .Shr [a,b] = (s, [Fin.shiftRight b a]) := rfl lemma EVMSar' : primCall s .Sar [a,b] = (s, [UInt256.sar a b]) := rfl -lemma EVMKeccak256' : primCall s .Keccak256 [a,b] = match s.evm.keccak256 a b with | .some (val, evm') => (s.setEvm evm', [val]) | _ => (s.setEvm s.evm.addHashCollision, [0]) := rfl +lemma EVMKeccak256' : primCall s .Keccak256 [a,b] = match s.evm.keccak256 a b with | .some a => (s.setEvm a.snd, [a.fst]) | .none => (s.setEvm s.evm.addHashCollision, [0]) := rfl lemma EVMAddress' : primCall s .Address [] = (s, ([s.evm.execution_env.code_owner] : List Literal)) := rfl lemma EVMBalance' : primCall s .Balance [a] = (s, [s.evm.balanceOf a]) := rfl lemma EVMOrigin' : primCall s .Origin [] = (s, ([s.evm.execution_env.sender] : List Literal)) := rfl diff --git a/Clear/State.lean b/Clear/State.lean index 29d23ccc..2f9f644b 100644 --- a/Clear/State.lean +++ b/Clear/State.lean @@ -66,6 +66,8 @@ def isLeave : State → Prop | .Checkpoint (.Leave _ _) => True | _ => False +def allGood (s : State) : Prop := s.isOk ∧ ¬ s.evm.hash_collision + -- ============================================================================ -- STATE TRANSFORMERS -- ============================================================================ @@ -104,6 +106,10 @@ def setLeave : State → State | Ok evm store => Checkpoint (.Leave evm store) | s => s +def setRevert : State → State + | Ok evm store => Ok {evm with reverted := true} store + | s => s + -- | Indicate that we've hit an infinite loop/ran out of fuel. def diverge : State → State | Ok _ _ => .OutOfFuel @@ -273,6 +279,28 @@ lemma State_of_isOk (h : isOk s) : ∃ evm store, s = Ok evm store unfold isOk at h rcases s <;> simp at * +@[simp] +lemma store_eq_store {evm' : EVMState} {varstore' : VarStore} : + (Ok evm' varstore').store = varstore' := + by simp [State.store] + +@[aesop norm simp] +lemma store_eq_store' {s' : State} {evm' : EVMState} {varstore' : VarStore} (h : s' = Ok evm' varstore') : + s'.store = varstore' := by + rw[h] + simp [State.store] + +@[simp] +lemma evm_eq_evm {evm' : EVMState} {varstore' : VarStore} : + (Ok evm' varstore').evm = evm' := + by simp [State.evm] + +@[aesop norm simp] +lemma evm_eq_evm' {s' : State} {evm' : EVMState} {varstore' : VarStore} (h : s' = Ok evm' varstore') : + s'.evm = evm' := by + rw[h] + simp [State.evm] + -- | We can unpack an infinite loop state. lemma State_of_isOutOfFuel (h : isOutOfFuel s) : s = OutOfFuel := by @@ -389,6 +417,10 @@ lemma overwrite?_insert : (s.overwrite? (s'.insert var x)) = s.overwrite? s' unfold insert overwrite? rcases s' <;> simp +lemma insert_of_ok : (Ok evm store)⟦var ↦ val⟧ = Ok evm (store.insert var val) +:= by + rfl + -- | Looking up a variable you've just inserted gives you the value you inserted. @[simp] lemma lookup_insert : (Ok evm store)⟦var ↦ x⟧[var]!! = x @@ -401,7 +433,6 @@ lemma lookup_insert' (h : isOk s) : s⟦var ↦ x⟧[var]!! = x := by unfold insert lookup! rcases s <;> simp at * - aesop -- | Inserting with the same key twice overwrites. @[simp] @@ -578,8 +609,6 @@ lemma setStore_initcall : (initcall vars vals s).setStore (Ok evm store) = s.set subst this subst h simp - unfold evm - simp only @[simp] lemma setStore_same : s.setStore s = s @@ -633,6 +662,64 @@ lemma lookup_initcall_5 (ha : ve ≠ va) (hb : ve ≠ vb) (hc : ve ≠ vc) (hd : rw [lookup_insert'] aesop +@[simp] +lemma get_evm_of_ok : (Ok evm store).evm = evm +:= by + unfold evm + simp + +lemma get_evm_of_isOk (h : isOk s) : ∃ evm, s.evm = evm +:= by + let ⟨evm, store, h'⟩ := State_of_isOk h + exists evm + rw [h'] + simp + +@[simp] +lemma evm_get_set_of_ok : ((Ok evm store).setEvm evm').evm = evm' +:= by + unfold setEvm evm + simp + +@[simp] +lemma evm_get_set_of_isOk (h : isOk s) : (s.setEvm evm').evm = evm' +:= by + unfold setEvm evm + rcases s <;> simp <;> try contradiction + +@[simp] +lemma setEvm_insert_comm : s⟦var ↦ val⟧.setEvm evm' = (s.setEvm evm')⟦var ↦ val⟧ +:= by + rcases s <;> [(try simp only); aesop_spec; aesop_spec] + rfl + +-- @[simp] +lemma insert_setEvm_insert : (s.setEvm evm')⟦var ↦ val⟧ = s⟦var ↦ val⟧.setEvm evm' +:= by + rcases s <;> [(try simp only); aesop_spec; aesop_spec] + rfl + +-- TODO: Option.get!_some in newer mathlib +theorem come_get!_some {α} [Inhabited α] {a : α} : (some a).get! = a := rfl + +open Lean Meta Elab Tactic in +elab "clr_match" : tactic => do + evalTactic <| ← `(tactic| ( + simp only [lookup!, setEvm, Fin.isValue, insert_of_ok, + multifill_cons, multifill_nil', Finmap.lookup_insert, + come_get!_some, isOk_Ok] + rw [← State.insert_of_ok] + )) + +open Lean Meta Elab Tactic in +elab "clr_match" "at" h:ident : tactic => do + evalTactic <| ← `(tactic| ( + simp only [lookup!, setEvm, Fin.isValue, insert_of_ok, + multifill_cons, multifill_nil', Finmap.lookup_insert, + come_get!_some, isOk_Ok] at $h:ident + repeat rw [← State.insert_of_ok] at $h:ident + )) + end end State diff --git a/Clear/UInt256.lean b/Clear/UInt256.lean index 390a6de6..7464f269 100644 --- a/Clear/UInt256.lean +++ b/Clear/UInt256.lean @@ -11,15 +11,12 @@ import Mathlib.Tactic -- 2^256 @[simp] -def UInt256.size : ℕ := 115792089237316195423570985008687907853269984665640564039457584007913129639936 +def UInt256.size : ℕ := 2 ^ 256 instance : NeZero UInt256.size := ⟨by decide⟩ abbrev UInt256 := Fin UInt256.size -instance : SizeOf UInt256 where - sizeOf := 1 - instance (n : ℕ) : OfNat UInt256 n := ⟨Fin.ofNat n⟩ instance : Inhabited UInt256 := ⟨0⟩ instance : NatCast UInt256 := ⟨Fin.ofNat⟩ @@ -27,6 +24,21 @@ instance : NatCast UInt256 := ⟨Fin.ofNat⟩ abbrev Nat.toUInt256 : ℕ → UInt256 := Fin.ofNat abbrev UInt8.toUInt256 (a : UInt8) : UInt256 := a.toNat.toUInt256 +def UInt256.top : ℕ := (⊤ : UInt256).val + +lemma UInt256.top_def : UInt256.top = 2 ^ 256 - 1 := by + unfold top + rw [Fin.top_eq_last] + simp + +lemma UInt256.top_def' + : UInt256.top = 115792089237316195423570985008687907853269984665640564039457584007913129639935 := by + rw [UInt256.top_def]; simp + +lemma UInt256.size_def + : UInt256.size = 115792089237316195423570985008687907853269984665640564039457584007913129639936 := by + unfold size; simp + def Bool.toUInt256 (b : Bool) : UInt256 := if b then 1 else 0 @[simp] @@ -235,6 +247,13 @@ def toBytes! (n : UInt256) : List UInt8 := zeroPadBytes 32 (toBytes' n) @[simp] lemma length_toBytes! {n : UInt256} : (toBytes! n).length = 32 := zeroPadBytes_len (toBytes'_UInt256_le n.2) +lemma fromBytes!_toBytes! : ∀ {n}, ↑(fromBytes! (toBytes! n)) = n := by + intro n + unfold fromBytes! + rw [ ← length_toBytes! (n := n) ] + unfold toBytes! + simp + lemma UInt256_pow_def {a b : UInt256} : a ^ b = a ^ b.val := by rfl diff --git a/Clear/Utilities.lean b/Clear/Utilities.lean index 434a9845..ab9fd5e4 100644 --- a/Clear/Utilities.lean +++ b/Clear/Utilities.lean @@ -29,6 +29,25 @@ lemma spec_eq {P P' : State → State → Prop} {s₀ s₉ : State} : simp only exact h +-- @[aesop safe apply (rule_sets := [Clear.aesop_spec])] +-- lemma collision_spec_eq {P P' : State → State → Prop} {s₀ s₉ : State} : +-- (¬ s₉.evm.hash_collision → Spec P s₀ s₉ → Spec P' s₀ s₉) → CollidingSpec P s₀ s₉ → CollidingSpec P' s₀ s₉ := by +-- unfold CollidingSpec +-- intro S'_of_S +-- split +-- simp +-- intro Spec_of_c c +-- exact S'_of_S c (Spec_of_c c) + +-- @[aesop safe apply (rule_sets := [Clear.aesop_spec])] +-- lemma collision_spec_eq' {P P' : State → State → Prop} {s₀ s₉ : State} : +-- (¬ s₉.evm.hash_collision → ¬❓ s₉ → P s₀ s₉ → P' s₀ s₉) → CollidingSpec P s₀ s₉ → CollidingSpec P' s₀ s₉ := by +-- intro P'_of_P +-- apply collision_spec_eq +-- intro c +-- apply spec_eq +-- exact P'_of_P c + @[simp] lemma checkpt_insert_elim {var} {val} {j} : (.Checkpoint j)⟦var ↦ val⟧ = .Checkpoint j := by simp only [State.insert] @@ -47,7 +66,6 @@ lemma isPure_insert {s : State} {var val} : isPure s (s⟦var↦val⟧) := by unfold State.insert isPure aesop -@[simp] lemma isPure_trans {s₀ s₁ s₂ : State} : isOk s₁ → isPure s₀ s₁ → isPure s₁ s₂ → isPure s₀ s₂ := by unfold isPure match s₀ with @@ -63,7 +81,6 @@ lemma isPure_trans {s₀ s₁ s₂ : State} : isOk s₁ → isPure s₀ s₁ → lemma isPure_rfl {s : State} : isPure s s := by unfold isPure; aesop -@[simp] lemma mload_eq_of_isPure {s s' : State} {a : UInt256} : isOk s → isOk s' → isPure s s' → State.mload a s = State.mload a s' := by unfold mload isOk isPure cases s <;> cases s' <;> aesop @@ -82,4 +99,68 @@ lemma evm_eq_symm_of_isPure_ok_ok {evm evm'} {vs vs'} (h : isPure (Ok evm vs) (O symm aesop_spec +def preservesEvm (s₀ : State) (s₁ : State) : Prop := + match s₀, s₁ with + | .Ok e₀ _, .Ok e₁ _ => Preserved e₀ e₁ + | _, _ => True + +lemma preservesEvm_of_isOk {s₀ s₁ : State} (s₀_ok : s₀.isOk) (s₁_ok : s₁.isOk) : + preservesEvm s₀ s₁ → + (s₀.evm.account_map = s₁.evm.account_map ∧ + s₀.evm.hash_collision = s₁.evm.hash_collision ∧ + s₀.evm.execution_env = s₁.evm.execution_env ∧ + s₀.evm.keccak_map ≤ s₁.evm.keccak_map) := by + unfold preservesEvm + cases s₀ <;> cases s₁ <;> simp at * + rw [Preserved_def] + intro _; assumption + +lemma Preserved_of_preservesEvm_of_Ok {σ₀ σ₁} {store₀ store₁} : + preservesEvm (Ok σ₀ store₀) (Ok σ₁ store₁) → Preserved σ₀ σ₁ := by + intro h + obtain ⟨_,_,_,_⟩ := preservesEvm_of_isOk isOk_Ok isOk_Ok h + constructor + all_goals assumption + +@[simp] +lemma preservesEvm_rfl {s : State} : preservesEvm s s := by + unfold preservesEvm + cases s <;> simp + +lemma preservesEvm_trans {s₀ s₁ s₂} (h : s₁.isOk) : + preservesEvm s₀ s₁ → preservesEvm s₁ s₂ → preservesEvm s₀ s₂ := by + unfold preservesEvm + cases s₀ <;> cases s₁ <;> cases s₂ <;> simp_all + exact Preserved.trans + +lemma preservesEvm_of_preserved (s₀ : State) (s₁ : State) : + Preserved s₀.evm s₁.evm → preservesEvm s₀ s₁ := by + unfold preservesEvm + cases s₀ <;> cases s₁ <;> simp + +lemma sload_eq_of_preservesEvm + {s s' : State} {a : UInt256} (h : s.isOk) (h' : s'.isOk) (hss : preservesEvm s s') : + s.evm.sload a = s'.evm.sload a := by + unfold preservesEvm at hss + unfold isOk at h h' + cases s <;> cases s' <;> simp [evm] at * + exact EVMState.sload_eq_of_preserved hss + +@[aesop safe norm (rule_sets := [Clear.aesop_spec])] +lemma preservesEvm_of_insert {s₀ s₁} {var val} : + preservesEvm (s₀⟦var ↦ val⟧) s₁ ↔ preservesEvm s₀ s₁ := by + unfold preservesEvm + cases s₀ <;> cases s₁ <;> simp + unfold State.insert; simp + unfold State.insert; simp + +@[aesop safe norm (rule_sets := [Clear.aesop_spec])] +lemma preservesEvm_of_insert' {s₀ s₁} {var val} : + preservesEvm s₀ (s₁⟦var ↦ val⟧) ↔ preservesEvm s₀ s₁ := by + unfold preservesEvm + cases s₀ <;> cases s₁ <;> simp + swap + unfold State.insert; simp + unfold State.insert; simp + end Clear.Utilities diff --git a/Clear/Wheels.lean b/Clear/Wheels.lean index de70965d..5d30bff2 100644 --- a/Clear/Wheels.lean +++ b/Clear/Wheels.lean @@ -1,7 +1,17 @@ import Aesop +import Mathlib.Data.Rel import Mathlib.Tactic.ApplyAt +instance instRelInter {α β} : Inter (Rel α β) where + inter r s := λ a b ↦ r a b ∧ s a b + +def Rel.inter {α β} (r : α → β → Prop) (s : α → β → Prop) : α → β → Prop := + λ a b ↦ r a b ∧ s a b + +instance instFunInter {α β : Type} : Inter (α → β → Prop) where + inter r s := λ a b ↦ r a b ∧ s a b + declare_aesop_rule_sets [Clear.aesop_ok, Clear.aesop_spec, Clear.aesop_varstore] set_option hygiene false in @@ -40,12 +50,29 @@ elab "aesop_varstore" : tactic => do set_option hygiene false in open Lean Elab Tactic in -elab "clr_varstore" : tactic => do - evalTactic <| ← `(tactic| ( - repeat ( - first | rw [State.lookup_insert (by assumption)] at * | - rw [State.lookup_insert' (by aesop_spec)] at * | - rw [State.lookup_insert_of_ne (by decide)] at * - ) - ) - ) +elab "clr_varstore" id:(ident)? "," : tactic => + match id with + | .none => do evalTactic <| ← `(tactic| ( + repeat ( + first | rw [State.lookup_insert (by assumption)] at * | + rw [State.lookup_insert' (by aesop_spec)] at * | + rw [State.lookup_insert_of_ne (by decide)] at * + ))) + | .some id => do + evalTactic <| ← `(tactic| ( + repeat ( + first | rw [State.lookup_insert (by assumption)] at $id:ident | + rw [State.lookup_insert' (by aesop_spec)] at $id:ident | + rw [State.lookup_insert_of_ne (by decide)] at $id:ident + ) + ) + ) + +set_option hygiene false in +open Lean Elab Tactic in +elab "clr_varstore_target" : tactic => + do evalTactic <| ← `(tactic| ( + repeat ( + first | (rw [State.lookup_insert' ?XX]; case XX => ((try simp [primCall]); aesop_spec)) | + rw [State.lookup_insert_of_ne (by decide)] + ))) diff --git a/Generated/erc20shim/ERC20Shim/Common/aaaa.lean b/Generated/erc20shim/ERC20Shim/Common/aaaa.lean new file mode 100644 index 00000000..4141267a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/aaaa.lean @@ -0,0 +1,146 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +-- set_option maxHeartbeats 2500000 +-- set_option maxRecDepth 1000 + +theorem ERC20Shim.Common.extracted_1 {s₉ : State} (evm₀ : EVM) (varstore₀ : VarStore) (s1 s2 s3 s4 : State) + (hasFuel : ¬❓ s4) (s₀ : State) (s0_all : Ok evm₀ varstore₀ = s₀) (s0_ok : s₀.isOk) (_3 : s₀["_3"]!! = 0) + (code : s4 = s₉) (s3_hasFuel : ¬❓ s3) + (s2insert_hasFuel : ¬❓ (s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧)) (s2_hasFuel : ¬❓ s2) + (s1insert_hasFuel : + ¬❓ + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧)) + (s1_hasFuel : ¬❓ s1) + (mapping1 : + s1.isOk ∧ + (preservesEvm (s₀⟦"_4"↦0⟧) s1 ∧ + (isEVMState s₀⟦"_4"↦0⟧.evm → isEVMState s1.evm) ∧ + (∃ keccak, + Finmap.lookup [↑↑(Address.ofUInt256 (s₀["var_from"]!!)), 0] s1.evm.keccak_map = some keccak ∧ + s1.store = s₀⟦"_4"↦0⟧⟦"_5"↦keccak⟧.store) ∧ + s1.evm.hash_collision = false ∨ + s1.evm.hash_collision = true) ∧ + (s₀⟦"_4"↦0⟧.evm.hash_collision = true → s1.evm.hash_collision = true)) + (if308 : + s2.isOk ∧ + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧.evm.hash_collision = + false → + preservesEvm + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧) + s2 ∧ + s2.evm.reverted = true ∧ + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧["_7"]!! ≠ + 0 ∨ + preservesEvm + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧) + s2 ∧ + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧["_7"]!! = + 0 ∨ + s2.evm.hash_collision = true) ∧ + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧.evm.hash_collision = + true → + s2.evm.hash_collision = true)) + (mapping2 : + s3.isOk ∧ + (preservesEvm (s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧) s3 ∧ + (isEVMState s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧.evm → isEVMState s3.evm) ∧ + (∃ keccak, + Finmap.lookup [↑↑(Address.ofUInt256 (s2["var_from"]!!)), s2["_4"]!!] s3.evm.keccak_map = some keccak ∧ + s3.store = s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧⟦"_16"↦keccak⟧.store) ∧ + s3.evm.hash_collision = false ∨ + s3.evm.hash_collision = true) ∧ + (s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧.evm.hash_collision = true → + s3.evm.hash_collision = true)) + (update1 : + s4.isOk ∧ + (s3.evm.hash_collision = false → + (let s := Ok (sstore s3.evm (s3["_16"]!!) (s3["expr_4"]!!)) s3.store; + preservesEvm s s4) ∨ + s4.evm.hash_collision = true) ∧ + (s3.evm.hash_collision = true → s4.evm.hash_collision = true)) : + s₉.isOk ∧ + (s₀.evm.hash_collision = false → + ((∃ slot value, preservesEvm (Ok (sstore s₀.evm slot value) s₀.store) s₉) ∧ s₉.evm.hash_collision = false ∨ + preservesEvm s₀ s₉ ∧ s₉.evm.hash_collision = false) ∨ + preservesEvm s₀ s₉ ∧ s₉.evm.hash_collision = false ∨ s₉.evm.hash_collision = true) ∧ + (s₀.evm.hash_collision = true → s₉.evm.hash_collision = true) := sorry + + + + + + + + + + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453.lean b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453.lean new file mode 100644 index 00000000..45e32dcf --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453.lean @@ -0,0 +1,35 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453_gen + +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453_user + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma for_1821242857744567453_post_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel (Block for_1821242857744567453_post) s₀ = s₉ → + Spec APost_for_1821242857744567453 s₀ s₉ := + λ _ h ↦ for_1821242857744567453_concrete_of_post_abs (for_1821242857744567453_post_concrete_of_code.2 h) + +lemma for_1821242857744567453_body_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel (Block for_1821242857744567453_body) s₀ = s₉ → + Spec ABody_for_1821242857744567453 s₀ s₉ := + λ _ h ↦ for_1821242857744567453_concrete_of_body_abs (for_1821242857744567453_body_concrete_of_code.2 h) + +-- | Code → Abstract (autogenerated). +lemma for_1821242857744567453_abs_of_code {s₀ fuel} : ∀ s₉, exec fuel for_1821242857744567453 s₀ = s₉ → Spec AFor_for_1821242857744567453 s₀ s₉ := by + intros s₉ + intros hcode + apply reasoning_principle_3 for_1821242857744567453_cond for_1821242857744567453_post for_1821242857744567453_body ACond_for_1821242857744567453 APost_for_1821242857744567453 ABody_for_1821242857744567453 AFor_for_1821242857744567453 AZero_for_1821242857744567453 AOk_for_1821242857744567453 AContinue_for_1821242857744567453 ABreak_for_1821242857744567453 ALeave_for_1821242857744567453 @for_1821242857744567453_cond_abs_of_code @for_1821242857744567453_post_abs_of_code @for_1821242857744567453_body_abs_of_code hcode + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_gen.lean b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_gen.lean new file mode 100644 index 00000000..1f5872ac --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_gen.lean @@ -0,0 +1,144 @@ +import Clear.ReasoningPrinciple + + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def for_1821242857744567453_cond := << + lt(i, length) +>> + +def for_1821242857744567453_post : List Stmt := + +def for_1821242857744567453_body : List Stmt := + +def for_1821242857744567453 := + +set_option maxRecDepth 4000 + +-- ============================================================================= +-- POST +-- ============================================================================= + +def for_1821242857744567453_post_concrete_of_code +: { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel (Block for_1821242857744567453_post) s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec for_1821242857744567453_post + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · aesop + · aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +-- ============================================================================= +-- BODY +-- ============================================================================= + +def for_1821242857744567453_body_concrete_of_code +: { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel (Block for_1821242857744567453_body) s₀ = s₉ + → Spec C s₀ s₉ + } +:= by + constructor + intros s₀ s₉ fuel + + unfold Spec for_1821242857744567453_body + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · aesop + · aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_user.lean b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_user.lean new file mode 100644 index 00000000..7dfc77f7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_1821242857744567453_user.lean @@ -0,0 +1,43 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453_gen + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def ACond_for_1821242857744567453 (s₀ : State) : Literal := sorry +def APost_for_1821242857744567453 (s₀ s₉ : State) : Prop := sorry +def ABody_for_1821242857744567453 (s₀ s₉ : State) : Prop := sorry +def AFor_for_1821242857744567453 (s₀ s₉ : State) : Prop := sorry + +lemma for_1821242857744567453_cond_abs_of_code {s₀ fuel} : eval fuel for_1821242857744567453_cond (s₀) = (s₀, ACond_for_1821242857744567453 (s₀)) := by + unfold eval ACond_for_1821242857744567453 + sorry + +lemma for_1821242857744567453_concrete_of_post_abs {s₀ s₉ : State} : + Spec for_1821242857744567453_post_concrete_of_code s₀ s₉ → + Spec APost_for_1821242857744567453 s₀ s₉ := by + sorry + +lemma for_1821242857744567453_concrete_of_body_abs {s₀ s₉ : State} : + Spec for_1821242857744567453_body_concrete_of_code s₀ s₉ → + Spec ABody_for_1821242857744567453 s₀ s₉ := by + sorry + +lemma AZero_for_1821242857744567453 : ∀ s₀, isOk s₀ → ACond_for_1821242857744567453 (👌 s₀) = 0 → AFor_for_1821242857744567453 s₀ s₀ := sorry +lemma AOk_for_1821242857744567453 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isOk s₂ → ¬ ❓ s₅ → ¬ ACond_for_1821242857744567453 s₀ = 0 → ABody_for_1821242857744567453 s₀ s₂ → APost_for_1821242857744567453 s₂ s₄ → Spec AFor_for_1821242857744567453 s₄ s₅ → AFor_for_1821242857744567453 s₀ s₅ +:= sorry +lemma AContinue_for_1821242857744567453 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isContinue s₂ → ¬ ACond_for_1821242857744567453 s₀ = 0 → ABody_for_1821242857744567453 s₀ s₂ → Spec APost_for_1821242857744567453 (🧟s₂) s₄ → Spec AFor_for_1821242857744567453 s₄ s₅ → AFor_for_1821242857744567453 s₀ s₅ := sorry +lemma ABreak_for_1821242857744567453 : ∀ s₀ s₂, isOk s₀ → isBreak s₂ → ¬ ACond_for_1821242857744567453 s₀ = 0 → ABody_for_1821242857744567453 s₀ s₂ → AFor_for_1821242857744567453 s₀ (🧟s₂) := sorry +lemma ALeave_for_1821242857744567453 : ∀ s₀ s₂, isOk s₀ → isLeave s₂ → ¬ ACond_for_1821242857744567453 s₀ = 0 → ABody_for_1821242857744567453 s₀ s₂ → AFor_for_1821242857744567453 s₀ s₂ := sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335.lean b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335.lean new file mode 100644 index 00000000..d0fa764a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335.lean @@ -0,0 +1,35 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335_gen + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335_user + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma for_6088573059593786335_post_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel (Block for_6088573059593786335_post) s₀ = s₉ → + Spec APost_for_6088573059593786335 s₀ s₉ := + λ _ h ↦ for_6088573059593786335_concrete_of_post_abs (for_6088573059593786335_post_concrete_of_code.2 h) + +lemma for_6088573059593786335_body_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel (Block for_6088573059593786335_body) s₀ = s₉ → + Spec ABody_for_6088573059593786335 s₀ s₉ := + λ _ h ↦ for_6088573059593786335_concrete_of_body_abs (for_6088573059593786335_body_concrete_of_code.2 h) + +-- | Code → Abstract (autogenerated). +lemma for_6088573059593786335_abs_of_code {s₀ fuel} : ∀ s₉, exec fuel for_6088573059593786335 s₀ = s₉ → Spec AFor_for_6088573059593786335 s₀ s₉ := by + intros s₉ + intros hcode + apply reasoning_principle_3 for_6088573059593786335_cond for_6088573059593786335_post for_6088573059593786335_body ACond_for_6088573059593786335 APost_for_6088573059593786335 ABody_for_6088573059593786335 AFor_for_6088573059593786335 AZero_for_6088573059593786335 AOk_for_6088573059593786335 AContinue_for_6088573059593786335 ABreak_for_6088573059593786335 ALeave_for_6088573059593786335 @for_6088573059593786335_cond_abs_of_code @for_6088573059593786335_post_abs_of_code @for_6088573059593786335_body_abs_of_code hcode + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_gen.lean b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_gen.lean new file mode 100644 index 00000000..06b20b29 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_gen.lean @@ -0,0 +1,141 @@ +import Clear.ReasoningPrinciple + + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def for_6088573059593786335_cond := << + lt(i, length) +>> + +def for_6088573059593786335_post : List Stmt := + +def for_6088573059593786335_body : List Stmt := + +def for_6088573059593786335 := + +set_option maxRecDepth 4000 + +-- ============================================================================= +-- POST +-- ============================================================================= + +def for_6088573059593786335_post_concrete_of_code +: { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel (Block for_6088573059593786335_post) s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec for_6088573059593786335_post + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · aesop + · aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +-- ============================================================================= +-- BODY +-- ============================================================================= + +def for_6088573059593786335_body_concrete_of_code +: { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel (Block for_6088573059593786335_body) s₀ = s₉ + → Spec C s₀ s₉ + } +:= by + constructor + intros s₀ s₉ fuel + + unfold Spec for_6088573059593786335_body + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · aesop + · aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_user.lean b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_user.lean new file mode 100644 index 00000000..bf9e7dc4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/for_6088573059593786335_user.lean @@ -0,0 +1,43 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335_gen + + +namespace ERC20Shim.Common + +set_option autoImplicit false + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def ACond_for_6088573059593786335 (s₀ : State) : Literal := sorry +def APost_for_6088573059593786335 (s₀ s₉ : State) : Prop := sorry +def ABody_for_6088573059593786335 (s₀ s₉ : State) : Prop := sorry +def AFor_for_6088573059593786335 (s₀ s₉ : State) : Prop := sorry + +lemma for_6088573059593786335_cond_abs_of_code {s₀ fuel} : eval fuel for_6088573059593786335_cond (s₀) = (s₀, ACond_for_6088573059593786335 (s₀)) := by + unfold eval ACond_for_6088573059593786335 + sorry + +lemma for_6088573059593786335_concrete_of_post_abs {s₀ s₉ : State} : + Spec for_6088573059593786335_post_concrete_of_code s₀ s₉ → + Spec APost_for_6088573059593786335 s₀ s₉ := by + sorry + +lemma for_6088573059593786335_concrete_of_body_abs {s₀ s₉ : State} : + Spec for_6088573059593786335_body_concrete_of_code s₀ s₉ → + Spec ABody_for_6088573059593786335 s₀ s₉ := by + sorry + +lemma AZero_for_6088573059593786335 : ∀ s₀, isOk s₀ → ACond_for_6088573059593786335 (👌 s₀) = 0 → AFor_for_6088573059593786335 s₀ s₀ := sorry +lemma AOk_for_6088573059593786335 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isOk s₂ → ¬ ❓ s₅ → ¬ ACond_for_6088573059593786335 s₀ = 0 → ABody_for_6088573059593786335 s₀ s₂ → APost_for_6088573059593786335 s₂ s₄ → Spec AFor_for_6088573059593786335 s₄ s₅ → AFor_for_6088573059593786335 s₀ s₅ +:= sorry +lemma AContinue_for_6088573059593786335 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isContinue s₂ → ¬ ACond_for_6088573059593786335 s₀ = 0 → ABody_for_6088573059593786335 s₀ s₂ → Spec APost_for_6088573059593786335 (🧟s₂) s₄ → Spec AFor_for_6088573059593786335 s₄ s₅ → AFor_for_6088573059593786335 s₀ s₅ := sorry +lemma ABreak_for_6088573059593786335 : ∀ s₀ s₂, isOk s₀ → isBreak s₂ → ¬ ACond_for_6088573059593786335 s₀ = 0 → ABody_for_6088573059593786335 s₀ s₂ → AFor_for_6088573059593786335 s₀ (🧟s₂) := sorry +lemma ALeave_for_6088573059593786335 : ∀ s₀ s₂, isOk s₀ → isLeave s₂ → ¬ ACond_for_6088573059593786335 s₀ = 0 → ABody_for_6088573059593786335 s₀ s₂ → AFor_for_6088573059593786335 s₀ s₂ := sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229.lean b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229.lean new file mode 100644 index 00000000..9fb8b54d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229_gen + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma if_1438067688173587229_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_1438067688173587229 s₀ = s₉ → + Spec A_if_1438067688173587229 s₀ s₉ := + λ _ h ↦ if_1438067688173587229_abs_of_concrete (if_1438067688173587229_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_gen.lean new file mode 100644 index 00000000..1f0b965a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_gen.lean @@ -0,0 +1,67 @@ +import Clear.ReasoningPrinciple + + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def if_1438067688173587229 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_1438067688173587229_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_1438067688173587229 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_1438067688173587229 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_user.lean new file mode 100644 index 00000000..cefad9a1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_1438067688173587229_user.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_if_1438067688173587229 (s₀ s₉ : State) : Prop := sorry + +lemma if_1438067688173587229_abs_of_concrete {s₀ s₉ : State} : + Spec if_1438067688173587229_concrete_of_code s₀ s₉ → + Spec A_if_1438067688173587229 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657.lean b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657.lean new file mode 100644 index 00000000..ff12c5d9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657_gen + +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_2395397427938978657_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_2395397427938978657 s₀ = s₉ → + Spec A_if_2395397427938978657 s₀ s₉ := + λ _ h ↦ if_2395397427938978657_abs_of_concrete (if_2395397427938978657_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_gen.lean new file mode 100644 index 00000000..51d23f63 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_gen.lean @@ -0,0 +1,114 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_2395397427938978657 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_2395397427938978657_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_2395397427938978657 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_2395397427938978657 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_tuple_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_user.lean new file mode 100644 index 00000000..b26e6d86 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2395397427938978657_user.lean @@ -0,0 +1,208 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_2395397427938978657 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : Reversion + preservesEvm s₀ s₉ ∧ + s₉.evm.reverted = true ∧ + s₀["_13"]!! ≠ 0 ∧ + s₉.evm.hash_collision = false + ) + ∨ + ( -- Case 1.2 : No Reversion + preservesEvm s₀ s₉ ∧ + s₀["_13"]!! = 0 ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 400000 + +lemma if_2395397427938978657_abs_of_concrete {s₀ s₉ : State} : + Spec if_2395397427938978657_concrete_of_code s₀ s₉ → + Spec A_if_2395397427938978657 s₀ s₉ := by + + unfold if_2395397427938978657_concrete_of_code A_if_2395397427938978657 + + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + rintro hasFuel ⟨s, call_encode_tuple, code⟩ + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold A_abi_encode_tuple_address at call_encode_tuple + --clr_varstore + + rw [←s0_all] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + simp at call_encode_tuple + unfold setEvm at call_encode_tuple + unfold multifill at call_encode_tuple + simp at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + unfold lookup! at call_encode_tuple + simp at call_encode_tuple + + generalize s0__all : (Ok + (mstore evm₀ + (Finmap.lookup "_15" + (Finmap.insert "_16" (Fin.shiftLeft 3963891461 224) + (Finmap.insert "_15" (EVMState.mload evm₀ 64) + (Finmap.insert "_14" 64 (Finmap.insert "expr_3" 0 varstore₀))))).get! + (Fin.shiftLeft 3963891461 224)) + (Finmap.insert "_18" + ((Finmap.lookup "_15" + (Finmap.insert "_17" 4 + (Finmap.insert "_16" (Fin.shiftLeft 3963891461 224) + (Finmap.insert "_15" (EVMState.mload evm₀ 64) + (Finmap.insert "_14" 64 (Finmap.insert "expr_3" 0 varstore₀)))))).get! + + 4) + (Finmap.insert "_17" 4 + (Finmap.insert "_16" (Fin.shiftLeft 3963891461 224) + (Finmap.insert "_15" (EVMState.mload evm₀ 64) + (Finmap.insert "_14" 64 (Finmap.insert "expr_3" 0 varstore₀))))))) = s0_ at * + + have : preservesEvm s₀ s0_ := by + have : Preserved evm₀ (mstore evm₀ + (Finmap.lookup "_15" + (Finmap.insert "_16" (Fin.shiftLeft 3963891461 224) + (Finmap.insert "_15" (EVMState.mload evm₀ 64) + (Finmap.insert "_14" 64 (Finmap.insert "expr_3" 0 varstore₀))))).get! + (Fin.shiftLeft 3963891461 224)) := by + apply mstore_preserved + aesop + + have s0__ok : s0_.isOk := by aesop + + by_cases _13_var : s₀["_13"]!! ≠ 0 + · simp [_13_var] at code + clr_spec at call_encode_tuple + obtain ⟨s_ok, ⟨s_preserves_evm, encode, s_no_collision⟩ | s_collision ⟩ := call_encode_tuple + · obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have s0_s_preservesEvm : preservesEvm s₀ s := by + apply preservesEvm_trans s0__ok + aesop + aesop + + have s_s9_preservesEvm : preservesEvm s s₉ := by + have : Preserved s.evm s₉.evm := by + have : (s.evm.account_map = s₉.evm.account_map ∧ + s.evm.hash_collision = s₉.evm.hash_collision ∧ + s.evm.execution_env = s₉.evm.execution_env ∧ + s.evm.keccak_map ≤ s₉.evm.keccak_map) := by + rw[←code] + unfold setEvm + simp [s_all] + rw [insert_of_ok] + unfold evm_revert + unfold evm_return + simp + + simp [Preserved_def] + aesop + aesop + + unfold setEvm at code + simp [s_all] at code + split_ands + · aesop + · intro s0_no_collision + left + split_ands + · apply preservesEvm_trans s_ok + all_goals aesop + · aesop + · aesop + · aesop + + · -- collision at s0 + intro s0_colliision + + have s0_s_preservesEvm : preservesEvm s₀ s := by + apply preservesEvm_trans s0__ok + aesop + aesop + + have s_s9_preservesEvm : preservesEvm s s₉ := by + have : Preserved s.evm s₉.evm := by + have : (s.evm.account_map = s₉.evm.account_map ∧ + s.evm.hash_collision = s₉.evm.hash_collision ∧ + s.evm.execution_env = s₉.evm.execution_env ∧ + s.evm.keccak_map ≤ s₉.evm.keccak_map) := by + rw[←code] + simp [s_all] + rw [insert_of_ok] + unfold evm_revert + unfold evm_return + simp + + simp [Preserved_def] + aesop + aesop + + have this : preservesEvm s₀ s₉ := by + apply preservesEvm_trans s_ok + all_goals aesop + + clr_varstore, + simp [←s0_all, ←code] at this + unfold evm_revert at this + unfold preservesEvm at this + unfold lookup! at this + unfold State.insert at this + simp at this + + generalize updated_evm : ({ + account_map := s_evm.account_map, + machine_state := s_evm.machine_state, + execution_env := s_evm.execution_env, + keccak_map := s_evm.keccak_map, + keccak_range := s_evm.keccak_range, + used_range := s_evm.used_range, + blocks := s_evm.blocks, + hash_collision := s_evm.hash_collision, + reverted := true + }: EVMState) = upd_evm + + have : upd_evm.hash_collision = evm₀.hash_collision := by + simp [Preserved_def] at this + unfold evm_return at this + aesop + + aesop + aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933.lean b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933.lean new file mode 100644 index 00000000..66968113 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933_gen + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_2792370840247009933_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_2792370840247009933 s₀ = s₉ → + Spec A_if_2792370840247009933 s₀ s₉ := + λ _ h ↦ if_2792370840247009933_abs_of_concrete (if_2792370840247009933_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_gen.lean new file mode 100644 index 00000000..3f042389 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_gen.lean @@ -0,0 +1,68 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_2792370840247009933 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_2792370840247009933_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_2792370840247009933 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_2792370840247009933 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (panic_error_0x11_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_user.lean new file mode 100644 index 00000000..6334b113 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_2792370840247009933_user.lean @@ -0,0 +1,82 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_2792370840247009933 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : Reversion + let s_evm := EVMState.mstore s₀.evm 0 (Fin.shiftLeft 1313373041 224) + let s'_evm := EVMState.mstore s_evm 4 17 + preservesEvm s₀ s₉ ∧ + s'_evm.evm_revert 0 36 = s₉.evm ∧ + s₀["_1"]!! ≠ 0 ∧ + s₀.store = s₉.store ∧ + s₉.evm.hash_collision = false + ) + ∨ + ( -- Case 1.2 : No Reversion + preservesEvm s₀ s₉ ∧ + s₀["_1"]!! = 0 ∧ + s₀.store = s₉.store ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma if_2792370840247009933_abs_of_concrete {s₀ s₉ : State} : + Spec if_2792370840247009933_concrete_of_code s₀ s₉ → + Spec A_if_2792370840247009933 s₀ s₉ := by + + + unfold if_2792370840247009933_concrete_of_code A_if_2792370840247009933 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + rintro hasFuel ⟨s, call_panic, code⟩ + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold A_panic_error_0x11 at call_panic + + by_cases reversion : s₀["_1"]!! ≠ 0 + · clr_spec at call_panic + + obtain ⟨s_ok, s0_no_collision, s0_collision⟩ := call_panic + by_cases collision_s0 : s₀.evm.hash_collision = false + + · split_ands + · aesop + · simp[collision_s0] + simp[collision_s0] at s0_no_collision + by_cases collision_s : s.evm.hash_collision = false + · simp[collision_s] at s0_no_collision + aesop + · aesop + · aesop + · aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189.lean b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189.lean new file mode 100644 index 00000000..6bc500e2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189_gen + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_3812165059632449189_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_3812165059632449189 s₀ = s₉ → + Spec A_if_3812165059632449189 s₀ s₉ := + λ _ h ↦ if_3812165059632449189_abs_of_concrete (if_3812165059632449189_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_gen.lean new file mode 100644 index 00000000..64a65b89 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_gen.lean @@ -0,0 +1,114 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_3812165059632449189 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_3812165059632449189_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_3812165059632449189 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_3812165059632449189 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_tuple_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_user.lean new file mode 100644 index 00000000..37a8ef1e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3812165059632449189_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_3812165059632449189 (s₀ s₉ : State) : Prop := sorry + +lemma if_3812165059632449189_abs_of_concrete {s₀ s₉ : State} : + Spec if_3812165059632449189_concrete_of_code s₀ s₉ → + Spec A_if_3812165059632449189 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899.lean b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899.lean new file mode 100644 index 00000000..b446d0c7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899_gen + +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_384845947645085899_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_384845947645085899 s₀ = s₉ → + Spec A_if_384845947645085899 s₀ s₉ := + λ _ h ↦ if_384845947645085899_abs_of_concrete (if_384845947645085899_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_gen.lean new file mode 100644 index 00000000..280756ff --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_gen.lean @@ -0,0 +1,68 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_384845947645085899 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_384845947645085899_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_384845947645085899 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_384845947645085899 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (panic_error_0x22_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_user.lean new file mode 100644 index 00000000..df86783f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_384845947645085899_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_384845947645085899 (s₀ s₉ : State) : Prop := sorry + +lemma if_384845947645085899_abs_of_concrete {s₀ s₉ : State} : + Spec if_384845947645085899_concrete_of_code s₀ s₉ → + Spec A_if_384845947645085899 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473.lean b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473.lean new file mode 100644 index 00000000..51793895 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473_gen + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_3856757177752523473_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_3856757177752523473 s₀ = s₉ → + Spec A_if_3856757177752523473 s₀ s₉ := + λ _ h ↦ if_3856757177752523473_abs_of_concrete (if_3856757177752523473_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_gen.lean new file mode 100644 index 00000000..bd26a869 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_gen.lean @@ -0,0 +1,118 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_3856757177752523473 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_3856757177752523473_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_3856757177752523473 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_3856757177752523473 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_address_uint256_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_user.lean new file mode 100644 index 00000000..cff7d372 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3856757177752523473_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_3856757177752523473 (s₀ s₉ : State) : Prop := sorry + +lemma if_3856757177752523473_abs_of_concrete {s₀ s₉ : State} : + Spec if_3856757177752523473_concrete_of_code s₀ s₉ → + Spec A_if_3856757177752523473 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942.lean b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942.lean new file mode 100644 index 00000000..95d7723e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942_gen + +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_3989404597755436942_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_3989404597755436942 s₀ = s₉ → + Spec A_if_3989404597755436942 s₀ s₉ := + λ _ h ↦ if_3989404597755436942_abs_of_concrete (if_3989404597755436942_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_gen.lean new file mode 100644 index 00000000..9f5ea7a3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_gen.lean @@ -0,0 +1,118 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_3989404597755436942 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_3989404597755436942_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_3989404597755436942 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_3989404597755436942 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_address_uint256_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_user.lean new file mode 100644 index 00000000..4459128e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_3989404597755436942_user.lean @@ -0,0 +1,182 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_3989404597755436942 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : Reversion + preservesEvm s₀ s₉ ∧ + s₉.evm.reverted = true ∧ + s₀["_7"]!! ≠ 0 + ) + ∨ + ( -- Case 1.2 : No Reversion + preservesEvm s₀ s₉ ∧ + s₀["_7"]!! = 0 + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma if_3989404597755436942_abs_of_concrete {s₀ s₉ : State} : + Spec if_3989404597755436942_concrete_of_code s₀ s₉ → + Spec A_if_3989404597755436942 s₀ s₉ := by + unfold if_3989404597755436942_concrete_of_code A_if_3989404597755436942 + + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + rintro hasFuel ⟨s, call_encode, code⟩ + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold A_abi_encode_address_uint256_uint256 at call_encode + + rw [←s0_all] at call_encode + rw [insert_of_ok] at call_encode + rw [insert_of_ok] at call_encode + rw [insert_of_ok] at call_encode + simp at call_encode + unfold setEvm at call_encode + unfold multifill at call_encode + simp at call_encode + rw [insert_of_ok] at call_encode + rw [insert_of_ok] at call_encode + unfold lookup! at call_encode + unfold State.insert at call_encode + simp at call_encode + + generalize general_1 : (Finmap.lookup "_9" + (Finmap.insert "_11" 4 + (Finmap.insert "_10" (Fin.shiftLeft 957625571 226) + (Finmap.insert "_9" (EVMState.mload evm₀ 64) + (Finmap.insert "_8" 64 + (Finmap.insert "expr_3" + (Finmap.lookup "var_value" + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀))).get! + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)))))))).get! = gen_1 at * + generalize general_2 : (Finmap.insert "_12" (gen_1 + 4) + (Finmap.insert "_11" 4 + (Finmap.insert "_10" (Fin.shiftLeft 957625571 226) + (Finmap.insert "_9" (EVMState.mload evm₀ 64) + (Finmap.insert "_8" 64 + (Finmap.insert "expr_3" + (Finmap.lookup "var_value" + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀))).get! + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! + varstore₀)))))))) = gen_2 at * + generalize general_evm : (mstore evm₀ + (Finmap.lookup "_9" + (Finmap.insert "_10" (Fin.shiftLeft 957625571 226) + (Finmap.insert "_9" (EVMState.mload evm₀ 64) + (Finmap.insert "_8" 64 + (Finmap.insert "expr_3" + (Finmap.lookup "var_value" + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! varstore₀))).get! + (Finmap.insert "expr_2" + (Finmap.lookup "_6" + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! varstore₀)).get! + (Finmap.insert "expr_1" (Finmap.lookup "var_from" varstore₀).get! varstore₀))))))).get! + (Fin.shiftLeft 957625571 226)) = gen_evm at * + + have s0__ok : (Ok gen_evm gen_2).isOk := by aesop + by_cases _3_var : s₀["_7"]!! ≠ 0 + + · clr_spec at call_encode + + simp [_3_var] at code + obtain ⟨s_ok, ⟨s_preservesEvm, encode, s_no_collision⟩ | s_collision ⟩ := call_encode + · obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have : Preserved evm₀ gen_evm := by + rw[←general_evm] + apply mstore_preserved + + have s0_s_preservesEvm : preservesEvm s₀ s := by + apply preservesEvm_trans s0__ok + aesop + aesop + + have s_s9_preservesEvm : preservesEvm s s₉ := by + have : Preserved s.evm s₉.evm := by + have : (s.evm.account_map = s₉.evm.account_map ∧ + s.evm.hash_collision = s₉.evm.hash_collision ∧ + s.evm.execution_env = s₉.evm.execution_env ∧ + s.evm.keccak_map ≤ s₉.evm.keccak_map) := by + rw[←code] + unfold setEvm + simp [s_all] + rw [insert_of_ok] + unfold evm_revert + unfold evm_return + simp + + simp [Preserved_def] + aesop + aesop + + unfold setEvm at code + simp [s_all] at code + split_ands + · aesop + · intro s0_no_collision + left + split_ands + · apply preservesEvm_trans s_ok + all_goals aesop + · aesop + · aesop + · rw[←code] + unfold lookup! State.insert evm_revert evm_return + simp + unfold preservesEvm at s0_s_preservesEvm + simp[←s0_all, s_all, Preserved_def] at s0_s_preservesEvm + aesop + · aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172.lean b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172.lean new file mode 100644 index 00000000..293609f1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172_gen + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma if_4024499920364541172_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_4024499920364541172 s₀ = s₉ → + Spec A_if_4024499920364541172 s₀ s₉ := + λ _ h ↦ if_4024499920364541172_abs_of_concrete (if_4024499920364541172_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_gen.lean new file mode 100644 index 00000000..aa54b470 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_gen.lean @@ -0,0 +1,64 @@ +import Clear.ReasoningPrinciple + + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def if_4024499920364541172 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_4024499920364541172_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_4024499920364541172 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_4024499920364541172 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_user.lean new file mode 100644 index 00000000..93c4a6d7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4024499920364541172_user.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_if_4024499920364541172 (s₀ s₉ : State) : Prop := sorry + +lemma if_4024499920364541172_abs_of_concrete {s₀ s₉ : State} : + Spec if_4024499920364541172_concrete_of_code s₀ s₉ → + Spec A_if_4024499920364541172 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326.lean b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326.lean new file mode 100644 index 00000000..bb175f10 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326_gen + +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_4692225504622348326_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_4692225504622348326 s₀ = s₉ → + Spec A_if_4692225504622348326 s₀ s₉ := + λ _ h ↦ if_4692225504622348326_abs_of_concrete (if_4692225504622348326_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_gen.lean new file mode 100644 index 00000000..18a88790 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_gen.lean @@ -0,0 +1,114 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_4692225504622348326 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_4692225504622348326_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_4692225504622348326 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_4692225504622348326 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_tuple_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_user.lean new file mode 100644 index 00000000..67fa2b8e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_4692225504622348326_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_4692225504622348326 (s₀ s₉ : State) : Prop := sorry + +lemma if_4692225504622348326_abs_of_concrete {s₀ s₉ : State} : + Spec if_4692225504622348326_concrete_of_code s₀ s₉ → + Spec A_if_4692225504622348326 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685.lean b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685.lean new file mode 100644 index 00000000..221d82f3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685_gen + +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_5042234445269809685_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_5042234445269809685 s₀ = s₉ → + Spec A_if_5042234445269809685 s₀ s₉ := + λ _ h ↦ if_5042234445269809685_abs_of_concrete (if_5042234445269809685_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_gen.lean new file mode 100644 index 00000000..810acc15 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_gen.lean @@ -0,0 +1,103 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_5042234445269809685 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_5042234445269809685_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_5042234445269809685 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_5042234445269809685 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMLog3'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_user.lean new file mode 100644 index 00000000..aaa12e5e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_5042234445269809685_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_5042234445269809685 (s₀ s₉ : State) : Prop := sorry + +lemma if_5042234445269809685_abs_of_concrete {s₀ s₉ : State} : + Spec if_5042234445269809685_concrete_of_code s₀ s₉ → + Spec A_if_5042234445269809685 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831.lean b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831.lean new file mode 100644 index 00000000..9e2d42b7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831_gen + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_7164014626810332831_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_7164014626810332831 s₀ = s₉ → + Spec A_if_7164014626810332831 s₀ s₉ := + λ _ h ↦ if_7164014626810332831_abs_of_concrete (if_7164014626810332831_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_gen.lean new file mode 100644 index 00000000..396e7c28 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_gen.lean @@ -0,0 +1,68 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_7164014626810332831 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_7164014626810332831_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_7164014626810332831 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_7164014626810332831 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_user.lean new file mode 100644 index 00000000..6ea20301 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_7164014626810332831_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_7164014626810332831 (s₀ s₉ : State) : Prop := sorry + +lemma if_7164014626810332831_abs_of_concrete {s₀ s₉ : State} : + Spec if_7164014626810332831_concrete_of_code s₀ s₉ → + Spec A_if_7164014626810332831 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506.lean b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506.lean new file mode 100644 index 00000000..2679d074 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506_gen + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma if_8073281237182003506_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_8073281237182003506 s₀ = s₉ → + Spec A_if_8073281237182003506 s₀ s₉ := + λ _ h ↦ if_8073281237182003506_abs_of_concrete (if_8073281237182003506_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_gen.lean new file mode 100644 index 00000000..f218f968 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_gen.lean @@ -0,0 +1,67 @@ +import Clear.ReasoningPrinciple + + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def if_8073281237182003506 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_8073281237182003506_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_8073281237182003506 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_8073281237182003506 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_user.lean new file mode 100644 index 00000000..ebd03fc2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8073281237182003506_user.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_if_8073281237182003506 (s₀ s₉ : State) : Prop := sorry + +lemma if_8073281237182003506_abs_of_concrete {s₀ s₉ : State} : + Spec if_8073281237182003506_concrete_of_code s₀ s₉ → + Spec A_if_8073281237182003506 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919.lean b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919.lean new file mode 100644 index 00000000..cbd184c9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919_gen + +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma if_8475192588736690919_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_8475192588736690919 s₀ = s₉ → + Spec A_if_8475192588736690919 s₀ s₉ := + λ _ h ↦ if_8475192588736690919_abs_of_concrete (if_8475192588736690919_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_gen.lean new file mode 100644 index 00000000..8499ab50 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_gen.lean @@ -0,0 +1,122 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def if_8475192588736690919 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_8475192588736690919_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_8475192588736690919 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_8475192588736690919 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMLt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_3856757177752523473_abs_of_code if_3856757177752523473 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun__approve_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_user.lean new file mode 100644 index 00000000..0de78102 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_8475192588736690919_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3856757177752523473 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_if_8475192588736690919 (s₀ s₉ : State) : Prop := sorry + +lemma if_8475192588736690919_abs_of_concrete {s₀ s₉ : State} : + Spec if_8475192588736690919_concrete_of_code s₀ s₉ → + Spec A_if_8475192588736690919 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040.lean b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040.lean new file mode 100644 index 00000000..5a61c642 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040_gen + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_9141570808380448040_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_9141570808380448040 s₀ = s₉ → + Spec A_if_9141570808380448040 s₀ s₉ := + λ _ h ↦ if_9141570808380448040_abs_of_concrete (if_9141570808380448040_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_gen.lean new file mode 100644 index 00000000..35b715d1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_gen.lean @@ -0,0 +1,112 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_9141570808380448040 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_9141570808380448040_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_9141570808380448040 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_9141570808380448040 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_tuple_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_user.lean new file mode 100644 index 00000000..1bdd6452 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9141570808380448040_user.lean @@ -0,0 +1,207 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_9141570808380448040 (s₀ s₉ : State) : Prop := + + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : Reversion + preservesEvm s₀ s₉ ∧ + s₉.evm.reverted = true ∧ + s₀["_3"]!! ≠ 0 ∧ + s₉.evm.hash_collision = false + ) + ∨ + ( -- Case 1.2 : No Reversion + preservesEvm s₀ s₉ ∧ + s₀["_3"]!! = 0 ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 400000 + +lemma if_9141570808380448040_abs_of_concrete {s₀ s₉ : State} : + Spec if_9141570808380448040_concrete_of_code s₀ s₉ → + Spec A_if_9141570808380448040 s₀ s₉ := by + unfold if_9141570808380448040_concrete_of_code A_if_9141570808380448040 + + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + rintro hasFuel ⟨s, call_encode_tuple, code⟩ + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold A_abi_encode_tuple_address at call_encode_tuple + clr_varstore + + rw [←s0_all] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + simp at call_encode_tuple + unfold setEvm at call_encode_tuple + unfold multifill at call_encode_tuple + simp at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + rw [insert_of_ok] at call_encode_tuple + unfold lookup! at call_encode_tuple + simp at call_encode_tuple + + generalize s0__all : (Ok + (mstore evm₀ + (Finmap.lookup "_5" + (Finmap.insert "_6" (Fin.shiftLeft 1264811663 225) + (Finmap.insert "_5" (EVMState.mload evm₀ 64) + (Finmap.insert "_4" 64 (Finmap.insert "expr_1" 0 varstore₀))))).get! + (Fin.shiftLeft 1264811663 225)) + (Finmap.insert "_8" + ((Finmap.lookup "_5" + (Finmap.insert "_7" 4 + (Finmap.insert "_6" (Fin.shiftLeft 1264811663 225) + (Finmap.insert "_5" (EVMState.mload evm₀ 64) + (Finmap.insert "_4" 64 (Finmap.insert "expr_1" 0 varstore₀)))))).get! + + 4) + (Finmap.insert "_7" 4 + (Finmap.insert "_6" (Fin.shiftLeft 1264811663 225) + (Finmap.insert "_5" (EVMState.mload evm₀ 64) (Finmap.insert "_4" 64 (Finmap.insert "expr_1" 0 varstore₀))))))) = s0_ at * + + have : preservesEvm s₀ s0_ := by + have : Preserved evm₀ (mstore evm₀ + (Finmap.lookup "_5" + (Finmap.insert "_6" (Fin.shiftLeft 1264811663 225) + (Finmap.insert "_5" (EVMState.mload evm₀ 64) + (Finmap.insert "_4" 64 (Finmap.insert "expr_1" 0 varstore₀))))).get! + (Fin.shiftLeft 1264811663 225)) := by + apply mstore_preserved + aesop + + have s0__ok : s0_.isOk := by aesop + + by_cases _3_var : s₀["_3"]!! ≠ 0 + · simp [_3_var] at code + clr_spec at call_encode_tuple + obtain ⟨s_ok, ⟨s_preserves_evm, encode, s_no_collision⟩ | s_collision ⟩ := call_encode_tuple + · obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have s0_s_preservesEvm : preservesEvm s₀ s := by + apply preservesEvm_trans s0__ok + aesop + aesop + + have s_s9_preservesEvm : preservesEvm s s₉ := by + have : Preserved s.evm s₉.evm := by + have : (s.evm.account_map = s₉.evm.account_map ∧ + s.evm.hash_collision = s₉.evm.hash_collision ∧ + s.evm.execution_env = s₉.evm.execution_env ∧ + s.evm.keccak_map ≤ s₉.evm.keccak_map) := by + rw[←code] + unfold setEvm + simp [s_all] + rw [insert_of_ok] + unfold evm_revert + unfold evm_return + simp + + simp [Preserved_def] + aesop + aesop + + unfold setEvm at code + simp [s_all] at code + split_ands + · aesop + · intro s0_no_collision + left + split_ands + · apply preservesEvm_trans s_ok + all_goals aesop + · aesop + · aesop + · aesop + + · -- collision at s0 + intro s0_colliision + + have s0_s_preservesEvm : preservesEvm s₀ s := by + apply preservesEvm_trans s0__ok + aesop + aesop + + have s_s9_preservesEvm : preservesEvm s s₉ := by + have : Preserved s.evm s₉.evm := by + have : (s.evm.account_map = s₉.evm.account_map ∧ + s.evm.hash_collision = s₉.evm.hash_collision ∧ + s.evm.execution_env = s₉.evm.execution_env ∧ + s.evm.keccak_map ≤ s₉.evm.keccak_map) := by + rw[←code] + simp [s_all] + rw [insert_of_ok] + unfold evm_revert + unfold evm_return + simp + + simp [Preserved_def] + aesop + aesop + + have this : preservesEvm s₀ s₉ := by + apply preservesEvm_trans s_ok + all_goals aesop + + clr_varstore, + simp [←s0_all, ←code] at this + unfold evm_revert at this + unfold preservesEvm at this + unfold lookup! at this + unfold State.insert at this + simp at this + + generalize updated_evm : ({ + account_map := s_evm.account_map, + machine_state := s_evm.machine_state, + execution_env := s_evm.execution_env, + keccak_map := s_evm.keccak_map, + keccak_range := s_evm.keccak_range, + used_range := s_evm.used_range, + blocks := s_evm.blocks, + hash_collision := s_evm.hash_collision, + reverted := true + }: EVMState) = upd_evm + + have : upd_evm.hash_collision = evm₀.hash_collision := by + simp [Preserved_def] at this + unfold evm_return at this + aesop + + aesop + aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225.lean b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225.lean new file mode 100644 index 00000000..a7f96763 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225_gen + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma if_9222169807163418225_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel if_9222169807163418225 s₀ = s₉ → + Spec A_if_9222169807163418225 s₀ s₉ := + λ _ h ↦ if_9222169807163418225_abs_of_concrete (if_9222169807163418225_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_gen.lean b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_gen.lean new file mode 100644 index 00000000..5e4c1bc3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_gen.lean @@ -0,0 +1,68 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def if_9222169807163418225 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def if_9222169807163418225_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel if_9222169807163418225 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec if_9222169807163418225 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize If _ _ = f; aesop + · generalize If _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [If'] + + -- AST-specific tactics + + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (panic_error_0x41_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_user.lean b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_user.lean new file mode 100644 index 00000000..0d2870bf --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/if_9222169807163418225_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_if_9222169807163418225 (s₀ s₉ : State) : Prop := sorry + +lemma if_9222169807163418225_abs_of_concrete {s₀ s₉ : State} : + Spec if_9222169807163418225_concrete_of_code s₀ s₉ → + Spec A_if_9222169807163418225 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/new_lemmas.lean b/Generated/erc20shim/ERC20Shim/Common/new_lemmas.lean new file mode 100644 index 00000000..078bf5f2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/new_lemmas.lean @@ -0,0 +1,114 @@ +import Clear.ReasoningPrinciple + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma lookupAcc_preserves_eq {evm evm' : EVMState} {varstore varstore' : VarStore} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + unfold lookupAccount + intro preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + have h2 : evm.account_map = evm'.account_map := by + simp [preserves] + rw[h1,h2] + +lemma updateAcc_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} {act : Account}: + preservesEvm (Ok evm varstore) (Ok evm' varstore') ∧ + evm.lookupAccount evm.execution_env.code_owner = act + → + Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + intro h + obtain ⟨preserves, lookup⟩ := h + + have : evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have : evm'.lookupAccount evm'.execution_env.code_owner = act := by + rw[←this] + exact lookup + + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + rw[h1] + simp[Preserved_def] + unfold updateAccount + simp + obtain ⟨account, hash, exec, keccak⟩ := preserves + aesop + +lemma sstore_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + preservesEvm (Ok (sstore evm slot value) varstore) + (Ok (sstore evm' slot value) varstore') := by + intro preserves + unfold preservesEvm + simp [Preserved_def] + have : evm.lookupAccount evm.execution_env.code_owner = + evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have preserves_ : preservesEvm (Ok evm varstore) (Ok evm' varstore') := + by exact preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + obtain ⟨account, hash, exec, keccak⟩ := preserves + unfold sstore + simp[this] + + cases h: evm'.lookupAccount evm'.execution_env.code_owner with + | none => + simp [account, hash, exec, keccak] + | some act => + simp[h] + have : Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + apply updateAcc_preserved_eq + rw[←this] at h + exact ⟨preserves_, h⟩ + simp[Preserved_def] at this + exact this + +lemma decide_UInt256_true {p :Prop} [h : Decidable p] : + (decide p).toUInt256 ≠ 0 → p := by + unfold Bool.toUInt256 + simp + +lemma decide_UInt256_false {p :Prop} [h : Decidable p] : + (decide p).toUInt256 ≠ 1 → ¬p := by + unfold Bool.toUInt256 + simp + +lemma preserves_evm_eq {evm : EVMState} {store store' : VarStore} : + preservesEvm (Ok evm store) (Ok evm store') := by + unfold preservesEvm + simp + +@[simp] + lemma store_eq_store {evm' : EVMState} {varstore' : VarStore} : + (Ok evm' varstore').store = varstore' := + by simp [State.store] + + @[aesop norm simp] + lemma store_eq_store' {s' : State} {evm' : EVMState} {varstore' : VarStore} (h : s' = Ok evm' varstore') : + s'.store = varstore' := by + rw[h] + simp [State.store] + + @[simp] + lemma evm_eq_evm {evm' : EVMState} {varstore' : VarStore} : + (Ok evm' varstore').evm = evm' := + by simp [State.evm] + + @[aesop norm simp] + lemma evm_eq_evm' {s' : State} {evm' : EVMState} {varstore' : VarStore} (h : s' = Ok evm' varstore') : + s'.evm = evm' := by + rw[h] + simp [State.evm] \ No newline at end of file diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734.lean b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734.lean new file mode 100644 index 00000000..4af1c859 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734_gen + +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma switch_1041419350816529734_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel switch_1041419350816529734 s₀ = s₉ → + Spec A_switch_1041419350816529734 s₀ s₉ := + λ _ h ↦ switch_1041419350816529734_abs_of_concrete (switch_1041419350816529734_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_gen.lean b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_gen.lean new file mode 100644 index 00000000..46b968d1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_gen.lean @@ -0,0 +1,145 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def switch_1041419350816529734 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def switch_1041419350816529734_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel switch_1041419350816529734 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec switch_1041419350816529734 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Switch _ _ _ = f; aesop + · generalize Switch _ _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [Switch'] + + -- AST-specific tactics + + unfold execSwitchCases + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + (try (unfold execSwitchCases)) + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_storage_value_offsett_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + generalize hdefault : exec _ _ _ = sdef + (try (unfold execSwitchCases)) + subst hdefault + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_storage_value_offsett_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_user.lean b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_user.lean new file mode 100644 index 00000000..370b441e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_1041419350816529734_user.lean @@ -0,0 +1,223 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_switch_1041419350816529734 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + -- Case 1.1 : _24 = 0 + (∃ slot value, + let s:= (Ok (sstore s₀.evm slot value) s₀.store) + preservesEvm s s₉) ∧ + s₉.evm.hash_collision = false + + ) + ∨ + ( -- Case 1.2 : Default + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma lookupAcc_preserves_eq {evm evm' : EVMState} {varstore varstore' : VarStore} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + unfold lookupAccount + intro preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + have h2 : evm.account_map = evm'.account_map := by + simp [preserves] + rw[h1,h2] + +lemma updateAcc_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} {act : Account}: + preservesEvm (Ok evm varstore) (Ok evm' varstore') ∧ + evm.lookupAccount evm.execution_env.code_owner = act + → + Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + intro h + obtain ⟨preserves, lookup⟩ := h + + have : evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have : evm'.lookupAccount evm'.execution_env.code_owner = act := by + rw[←this] + exact lookup + + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + rw[h1] + simp[Preserved_def] + unfold updateAccount + simp + obtain ⟨account, hash, exec, keccak⟩ := preserves + aesop + +lemma sstore_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + preservesEvm (Ok (sstore evm slot value) varstore) + (Ok (sstore evm' slot value) varstore') := by + intro preserves + unfold preservesEvm + simp [Preserved_def] + have : evm.lookupAccount evm.execution_env.code_owner = + evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have preserves_ : preservesEvm (Ok evm varstore) (Ok evm' varstore') := + by exact preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + obtain ⟨account, hash, exec, keccak⟩ := preserves + unfold sstore + simp[this] + + cases h: evm'.lookupAccount evm'.execution_env.code_owner with + | none => + simp [account, hash, exec, keccak] + | some act => + simp[h] + have : Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + apply updateAcc_preserved_eq + rw[←this] at h + exact ⟨preserves_, h⟩ + simp[Preserved_def] at this + exact this + +lemma switch_1041419350816529734_abs_of_concrete {s₀ s₉ : State} : + Spec switch_1041419350816529734_concrete_of_code s₀ s₉ → + Spec A_switch_1041419350816529734 s₀ s₉ := by + unfold switch_1041419350816529734_concrete_of_code A_switch_1041419350816529734 + + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + apply spec_eq + clr_varstore, + rintro hasFuel ⟨s1, mapping, + ⟨s2, update1, + ⟨s3, update2, code⟩⟩⟩ + + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + have s0_ok : s₀.isOk := by aesop + + + by_cases _24 : s₀["_24"]!! = 0 + + · simp[_24] at code + clear update2 + + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping + clr_spec at mapping + unfold A_update_storage_value_offsett_uint256_to_uint256 at update1 + clr_spec at update1 + + clr_varstore, + + obtain ⟨s1_ok, ⟨s0s1_preserves, s0s1_state, s1_keccak, s1_no_collision⟩ | s1_collision, s0s1_collision⟩ := mapping + + · -- no collision at s1 mapping + obtain ⟨s1_evm, ⟨s1_varstore, s1_all⟩⟩ := State_of_isOk s1_ok + + obtain ⟨s2_ok, no_collision_s1, s1s2_collision⟩ := update1 + obtain ⟨s2_evm, ⟨s2_varstore, s2_all⟩⟩ := State_of_isOk s2_ok + + simp[s1_no_collision] at no_collision_s1 + + have s0_no_collision : s₀.evm.hash_collision = false := by aesop + simp[s0_no_collision] + + split_ands + · aesop + · by_cases s9_collision : s₉.evm.hash_collision = false + · left + split_ands + · rw[←code] + have s1__ok : (Ok (sstore s1.evm (s1["_26"]!!) (sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!))) + (s1⟦"_27"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_28"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_29"↦sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!)⟧.store)).isOk := by aesop + have h2 : preservesEvm + (Ok (sstore s1.evm (s1["_26"]!!) (sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!))) + (s1⟦"_27"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_28"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_29"↦sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!)⟧.store)) + s2 := by aesop + have preserves_sstore : preservesEvm + (Ok (sstore s₀.evm (s1["_26"]!!) (sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!))) varstore₀) + (Ok (sstore s1.evm (s1["_26"]!!) (sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!))) + (s1⟦"_27"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_28"↦sload s1.evm + (s1["_26"]!!)⟧⟦"_29"↦sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!)⟧.store)) + := by + apply sstore_preserved_eq + aesop + have s0s1_preservesEvm : preservesEvm s₀ s1 := by aesop + have : preservesEvm (Ok (sstore s₀.evm (s1["_26"]!!) (sload s1.evm (s1["_26"]!!) + (s1["var_value"]!!))) s₀.store) s2 := by + apply preservesEvm_trans s1__ok + · aesop + · aesop + aesop + · aesop + · aesop + · -- collision at s1 mapping + aesop + + · -- Default case + have : 0 ≠ s₀["_24"]!! := by aesop + simp[this] at code + + clear mapping update1 this + + unfold A_update_storage_value_offsett_uint256_to_uint256 at update2 + clr_spec at update2 + + obtain ⟨s3_ok, no_collision_s0, s0s3_collision⟩ := update2 + obtain ⟨s3_evm, ⟨s3_varstore, s3_all⟩⟩ := State_of_isOk s3_ok + + by_cases s0_collision : s₀.evm.hash_collision = false + + · split_ands + · aesop + · simp[s0_collision] + by_cases s9_collision : s₉.evm.hash_collision = false + · left + split_ands + · rw[←code] + simp[s0_collision] at no_collision_s0 + aesop + · aesop + · aesop + · aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941.lean b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941.lean new file mode 100644 index 00000000..b3ced954 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941.lean @@ -0,0 +1,27 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_gen + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma switch_2364266820542243941_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel switch_2364266820542243941 s₀ = s₉ → + Spec A_switch_2364266820542243941 s₀ s₉ := + λ _ h ↦ switch_2364266820542243941_abs_of_concrete (switch_2364266820542243941_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_gen.lean b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_gen.lean new file mode 100644 index 00000000..dea724b5 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_gen.lean @@ -0,0 +1,202 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def switch_2364266820542243941 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def switch_2364266820542243941_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel switch_2364266820542243941 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec switch_2364266820542243941 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Switch _ _ _ = f; aesop + · generalize Switch _ _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [Switch'] + + -- AST-specific tactics + + unfold execSwitchCases + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + (try (unfold execSwitchCases)) + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMLt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_3989404597755436942_abs_of_code if_3989404597755436942 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_storage_value_offsett_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + generalize hdefault : exec _ _ _ = sdef + (try (unfold execSwitchCases)) + subst hdefault + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (checked_add_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_storage_value_offsett_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_user.lean b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_user.lean new file mode 100644 index 00000000..0809d11d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_2364266820542243941_user.lean @@ -0,0 +1,400 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.Common.if_3989404597755436942 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_switch_2364266820542243941 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : _3 = 0 + (-- Case 1.1.1: _7 = 1 (Reversion) + (∃ slot value, + let s:= (Ok (sstore s₀.evm slot value) s₀.store) + preservesEvm s s₉) ∧ + s₉.evm.hash_collision = false + ) + ∨ + (-- Case 1.1.2 _7 =/ 0 (Non Reversion) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false + ) + ) + ∨ + ( -- Case 1.2 : Default + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 2000000 +set_option maxRecDepth 1000 + + +lemma lookupAcc_preserves_eq {evm evm' : EVMState} {varstore varstore' : VarStore} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + unfold lookupAccount + intro preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + have h2 : evm.account_map = evm'.account_map := by + simp [preserves] + rw[h1,h2] + +lemma updateAcc_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} {act : Account}: + preservesEvm (Ok evm varstore) (Ok evm' varstore') ∧ + evm.lookupAccount evm.execution_env.code_owner = act + → + Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + intro h + obtain ⟨preserves, lookup⟩ := h + + have : evm.lookupAccount evm.execution_env.code_owner = evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have : evm'.lookupAccount evm'.execution_env.code_owner = act := by + rw[←this] + exact lookup + + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + have h1 : evm.execution_env.code_owner = evm'.execution_env.code_owner := by + simp [preserves.2.2.1] + rw[h1] + simp[Preserved_def] + unfold updateAccount + simp + obtain ⟨account, hash, exec, keccak⟩ := preserves + aesop + +lemma sstore_preserved_eq {evm evm' : EVMState} {varstore varstore' : VarStore} {slot value : UInt256} : + preservesEvm (Ok evm varstore) (Ok evm' varstore') → + preservesEvm (Ok (sstore evm slot value) varstore) + (Ok (sstore evm' slot value) varstore') := by + intro preserves + unfold preservesEvm + simp [Preserved_def] + have : evm.lookupAccount evm.execution_env.code_owner = + evm'.lookupAccount evm'.execution_env.code_owner := by + apply lookupAcc_preserves_eq preserves + have preserves_ : preservesEvm (Ok evm varstore) (Ok evm' varstore') := + by exact preserves + unfold preservesEvm at preserves + simp [Preserved_def] at preserves + obtain ⟨account, hash, exec, keccak⟩ := preserves + unfold sstore + simp[this] + + cases h: evm'.lookupAccount evm'.execution_env.code_owner with + | none => + simp [account, hash, exec, keccak] + | some act => + simp[h] + have : Preserved (evm.updateAccount evm.execution_env.code_owner (act.updateStorage slot value)) + (evm'.updateAccount evm'.execution_env.code_owner (act.updateStorage slot value)) := by + apply updateAcc_preserved_eq + rw[←this] at h + exact ⟨preserves_, h⟩ + simp[Preserved_def] at this + exact this + +lemma switch_2364266820542243941_abs_of_concrete {s₀ s₉ : State} : + Spec switch_2364266820542243941_concrete_of_code s₀ s₉ → + Spec A_switch_2364266820542243941 s₀ s₉ := by + + unfold switch_2364266820542243941_concrete_of_code A_switch_2364266820542243941 + + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + apply spec_eq + + rintro hasFuel ⟨s1, mapping1, + ⟨s2, if308, + ⟨s3, mapping2, + ⟨s4, update1, + ⟨s5, add, + ⟨s6, update2, code⟩⟩⟩⟩⟩⟩ + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + have s0_ok : s₀.isOk := by aesop + + by_cases _3 : s₀["_3"]!! = 0 + + · -- _3 case + simp[_3] at code + + clear update2 add + + clr_varstore mapping1, + clr_varstore mapping2, + + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping1 + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping2 + unfold A_if_3989404597755436942 at if308 + unfold A_update_storage_value_offsett_uint256_to_uint256 at update1 + + rw[←code] at hasFuel + have s3_hasFuel: ¬❓ s3 := by + apply not_isOutOfFuel_Spec update1 hasFuel + have s2insert_hasFuel : ¬❓ (s2⟦"expr_4"↦s2["_6"]!! - (s2["var_value"]!!)⟧⟦"_15"↦s2["_4"]!!⟧) := by + apply not_isOutOfFuel_Spec mapping2 s3_hasFuel + have s2_hasFuel : ¬❓ s2 := by aesop + + have s1insert_hasFuel : ¬❓ (s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧⟦"_7"↦(decide + (s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm (s1["_5"]!!)⟧["_6"]!!⟧["_6"]!! < + s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧⟦"var_fromBalance"↦s1⟦"_6"↦sload s1.evm + (s1["_5"]!!)⟧["_6"]!!⟧["var_value"]!!)).toUInt256⟧) := by + apply not_isOutOfFuel_Spec if308 s2_hasFuel + have s1_hasFuel : ¬❓ s1 := by aesop + + -- These all work, sorrys for speed + apply Spec_ok_unfold (by sorry) (by sorry) at mapping1 + apply Spec_ok_unfold (by sorry) (by sorry) at if308 + apply Spec_ok_unfold (by sorry) (by sorry) at mapping2 + apply Spec_ok_unfold (by sorry) (by sorry) at update1 + + clr_varstore if308, + obtain ⟨s1_ok, ⟨s0s1_preserves, s0s1_state, s1_keccak, s1_no_collision⟩ | s1_collision, s0s1_collision⟩ := mapping1 + · -- NO collision in mapping1 + obtain ⟨s1_evm, ⟨s1_varstore, s1_all⟩⟩ := State_of_isOk s1_ok + by_cases _7 : (decide (sload s1.evm (s1["_5"]!!) < s1["var_value"]!!)).toUInt256 = 1 + + · -- _7 = 1 (Reversion) + simp[s1_no_collision, _7] at if308 + obtain ⟨s2_ok, ⟨s1s2_preserves, s2_reverted⟩| s2_collision⟩ := if308 + + · -- no Collision in if308 + obtain ⟨s2_evm, ⟨s2_varstore, s2_all⟩⟩ := State_of_isOk s2_ok + obtain ⟨s3_ok, ⟨s2s3_preserves, s2s3_state, s3_keccak, s3_no_collision⟩ | s3_collision, s2s3_colliion⟩ := mapping2 + + · -- No collision in mapping2 + obtain ⟨s3_evm, ⟨s3_varstore, s3_all⟩⟩ := State_of_isOk s3_ok + have s3__ok : (Ok (sstore s3.evm (s3["_16"]!!) (s3["expr_4"]!!)) s3.store).isOk := by aesop + simp[s3_no_collision, _7] at update1 + obtain ⟨s4_ok, s3s4_preserves | s4_collision⟩ := update1 + + · -- No collision in update1 + obtain ⟨s4_evm, ⟨s4_varstore, s4_all⟩⟩ := State_of_isOk s4_ok + rw[←code] + split_ands + · aesop + · intro s0_no_collison + + by_cases s9_no_collision : s₉.evm.hash_collision = false + + · -- No collision in function + left + left + split_ands + · have s0s3_preserves : preservesEvm s₀ s3 := by + apply preservesEvm_trans s1_ok + · aesop + · apply preservesEvm_trans s2_ok + · aesop + · aesop + have : preservesEvm (Ok (sstore s₀.evm (s3["_16"]!!) (s3["expr_4"]!!)) s₀.store) + (Ok (sstore s3.evm (s3["_16"]!!) (s3["expr_4"]!!)) s3.store) := by + apply sstore_preserved_eq + aesop + + have : preservesEvm (Ok (sstore s₀.evm (s3["_16"]!!) (s3["expr_4"]!!)) s₀.store) s4 := by + apply preservesEvm_trans s3__ok + · aesop + · aesop + aesop + · aesop + + · -- Collision in function + aesop + + · aesop + + · -- Collision in update 1 + aesop + + · -- Collision in mapping 2 + aesop + + · -- collision in if308 + aesop + + · -- _7 = 0 (No reversion) + have : (decide (sload s1.evm (s1["_5"]!!) < s1["var_value"]!!)).toUInt256 = 0 := by + unfold Bool.toUInt256 + unfold Bool.toUInt256 at _7 + aesop + + simp[s1_no_collision, this] at if308 + obtain ⟨s2_ok, s1s2_preserves| s2_collision⟩ := if308 + + · -- no Collision in if308 + obtain ⟨s2_evm, ⟨s2_varstore, s2_all⟩⟩ := State_of_isOk s2_ok + obtain ⟨s3_ok, ⟨s2s3_preserves, s2s3_state, s3_keccak, s3_no_collision⟩ | s3_collision, s2s3_colliion⟩ := mapping2 + + · -- No collision in mapping2 + obtain ⟨s3_evm, ⟨s3_varstore, s3_all⟩⟩ := State_of_isOk s3_ok + have s3__ok : (Ok (sstore s3.evm (s3["_16"]!!) (s3["expr_4"]!!)) s3.store).isOk := by aesop + simp[s3_no_collision, _7] at update1 + obtain ⟨s4_ok, s3s4_preserves | s4_collision⟩ := update1 + + · -- No collision in update1 + obtain ⟨s4_evm, ⟨s4_varstore, s4_all⟩⟩ := State_of_isOk s4_ok + rw[←code] + split_ands + · aesop + · intro s0_no_collison + + by_cases s9_no_collision : s₉.evm.hash_collision = false + + · -- No collision in function + left + left + split_ands + · have s0s3_preserves : preservesEvm s₀ s3 := by + apply preservesEvm_trans s1_ok + · aesop + · apply preservesEvm_trans s2_ok + · aesop + · aesop + have : preservesEvm (Ok (sstore s₀.evm (s3["_16"]!!) (s3["expr_4"]!!)) s₀.store) + (Ok (sstore s3.evm (s3["_16"]!!) (s3["expr_4"]!!)) s3.store) := by + apply sstore_preserved_eq + aesop + have : preservesEvm (Ok (sstore s₀.evm (s3["_16"]!!) (s3["expr_4"]!!)) s₀.store) s4 := by + apply preservesEvm_trans s3__ok + · aesop + · aesop + aesop + · aesop + + · -- Collision in function + aesop + + · aesop + + · -- Collision in update 1 + aesop + + · -- Collision in mapping 2 + aesop + + · -- collision in if308 + aesop + · aesop + + · -- No _3 case + clear update1 if308 mapping1 mapping2 + + have : 0 ≠ s₀["_3"]!! := by aesop + simp[this] at code + clear this + + unfold A_checked_add_uint256 at add + unfold A_update_storage_value_offsett_uint256_to_uint256 at update2 + clr_varstore, + + clr_spec at add + clr_spec at update2 + + by_cases s0_no_collision : s₀.evm.hash_collision = false + + · simp[s0_no_collision] at add + obtain ⟨s5_ok, + (⟨s0s5_preserves, s5_reverted, s5_load, s5_no_collision⟩ | + ⟨s0s5_preserves, s5_load, s5_no_collision⟩ | + s5_collision)⟩ := add + · -- reversion in add + obtain ⟨s5_evm, ⟨s5_varstore, s5_all⟩⟩ := State_of_isOk s5_ok + + simp[s5_no_collision] at update2 + obtain ⟨s6_ok, s5s6_preserves | s6_collision⟩ := update2 + + · -- no collision at update2 + simp[s0_no_collision] + split_ands + · aesop + · by_cases s9_no_collision : s₉.evm.hash_collision = false + · left + left + split_ands + · rw[←code] + have : preservesEvm s₀ s5 := by aesop + have : preservesEvm (Ok (sstore s₀.evm (s5["_17"]!!) (s5["_20"]!!)) s₀.store) + (Ok (sstore s5.evm (s5["_17"]!!) (s5["_20"]!!)) (s5⟦"_21"↦s5["_17"]!!⟧.store)) := by + apply sstore_preserved_eq + aesop + have s5__ok : (Ok (sstore s5.evm (s5["_17"]!!) (s5["_20"]!!)) (s5⟦"_21"↦s5["_17"]!!⟧.store)).isOk := by aesop + have : preservesEvm (Ok (sstore s₀.evm (s5["_17"]!!) (s5["_20"]!!)) s₀.store) s6 := by + apply preservesEvm_trans s5__ok + · aesop + · aesop + aesop + · aesop + · aesop + · aesop + + · -- No reversion in add + obtain ⟨s5_evm, ⟨s5_varstore, s5_all⟩⟩ := State_of_isOk s5_ok + + simp[s5_no_collision] at update2 + obtain ⟨s6_ok, s5s6_preserves | s6_collision⟩ := update2 + + · -- no collision at update2 + simp[s0_no_collision] + split_ands + · aesop + · by_cases s9_no_collision : s₉.evm.hash_collision = false + · left + left + split_ands + · rw[←code] + have : preservesEvm s₀ s5 := by aesop + have : preservesEvm (Ok (sstore s₀.evm (s5["_17"]!!) (s5["_20"]!!)) s₀.store) + (Ok (sstore s5.evm (s5["_17"]!!) (s5["_20"]!!)) (s5⟦"_21"↦s5["_17"]!!⟧.store)) := by + apply sstore_preserved_eq + aesop + have s5__ok : (Ok (sstore s5.evm (s5["_17"]!!) (s5["_20"]!!)) (s5⟦"_21"↦s5["_17"]!!⟧.store)).isOk := by aesop + have : preservesEvm (Ok (sstore s₀.evm (s5["_17"]!!) (s5["_20"]!!)) s₀.store) s6 := by + apply preservesEvm_trans s5__ok + · aesop + · aesop + aesop + · aesop + · aesop + · aesop + · aesop + · aesop + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348.lean b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348.lean new file mode 100644 index 00000000..b48026eb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453 + +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348_gen + +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348_user + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma switch_8164987986085659348_abs_of_code {s₀ : State} {fuel : Nat} : + ∀ s₉, exec fuel switch_8164987986085659348 s₀ = s₉ → + Spec A_switch_8164987986085659348 s₀ s₉ := + λ _ h ↦ switch_8164987986085659348_abs_of_concrete (switch_8164987986085659348_concrete_of_code.2 h) + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_gen.lean b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_gen.lean new file mode 100644 index 00000000..60ae0033 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_gen.lean @@ -0,0 +1,155 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453 + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def switch_8164987986085659348 := + +set_option maxRecDepth 5000 +set_option maxHeartbeats 400000 + +def switch_8164987986085659348_concrete_of_code : { + C : State → State → Prop + // ∀ {s₀ s₉ fuel} + , exec fuel switch_8164987986085659348 s₀ = s₉ + → Spec C s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + + unfold Spec switch_8164987986085659348 + rcases s₀ with ⟨evm₀, store₀⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Switch _ _ _ = f; aesop + · generalize Switch _ _ _ = f; aesop + swap + generalize hok : Ok evm₀ store₀ = s₀ + intros h _ + revert h + + rw [Switch'] + + -- AST-specific tactics + + unfold execSwitchCases + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + (try (unfold execSwitchCases)) + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMNot'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + (try (unfold execSwitchCases)) + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (array_dataslot_string_storage_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract for_1821242857744567453_abs_of_code for_1821242857744567453 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + + generalize hdefault : exec _ _ _ = sdef + (try (unfold execSwitchCases)) + subst hdefault + + + -- tacticsOfStmt offsetting + try rw [nil] + try simp [Bool.toUInt256, UInt256.size] + intros h + exact h + + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_user.lean b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_user.lean new file mode 100644 index 00000000..a29a7df6 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Common/switch_8164987986085659348_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage +import Generated.erc20shim.ERC20Shim.Common.for_1821242857744567453 + +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348_gen + + +namespace ERC20Shim.Common + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_switch_8164987986085659348 (s₀ s₉ : State) : Prop := sorry + +lemma switch_8164987986085659348_abs_of_concrete {s₀ s₉ : State} : + Spec switch_8164987986085659348_concrete_of_code s₀ s₉ → + Spec A_switch_8164987986085659348 s₀ s₉ := by + sorry + +end + +end ERC20Shim.Common diff --git a/Generated/erc20shim/ERC20Shim/Predicate.lean b/Generated/erc20shim/ERC20Shim/Predicate.lean new file mode 100644 index 00000000..3d2b08d6 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Predicate.lean @@ -0,0 +1,135 @@ +import Mathlib.Data.Finmap + +import Clear.State +import Clear.Utilities + +import Generated.erc20shim.ERC20Shim.Variables + +open Clear State Utilities + +namespace Generated.erc20shim.ERC20Shim + +abbrev BalanceMap := Finmap (λ _ : Address ↦ UInt256) +abbrev AllowanceMap := Finmap (λ _ : Address × Address ↦ UInt256) + +structure ERC20 where + supply : UInt256 + balances : BalanceMap + allowances : AllowanceMap + +set_option linter.setOption false +set_option pp.coercions false + +def not_mem_private (a : Option UInt256) : Prop := + match a with + | some el => el ∉ ERC20Private.toFinset + | none => true + +lemma not_mem_private_of_some {a : UInt256} (h : not_mem_private (some a)) : + a ∉ ERC20Private.toFinset := by + unfold not_mem_private at h + simp at h + exact h + +structure IsERC20 (erc20 : ERC20) (s : State) : Prop where + hasSupply : s.evm.sload ERC20Private.totalSupply = erc20.supply + + hasBalance : + ∀ {account}, (account ∈ erc20.balances) → + ∃ (address : UInt256), + s.evm.keccak_map.lookup [ ↑account , ERC20Private.balances ] = some address ∧ + erc20.balances.lookup account = some (s.evm.sload address) + + hasAllowance : + ∀ {owner spender}, ((owner, spender) ∈ erc20.allowances) → + ∃ (address : UInt256) (intermediate : UInt256), + s.evm.keccak_map.lookup [ ↑owner , ERC20Private.allowances ] = some intermediate ∧ + s.evm.keccak_map.lookup [ ↑spender , intermediate ] = some address ∧ + erc20.allowances.lookup ⟨owner, spender⟩ = some (s.evm.sload address) + + storageDom : + s.evm.storage.keys = + { address | ∃ account, + account ∈ erc20.balances ∧ + some address = s.evm.keccak_map.lookup [ ↑account, ERC20Private.balances ] }.toFinset ∪ + { address | ∃ owner spender, + (owner, spender) ∈ erc20.allowances ∧ + ∀ {intermediate}, s.evm.keccak_map.lookup [ ↑owner , ERC20Private.allowances ] = some intermediate → + s.evm.keccak_map.lookup [ ↑spender , intermediate ] = some address }.toFinset ∪ + ERC20Private.toFinset + + block_acc_range : + ∀ {var}, + not_mem_private (s.evm.keccak_map.lookup [ var, ERC20Private.balances ]) ∧ + not_mem_private (s.evm.keccak_map.lookup [ var, ERC20Private.allowances ]) ∧ + (∀ var₂ intermediate, s.evm.keccak_map.lookup [ var, ERC20Private.allowances ] = some intermediate + → not_mem_private (s.evm.keccak_map.lookup [ var₂, intermediate ])) + + -- block_allowance_range : + -- ∀ {owner}, s.evm.keccak_map.lookup [ ↑owner, ERC20Private.allowances ] ∉ ERC20Private.toFinset + + -- equivalent statements + -- s.evm.sload address ∈ erc20.balances.lookup account + -- ⟨account, s.evm.sload address⟩ ∈ erc20.balances.entries + +lemma w {erc20} {s} {account} (is_erc20 : IsERC20 erc20 s) (not_mem: account ∉ erc20.balances) : + (s.evm.keccak_range.partition (λ x ↦ x ∈ s.evm.used_range)).2 ∩ s.evm.storage.keys.toList = ∅ + := by + sorry + +lemma IsERC20_of_insert {erc20} {s : State} : + ∀ {var val}, IsERC20 erc20 s → IsERC20 erc20 (s⟦var↦val⟧) := by + intro var val is_erc + constructor <;> rw [State.evm_insert] + · exact is_erc.hasSupply + · exact is_erc.hasBalance + · exact is_erc.hasAllowance + · exact is_erc.storageDom + sorry + +lemma IsERC20_of_ok_forall_store {erc20} {evm} {s₀ s₁} : + IsERC20 erc20 (Ok evm s₀) → IsERC20 erc20 (Ok evm s₁) := by + intro is_erc + constructor <;> (try simp [State.evm]) + · exact is_erc.hasSupply + · exact is_erc.hasBalance + · exact is_erc.hasAllowance + · exact is_erc.storageDom + sorry + +lemma IsERC20_of_ok_of_Preserved {erc20} {store} {σ₀ σ₁} (h : Preserved σ₀ σ₁) : + IsERC20 erc20 (Ok σ₀ store) → IsERC20 erc20 (Ok σ₁ store) := by + sorry + +lemma IsERC20_of_preservesEvm {erc20} {s₀ s₁} : + preservesEvm s₀ s₁ → IsERC20 erc20 s₀ → IsERC20 erc20 s₁ := by + sorry + +lemma t {erc20} {s₀ s₁} (is_erc20 : IsERC20 erc20 s₀) (h : preservesEvm s₀ s₁) : + ∀ {addr}, addr ∉ s₀.evm.keccak_range ∧ addr ∈ s₁.evm.keccak_range → + addr ∉ s₀.evm.storage.keys := by + sorry + +def update_balances (erc20 : ERC20) from_addr to_addr transfer_value := + if from_addr = to_addr then erc20.balances + else + Finmap.insert + to_addr + (((erc20.balances.lookup to_addr).getD 0) + transfer_value) + ( + Finmap.insert + from_addr + (((erc20.balances.lookup from_addr).getD 0) - transfer_value) + erc20.balances + ) + +def update_allowances (erc20 : ERC20) owner_addr spender_addr transfer_value := + let currentAllowance := (erc20.allowances.lookup (owner_addr, spender_addr)).getD 0 + if currentAllowance = UInt256.top then erc20.allowances else + -- if currentAllowance < transfer_value then erc20.allowances else + Finmap.insert + (owner_addr, spender_addr) + (currentAllowance - transfer_value) + erc20.allowances + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/Variables.lean b/Generated/erc20shim/ERC20Shim/Variables.lean new file mode 100644 index 00000000..cc02ef74 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/Variables.lean @@ -0,0 +1,48 @@ +import Mathlib.Data.Finmap +import Clear.Ast +import Clear.EVMState +import Clear.UInt256 +import Clear.State + +open Clear + +namespace Generated.erc20shim.ERC20Shim + +structure PrivateAddresses where + balances : UInt256 + allowances : UInt256 + totalSupply : UInt256 + name : UInt256 + symbol : UInt256 + +def PrivateAddresses.toFinset (p : PrivateAddresses) : Finset UInt256 := + { p.balances, p.allowances, p.totalSupply, p.name, p.symbol } + +def ERC20Private : PrivateAddresses := + { balances := 0, allowances := 1, totalSupply := 2, name := 3, symbol := 4 } + +namespace Variables + +lemma balances_def : ERC20Private.balances = 0 := by + unfold ERC20Private + simp only + +lemma allowances_def : ERC20Private.allowances = 1 := by + unfold ERC20Private + simp only + +lemma totalSupply_def : ERC20Private.totalSupply = 2 := by + unfold ERC20Private + simp only + +lemma name_def : ERC20Private.name = 3 := by + unfold ERC20Private + simp only + +lemma symbol_def : ERC20Private.symbol = 4 := by + unfold ERC20Private + simp only + +end Variables + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode.lean b/Generated/erc20shim/ERC20Shim/abi_decode.lean new file mode 100644 index 00000000..3ab572aa --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + +import Generated.erc20shim.ERC20Shim.abi_decode_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_decode_abs_of_code {s₀ s₉ : State} { headStart dataEnd} {fuel : Nat} : + execCall fuel abi_decode [] (s₀, [headStart, dataEnd]) = s₉ → + Spec (A_abi_decode headStart dataEnd) s₀ s₉ +:= λ h ↦ abi_decode_abs_of_concrete (abi_decode_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_address.lean b/Generated/erc20shim/ERC20Shim/abi_decode_address.lean new file mode 100644 index 00000000..d06470e0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_address.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_address + +import Generated.erc20shim.ERC20Shim.abi_decode_address_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_decode_address_abs_of_code {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn} {fuel : Nat} : + execCall fuel abi_decode_address [value] (s₀, [offset, end_clear_sanitised_hrafn]) = s₉ → + Spec (A_abi_decode_address value offset end_clear_sanitised_hrafn) s₀ s₉ +:= λ h ↦ abi_decode_address_abs_of_concrete (abi_decode_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_address_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_address_gen.lean new file mode 100644 index 00000000..fbb0e059 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_address_gen.lean @@ -0,0 +1,107 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_decode_address : FunctionDefinition := value + +{ + value := calldataload(offset) + validator_revert_address(value) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_address_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn fuel}, + execCall fuel abi_decode_address [value] (s₀, [offset, end_clear_sanitised_hrafn]) = s₉ → + Spec (C value offset end_clear_sanitised_hrafn) s₀ s₉ + } := by + constructor + intros s₀ s₉ value offset end_clear_sanitised_hrafn fuel + unfold abi_decode_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMCalldataload'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (validator_revert_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_address_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_address_user.lean new file mode 100644 index 00000000..2321fea9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_address_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_address + +import Generated.erc20shim.ERC20Shim.abi_decode_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_decode_address (value : Identifier) (offset end_clear_sanitised_hrafn : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_address_abs_of_concrete {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn} : + Spec (abi_decode_address_concrete_of_code.1 value offset end_clear_sanitised_hrafn) s₀ s₉ → + Spec (A_abi_decode_address value offset end_clear_sanitised_hrafn) s₀ s₉ := by + unfold abi_decode_address_concrete_of_code A_abi_decode_address + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address.lean new file mode 100644 index 00000000..5ad32ae0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_decode_addresst_address_abs_of_code {s₀ s₉ : State} {value0 value1 headStart dataEnd} {fuel : Nat} : + execCall fuel abi_decode_addresst_address [value0, value1] (s₀, [headStart, dataEnd]) = s₉ → + Spec (A_abi_decode_addresst_address value0 value1 headStart dataEnd) s₀ s₉ +:= λ h ↦ abi_decode_addresst_address_abs_of_concrete (abi_decode_addresst_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_gen.lean new file mode 100644 index 00000000..8a677bdb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_gen.lean @@ -0,0 +1,152 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_decode_addresst_address : FunctionDefinition := value0, value1 + +{ + let _1 := 64 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + {revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b()} + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_address(_5, dataEnd) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_addresst_address_concrete_of_code +: { + C : + _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value0 value1 headStart dataEnd fuel}, + execCall fuel abi_decode_addresst_address [value0, value1] (s₀, [headStart, dataEnd]) = s₉ → + Spec (C value0 value1 headStart dataEnd) s₀ s₉ + } := by + constructor + intros s₀ s₉ value0 value1 headStart dataEnd fuel + unfold abi_decode_addresst_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSlt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_7164014626810332831_abs_of_code if_7164014626810332831 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_user.lean new file mode 100644 index 00000000..8830eab3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_address_user.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_decode_addresst_address (value0 value1 : Identifier) (headStart dataEnd : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_addresst_address_abs_of_concrete {s₀ s₉ : State} {value0 value1 headStart dataEnd} : + Spec (abi_decode_addresst_address_concrete_of_code.1 value0 value1 headStart dataEnd) s₀ s₉ → + Spec (A_abi_decode_addresst_address value0 value1 headStart dataEnd) s₀ s₉ := by + unfold abi_decode_addresst_address_concrete_of_code A_abi_decode_addresst_address + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256.lean new file mode 100644 index 00000000..6d3b5122 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_decode_addresst_addresst_uint256_abs_of_code {s₀ s₉ : State} {value0 value1 value2 headStart dataEnd} {fuel : Nat} : + execCall fuel abi_decode_addresst_addresst_uint256 [value0, value1, value2] (s₀, [headStart, dataEnd]) = s₉ → + Spec (A_abi_decode_addresst_addresst_uint256 value0 value1 value2 headStart dataEnd) s₀ s₉ +:= λ h ↦ abi_decode_addresst_addresst_uint256_abs_of_concrete (abi_decode_addresst_addresst_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_gen.lean new file mode 100644 index 00000000..b3a27de4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_gen.lean @@ -0,0 +1,174 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_decode_addresst_addresst_uint256 : FunctionDefinition := value0, value1, value2 + +{ + let _1 := 96 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + {revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b()} + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_address(_5, dataEnd) + let _6 := 64 + let _7 := add(headStart, _6) + value2 := abi_decode_uint256(_7, dataEnd) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_addresst_addresst_uint256_concrete_of_code +: { + C : + _ → _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value0 value1 value2 headStart dataEnd fuel}, + execCall fuel abi_decode_addresst_addresst_uint256 [value0, value1, value2] (s₀, [headStart, dataEnd]) = s₉ → + Spec (C value0 value1 value2 headStart dataEnd) s₀ s₉ + } := by + constructor + intros s₀ s₉ value0 value1 value2 headStart dataEnd fuel + unfold abi_decode_addresst_addresst_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSlt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_7164014626810332831_abs_of_code if_7164014626810332831 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_user.lean new file mode 100644 index 00000000..b0abd84a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_addresst_uint256_user.lean @@ -0,0 +1,27 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_addresst_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_decode_addresst_addresst_uint256 (value0 value1 value2 : Identifier) (headStart dataEnd : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_addresst_addresst_uint256_abs_of_concrete {s₀ s₉ : State} {value0 value1 value2 headStart dataEnd} : + Spec (abi_decode_addresst_addresst_uint256_concrete_of_code.1 value0 value1 value2 headStart dataEnd) s₀ s₉ → + Spec (A_abi_decode_addresst_addresst_uint256 value0 value1 value2 headStart dataEnd) s₀ s₉ := by + unfold abi_decode_addresst_addresst_uint256_concrete_of_code A_abi_decode_addresst_addresst_uint256 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256.lean new file mode 100644 index 00000000..28ce57f9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_decode_addresst_uint256_abs_of_code {s₀ s₉ : State} {value0 value1 headStart dataEnd} {fuel : Nat} : + execCall fuel abi_decode_addresst_uint256 [value0, value1] (s₀, [headStart, dataEnd]) = s₉ → + Spec (A_abi_decode_addresst_uint256 value0 value1 headStart dataEnd) s₀ s₉ +:= λ h ↦ abi_decode_addresst_uint256_abs_of_concrete (abi_decode_addresst_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_gen.lean new file mode 100644 index 00000000..9c9f979d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_gen.lean @@ -0,0 +1,153 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_decode_addresst_uint256 : FunctionDefinition := value0, value1 + +{ + let _1 := 64 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + {revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b()} + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_uint256(_5, dataEnd) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_addresst_uint256_concrete_of_code +: { + C : + _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value0 value1 headStart dataEnd fuel}, + execCall fuel abi_decode_addresst_uint256 [value0, value1] (s₀, [headStart, dataEnd]) = s₉ → + Spec (C value0 value1 headStart dataEnd) s₀ s₉ + } := by + constructor + intros s₀ s₉ value0 value1 headStart dataEnd fuel + unfold abi_decode_addresst_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSlt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_7164014626810332831_abs_of_code if_7164014626810332831 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_user.lean new file mode 100644 index 00000000..3523e32c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_addresst_uint256_user.lean @@ -0,0 +1,27 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address +import Generated.erc20shim.ERC20Shim.abi_decode_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_addresst_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_decode_addresst_uint256 (value0 value1 : Identifier) (headStart dataEnd : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_addresst_uint256_abs_of_concrete {s₀ s₉ : State} {value0 value1 headStart dataEnd} : + Spec (abi_decode_addresst_uint256_concrete_of_code.1 value0 value1 headStart dataEnd) s₀ s₉ → + Spec (A_abi_decode_addresst_uint256 value0 value1 headStart dataEnd) s₀ s₉ := by + unfold abi_decode_addresst_uint256_concrete_of_code A_abi_decode_addresst_uint256 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_gen.lean new file mode 100644 index 00000000..0151f5bb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_gen.lean @@ -0,0 +1,117 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_decode : FunctionDefinition := + +{ + let _1 := 0 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + {revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b()} +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { headStart dataEnd fuel}, + execCall fuel abi_decode [] (s₀, [headStart, dataEnd]) = s₉ → + Spec (C headStart dataEnd) s₀ s₉ + } := by + constructor + intros s₀ s₉ headStart dataEnd fuel + unfold abi_decode + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSlt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_7164014626810332831_abs_of_code if_7164014626810332831 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address.lean b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address.lean new file mode 100644 index 00000000..fa98ba7c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_decode_tuple_address_abs_of_code {s₀ s₉ : State} {value0 headStart dataEnd} {fuel : Nat} : + execCall fuel abi_decode_tuple_address [value0] (s₀, [headStart, dataEnd]) = s₉ → + Spec (A_abi_decode_tuple_address value0 headStart dataEnd) s₀ s₉ +:= λ h ↦ abi_decode_tuple_address_abs_of_concrete (abi_decode_tuple_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_gen.lean new file mode 100644 index 00000000..47407465 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_gen.lean @@ -0,0 +1,131 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_decode_tuple_address : FunctionDefinition := value0 + +{ + let _1 := 32 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + {revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b()} + value0 := abi_decode_address(headStart, dataEnd) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_tuple_address_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value0 headStart dataEnd fuel}, + execCall fuel abi_decode_tuple_address [value0] (s₀, [headStart, dataEnd]) = s₉ → + Spec (C value0 headStart dataEnd) s₀ s₉ + } := by + constructor + intros s₀ s₉ value0 headStart dataEnd fuel + unfold abi_decode_tuple_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSlt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_7164014626810332831_abs_of_code if_7164014626810332831 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_decode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_user.lean new file mode 100644 index 00000000..ccfc0270 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_tuple_address_user.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b +import Generated.erc20shim.ERC20Shim.abi_decode_address + +import Generated.erc20shim.ERC20Shim.abi_decode_tuple_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_decode_tuple_address (value0 : Identifier) (headStart dataEnd : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_tuple_address_abs_of_concrete {s₀ s₉ : State} {value0 headStart dataEnd} : + Spec (abi_decode_tuple_address_concrete_of_code.1 value0 headStart dataEnd) s₀ s₉ → + Spec (A_abi_decode_tuple_address value0 headStart dataEnd) s₀ s₉ := by + unfold abi_decode_tuple_address_concrete_of_code A_abi_decode_tuple_address + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_decode_uint256.lean new file mode 100644 index 00000000..378ad62c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_uint256.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_decode_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_decode_uint256_abs_of_code {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn} {fuel : Nat} : + execCall fuel abi_decode_uint256 [value] (s₀, [offset, end_clear_sanitised_hrafn]) = s₉ → + Spec (A_abi_decode_uint256 value offset end_clear_sanitised_hrafn) s₀ s₉ +:= λ h ↦ abi_decode_uint256_abs_of_concrete (abi_decode_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_decode_uint256_gen.lean new file mode 100644 index 00000000..10f1d4ba --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_uint256_gen.lean @@ -0,0 +1,107 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_decode_uint256 : FunctionDefinition := value + +{ + value := calldataload(offset) + validator_revert_uint256(value) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_decode_uint256_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn fuel}, + execCall fuel abi_decode_uint256 [value] (s₀, [offset, end_clear_sanitised_hrafn]) = s₉ → + Spec (C value offset end_clear_sanitised_hrafn) s₀ s₉ + } := by + constructor + intros s₀ s₉ value offset end_clear_sanitised_hrafn fuel + unfold abi_decode_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMCalldataload'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (validator_revert_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_uint256_user.lean new file mode 100644 index 00000000..c1de9723 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_uint256_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256 + +import Generated.erc20shim.ERC20Shim.abi_decode_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_decode_uint256 (value : Identifier) (offset end_clear_sanitised_hrafn : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_uint256_abs_of_concrete {s₀ s₉ : State} {value offset end_clear_sanitised_hrafn} : + Spec (abi_decode_uint256_concrete_of_code.1 value offset end_clear_sanitised_hrafn) s₀ s₉ → + Spec (A_abi_decode_uint256 value offset end_clear_sanitised_hrafn) s₀ s₉ := by + unfold abi_decode_uint256_concrete_of_code A_abi_decode_uint256 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_decode_user.lean b/Generated/erc20shim/ERC20Shim/abi_decode_user.lean new file mode 100644 index 00000000..b8235d06 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_decode_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_7164014626810332831 +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + +import Generated.erc20shim.ERC20Shim.abi_decode_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_decode (headStart dataEnd : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_decode_abs_of_concrete {s₀ s₉ : State} { headStart dataEnd} : + Spec (abi_decode_concrete_of_code.1 headStart dataEnd) s₀ s₉ → + Spec (A_abi_decode headStart dataEnd) s₀ s₉ := by + unfold abi_decode_concrete_of_code A_abi_decode + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address.lean new file mode 100644 index 00000000..2947fd65 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_address_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma abi_encode_address_abs_of_code {s₀ s₉ : State} { value pos} {fuel : Nat} : + execCall fuel abi_encode_address [] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_address value pos) s₀ s₉ +:= λ h ↦ abi_encode_address_abs_of_concrete (abi_encode_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address_gen.lean new file mode 100644 index 00000000..1408f79a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address_gen.lean @@ -0,0 +1,105 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def abi_encode_address : FunctionDefinition := + +{ + let _1 := sub(shl(160, 1), 1) + let _2 := and(value, _1) + mstore(pos, _2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_address_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value pos fuel}, + execCall fuel abi_encode_address [] (s₀, [value, pos]) = s₉ → + Spec (C value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ value pos fuel + unfold abi_encode_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256.lean new file mode 100644 index 00000000..518f1128 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_address_uint256_uint256_abs_of_code {s₀ s₉ : State} {tail headStart value0 value1 value2} {fuel : Nat} : + execCall fuel abi_encode_address_uint256_uint256 [tail] (s₀, [headStart, value0, value1, value2]) = s₉ → + Spec (A_abi_encode_address_uint256_uint256 tail headStart value0 value1 value2) s₀ s₉ +:= λ h ↦ abi_encode_address_uint256_uint256_abs_of_concrete (abi_encode_address_uint256_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_gen.lean new file mode 100644 index 00000000..d43c14ae --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_gen.lean @@ -0,0 +1,157 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_address_uint256_uint256 : FunctionDefinition := tail + +{ + let _1 := 96 + tail := add(headStart, _1) + abi_encode_address(value0, headStart) + let _2 := 32 + let _3 := add(headStart, _2) + abi_encode_uint256_to_uint256(value1, _3) + let _4 := 64 + let _5 := add(headStart, _4) + abi_encode_uint256_to_uint256(value2, _5) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_address_uint256_uint256_concrete_of_code +: { + C : + _ → _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 value1 value2 fuel}, + execCall fuel abi_encode_address_uint256_uint256 [tail] (s₀, [headStart, value0, value1, value2]) = s₉ → + Spec (C tail headStart value0 value1 value2) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 value1 value2 fuel + unfold abi_encode_address_uint256_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_user.lean new file mode 100644 index 00000000..0f01d408 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address_uint256_uint256_user.lean @@ -0,0 +1,163 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_address_uint256_uint256 (tail : Identifier) (headStart value0 value1 value2 : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + ( + (-- Case of no collision + let s := s₀⟦tail ↦ headStart + 96⟧ + preservesEvm s₀ s₉ ∧ + -- Second encode int + (Ok (EVMState.mstore + -- First encode int + (EVMState.mstore + -- Encode address + (EVMState.mstore s₀.evm headStart (Fin.land value0 (Fin.shiftLeft 1 160 - 1))) + (headStart+32) + value1) + (headStart+64) + value2) + s.store) = s₉ ∧ + s₉.evm.hash_collision = false + ) + -- Collision + ∨ s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 2500000 +set_option maxRecDepth 1000 + +lemma abi_encode_address_uint256_uint256_abs_of_concrete {s₀ s₉ : State} {tail headStart value0 value1 value2} : + Spec (abi_encode_address_uint256_uint256_concrete_of_code.1 tail headStart value0 value1 value2) s₀ s₉ → + Spec (A_abi_encode_address_uint256_uint256 tail headStart value0 value1 value2) s₀ s₉ := by + unfold abi_encode_address_uint256_uint256_concrete_of_code A_abi_encode_address_uint256_uint256 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + clr_varstore, + rintro hasFuel ⟨s, call_encode_address, ⟨s', call_encode_uint, ⟨s'', call_encode_uint', code⟩⟩⟩ + generalize s_inhabited_all : + (Ok evm₀ + Inhabited.default⟦"value2"↦value2⟧⟦"value1"↦value1⟧⟦"value0"↦value0⟧⟦"headStart"↦headStart⟧⟦"_1"↦96⟧⟦"tail"↦headStart + 96⟧) + = s_inhab at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + generalize s_new_evm : (mstore s_inhab.evm headStart (Fin.land value0 (Fin.shiftLeft 1 160 - 1))) + = s_evm_ at * + generalize s_new_varstore : s_inhab.store = s_varstore_ at * + + have sinhab_s0 : s_inhab.evm = s₀.evm := by aesop + + unfold A_abi_encode_address at call_encode_address + apply Spec_ok_unfold (by sorry) (by sorry) at call_encode_address + + unfold A_abi_encode_uint256_to_uint256 at call_encode_uint + have s_ok : s.isOk := by aesop + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + unfold lookup! at call_encode_uint + simp [s_all] at call_encode_uint + apply Spec_ok_unfold (by sorry) (by sorry) at call_encode_uint + + unfold A_abi_encode_uint256_to_uint256 at call_encode_uint' + have s'_ok : s'.isOk := by aesop + obtain ⟨s'_evm, ⟨s'_varstore, s'_all⟩⟩ := State_of_isOk s'_ok + unfold lookup! at call_encode_uint' + simp [s'_all] at call_encode_uint' + apply Spec_ok_unfold (by sorry) (by sorry) at call_encode_uint' + + unfold reviveJump at code + have s''_ok : s''.isOk := by aesop + obtain ⟨s''_evm, ⟨s''_varstore, s''_all⟩⟩ := State_of_isOk s''_ok + unfold lookup! at code + simp [s''_all, ←s0_all] at code + + generalize s'_new_evm : (mstore + (Ok s_evm + (Finmap.insert "_3" ((Finmap.lookup "headStart" (Finmap.insert "_2" 32 s_varstore)).get! + 32) + (Finmap.insert "_2" 32 s_varstore))).evm + ((Finmap.lookup "headStart" (Finmap.insert "_2" 32 s_varstore)).get! + 32) + (Finmap.lookup "value1" + (Finmap.insert "_3" ((Finmap.lookup "headStart" (Finmap.insert "_2" 32 s_varstore)).get! + 32) + (Finmap.insert "_2" 32 s_varstore))).get!) = s'_evm_ at * + generalize s'_new_varstore : (Ok s_evm + (Finmap.insert "_3" ((Finmap.lookup "headStart" (Finmap.insert "_2" 32 s_varstore)).get! + 32) + (Finmap.insert "_2" 32 s_varstore))).store = s'_varstore_ at * + + generalize s''_new_evm : (mstore + (Ok s'_evm + (Finmap.insert "_5" ((Finmap.lookup "headStart" (Finmap.insert "_4" 64 s'_varstore)).get! + 64) + (Finmap.insert "_4" 64 s'_varstore))).evm + ((Finmap.lookup "headStart" (Finmap.insert "_4" 64 s'_varstore)).get! + 64) + (Finmap.lookup "value2" + (Finmap.insert "_5" ((Finmap.lookup "headStart" (Finmap.insert "_4" 64 s'_varstore)).get! + 64) + (Finmap.insert "_4" 64 s'_varstore))).get!) = s''_evm_ at * + generalize s''_new_varstore : (Ok s'_evm + (Finmap.insert "_5" ((Finmap.lookup "headStart" (Finmap.insert "_4" 64 s'_varstore)).get! + 64) + (Finmap.insert "_4" 64 s'_varstore))).store = s''_varstore_ at * + + obtain ⟨s_ok, ⟨sinhab_no_collision, sinhab_collision⟩⟩ + := call_encode_address + + by_cases no_sinhab_collision : s_inhab.evm.hash_collision = false + + · simp [no_sinhab_collision] at sinhab_no_collision + obtain ⟨sinhab_s_preservesEvm, s_new, s_no_collision⟩ := sinhab_no_collision + + obtain ⟨s'_ok, ⟨s_no_collision, s_collision⟩⟩ + := call_encode_uint + + · by_cases no_s_collision : s.evm.hash_collision = false + + · have : s_evm.hash_collision = false := by aesop + simp [this] at s_no_collision + obtain ⟨s_s'_preservesEvm, s'_new, s'_no_collision⟩ := s_no_collision + + obtain ⟨s''_ok, ⟨s'_no_collision, s'_collision⟩⟩ + := call_encode_uint' + + · by_cases no_s'_collision : s'.evm.hash_collision = false + + · have : s'_evm.hash_collision = false := by aesop + simp [this] at s'_no_collision + obtain ⟨s'_s''_preservesEvm, s''_new, s''_no_collision⟩ := s'_no_collision + · + split_ands + · rw[←code] + simp + · left + split_ands + · rw[←code] + apply preservesEvm_trans s'_ok + · apply preservesEvm_trans s_ok + · aesop + · aesop + · aesop + · rw[←code] + simp + split_ands + · aesop + · aesop + · aesop + · aesop + · aesop + · aesop + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_address_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_address_user.lean new file mode 100644 index 00000000..380fe9bc --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_address_user.lean @@ -0,0 +1,89 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_abi_encode_address (value pos : Literal) (s₀ s₉ : State) : Prop := + + s₉.isOk ∧ + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + (-- Case 1.1 No hash collision in function + preservesEvm s₀ s₉ ∧ + (Ok (EVMState.mstore s₀.evm pos (Fin.land value (Fin.shiftLeft 1 160 - 1))) s₀.store) = s₉ ∧ + s₉.evm.hash_collision = false + ) + -- Case 1.2 collision in function + ∨ s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma abi_encode_address_abs_of_concrete {s₀ s₉ : State} { value pos} : + Spec (abi_encode_address_concrete_of_code.1 value pos) s₀ s₉ → + Spec (A_abi_encode_address value pos) s₀ s₉ := by + unfold abi_encode_address_concrete_of_code A_abi_encode_address + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel code + + generalize s_inhabited_all : + (Ok evm₀ Inhabited.default⟦"pos"↦pos⟧⟦"value"↦value⟧) = s_inhabited at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold reviveJump at code + rw[←s_inhabited_all, ←s0_all] at code + rw[EVMShl'] at code + unfold multifill at code + unfold setEvm at code + unfold lookup! at code + simp at code + rw [State.insert_of_ok] at code + rw [State.insert_of_ok] at code + rw [State.insert_of_ok] at code + simp at code + rw [State.insert_of_ok] at code + simp at code + generalize val_arg : (Fin.land value (Fin.shiftLeft 1 160 - 1)) = value_arg at * + generalize lkup_arg : (Finmap.lookup "pos" _) = lookup_arg at * + + have s0_s9_preservesEvm : preservesEvm s₀ s₉ := by + rw [←s0_all, ←code ] + unfold preservesEvm + have : Preserved evm₀ (mstore evm₀ lookup_arg.get! value_arg) := by + apply mstore_preserved + aesop + + split_ands + + · aesop + · by_cases s0_collision : evm₀.hash_collision + · intro s0_no_collision + right + aesop + · intro s0_no_collision + left + split_ands + · exact s0_s9_preservesEvm + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool.lean new file mode 100644 index 00000000..027a0d4b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_bool_abs_of_code {s₀ s₉ : State} {tail headStart value0} {fuel : Nat} : + execCall fuel abi_encode_bool [tail] (s₀, [headStart, value0]) = s₉ → + Spec (A_abi_encode_bool tail headStart value0) s₀ s₉ +:= λ h ↦ abi_encode_bool_abs_of_concrete (abi_encode_bool_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool_gen.lean new file mode 100644 index 00000000..af224c19 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool_gen.lean @@ -0,0 +1,110 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_bool : FunctionDefinition := tail + +{ + let _1 := 32 + tail := add(headStart, _1) + abi_encode_bool_to_bool(value0, headStart) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_bool_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 fuel}, + execCall fuel abi_encode_bool [tail] (s₀, [headStart, value0]) = s₉ → + Spec (C tail headStart value0) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 fuel + unfold abi_encode_bool + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_bool_to_bool_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool.lean new file mode 100644 index 00000000..600c2696 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma abi_encode_bool_to_bool_abs_of_code {s₀ s₉ : State} { value pos} {fuel : Nat} : + execCall fuel abi_encode_bool_to_bool [] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_bool_to_bool value pos) s₀ s₉ +:= λ h ↦ abi_encode_bool_to_bool_abs_of_concrete (abi_encode_bool_to_bool_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_gen.lean new file mode 100644 index 00000000..e1177522 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_gen.lean @@ -0,0 +1,105 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def abi_encode_bool_to_bool : FunctionDefinition := + +{ + let _1 := iszero(value) + let _2 := iszero(_1) + mstore(pos, _2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_bool_to_bool_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value pos fuel}, + execCall fuel abi_encode_bool_to_bool [] (s₀, [value, pos]) = s₉ → + Spec (C value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ value pos fuel + unfold abi_encode_bool_to_bool + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_user.lean new file mode 100644 index 00000000..8f51251e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool_to_bool_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_abi_encode_bool_to_bool (value pos : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_bool_to_bool_abs_of_concrete {s₀ s₉ : State} { value pos} : + Spec (abi_encode_bool_to_bool_concrete_of_code.1 value pos) s₀ s₉ → + Spec (A_abi_encode_bool_to_bool value pos) s₀ s₉ := by + unfold abi_encode_bool_to_bool_concrete_of_code A_abi_encode_bool_to_bool + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_bool_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_bool_user.lean new file mode 100644 index 00000000..b81ad83f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_bool_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_to_bool + +import Generated.erc20shim.ERC20Shim.abi_encode_bool_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_bool (tail : Identifier) (headStart value0 : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_bool_abs_of_concrete {s₀ s₉ : State} {tail headStart value0} : + Spec (abi_encode_bool_concrete_of_code.1 tail headStart value0) s₀ s₉ → + Spec (A_abi_encode_bool tail headStart value0) s₀ s₉ := by + unfold abi_encode_bool_concrete_of_code A_abi_encode_bool + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string.lean new file mode 100644 index 00000000..c6be116a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr + +import Generated.erc20shim.ERC20Shim.abi_encode_string_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_string_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_string_abs_of_code {s₀ s₉ : State} {tail headStart value0} {fuel : Nat} : + execCall fuel abi_encode_string [tail] (s₀, [headStart, value0]) = s₉ → + Spec (A_abi_encode_string tail headStart value0) s₀ s₉ +:= λ h ↦ abi_encode_string_abs_of_concrete (abi_encode_string_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_gen.lean new file mode 100644 index 00000000..5f1cc73a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_gen.lean @@ -0,0 +1,117 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_string : FunctionDefinition := tail + +{ + let _1 := 32 + tail := add(headStart, _1) + let _2 := _1 + mstore(headStart, _1) + tail := abi_encode_string_memory_ptr(value0, tail) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_string_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 fuel}, + execCall fuel abi_encode_string [tail] (s₀, [headStart, value0]) = s₉ → + Spec (C tail headStart value0) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 fuel + unfold abi_encode_string + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_string_memory_ptr_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr.lean new file mode 100644 index 00000000..57f23931 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_string_memory_ptr_abs_of_code {s₀ s₉ : State} {end_clear_sanitised_hrafn value pos} {fuel : Nat} : + execCall fuel abi_encode_string_memory_ptr [end_clear_sanitised_hrafn] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_string_memory_ptr end_clear_sanitised_hrafn value pos) s₀ s₉ +:= λ h ↦ abi_encode_string_memory_ptr_abs_of_concrete (abi_encode_string_memory_ptr_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_gen.lean new file mode 100644 index 00000000..95219b68 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_gen.lean @@ -0,0 +1,157 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_string_memory_ptr : FunctionDefinition := end_clear_sanitised_hrafn + +{ + let length := mload(value) + pos := array_storeLengthForEncoding_string_fromStack(pos, length) + let _1 := 32 + let _2 := add(value, _1) + copy_memory_to_memory_with_cleanup(_2, pos, length) + let _3 := not(31) + let _4 := 31 + let _5 := add(length, _4) + let _6 := and(_5, _3) + end_clear_sanitised_hrafn := add(pos, _6) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_string_memory_ptr_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {end_clear_sanitised_hrafn value pos fuel}, + execCall fuel abi_encode_string_memory_ptr [end_clear_sanitised_hrafn] (s₀, [value, pos]) = s₉ → + Spec (C end_clear_sanitised_hrafn value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ end_clear_sanitised_hrafn value pos fuel + unfold abi_encode_string_memory_ptr + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (array_storeLengthForEncoding_string_fromStack_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (copy_memory_to_memory_with_cleanup_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMNot'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_user.lean new file mode 100644 index 00000000..5f348b9e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_memory_ptr_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_string_memory_ptr (end_clear_sanitised_hrafn : Identifier) (value pos : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_string_memory_ptr_abs_of_concrete {s₀ s₉ : State} {end_clear_sanitised_hrafn value pos} : + Spec (abi_encode_string_memory_ptr_concrete_of_code.1 end_clear_sanitised_hrafn value pos) s₀ s₉ → + Spec (A_abi_encode_string_memory_ptr end_clear_sanitised_hrafn value pos) s₀ s₉ := by + unfold abi_encode_string_memory_ptr_concrete_of_code A_abi_encode_string_memory_ptr + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_storage.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage.lean new file mode 100644 index 00000000..508cb074 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348 +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma abi_encode_string_storage_abs_of_code {s₀ s₉ : State} {ret value pos} {fuel : Nat} : + execCall fuel abi_encode_string_storage [ret] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_string_storage ret value pos) s₀ s₉ +:= λ h ↦ abi_encode_string_storage_abs_of_concrete (abi_encode_string_storage_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_gen.lean new file mode 100644 index 00000000..1f84e272 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_gen.lean @@ -0,0 +1,169 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348 +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def abi_encode_string_storage : FunctionDefinition := ret + +{ + let slotValue := sload(value) + let length := extract_byte_array_length(slotValue) + pos := array_storeLengthForEncoding_string(pos, length) + let _1 := 1 + let _2 := and(slotValue, _1) + switch _2 case 0 { + let _3 := not(255) + let _4 := and(slotValue, _3) + mstore(pos, _4) + let _5 := iszero(length) + let _6 := iszero(_5) + let _7 := shl(5, _6) + ret := add(pos, _7) + } + case 1 { + let dataPos := array_dataslot_string_storage(value) + let i := 0 + for { } lt(i, length) { + let _8 := 32 + i := add(i, _8) + } { + let _9 := sload(dataPos) + let _10 := add(pos, i) + mstore(_10, _9) + let _11 := _1 + dataPos := add(dataPos, _1) + } + ret := add(pos, i) + } + default + { } +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_string_storage_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {ret value pos fuel}, + execCall fuel abi_encode_string_storage [ret] (s₀, [value, pos]) = s₉ → + Spec (C ret value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ ret value pos fuel + unfold abi_encode_string_storage + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (extract_byte_array_length_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (array_storeLengthForEncoding_string_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract switch_8164987986085659348_abs_of_code switch_8164987986085659348 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_user.lean new file mode 100644 index 00000000..9e7dfe16 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_storage_user.lean @@ -0,0 +1,27 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string +import Generated.erc20shim.ERC20Shim.Common.switch_8164987986085659348 +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_abi_encode_string_storage (ret : Identifier) (value pos : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_string_storage_abs_of_concrete {s₀ s₉ : State} {ret value pos} : + Spec (abi_encode_string_storage_concrete_of_code.1 ret value pos) s₀ s₉ → + Spec (A_abi_encode_string_storage ret value pos) s₀ s₉ := by + unfold abi_encode_string_storage_concrete_of_code A_abi_encode_string_storage + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_string_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_string_user.lean new file mode 100644 index 00000000..d56dd56a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_string_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_memory_ptr + +import Generated.erc20shim.ERC20Shim.abi_encode_string_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_string (tail : Identifier) (headStart value0 : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_string_abs_of_concrete {s₀ s₉ : State} {tail headStart value0} : + Spec (abi_encode_string_concrete_of_code.1 tail headStart value0) s₀ s₉ → + Spec (A_abi_encode_string tail headStart value0) s₀ s₉ := by + unfold abi_encode_string_concrete_of_code A_abi_encode_string + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address.lean b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address.lean new file mode 100644 index 00000000..e77acaa0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_tuple_address_abs_of_code {s₀ s₉ : State} {tail headStart value0} {fuel : Nat} : + execCall fuel abi_encode_tuple_address [tail] (s₀, [headStart, value0]) = s₉ → + Spec (A_abi_encode_tuple_address tail headStart value0) s₀ s₉ +:= λ h ↦ abi_encode_tuple_address_abs_of_concrete (abi_encode_tuple_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_gen.lean new file mode 100644 index 00000000..7d1f8037 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_gen.lean @@ -0,0 +1,110 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_tuple_address : FunctionDefinition := tail + +{ + let _1 := 32 + tail := add(headStart, _1) + abi_encode_address(value0, headStart) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_tuple_address_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 fuel}, + execCall fuel abi_encode_tuple_address [tail] (s₀, [headStart, value0]) = s₉ → + Spec (C tail headStart value0) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 fuel + unfold abi_encode_tuple_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_user.lean new file mode 100644 index 00000000..e680559b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_tuple_address_user.lean @@ -0,0 +1,71 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_address + +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_tuple_address (tail : Identifier) (headStart value0 : Literal) (s₀ s₉ : State) : Prop := + + --Case of no collision + s₉.isOk ∧ + ( + --Case of no collision + let s := s₀⟦tail ↦ headStart + 32⟧ + (preservesEvm s₀ s₉ ∧ + (Ok (EVMState.mstore s₀.evm headStart (Fin.land value0 (Fin.shiftLeft 1 160 - 1))) s.store) = s₉ ∧ + s₉.evm.hash_collision = false) + + -- Case of collision + ∨ + s₉.evm.hash_collision = true + ) + +lemma abi_encode_tuple_address_abs_of_concrete {s₀ s₉ : State} {tail headStart value0} : + Spec (abi_encode_tuple_address_concrete_of_code.1 tail headStart value0) s₀ s₉ → + Spec (A_abi_encode_tuple_address tail headStart value0) s₀ s₉ := by + unfold abi_encode_tuple_address_concrete_of_code A_abi_encode_tuple_address + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel ⟨s, call_encode_address, code⟩ + + generalize s_inhabited_all : + (Ok evm₀ Inhabited.default⟦"value0"↦value0⟧⟦"headStart"↦headStart⟧⟦"_1"↦32⟧⟦"tail"↦Ok evm₀ + Inhabited.default⟦"value0"↦value0⟧⟦"headStart"↦headStart⟧⟦"_1"↦32⟧["headStart"]!! + + (Ok evm₀ Inhabited.default⟦"value0"↦value0⟧⟦"headStart"↦headStart⟧⟦"_1"↦32⟧["_1"]!!)⟧) = s_inhabited at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + have s0_ok : s₀.isOk := by aesop + have sinhab_ok : s_inhabited.isOk := by aesop + + unfold A_abi_encode_address at call_encode_address + clr_spec at call_encode_address + + obtain ⟨s_ok, s_no_collision, s_collision⟩ + := call_encode_address + + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + unfold reviveJump at code + simp [s_all, ←s0_all] at code + + by_cases no_s_collision : s_inhabited.evm.hash_collision = false + + · have : s_inhabited.evm.hash_collision = false := by aesop + simp [this] at s_no_collision + obtain ⟨sinhab_s_preservesEvm,s_new, s_no_collision⟩ := s_no_collision + all_goals aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256.lean new file mode 100644 index 00000000..e52a9fa9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_uint256_abs_of_code {s₀ s₉ : State} {tail headStart value0} {fuel : Nat} : + execCall fuel abi_encode_uint256 [tail] (s₀, [headStart, value0]) = s₉ → + Spec (A_abi_encode_uint256 tail headStart value0) s₀ s₉ +:= λ h ↦ abi_encode_uint256_abs_of_concrete (abi_encode_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_gen.lean new file mode 100644 index 00000000..3531b624 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_gen.lean @@ -0,0 +1,110 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_uint256 : FunctionDefinition := tail + +{ + let _1 := 32 + tail := add(headStart, _1) + abi_encode_uint256_to_uint256(value0, headStart) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_uint256_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 fuel}, + execCall fuel abi_encode_uint256 [tail] (s₀, [headStart, value0]) = s₉ → + Spec (C tail headStart value0) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 fuel + unfold abi_encode_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256.lean new file mode 100644 index 00000000..fa24cb26 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma abi_encode_uint256_to_uint256_abs_of_code {s₀ s₉ : State} { value pos} {fuel : Nat} : + execCall fuel abi_encode_uint256_to_uint256 [] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_uint256_to_uint256 value pos) s₀ s₉ +:= λ h ↦ abi_encode_uint256_to_uint256_abs_of_concrete (abi_encode_uint256_to_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_gen.lean new file mode 100644 index 00000000..8e9cfdfa --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_gen.lean @@ -0,0 +1,91 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def abi_encode_uint256_to_uint256 : FunctionDefinition := + +{mstore(pos, value)} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_uint256_to_uint256_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value pos fuel}, + execCall fuel abi_encode_uint256_to_uint256 [] (s₀, [value, pos]) = s₉ → + Spec (C value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ value pos fuel + unfold abi_encode_uint256_to_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_user.lean new file mode 100644 index 00000000..7a27acd8 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_to_uint256_user.lean @@ -0,0 +1,78 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_abi_encode_uint256_to_uint256 (value pos : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + (-- Case 1.1 No hash collision in function + preservesEvm s₀ s₉ ∧ + (Ok (EVMState.mstore s₀.evm pos value) s₀.store) = s₉ ∧ + s₉.evm.hash_collision = false + ) + -- Case 1.2 collision in function + ∨ s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma abi_encode_uint256_to_uint256_abs_of_concrete {s₀ s₉ : State} { value pos} : + Spec (abi_encode_uint256_to_uint256_concrete_of_code.1 value pos) s₀ s₉ → + Spec (A_abi_encode_uint256_to_uint256 value pos) s₀ s₉ := by + unfold abi_encode_uint256_to_uint256_concrete_of_code A_abi_encode_uint256_to_uint256 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel code + generalize s_inhabited_all : + (Ok evm₀ Inhabited.default⟦"pos"↦pos⟧⟦"value"↦value⟧) = s_inhabited at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold reviveJump at code + rw[←s_inhabited_all, ←s0_all] at code + unfold setEvm at code + unfold State.insert at code + simp at code + + extract_goal + have s0_s9_preservesEvm : preservesEvm s₀ s₉ := by + rw [←s0_all, ←code] + unfold preservesEvm + have : Preserved evm₀ (mstore evm₀ pos value) := by + apply mstore_preserved + aesop + + split_ands + + · aesop + · by_cases s0_collision : evm₀.hash_collision + · intro s0_no_collision + right + aesop + · intro s0_no_collision + left + split_ands + · exact s0_s9_preservesEvm + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint256_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_user.lean new file mode 100644 index 00000000..d628e1ca --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint256_user.lean @@ -0,0 +1,104 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_to_uint256 + +import Generated.erc20shim.ERC20Shim.abi_encode_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_uint256 (tail : Identifier) (headStart value0 : Literal) (s₀ s₉ : State) : Prop := + --Case of no collision + s₉.isOk ∧ + ( --Case 1 : no initial collision + s₀.evm.hash_collision = false → + ( + let s := s₀⟦tail ↦ headStart + 32⟧ + ( -- Case 1.1 : no collision in function + preservesEvm s₀ s₉ ∧ + (Ok (EVMState.mstore s₀.evm headStart value0) s.store) = s₉ ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.2 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma abi_encode_uint256_abs_of_concrete {s₀ s₉ : State} {tail headStart value0} : + Spec (abi_encode_uint256_concrete_of_code.1 tail headStart value0) s₀ s₉ → + Spec (A_abi_encode_uint256 tail headStart value0) s₀ s₉ := by + + unfold abi_encode_uint256_concrete_of_code A_abi_encode_uint256 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel ⟨s1, encode, code⟩ + generalize s_inhabited_all : + (Ok evm₀ Inhabited.default⟦"value0"↦value0⟧⟦"headStart"↦headStart⟧⟦"_1"↦32⟧) = s_inhabited at * + have sinhab_ok : s_inhabited.isOk := by aesop + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold A_abi_encode_uint256_to_uint256 at encode + clr_spec at encode + + clr_varstore, + have s1_ok : s1.isOk := by aesop + obtain ⟨s1_evm, ⟨s1_varstore, s1_all⟩⟩ := State_of_isOk s1_ok + + unfold reviveJump at code + simp[s1_all, ←s0_all] at code + + obtain ⟨s1_ok, no_collision, collision⟩ := encode + + split_ands + · aesop + · by_cases s0_collision : s₀.evm.hash_collision = false + · simp[s0_collision] + simp at no_collision + have : s_inhabited.evm.hash_collision = false := by aesop + simp[this] at no_collision + cases no_collision + · left + rw[←code] + split_ands + · + unfold lookup! + simp + have : preservesEvm s1 (Ok s1_evm (Finmap.insert tail (Finmap.lookup "tail" s1_varstore).get! varstore₀)) := by + simp[s1_all] + unfold preservesEvm + aesop + + have : preservesEvm (s_inhabited⟦"tail"↦s_inhabited["headStart"]!! + (s_inhabited["_1"]!!)⟧) s1 := by aesop + have sinhab__ok : (s_inhabited⟦"tail"↦s_inhabited["headStart"]!! + (s_inhabited["_1"]!!)⟧).isOk := by aesop + have : preservesEvm s_inhabited (s_inhabited⟦"tail"↦s_inhabited["headStart"]!! + (s_inhabited["_1"]!!)⟧) := by + simp[←s_inhabited_all] + unfold preservesEvm State.insert lookup! + aesop + have : preservesEvm s₀ s_inhabited := by aesop + have : preservesEvm s₀ (Ok s1_evm (Finmap.insert tail (Finmap.lookup "tail" s1_varstore).get! varstore₀)) := by + apply preservesEvm_trans s1_ok + · aesop + · aesop + aesop + · aesop + · aesop + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8.lean new file mode 100644 index 00000000..859d0261 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8 + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma abi_encode_uint8_abs_of_code {s₀ s₉ : State} {tail headStart value0} {fuel : Nat} : + execCall fuel abi_encode_uint8 [tail] (s₀, [headStart, value0]) = s₉ → + Spec (A_abi_encode_uint8 tail headStart value0) s₀ s₉ +:= λ h ↦ abi_encode_uint8_abs_of_concrete (abi_encode_uint8_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_gen.lean new file mode 100644 index 00000000..574723e3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_gen.lean @@ -0,0 +1,110 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def abi_encode_uint8 : FunctionDefinition := tail + +{ + let _1 := 32 + tail := add(headStart, _1) + abi_encode_uint8_to_uint8(value0, headStart) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_uint8_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {tail headStart value0 fuel}, + execCall fuel abi_encode_uint8 [tail] (s₀, [headStart, value0]) = s₉ → + Spec (C tail headStart value0) s₀ s₉ + } := by + constructor + intros s₀ s₉ tail headStart value0 fuel + unfold abi_encode_uint8 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint8_to_uint8_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8.lean new file mode 100644 index 00000000..0505e7df --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8_gen + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma abi_encode_uint8_to_uint8_abs_of_code {s₀ s₉ : State} { value pos} {fuel : Nat} : + execCall fuel abi_encode_uint8_to_uint8 [] (s₀, [value, pos]) = s₉ → + Spec (A_abi_encode_uint8_to_uint8 value pos) s₀ s₉ +:= λ h ↦ abi_encode_uint8_to_uint8_abs_of_concrete (abi_encode_uint8_to_uint8_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_gen.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_gen.lean new file mode 100644 index 00000000..7d71852a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_gen.lean @@ -0,0 +1,101 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def abi_encode_uint8_to_uint8 : FunctionDefinition := + +{ + let _1 := 255 + let _2 := and(value, _1) + mstore(pos, _2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def abi_encode_uint8_to_uint8_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value pos fuel}, + execCall fuel abi_encode_uint8_to_uint8 [] (s₀, [value, pos]) = s₉ → + Spec (C value pos) s₀ s₉ + } := by + constructor + intros s₀ s₉ value pos fuel + unfold abi_encode_uint8_to_uint8 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_user.lean new file mode 100644 index 00000000..e82c9538 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_to_uint8_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_abi_encode_uint8_to_uint8 (value pos : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_uint8_to_uint8_abs_of_concrete {s₀ s₉ : State} { value pos} : + Spec (abi_encode_uint8_to_uint8_concrete_of_code.1 value pos) s₀ s₉ → + Spec (A_abi_encode_uint8_to_uint8 value pos) s₀ s₉ := by + unfold abi_encode_uint8_to_uint8_concrete_of_code A_abi_encode_uint8_to_uint8 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/abi_encode_uint8_user.lean b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_user.lean new file mode 100644 index 00000000..97d8dad7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/abi_encode_uint8_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_to_uint8 + +import Generated.erc20shim.ERC20Shim.abi_encode_uint8_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_abi_encode_uint8 (tail : Identifier) (headStart value0 : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma abi_encode_uint8_abs_of_concrete {s₀ s₉ : State} {tail headStart value0} : + Spec (abi_encode_uint8_concrete_of_code.1 tail headStart value0) s₀ s₉ → + Spec (A_abi_encode_uint8 tail headStart value0) s₀ s₉ := by + unfold abi_encode_uint8_concrete_of_code A_abi_encode_uint8 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage.lean b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage.lean new file mode 100644 index 00000000..b1ce4f8a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage_gen + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma array_dataslot_string_storage_abs_of_code {s₀ s₉ : State} {data ptr} {fuel : Nat} : + execCall fuel array_dataslot_string_storage [data] (s₀, [ptr]) = s₉ → + Spec (A_array_dataslot_string_storage data ptr) s₀ s₉ +:= λ h ↦ array_dataslot_string_storage_abs_of_concrete (array_dataslot_string_storage_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_gen.lean b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_gen.lean new file mode 100644 index 00000000..59340dff --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_gen.lean @@ -0,0 +1,105 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def array_dataslot_string_storage : FunctionDefinition := data + +{ + let _1 := 0 + mstore(_1, ptr) + let _2 := 32 + let _3 := _1 + data := keccak256(_1, _2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def array_dataslot_string_storage_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {data ptr fuel}, + execCall fuel array_dataslot_string_storage [data] (s₀, [ptr]) = s₉ → + Spec (C data ptr) s₀ s₉ + } := by + constructor + intros s₀ s₉ data ptr fuel + unfold array_dataslot_string_storage + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMKeccak256'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_user.lean b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_user.lean new file mode 100644 index 00000000..69e62c55 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_dataslot_string_storage_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_dataslot_string_storage_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_array_dataslot_string_storage (data : Identifier) (ptr : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma array_dataslot_string_storage_abs_of_concrete {s₀ s₉ : State} {data ptr} : + Spec (array_dataslot_string_storage_concrete_of_code.1 data ptr) s₀ s₉ → + Spec (A_array_dataslot_string_storage data ptr) s₀ s₉ := by + unfold array_dataslot_string_storage_concrete_of_code A_array_dataslot_string_storage + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string.lean new file mode 100644 index 00000000..f90c6ddf --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_gen + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma array_storeLengthForEncoding_string_abs_of_code {s₀ s₉ : State} {updated_pos pos length} {fuel : Nat} : + execCall fuel array_storeLengthForEncoding_string [updated_pos] (s₀, [pos, length]) = s₉ → + Spec (A_array_storeLengthForEncoding_string updated_pos pos length) s₀ s₉ +:= λ h ↦ array_storeLengthForEncoding_string_abs_of_concrete (array_storeLengthForEncoding_string_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack.lean new file mode 100644 index 00000000..9e1dabca --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack_gen + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma array_storeLengthForEncoding_string_fromStack_abs_of_code {s₀ s₉ : State} {updated_pos pos length} {fuel : Nat} : + execCall fuel array_storeLengthForEncoding_string_fromStack [updated_pos] (s₀, [pos, length]) = s₉ → + Spec (A_array_storeLengthForEncoding_string_fromStack updated_pos pos length) s₀ s₉ +:= λ h ↦ array_storeLengthForEncoding_string_fromStack_abs_of_concrete (array_storeLengthForEncoding_string_fromStack_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_gen.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_gen.lean new file mode 100644 index 00000000..e69e5793 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_gen.lean @@ -0,0 +1,101 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def array_storeLengthForEncoding_string_fromStack : FunctionDefinition := updated_pos + +{ + mstore(pos, length) + let _1 := 32 + updated_pos := add(pos, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def array_storeLengthForEncoding_string_fromStack_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {updated_pos pos length fuel}, + execCall fuel array_storeLengthForEncoding_string_fromStack [updated_pos] (s₀, [pos, length]) = s₉ → + Spec (C updated_pos pos length) s₀ s₉ + } := by + constructor + intros s₀ s₉ updated_pos pos length fuel + unfold array_storeLengthForEncoding_string_fromStack + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_user.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_user.lean new file mode 100644 index 00000000..7d56206e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_fromStack_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_fromStack_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_array_storeLengthForEncoding_string_fromStack (updated_pos : Identifier) (pos length : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma array_storeLengthForEncoding_string_fromStack_abs_of_concrete {s₀ s₉ : State} {updated_pos pos length} : + Spec (array_storeLengthForEncoding_string_fromStack_concrete_of_code.1 updated_pos pos length) s₀ s₉ → + Spec (A_array_storeLengthForEncoding_string_fromStack updated_pos pos length) s₀ s₉ := by + unfold array_storeLengthForEncoding_string_fromStack_concrete_of_code A_array_storeLengthForEncoding_string_fromStack + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_gen.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_gen.lean new file mode 100644 index 00000000..6fb346eb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_gen.lean @@ -0,0 +1,101 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def array_storeLengthForEncoding_string : FunctionDefinition := updated_pos + +{ + mstore(pos, length) + let _1 := 32 + updated_pos := add(pos, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def array_storeLengthForEncoding_string_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {updated_pos pos length fuel}, + execCall fuel array_storeLengthForEncoding_string [updated_pos] (s₀, [pos, length]) = s₉ → + Spec (C updated_pos pos length) s₀ s₉ + } := by + constructor + intros s₀ s₉ updated_pos pos length fuel + unfold array_storeLengthForEncoding_string + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_user.lean b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_user.lean new file mode 100644 index 00000000..62335f18 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/array_storeLengthForEncoding_string_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.array_storeLengthForEncoding_string_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_array_storeLengthForEncoding_string (updated_pos : Identifier) (pos length : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma array_storeLengthForEncoding_string_abs_of_concrete {s₀ s₉ : State} {updated_pos pos length} : + Spec (array_storeLengthForEncoding_string_concrete_of_code.1 updated_pos pos length) s₀ s₉ → + Spec (A_array_storeLengthForEncoding_string updated_pos pos length) s₀ s₉ := by + unfold array_storeLengthForEncoding_string_concrete_of_code A_array_storeLengthForEncoding_string + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/checked_add_uint256.lean b/Generated/erc20shim/ERC20Shim/checked_add_uint256.lean new file mode 100644 index 00000000..08dc22a4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/checked_add_uint256.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933 +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + +import Generated.erc20shim.ERC20Shim.checked_add_uint256_gen + +import Generated.erc20shim.ERC20Shim.checked_add_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma checked_add_uint256_abs_of_code {s₀ s₉ : State} {sum x y} {fuel : Nat} : + execCall fuel checked_add_uint256 [sum] (s₀, [x, y]) = s₉ → + Spec (A_checked_add_uint256 sum x y) s₀ s₉ +:= λ h ↦ checked_add_uint256_abs_of_concrete (checked_add_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/checked_add_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/checked_add_uint256_gen.lean new file mode 100644 index 00000000..701f8e4d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/checked_add_uint256_gen.lean @@ -0,0 +1,119 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933 +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def checked_add_uint256 : FunctionDefinition := sum + +{ + x := x + y := y + sum := add(x, y) + let _1 := gt(x, sum) + if _1 + {panic_error_0x11()} +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def checked_add_uint256_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {sum x y fuel}, + execCall fuel checked_add_uint256 [sum] (s₀, [x, y]) = s₉ → + Spec (C sum x y) s₀ s₉ + } := by + constructor + intros s₀ s₉ sum x y fuel + unfold checked_add_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMGt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_2792370840247009933_abs_of_code if_2792370840247009933 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/checked_add_uint256_user.lean b/Generated/erc20shim/ERC20Shim/checked_add_uint256_user.lean new file mode 100644 index 00000000..f94215f7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/checked_add_uint256_user.lean @@ -0,0 +1,159 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_2792370840247009933 +import Generated.erc20shim.ERC20Shim.panic_error_0x11 + +import Generated.erc20shim.ERC20Shim.checked_add_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_checked_add_uint256 (sum : Identifier) (x y : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : Reversion + preservesEvm s₀ s₉ ∧ + s₉.evm.reverted = true ∧ + x > s₉[sum]!! ∧ + s₉.evm.hash_collision = false + ) + ∨ + ( -- Case 1.2 : No Reversion + preservesEvm s₀ s₉ ∧ + x ≤ s₉[sum]!! ∧ + s₉.evm.hash_collision = false + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 1000000 + +lemma checked_add_uint256_abs_of_concrete {s₀ s₉ : State} {sum x y} : + Spec (checked_add_uint256_concrete_of_code.1 sum x y) s₀ s₉ → + Spec (A_checked_add_uint256 sum x y) s₀ s₉ := by + + unfold checked_add_uint256_concrete_of_code A_checked_add_uint256 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + clr_varstore, + rintro hasFuel ⟨s, call_if, code⟩ + + generalize sinhab_all : + (Ok evm₀ Inhabited.default⟦"y"↦y⟧⟦"x"↦x⟧⟦"x"↦x⟧⟦"y"↦y⟧⟦"sum"↦x + y⟧⟦"_1"↦(decide (x + y < x)).toUInt256⟧) + = sinhab at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + have s0_sinhab_preservesEvm : preservesEvm s₀ sinhab := by + unfold preservesEvm + simp [←s0_all, ←sinhab_all] + unfold State.insert + simp + + unfold A_if_2792370840247009933 at call_if + clr_spec at call_if + + obtain ⟨s_ok, s_no_collision, s_collision⟩ := call_if + + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + unfold reviveJump at code + simp [←s0_all, s_all] at code + + by_cases collision_s0 : s₀.evm.hash_collision = false + + · -- no collision at s₀ + have : sinhab.evm.hash_collision = false := by aesop + simp[this] at s_no_collision + + obtain ⟨sinhab_s_preservesEvm, mstore, reversion, store_eq, s_no_collision⟩ | + ⟨sinhab_s_preservesEvm, reversion, s_store, s_no_collision⟩ | + collision_s := s_no_collision + · -- Reverted + have : ¬sinhab["_1"]!! = 0 → (decide (x + y < x)).toUInt256 ≠ 0 := by + simp + unfold lookup! + simp[←sinhab_all] + unfold State.insert + simp + + have : (decide (x + y < x)).toUInt256 ≠ 0 → x + y < x := by + unfold Bool.toUInt256 + simp + + split_ands + · aesop + · simp[collision_s0] + left + split_ands + · aesop + · aesop + · unfold lookup! + simp[←code] + unfold lookup! + simp + unfold State.insert at sinhab_all + simp at sinhab_all + have : s_varstore = (Finmap.insert "_1" (decide (x + y < x)).toUInt256 + (Finmap.insert "sum" (x + y) + (Finmap.insert "y" y (Finmap.insert "x" x (Finmap.insert "y" y Inhabited.default))))) := by aesop + simp[this] + aesop + · aesop + · aesop + · -- Not Reverted + + have h1 : sinhab["_1"]!! = 0 → (decide (x + y < x)).toUInt256 = 0 := by + simp + unfold lookup! + simp[←sinhab_all] + unfold State.insert + simp + + have h2 : (decide (x + y < x)).toUInt256 = 0 → x ≤ x + y := by + unfold Bool.toUInt256 + simp + + split_ands + · aesop + · simp[collision_s0] + right + left + split_ands + · aesop + · rw[←code] + unfold lookup! + simp + unfold State.insert at sinhab_all + simp at sinhab_all + have : s_varstore = (Finmap.insert "_1" (decide (x + y < x)).toUInt256 + (Finmap.insert "sum" (x + y) + (Finmap.insert "y" y (Finmap.insert "x" x (Finmap.insert "y" y Inhabited.default))))) := by aesop + simp[this] + have : x ≤ x + y := by aesop + aesop + · aesop + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string.lean b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string.lean new file mode 100644 index 00000000..ffaa2345 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage +import Generated.erc20shim.ERC20Shim.finalize_allocation + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string_gen + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma copy_array_from_storage_to_memory_string_abs_of_code {s₀ s₉ : State} {memPtr slot} {fuel : Nat} : + execCall fuel copy_array_from_storage_to_memory_string [memPtr] (s₀, [slot]) = s₉ → + Spec (A_copy_array_from_storage_to_memory_string memPtr slot) s₀ s₉ +:= λ h ↦ copy_array_from_storage_to_memory_string_abs_of_concrete (copy_array_from_storage_to_memory_string_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_gen.lean b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_gen.lean new file mode 100644 index 00000000..7193177f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_gen.lean @@ -0,0 +1,130 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage +import Generated.erc20shim.ERC20Shim.finalize_allocation + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def copy_array_from_storage_to_memory_string : FunctionDefinition := memPtr + +{ + let _1 := 64 + memPtr := mload(_1) + let _2 := abi_encode_string_storage(slot, memPtr) + let _3 := sub(_2, memPtr) + finalize_allocation(memPtr, _3) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def copy_array_from_storage_to_memory_string_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {memPtr slot fuel}, + execCall fuel copy_array_from_storage_to_memory_string [memPtr] (s₀, [slot]) = s₉ → + Spec (C memPtr slot) s₀ s₉ + } := by + constructor + intros s₀ s₉ memPtr slot fuel + unfold copy_array_from_storage_to_memory_string + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_string_storage_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (finalize_allocation_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_user.lean b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_user.lean new file mode 100644 index 00000000..db98dc93 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_array_from_storage_to_memory_string_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.abi_encode_string_storage +import Generated.erc20shim.ERC20Shim.finalize_allocation + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_copy_array_from_storage_to_memory_string (memPtr : Identifier) (slot : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma copy_array_from_storage_to_memory_string_abs_of_concrete {s₀ s₉ : State} {memPtr slot} : + Spec (copy_array_from_storage_to_memory_string_concrete_of_code.1 memPtr slot) s₀ s₉ → + Spec (A_copy_array_from_storage_to_memory_string memPtr slot) s₀ s₉ := by + unfold copy_array_from_storage_to_memory_string_concrete_of_code A_copy_array_from_storage_to_memory_string + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup.lean b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup.lean new file mode 100644 index 00000000..83d14dba --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335 + +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup_gen + +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +lemma copy_memory_to_memory_with_cleanup_abs_of_code {s₀ s₉ : State} { src dst length} {fuel : Nat} : + execCall fuel copy_memory_to_memory_with_cleanup [] (s₀, [src, dst, length]) = s₉ → + Spec (A_copy_memory_to_memory_with_cleanup src dst length) s₀ s₉ +:= λ h ↦ copy_memory_to_memory_with_cleanup_abs_of_concrete (copy_memory_to_memory_with_cleanup_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_gen.lean b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_gen.lean new file mode 100644 index 00000000..72e2b69d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_gen.lean @@ -0,0 +1,126 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def copy_memory_to_memory_with_cleanup : FunctionDefinition := + +{ + let i := 0 + for { } lt(i, length) { + let _1 := 32 + i := add(i, _1) + } { + let _2 := add(src, i) + let _3 := mload(_2) + let _4 := add(dst, i) + mstore(_4, _3) + } + let _5 := 0 + let _6 := add(dst, length) + mstore(_6, _5) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def copy_memory_to_memory_with_cleanup_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { src dst length fuel}, + execCall fuel copy_memory_to_memory_with_cleanup [] (s₀, [src, dst, length]) = s₉ → + Spec (C src dst length) s₀ s₉ + } := by + constructor + intros s₀ s₉ src dst length fuel + unfold copy_memory_to_memory_with_cleanup + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract for_6088573059593786335_abs_of_code for_6088573059593786335 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_user.lean b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_user.lean new file mode 100644 index 00000000..0904d840 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/copy_memory_to_memory_with_cleanup_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.for_6088573059593786335 + +import Generated.erc20shim.ERC20Shim.copy_memory_to_memory_with_cleanup_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def A_copy_memory_to_memory_with_cleanup (src dst length : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma copy_memory_to_memory_with_cleanup_abs_of_concrete {s₀ s₉ : State} { src dst length} : + Spec (copy_memory_to_memory_with_cleanup_concrete_of_code.1 src dst length) s₀ s₉ → + Spec (A_copy_memory_to_memory_with_cleanup src dst length) s₀ s₉ := by + unfold copy_memory_to_memory_with_cleanup_concrete_of_code A_copy_memory_to_memory_with_cleanup + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/extract_byte_array_length.lean b/Generated/erc20shim/ERC20Shim/extract_byte_array_length.lean new file mode 100644 index 00000000..27ad43a5 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/extract_byte_array_length.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172 +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899 +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length_gen + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma extract_byte_array_length_abs_of_code {s₀ s₉ : State} {length data} {fuel : Nat} : + execCall fuel extract_byte_array_length [length] (s₀, [data]) = s₉ → + Spec (A_extract_byte_array_length length data) s₀ s₉ +:= λ h ↦ extract_byte_array_length_abs_of_concrete (extract_byte_array_length_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/extract_byte_array_length_gen.lean b/Generated/erc20shim/ERC20Shim/extract_byte_array_length_gen.lean new file mode 100644 index 00000000..ee7ec0c2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/extract_byte_array_length_gen.lean @@ -0,0 +1,158 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172 +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899 +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def extract_byte_array_length : FunctionDefinition := length + +{ + let _1 := 1 + length := shr(_1, data) + let _2 := _1 + let outOfPlaceEncoding := and(data, _1) + let _3 := iszero(outOfPlaceEncoding) + if _3 + { + let _4 := 127 + length := and(length, _4) + } + let _5 := 32 + let _6 := lt(length, _5) + let _7 := eq(outOfPlaceEncoding, _6) + if _7 + {panic_error_0x22()} +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def extract_byte_array_length_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {length data fuel}, + execCall fuel extract_byte_array_length [length] (s₀, [data]) = s₉ → + Spec (C length data) s₀ s₉ + } := by + constructor + intros s₀ s₉ length data fuel + unfold extract_byte_array_length + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShr'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_4024499920364541172_abs_of_code if_4024499920364541172 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMLt'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMEq'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_384845947645085899_abs_of_code if_384845947645085899 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/extract_byte_array_length_user.lean b/Generated/erc20shim/ERC20Shim/extract_byte_array_length_user.lean new file mode 100644 index 00000000..16cc46ad --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/extract_byte_array_length_user.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_4024499920364541172 +import Generated.erc20shim.ERC20Shim.Common.if_384845947645085899 +import Generated.erc20shim.ERC20Shim.panic_error_0x22 + +import Generated.erc20shim.ERC20Shim.extract_byte_array_length_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_extract_byte_array_length (length : Identifier) (data : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma extract_byte_array_length_abs_of_concrete {s₀ s₉ : State} {length data} : + Spec (extract_byte_array_length_concrete_of_code.1 length data) s₀ s₉ → + Spec (A_extract_byte_array_length length data) s₀ s₉ := by + unfold extract_byte_array_length_concrete_of_code A_extract_byte_array_length + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/finalize_allocation.lean b/Generated/erc20shim/ERC20Shim/finalize_allocation.lean new file mode 100644 index 00000000..e648bcc1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/finalize_allocation.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225 +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + +import Generated.erc20shim.ERC20Shim.finalize_allocation_gen + +import Generated.erc20shim.ERC20Shim.finalize_allocation_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma finalize_allocation_abs_of_code {s₀ s₉ : State} { memPtr size} {fuel : Nat} : + execCall fuel finalize_allocation [] (s₀, [memPtr, size]) = s₉ → + Spec (A_finalize_allocation memPtr size) s₀ s₉ +:= λ h ↦ finalize_allocation_abs_of_concrete (finalize_allocation_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/finalize_allocation_gen.lean b/Generated/erc20shim/ERC20Shim/finalize_allocation_gen.lean new file mode 100644 index 00000000..4033e0c8 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/finalize_allocation_gen.lean @@ -0,0 +1,158 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225 +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def finalize_allocation : FunctionDefinition := + +{ + let _1 := not(31) + let _2 := 31 + let _3 := add(size, _2) + let _4 := and(_3, _1) + let newFreePtr := add(memPtr, _4) + let _5 := lt(newFreePtr, memPtr) + let _6 := 18446744073709551615 + let _7 := gt(newFreePtr, _6) + let _8 := or(_7, _5) + if _8 + {panic_error_0x41()} + let _9 := 64 + mstore(_9, newFreePtr) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def finalize_allocation_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { memPtr size fuel}, + execCall fuel finalize_allocation [] (s₀, [memPtr, size]) = s₉ → + Spec (C memPtr size) s₀ s₉ + } := by + constructor + intros s₀ s₉ memPtr size fuel + unfold finalize_allocation + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMNot'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAdd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMLt'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMGt'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMOr'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_9222169807163418225_abs_of_code if_9222169807163418225 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/finalize_allocation_user.lean b/Generated/erc20shim/ERC20Shim/finalize_allocation_user.lean new file mode 100644 index 00000000..ba9a41f4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/finalize_allocation_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9222169807163418225 +import Generated.erc20shim.ERC20Shim.panic_error_0x41 + +import Generated.erc20shim.ERC20Shim.finalize_allocation_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_finalize_allocation (memPtr size : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma finalize_allocation_abs_of_concrete {s₀ s₉ : State} { memPtr size} : + Spec (finalize_allocation_concrete_of_code.1 memPtr size) s₀ s₉ → + Spec (A_finalize_allocation memPtr size) s₀ s₉ := by + unfold finalize_allocation_concrete_of_code A_finalize_allocation + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__approve.lean b/Generated/erc20shim/ERC20Shim/fun__approve.lean new file mode 100644 index 00000000..813c41cd --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__approve.lean @@ -0,0 +1,30 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.fun__approve_gen + +import Generated.erc20shim.ERC20Shim.fun__approve_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma fun__approve_abs_of_code {s₀ s₉ : State} { var_owner var_spender var_value var_emitEvent} {fuel : Nat} : + execCall fuel fun__approve [] (s₀, [var_owner, var_spender, var_value, var_emitEvent]) = s₉ → + Spec (A_fun__approve var_owner var_spender var_value var_emitEvent) s₀ s₉ +:= λ h ↦ fun__approve_abs_of_concrete (fun__approve_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__approve_gen.lean b/Generated/erc20shim/ERC20Shim/fun__approve_gen.lean new file mode 100644 index 00000000..014a0742 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__approve_gen.lean @@ -0,0 +1,254 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def fun__approve : FunctionDefinition := + +{ + let expr := var_owner + let _1 := sub(shl(160, 1), 1) + let _2 := and(var_owner, _1) + let _3 := iszero(_2) + if _3 + { + let expr_1 := 0 + let _4 := 64 + let _5 := mload(_4) + let _6 := shl(224, 3858947845) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_tuple_address(_8, expr_1) + let _10 := sub(_9, _5) + revert(_5, _10) + } + let expr_2 := var_spender + let _11 := _1 + let _12 := and(var_spender, _1) + let _13 := iszero(_12) + if _13 + { + let expr_3 := 0 + let _14 := 64 + let _15 := mload(_14) + let _16 := shl(225, 1242826417) + mstore(_15, _16) + let _17 := 4 + let _18 := add(_15, _17) + let _19 := abi_encode_tuple_address(_18, expr_3) + let _20 := sub(_19, _15) + revert(_15, _20) + } + let expr_4 := var_value + let _21 := 1 + let _22 := mapping_index_access_mapping_address_mapping_address_uint256_of_address(_21, var_owner) + let _23 := mapping_index_access_mapping_address_uint256_of_address(_22, var_spender) + update_storage_value_offsett_uint256_to_uint256(_23, var_value) + if var_emitEvent + { + let expr_5 := var_owner + let expr_6 := var_spender + let expr_7 := var_value + let _24 := 63486140976153616755203102783360879283472101686154884697241723088393386309925 + let _25 := _2 + let _26 := _12 + let _27 := 64 + let _28 := mload(_27) + let _29 := abi_encode_uint256(_28, var_value) + let _30 := sub(_29, _28) + log3(_28, _30, _24, _2, _12) + } +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun__approve_concrete_of_code +: { + C : + _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { var_owner var_spender var_value var_emitEvent fuel}, + execCall fuel fun__approve [] (s₀, [var_owner, var_spender, var_value, var_emitEvent]) = s₉ → + Spec (C var_owner var_spender var_value var_emitEvent) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_owner var_spender var_value var_emitEvent fuel + unfold fun__approve + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_3812165059632449189_abs_of_code if_3812165059632449189 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_4692225504622348326_abs_of_code if_4692225504622348326 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_storage_value_offsett_uint256_to_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_5042234445269809685_abs_of_code if_5042234445269809685 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__approve_user.lean b/Generated/erc20shim/ERC20Shim/fun__approve_user.lean new file mode 100644 index 00000000..cb5d44f3 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__approve_user.lean @@ -0,0 +1,31 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_3812165059632449189 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_4692225504622348326 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.Common.if_5042234445269809685 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.fun__approve_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_fun__approve (var_owner var_spender var_value var_emitEvent : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma fun__approve_abs_of_concrete {s₀ s₉ : State} { var_owner var_spender var_value var_emitEvent} : + Spec (fun__approve_concrete_of_code.1 var_owner var_spender var_value var_emitEvent) s₀ s₉ → + Spec (A_fun__approve var_owner var_spender var_value var_emitEvent) s₀ s₉ := by + unfold fun__approve_concrete_of_code A_fun__approve + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__transfer.lean b/Generated/erc20shim/ERC20Shim/fun__transfer.lean new file mode 100644 index 00000000..155b61ae --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__transfer.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657 +import Generated.erc20shim.ERC20Shim.fun_update + +import Generated.erc20shim.ERC20Shim.fun__transfer_gen + +import Generated.erc20shim.ERC20Shim.fun__transfer_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma fun__transfer_abs_of_code {s₀ s₉ : State} { var_from var_to var_value} {fuel : Nat} : + execCall fuel fun__transfer [] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (A_fun__transfer var_from var_to var_value) s₀ s₉ +:= λ h ↦ fun__transfer_abs_of_concrete (fun__transfer_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__transfer_gen.lean b/Generated/erc20shim/ERC20Shim/fun__transfer_gen.lean new file mode 100644 index 00000000..e6718b7c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__transfer_gen.lean @@ -0,0 +1,194 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657 +import Generated.erc20shim.ERC20Shim.fun_update + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def fun__transfer : FunctionDefinition := + +{ + let expr := var_from + let _1 := sub(shl(160, 1), 1) + let _2 := and(var_from, _1) + let _3 := iszero(_2) + if _3 + { + let expr_1 := 0 + let _4 := 64 + let _5 := mload(_4) + let _6 := shl(225, 1264811663) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_tuple_address(_8, expr_1) + let _10 := sub(_9, _5) + revert(_5, _10) + } + let expr_2 := var_to + let _11 := _1 + let _12 := and(var_to, _1) + let _13 := iszero(_12) + if _13 + { + let expr_3 := 0 + let _14 := 64 + let _15 := mload(_14) + let _16 := shl(224, 3963891461) + mstore(_15, _16) + let _17 := 4 + let _18 := add(_15, _17) + let _19 := abi_encode_tuple_address(_18, expr_3) + let _20 := sub(_19, _15) + revert(_15, _20) + } + fun_update(var_from, var_to, var_value) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun__transfer_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { var_from var_to var_value fuel}, + execCall fuel fun__transfer [] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (C var_from var_to var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_from var_to var_value fuel + unfold fun__transfer + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_9141570808380448040_abs_of_code if_9141570808380448040 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_2395397427938978657_abs_of_code if_2395397427938978657 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_update_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun__transfer_user.lean b/Generated/erc20shim/ERC20Shim/fun__transfer_user.lean new file mode 100644 index 00000000..3d98ff52 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun__transfer_user.lean @@ -0,0 +1,76 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_9141570808380448040 +import Generated.erc20shim.ERC20Shim.abi_encode_tuple_address +import Generated.erc20shim.ERC20Shim.Common.if_2395397427938978657 +import Generated.erc20shim.ERC20Shim.fun_update + +import Generated.erc20shim.ERC20Shim.fun__transfer_gen + +import Generated.erc20shim.ERC20Shim.Predicate + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_fun__transfer (var_from var_to var_value : Literal) (s₀ s₉ : State) : Prop := + + let from_addr := Address.ofUInt256 var_from + let to_addr := Address.ofUInt256 var_to + let transfer_value : UInt256 := var_value + s₉.isOk ∧ + ( --Case 1: No Collision in s₀ + ∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState) → + -- Case 1.1: _transfer succeeds + ( + let balances := update_balances erc20 from_addr to_addr transfer_value + IsERC20 ({ erc20 with balances }) s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.evm.reverted = false + ) + ∨ + -- Case 1.2: _transfer fails + ( + IsERC20 erc20 s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉ = s₀.setRevert ∧ + (to_addr = 0 ∨ balanceOf s₀.evm from_addr < transfer_value) + ) + -- Case 1.3: Hash collision during transfer + ∨ s₉.evm.hash_collision = true + ) + -- Case 2 : existing hash collision in s₀ + ∧ (s₀.evm.hash_collision = true → s₉.evm.hash_collision = true) + +lemma fun__transfer_abs_of_concrete {s₀ s₉ : State} { var_from var_to var_value} : + Spec (fun__transfer_concrete_of_code.1 var_from var_to var_value) s₀ s₉ → + Spec (A_fun__transfer var_from var_to var_value) s₀ s₉ := by + unfold fun__transfer_concrete_of_code A_fun__transfer + rcases s₀ with ⟨s0_evm, s0_varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + apply spec_eq + + + clr_funargs + + generalize s_inhabited_all : (Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧) = s_inhabited at * + have s_inhabited_ok : s_inhabited.isOk := by + aesop_spec + + -- s₀ --> s₉ using _transfer + + rintro hasFuel ⟨s, call_914, ⟨s', call_239, ⟨s'', call_update, code⟩⟩⟩ + + -- Assign s₀ state to tidy up goal + generalize s0_all : Ok s0_evm s0_varstore = s₀ at * + have s0_ok : s₀.isOk := by + aesop + + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_allowance.lean b/Generated/erc20shim/ERC20Shim/fun_allowance.lean new file mode 100644 index 00000000..25b62db1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_allowance.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address + +import Generated.erc20shim.ERC20Shim.fun_allowance_gen + +import Generated.erc20shim.ERC20Shim.fun_allowance_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_allowance_abs_of_code {s₀ s₉ : State} {var var_owner var_spender} {fuel : Nat} : + execCall fuel fun_allowance [var] (s₀, [var_owner, var_spender]) = s₉ → + Spec (A_fun_allowance var var_owner var_spender) s₀ s₉ +:= λ h ↦ fun_allowance_abs_of_concrete (fun_allowance_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_allowance_gen.lean b/Generated/erc20shim/ERC20Shim/fun_allowance_gen.lean new file mode 100644 index 00000000..f500c7a6 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_allowance_gen.lean @@ -0,0 +1,122 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_allowance : FunctionDefinition := var + +{ + let _1 := 1 + let _2 := mapping_index_access_mapping_address_mapping_address_uint256_of_address(_1, var_owner) + let _3 := mapping_index_access_mapping_address_uint256_of_address(_2, var_spender) + var := sload(_3) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_allowance_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var var_owner var_spender fuel}, + execCall fuel fun_allowance [var] (s₀, [var_owner, var_spender]) = s₉ → + Spec (C var var_owner var_spender) s₀ s₉ + } := by + constructor + intros s₀ s₉ var var_owner var_spender fuel + unfold fun_allowance + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_allowance_user.lean b/Generated/erc20shim/ERC20Shim/fun_allowance_user.lean new file mode 100644 index 00000000..50c7216b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_allowance_user.lean @@ -0,0 +1,409 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_allowance_gen + +import Generated.erc20shim.ERC20Shim.Predicate + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +set_option maxHeartbeats 1000000 + +def A_fun_allowance (var : Identifier) (var_owner var_spender : Literal) (s₀ s₉ : State) : Prop := + (∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState) → + let owner := Address.ofUInt256 var_owner + let spender := Address.ofUInt256 var_spender + IsERC20 erc20 s₉ ∧ preservesEvm s₀ s₉ ∧ + s₉[var]!! = (erc20.allowances.lookup ⟨owner, spender⟩).getD 0 ∧ + s₉.evm.hash_collision = false) + ∨ s₉.evm.hash_collision = true + +lemma fun_allowance_abs_of_concrete {s₀ s₉ : State} {var var_owner var_spender} : + Spec (fun_allowance_concrete_of_code.1 var var_owner var_spender) s₀ s₉ → + Spec (A_fun_allowance var var_owner var_spender) s₀ s₉ := by + + -- unfold the definitions of the two functions + unfold fun_allowance_concrete_of_code A_fun_allowance + -- f + rcases s₀ with ⟨evm, varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel ⟨s, mapping, ⟨s', mapping', code⟩⟩ + + clr_varstore, + + -- what we can get right now from mapping function + unfold A_mapping_index_access_mapping_address_mapping_address_uint256_of_address at mapping + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping + clr_spec at mapping + +#exit + + obtain ⟨⟨preservesEvm, s_isOk, s_isEVMStatePreserved, ⟨⟨intermediate_keccak, keccak_using_intermediate, hStore⟩,hHashCollision⟩⟩, hHashCollision₁⟩ := mapping -- Adds a goal + · -- No hash collision from first keccak + + obtain ⟨evmₛ, varstoreₛ, s_eq_ok⟩ := State_of_isOk s_isOk + have keccak : Finmap.lookup [↑↑(Address.ofUInt256 var_owner), 1] s.evm.keccak_map = some (s["_2"]!!) := by + unfold store State.insert at hStore + unfold lookup! + aesop + rw [ ← Variables.allowances_def + , s_eq_ok, get_evm_of_ok, ← s_eq_ok + ] at keccak + + -- what we can get right now from mapping' function + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping' + clr_spec at mapping' + + obtain ⟨⟨preservesEvm', s_isOk', s_isEVMStatePreserved', ⟨⟨intermediate_keccak', keccak_using_intermediate', hStore'⟩,hHashCollision'⟩⟩, hHashCollision₁'⟩ := mapping' -- Adds a goal + · -- No hash collision from second keccak + left + intro erc20 is_erc20 s₀_isEVMState + obtain ⟨evmₛ', varstoreₛ', s_eq_ok'⟩ := State_of_isOk s_isOk' + have keccak' : Finmap.lookup [↑↑(Address.ofUInt256 (s["var_spender"]!!)), s["_2"]!!] s'.evm.keccak_map = some (s'["_3"]!!) := by + rw [s_eq_ok] + rw [s_eq_ok] at hStore' + rw [s_eq_ok'] + rw [s_eq_ok'] at hStore' + unfold store at hStore' + simp at hStore' + unfold State.insert at hStore' + simp at hStore' + conv_lhs => rw[←s_eq_ok]; rw[←s_eq_ok'] + rw [hStore'] + unfold lookup! + simp + exact keccak_using_intermediate' + rw [ s_eq_ok', get_evm_of_ok, ← s_eq_ok' + ] at keccak' + + -- simplify contract + unfold reviveJump at code + simp [s_eq_ok, s_eq_ok'] at code + rw [ ← State.insert_of_ok, ← State.insert_of_ok, ← s_eq_ok' ] at code + clr_varstore, + + -- get underlying Preserved from preservesEvm + rw [ s_eq_ok, preservesEvm_of_insert, preservesEvm_of_insert ] at preservesEvm + have hPreserved := Preserved_of_preservesEvm_of_Ok preservesEvm + + -- get underlying Preserved from preservesEvm' + rw [ s_eq_ok, s_eq_ok'] at preservesEvm' + have hPreserved' := Preserved_of_preservesEvm_of_Ok preservesEvm' + + -- make use of transitivity of Preserved + have hPreserved'' : Clear.Preserved evm evmₛ' := Preserved.trans hPreserved hPreserved' + + refine' ⟨IsERC20_of_preservesEvm (by aesop) is_erc20, (by aesop), ?returns_correct_value⟩ + rw [← code] + -- lookup allowance + clr_varstore, + by_cases mem : ⟨Address.ofUInt256 var_owner, Address.ofUInt256 var_spender⟩ ∈ erc20.allowances + · -- there is such ⟨owner, spender⟩ in allowances + split_ands <;> [skip; aesop] + + obtain ⟨address, intermediate, has_intermediate, has_address, allowance⟩ := is_erc20.hasAllowance mem + + have intermediate_def : s["_2"]!! = intermediate := by + rw [s_eq_ok] + rw [← Option.some_inj] + trans + · have := Eq.symm (s_eq_ok ▸ keccak) + exact this + · exact (keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved has_intermediate + ▸ has_intermediate) + + have address_def : s'["_3"]!! = address := by + rw [s_eq_ok'] + rw [← Option.some_inj] + trans + · have := Eq.symm (s_eq_ok' ▸ keccak') + exact this + · rw [intermediate_def] + have : s["var_spender"]!! = var_spender := by + rw [s_eq_ok] + rw [s_eq_ok] at hStore + unfold store at hStore + unfold State.insert at hStore + simp at hStore + rw [hStore] + unfold lookup! + simp + rw [Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp) + , Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp) + , Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp)] + simp + rw [this] + exact (keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved'' has_address ▸ has_address) + + rw [address_def] at code ⊢ + rw [ allowance + , Option.getD_some + , State.get_evm_of_ok + , ← sload_eq_of_preserved hPreserved'' + ] + · -- there is *no* such account in allowances + -- so sload should return 0 + + split_ands <;> [skip; aesop] + + rw [ Finmap.lookup_eq_none.mpr mem + , Option.getD_none + ] + + -- in order to do that it should be given storage address outside of + -- its domain + apply sload_of_not_mem_dom + have := State.get_evm_of_ok ▸ is_erc20.storageDom + rw [ ← storage_eq_of_preserved hPreserved'' + , this + ] + clear this + simp only [ Finset.not_mem_union, Set.mem_toFinset, Set.mem_def, setOf, not_exists, not_and ] + have s_erc20 : IsERC20 erc20 (Ok evmₛ _) := + IsERC20_of_ok_of_Preserved hPreserved is_erc20 + have s_erc20' : IsERC20 erc20 (Ok evmₛ' _) := + IsERC20_of_ok_of_Preserved hPreserved' s_erc20 + + split_ands + -- address not in balances + · intro account account_mem_balances + obtain ⟨address, has_address, balance⟩ := is_erc20.hasBalance account_mem_balances + rw [ ← keccak' + , keccak_map_lookup_eq_of_Preserved_of_lookup + hPreserved'' has_address ] + by_contra h + have : [↑↑account, ERC20Private.balances] ∈ evmₛ'.keccak_map.keys := by + rw [Finmap.mem_keys] + apply Finmap.lookup_isSome.mp + have := get_evm_of_ok ▸ has_address + rw [ ← keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved'' has_address + , this ] + simp + have IsEVMₛ' : evmₛ'.isEVMState := by aesop + have keccak_inj := IsEVMₛ'.1 this (Eq.symm h) + + rw [← Fin.ofNat''_eq_cast, ← Fin.ofNat''_eq_cast] at keccak_inj + unfold Fin.ofNat'' at keccak_inj + simp at keccak_inj + obtain ⟨keccak_inj₁, keccak_inj₂⟩ := keccak_inj + + have : ERC20Private.balances ≠ s["_2"]!! := by + obtain blocked_range := get_evm_of_ok ▸ s_erc20.block_acc_range.2.1 + rw [ keccak ] at blocked_range + apply not_mem_private_of_some at blocked_range + rw [@ne_comm] + unfold PrivateAddresses.toFinset at blocked_range + rw [Finset.mem_def] at blocked_range + simp at blocked_range -- Fails with: set_option maxHeartbeats 200000 + exact blocked_range.1 + contradiction + + -- address not in allowances + · intro owner spender owner_spender_mem_allowances + + obtain ⟨erc_address, erc_intermediate, owner_lookup, spender_lookup, eq⟩ := + is_erc20.hasAllowance owner_spender_mem_allowances + + rw [ ← keccak' + , keccak_map_lookup_eq_of_Preserved_of_lookup + hPreserved'' owner_lookup ] + by_contra h + have : [↑↑owner, ERC20Private.allowances] ∈ evmₛ.keccak_map.keys := by + rw [Finmap.mem_keys] + apply Finmap.lookup_isSome.mp + have owner_lookup' := get_evm_of_ok ▸ owner_lookup + have spender_lookup' := get_evm_of_ok ▸ spender_lookup + rw [ ← keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved owner_lookup + , owner_lookup' ] + simp + have owner_lookup' := get_evm_of_ok ▸ owner_lookup + have := keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved'' owner_lookup + rw [this] at owner_lookup' + have hSpender := h owner_lookup' + + + have spender_lookup' := get_evm_of_ok ▸ spender_lookup + have := keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved'' spender_lookup' + rw [this] at hSpender + + have : [↑↑(Address.ofUInt256 (s["var_spender"]!!)), s["_2"]!!] ∈ evmₛ'.keccak_map.keys := by + clear * -keccak_using_intermediate' s_eq_ok' + rw [s_eq_ok'] at keccak_using_intermediate' + simp at keccak_using_intermediate' + exact Finmap.mem_of_lookup_eq_some keccak_using_intermediate' + have IsEVMₛ' : evmₛ'.isEVMState := by aesop + have keccak_inj := IsEVMₛ'.1 this (Eq.symm hSpender) + rw [← Fin.ofNat''_eq_cast, ← Fin.ofNat''_eq_cast] at keccak_inj + unfold Fin.ofNat'' at keccak_inj + simp at keccak_inj + rw [Nat.mod_eq_of_lt, Nat.mod_eq_of_lt, Fin.val_eq_val] at keccak_inj <;> [skip; exact Address.val_lt_UInt256_size; exact Address.val_lt_UInt256_size] + + obtain ⟨keccak_inj₁, keccak_inj₂⟩ := keccak_inj + + + have hOwner : owner = Address.ofUInt256 var_owner := by + have := keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved owner_lookup + rw [←keccak_inj₂] at owner_lookup + rw [←keccak] at owner_lookup + have owner_lookup'' := get_evm_of_ok ▸ owner_lookup + rw [this] at owner_lookup'' + + have : [↑↑(Address.ofUInt256 var_owner), ERC20Private.allowances] ∈ evmₛ.keccak_map.keys := by + clear * -keccak_using_intermediate s_eq_ok + rw [s_eq_ok] at keccak_using_intermediate + simp at keccak_using_intermediate + exact Finmap.mem_of_lookup_eq_some keccak_using_intermediate + have IsEVMₛ : evmₛ.isEVMState := by aesop + have keccak_inj := IsEVMₛ.1 this (Eq.symm owner_lookup'') + rw [← Fin.ofNat''_eq_cast, ← Fin.ofNat''_eq_cast] at keccak_inj + unfold Fin.ofNat'' at keccak_inj + simp at keccak_inj + rw [Nat.mod_eq_of_lt, Nat.mod_eq_of_lt, Fin.val_eq_val] at keccak_inj <;> [skip; exact Address.val_lt_UInt256_size; exact Address.val_lt_UInt256_size] + symm + exact keccak_inj + + have hSpender : spender = Address.ofUInt256 var_spender := by + have : s["var_spender"]!! = var_spender := by + rw [s_eq_ok] + rw [s_eq_ok] at hStore + unfold store at hStore + unfold State.insert at hStore + simp at hStore + rw [hStore] + unfold lookup! + simp + rw [Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp) + , Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp) + , Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp)] + simp + rw [this] at keccak_inj₁ + symm + exact keccak_inj₁ + + rw [←hOwner, ←hSpender] at mem + contradiction + + -- address not in reserved space + · obtain blocked_range := get_evm_of_ok ▸ (s_erc20'.block_acc_range.2.2) + have := keccak_map_lookup_eq_of_Preserved_of_lookup hPreserved' keccak + rw [this] at keccak + rw [ keccak ] at blocked_range + + have blocked_range' := blocked_range (↑↑(Address.ofUInt256 (s["var_spender"]!!))) (s["_2"]!!) (by rfl) + rw [←Finset.mem_map' Function.Embedding.some] + + -- TODO make simpler: + have : Function.Embedding.some (s'["_3"]!!) = (some (s'["_3"]!!)) := by + simp + rw [this] + rw [←keccak'] + + unfold not_mem_private at blocked_range' + rw [keccak'] at blocked_range' + simp at blocked_range' + rw [keccak'] + simp + exact blocked_range' + + + · -- Hash collision from second keccak + rename_i hHashCollisionTrue + right + have : hash_collision (Ok evm Inhabited.default⟦"var_spender"↦var_spender⟧⟦"var_owner"↦var_owner⟧⟦"_1"↦1⟧.evm) + = evm.hash_collision := by + simp + rw [this] at hHashCollision₁ + by_cases s_isOk' : s'.isOk + · obtain ⟨evmₛ', varstoreₛ', s_eq_ok'⟩ := State_of_isOk s_isOk' + -- simplify contract + unfold reviveJump at code + simp [s_eq_ok, s_eq_ok'] at code + rw [ ← State.insert_of_ok, ← State.insert_of_ok, ← s_eq_ok' ] at code + clr_varstore, + rw [←code] + rw [s_eq_ok'] at hHashCollisionTrue + aesop + · rcases s' with ⟨evm, varstore⟩ | _ | _ <;> [skip; aesop_spec; skip] + · unfold reviveJump at code + simp at code + rw [←code] + aesop + · unfold reviveJump at code + simp at code + + rename_i j + unfold evm at hHashCollisionTrue + simp at hHashCollisionTrue + · -- Hash collision from first keccak + rename_i hHashCollisionTrue + right + + by_cases s_isOk : s.isOk + · unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping' + clr_spec at mapping' + + obtain ⟨⟨preservesEvm', s_isOk', s_isEVMStatePreserved', ⟨⟨intermediate_keccak', keccak_using_intermediate', hStore'⟩,hHashCollision'⟩⟩, hHashCollision₁'⟩ := mapping' -- Adds a goal + + have : hash_collision (Ok evm Inhabited.default⟦"var_spender"↦var_spender⟧⟦"var_owner"↦var_owner⟧⟦"_1"↦1⟧.evm) + = evm.hash_collision := by + simp + rw [this] at hHashCollision₁ + by_cases s_isOk' : s'.isOk + · obtain ⟨evmₛ', varstoreₛ', s_eq_ok'⟩ := State_of_isOk s_isOk' + -- simplify contract + unfold reviveJump at code + simp [s_eq_ok'] at code + rw [ ← State.insert_of_ok, ← State.insert_of_ok, ← s_eq_ok' ] at code + clr_varstore, + + · rw [←code] + have : Ok evmₛ' varstore⟦var↦sload evmₛ' (s'["_3"]!!)⟧.evm.hash_collision + = evmₛ'.hash_collision := by simp + rw [this] + aesop + + + · rcases s' with ⟨evm, varstore⟩ | _ | _ <;> [skip; aesop_spec; skip] + · unfold reviveJump at code + simp at code + rw [←code] + aesop + + · unfold reviveJump at code + simp at code + rename_i j + rcases j + · rename_i hHashCollisionTrue' + have : Ok evm Inhabited.default⟦"var_spender"↦var_spender⟧⟦"var_owner"↦var_owner⟧⟦"_1"↦1⟧.evm.hash_collision + = evm.hash_collision := by simp + rw [this] at hHashCollision₁ + rcases s' with ⟨evm, varstore⟩ | _ | _ <;> [skip; aesop_spec; skip] + · unfold reviveJump at code + simp at code + rw [←code] + aesop + + · unfold reviveJump at code + simp at code + unfold evm at hHashCollisionTrue' + simp at hHashCollisionTrue' + · unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping' + unfold Spec at mapping' + rcases s with ⟨evm, varstore⟩ | _ | _ <;> [skip; skip; skip] + · aesop + · simp at mapping' + rcases s' with ⟨evm, varstore⟩ | _ | _ <;> aesop_spec + · simp at mapping' + rcases s' with ⟨evm, varstore⟩ | _ | _ <;> [skip;skip;skip] + · simp at mapping' + · simp at mapping' + · unfold evm at hHashCollisionTrue + simp at hHashCollisionTrue + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve.lean b/Generated/erc20shim/ERC20Shim/fun_approve.lean new file mode 100644 index 00000000..820f5e4e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_approve_420 + +import Generated.erc20shim.ERC20Shim.fun_approve_gen + +import Generated.erc20shim.ERC20Shim.fun_approve_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_approve_abs_of_code {s₀ s₉ : State} {var var_spender var_value} {fuel : Nat} : + execCall fuel fun_approve [var] (s₀, [var_spender, var_value]) = s₉ → + Spec (A_fun_approve var var_spender var_value) s₀ s₉ +:= λ h ↦ fun_approve_abs_of_concrete (fun_approve_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve_420.lean b/Generated/erc20shim/ERC20Shim/fun_approve_420.lean new file mode 100644 index 00000000..5d961c88 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve_420.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.fun_approve_420_gen + +import Generated.erc20shim.ERC20Shim.fun_approve_420_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_approve_420_abs_of_code {s₀ s₉ : State} { var_owner var_spender var_value} {fuel : Nat} : + execCall fuel fun_approve_420 [] (s₀, [var_owner, var_spender, var_value]) = s₉ → + Spec (A_fun_approve_420 var_owner var_spender var_value) s₀ s₉ +:= λ h ↦ fun_approve_420_abs_of_concrete (fun_approve_420_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve_420_gen.lean b/Generated/erc20shim/ERC20Shim/fun_approve_420_gen.lean new file mode 100644 index 00000000..2b70feb4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve_420_gen.lean @@ -0,0 +1,108 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun__approve + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_approve_420 : FunctionDefinition := + +{ + let expr := var_owner + let _1 := 1 + fun__approve(var_owner, var_spender, var_value, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_approve_420_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { var_owner var_spender var_value fuel}, + execCall fuel fun_approve_420 [] (s₀, [var_owner, var_spender, var_value]) = s₉ → + Spec (C var_owner var_spender var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_owner var_spender var_value fuel + unfold fun_approve_420 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun__approve_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve_420_user.lean b/Generated/erc20shim/ERC20Shim/fun_approve_420_user.lean new file mode 100644 index 00000000..630e5c88 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve_420_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.fun_approve_420_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_approve_420 (var_owner var_spender var_value : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma fun_approve_420_abs_of_concrete {s₀ s₉ : State} { var_owner var_spender var_value} : + Spec (fun_approve_420_concrete_of_code.1 var_owner var_spender var_value) s₀ s₉ → + Spec (A_fun_approve_420 var_owner var_spender var_value) s₀ s₉ := by + unfold fun_approve_420_concrete_of_code A_fun_approve_420 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve_gen.lean b/Generated/erc20shim/ERC20Shim/fun_approve_gen.lean new file mode 100644 index 00000000..a04706a1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve_gen.lean @@ -0,0 +1,119 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_approve_420 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_approve : FunctionDefinition := var + +{ + let _1 := fun_msgSender() + fun_approve_420(_1, var_spender, var_value) + var := 1 +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_approve_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var var_spender var_value fuel}, + execCall fuel fun_approve [var] (s₀, [var_spender, var_value]) = s₉ → + Spec (C var var_spender var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var var_spender var_value fuel + unfold fun_approve + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_msgSender_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_approve_420_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_approve_user.lean b/Generated/erc20shim/ERC20Shim/fun_approve_user.lean new file mode 100644 index 00000000..ffa7f5e1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_approve_user.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_approve_420 + +import Generated.erc20shim.ERC20Shim.fun_approve_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_approve (var : Identifier) (var_spender var_value : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma fun_approve_abs_of_concrete {s₀ s₉ : State} {var var_spender var_value} : + Spec (fun_approve_concrete_of_code.1 var var_spender var_value) s₀ s₉ → + Spec (A_fun_approve var var_spender var_value) s₀ s₉ := by + unfold fun_approve_concrete_of_code A_fun_approve + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_balanceOf.lean b/Generated/erc20shim/ERC20Shim/fun_balanceOf.lean new file mode 100644 index 00000000..c2b9b22f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_balanceOf.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address + +import Generated.erc20shim.ERC20Shim.fun_balanceOf_gen + +import Generated.erc20shim.ERC20Shim.fun_balanceOf_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_balanceOf_abs_of_code {s₀ s₉ : State} {var var_account} {fuel : Nat} : + execCall fuel fun_balanceOf [var] (s₀, [var_account]) = s₉ → + Spec (A_fun_balanceOf var var_account) s₀ s₉ +:= λ h ↦ fun_balanceOf_abs_of_concrete (fun_balanceOf_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_balanceOf_gen.lean b/Generated/erc20shim/ERC20Shim/fun_balanceOf_gen.lean new file mode 100644 index 00000000..3f76422e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_balanceOf_gen.lean @@ -0,0 +1,108 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_balanceOf : FunctionDefinition := var + +{ + let _1 := 0 + let _2 := mapping_index_access_mapping_address_uint256_of_address(_1, var_account) + var := sload(_2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_balanceOf_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var var_account fuel}, + execCall fuel fun_balanceOf [var] (s₀, [var_account]) = s₉ → + Spec (C var var_account) s₀ s₉ + } := by + constructor + intros s₀ s₉ var var_account fuel + unfold fun_balanceOf + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (mapping_index_access_mapping_address_uint256_of_address_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_balanceOf_user.lean b/Generated/erc20shim/ERC20Shim/fun_balanceOf_user.lean new file mode 100644 index 00000000..1d8e8d4a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_balanceOf_user.lean @@ -0,0 +1,194 @@ +import Clear.ReasoningPrinciple + +-- import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.fun_balanceOf_gen + +import Generated.erc20shim.ERC20Shim.Predicate + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +section PleaseMoveTheseWhereAppropriatte + +variable {jmp : Jump} + +@[simp] +lemma hash_collision_evm_Checkpoint_eq_false : (Checkpoint jmp).evm.hash_collision = false := rfl + +end PleaseMoveTheseWhereAppropriatte + +def A_fun_balanceOf (var : Identifier) (var_account : Literal) (s₀ s₉ : State) : Prop := + (∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState) → + let account := Address.ofUInt256 var_account + IsERC20 erc20 s₉ ∧ preservesEvm s₀ s₉ ∧ + s₉[var]!! = (erc20.balances.lookup account).getD 0 ∧ + s₉.evm.hash_collision = false) + ∨ s₉.evm.hash_collision = true + +lemma fun_balanceOf_abs_of_concrete {s₀ s₉ : State} {var var_account} : + Spec (fun_balanceOf_concrete_of_code.1 var var_account) s₀ s₉ → + Spec (A_fun_balanceOf var var_account) s₀ s₉ := by + unfold fun_balanceOf_concrete_of_code A_fun_balanceOf + rcases s₀ with ⟨evm, varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel ⟨s, mapping, code⟩ + clr_varstore, + + -- what we can get right now from mapping function + unfold A_mapping_index_access_mapping_address_uint256_of_address at mapping + clr_spec at mapping + + -- Discharge the hash-colliding case immediately using `aesop_spec`. + rcases mapping with ⟨ + ⟨preservesEvm, s_isOk, s_isEVMStatePreserved, + ⟨⟨keccak_value, keccak_using_keccak_value, hStore⟩,hHashCollision⟩⟩ | _, hHashCollision₁ + ⟩ <;> [left; rcases s <;> aesop_spec] + + intro erc20 is_erc20 s₀_isEVMState + + obtain ⟨evmₛ, varstoreₛ, s_eq_ok⟩ := State_of_isOk s_isOk + + have keccak : Finmap.lookup [↑↑(Address.ofUInt256 var_account), 0] s.evm.keccak_map = some (s["_2"]!!) := by + unfold store State.insert at hStore + unfold lookup! + aesop + + rw [ ← Variables.balances_def + , s_eq_ok, get_evm_of_ok, ← s_eq_ok + ] at keccak + + -- simplify contract + unfold reviveJump at code + simp [s_eq_ok] at code + rw [ ← State.insert_of_ok, ← State.insert_of_ok, ← s_eq_ok ] at code + clr_varstore, + + -- get underlying Preserved from preservesEvm + rw [ s_eq_ok, preservesEvm_of_insert, preservesEvm_of_insert ] at preservesEvm + have Preserved := Preserved_of_preservesEvm_of_Ok preservesEvm + + refine' ⟨IsERC20_of_preservesEvm (by aesop) is_erc20, (by aesop), ?returns_correct_value⟩ + + rw [← code] + -- lookup balance + clr_varstore, + by_cases mem : Address.ofUInt256 var_account ∈ erc20.balances + · -- there is such account in balances + split_ands <;> [skip; aesop] + + obtain ⟨address, has_address, balance⟩ := is_erc20.hasBalance mem + + have address_def : s["_2"]!! = address := by + rw [s_eq_ok] + rw [← Option.some_inj] + trans + · exact Eq.symm (s_eq_ok ▸ keccak) + · exact (keccak_map_lookup_eq_of_Preserved_of_lookup Preserved has_address + ▸ has_address) + + rw [address_def] at code ⊢ + rw [ balance + , Option.getD_some + , State.get_evm_of_ok + , ← sload_eq_of_preserved Preserved + ] + + · -- there is *no* such account in balances + -- so sload should return 0 + + split_ands <;> [skip; aesop] + + rw [ Finmap.lookup_eq_none.mpr mem + , Option.getD_none + ] + + -- in order to do that it should be given storage address outside of + -- it's domain + apply sload_of_not_mem_dom + have := State.get_evm_of_ok ▸ is_erc20.storageDom + rw [ ← storage_eq_of_preserved Preserved + , this + ] + clear this + simp only [ Finset.not_mem_union, Set.mem_toFinset, Set.mem_def, setOf, not_exists, not_and ] + have s_erc20 : IsERC20 erc20 (Ok evmₛ _) := + IsERC20_of_ok_of_Preserved Preserved is_erc20 + + split_ands + -- address not in balances + · intro account account_mem_balances + obtain ⟨address, has_address, balance⟩ := is_erc20.hasBalance account_mem_balances + rw [ ← keccak + , keccak_map_lookup_eq_of_Preserved_of_lookup + Preserved has_address ] + by_contra h + have : [↑↑account, ERC20Private.balances] ∈ evmₛ.keccak_map.keys := by + rw [Finmap.mem_keys] + apply Finmap.lookup_isSome.mp + have := get_evm_of_ok ▸ has_address + rw [ ← keccak_map_lookup_eq_of_Preserved_of_lookup Preserved has_address + , this ] + simp + have IsEVMₛ : evmₛ.isEVMState := by aesop + have keccak_inj := IsEVMₛ.1 this (Eq.symm h) + + rw [← Fin.ofNat''_eq_cast, ← Fin.ofNat''_eq_cast] at keccak_inj + unfold Fin.ofNat'' at keccak_inj + simp at keccak_inj + rw [Nat.mod_eq_of_lt, Nat.mod_eq_of_lt, Fin.val_eq_val] at keccak_inj + rw [keccak_inj] at account_mem_balances + exact (mem account_mem_balances) + · exact Address.ofUInt256_lt_UInt256_size + · exact Address.val_lt_UInt256_size + + -- address not in allowances + · intro owner spender mem_allowances + obtain ⟨erc_address, erc_intermediate, owner_lookup, spender_lookup, eq⟩ := + is_erc20.hasAllowance mem_allowances + rw [get_evm_of_ok] at owner_lookup spender_lookup + have spender_lookup_s := keccak_map_lookup_eq_of_Preserved_of_lookup Preserved spender_lookup + push_neg + use erc_intermediate + rw [ ← keccak ] + by_contra h + rw [not_and'] at h + apply h at owner_lookup + exact owner_lookup + + rw [spender_lookup_s] + by_contra h + have : [↑↑spender, erc_intermediate] ∈ evmₛ.keccak_map.keys := by + rw [Finmap.mem_keys] + apply Finmap.lookup_isSome.mp + have := Eq.trans (Eq.symm spender_lookup_s) spender_lookup + rw [this] + simp + have IsEVMₛ : evmₛ.isEVMState := by aesop + have keccak_inj := IsEVMₛ.1 this h + simp at keccak_inj + have intermediate_ne_balances : erc_intermediate ≠ ERC20Private.balances := by + obtain blocked_range := get_evm_of_ok ▸ is_erc20.block_acc_range.2.1 + rw [owner_lookup] at blocked_range + unfold not_mem_private at blocked_range + simp at blocked_range + rw [← Finset.forall_mem_not_eq] at blocked_range + have bal_mem_private: ERC20Private.balances ∈ ERC20Private.toFinset := by + unfold PrivateAddresses.toFinset + simp + specialize blocked_range ERC20Private.balances + exact blocked_range bal_mem_private + + tauto + -- address not in reserved space + · -- NOTE: Technically can be a one liner with a bit more infrastructure for keccak. + -- QUESTION: I don't think it's worth revisiting post-haste; or is it? + have blocked_range := keccak ▸ get_evm_of_ok ▸ s_erc20.block_acc_range.1 + exact not_mem_private_of_some blocked_range + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_decimals.lean b/Generated/erc20shim/ERC20Shim/fun_decimals.lean new file mode 100644 index 00000000..701c7ba0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_decimals.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_decimals_gen + +import Generated.erc20shim.ERC20Shim.fun_decimals_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma fun_decimals_abs_of_code {s₀ s₉ : State} {var } {fuel : Nat} : + execCall fuel fun_decimals [var] (s₀, []) = s₉ → + Spec (A_fun_decimals var ) s₀ s₉ +:= λ h ↦ fun_decimals_abs_of_concrete (fun_decimals_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_decimals_gen.lean b/Generated/erc20shim/ERC20Shim/fun_decimals_gen.lean new file mode 100644 index 00000000..9fc6d1de --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_decimals_gen.lean @@ -0,0 +1,86 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def fun_decimals : FunctionDefinition := var + +{var := 18} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_decimals_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var fuel}, + execCall fuel fun_decimals [var] (s₀, []) = s₉ → + Spec (C var ) s₀ s₉ + } := by + constructor + intros s₀ s₉ var fuel + unfold fun_decimals + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_decimals_user.lean b/Generated/erc20shim/ERC20Shim/fun_decimals_user.lean new file mode 100644 index 00000000..93c38c43 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_decimals_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_decimals_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_fun_decimals (var : Identifier) (s₀ s₉ : State) : Prop := sorry + +lemma fun_decimals_abs_of_concrete {s₀ s₉ : State} {var } : + Spec (fun_decimals_concrete_of_code.1 var ) s₀ s₉ → + Spec (A_fun_decimals var ) s₀ s₉ := by + unfold fun_decimals_concrete_of_code A_fun_decimals + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_msgSender.lean b/Generated/erc20shim/ERC20Shim/fun_msgSender.lean new file mode 100644 index 00000000..3ef0fabb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_msgSender.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_msgSender_gen + +import Generated.erc20shim.ERC20Shim.fun_msgSender_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma fun_msgSender_abs_of_code {s₀ s₉ : State} {var } {fuel : Nat} : + execCall fuel fun_msgSender [var] (s₀, []) = s₉ → + Spec (A_fun_msgSender var ) s₀ s₉ +:= λ h ↦ fun_msgSender_abs_of_concrete (fun_msgSender_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_msgSender_gen.lean b/Generated/erc20shim/ERC20Shim/fun_msgSender_gen.lean new file mode 100644 index 00000000..684a6eb8 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_msgSender_gen.lean @@ -0,0 +1,90 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def fun_msgSender : FunctionDefinition := var + +{var := caller()} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_msgSender_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var fuel}, + execCall fuel fun_msgSender [var] (s₀, []) = s₉ → + Spec (C var ) s₀ s₉ + } := by + constructor + intros s₀ s₉ var fuel + unfold fun_msgSender + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMCaller'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_msgSender_user.lean b/Generated/erc20shim/ERC20Shim/fun_msgSender_user.lean new file mode 100644 index 00000000..7f3ee896 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_msgSender_user.lean @@ -0,0 +1,58 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_msgSender_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_fun_msgSender (var : Identifier) (s₀ s₉ : State) : Prop := + preservesEvm s₀ s₉ ∧ + s₉.isOk ∧ + (s₀.evm.isEVMState → s₉.evm.isEVMState) ∧ + -- Case: Existing Hash collision in s₀ + (s₀.evm.hash_collision = true → s₉.evm.hash_collision) ∧ + ( + -- Case: No hash collision + ( + match s₀ with + | Ok evm _ => let s : State := s₀⟦var ↦ evm.execution_env.source⟧ + s₉.store = s.store ∧ + s₉.evm.hash_collision = false + | _ => s₉.evm.hash_collision = false -- OutOfFuel or Checkpoint + ) + -- Case: Hash collision during msgSender + ∨ s₉.evm.hash_collision = true + ) + +lemma fun_msgSender_abs_of_concrete {s₀ s₉ : State} {var } : + Spec (fun_msgSender_concrete_of_code.1 var ) s₀ s₉ → + Spec (A_fun_msgSender var ) s₀ s₉ := by + unfold fun_msgSender_concrete_of_code A_fun_msgSender + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + rintro hasFuel code + simp at code + rw [←code] + simp + + split_ands + · unfold preservesEvm + rw [← State.insert_of_ok, lookup_insert, State.insert_of_ok] + simp + · by_cases h : evm₀.hash_collision <;> [(right;assumption);skip] + left + split_ands <;> [skip;aesop] + unfold lookup! + simp + unfold State.insert + dsimp + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_name.lean b/Generated/erc20shim/ERC20Shim/fun_name.lean new file mode 100644 index 00000000..08382f3e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_name.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + +import Generated.erc20shim.ERC20Shim.fun_name_gen + +import Generated.erc20shim.ERC20Shim.fun_name_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_name_abs_of_code {s₀ s₉ : State} {var__mpos } {fuel : Nat} : + execCall fuel fun_name [var__mpos] (s₀, []) = s₉ → + Spec (A_fun_name var__mpos ) s₀ s₉ +:= λ h ↦ fun_name_abs_of_concrete (fun_name_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_name_gen.lean b/Generated/erc20shim/ERC20Shim/fun_name_gen.lean new file mode 100644 index 00000000..774ea5bf --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_name_gen.lean @@ -0,0 +1,102 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_name : FunctionDefinition := var__mpos + +{ + let _1 := 3 + var__mpos := copy_array_from_storage_to_memory_string(_1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_name_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var__mpos fuel}, + execCall fuel fun_name [var__mpos] (s₀, []) = s₉ → + Spec (C var__mpos ) s₀ s₉ + } := by + constructor + intros s₀ s₉ var__mpos fuel + unfold fun_name + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (copy_array_from_storage_to_memory_string_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_name_user.lean b/Generated/erc20shim/ERC20Shim/fun_name_user.lean new file mode 100644 index 00000000..8120c8b0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_name_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + +import Generated.erc20shim.ERC20Shim.fun_name_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_name (var__mpos : Identifier) (s₀ s₉ : State) : Prop := sorry + +lemma fun_name_abs_of_concrete {s₀ s₉ : State} {var__mpos } : + Spec (fun_name_concrete_of_code.1 var__mpos ) s₀ s₉ → + Spec (A_fun_name var__mpos ) s₀ s₉ := by + unfold fun_name_concrete_of_code A_fun_name + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_spendAllowance.lean b/Generated/erc20shim/ERC20Shim/fun_spendAllowance.lean new file mode 100644 index 00000000..8dd3d3bd --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_spendAllowance.lean @@ -0,0 +1,26 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_allowance +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.fun_spendAllowance_gen + +import Generated.erc20shim.ERC20Shim.fun_spendAllowance_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma fun_spendAllowance_abs_of_code {s₀ s₉ : State} { var_owner var_spender var_value} {fuel : Nat} : + execCall fuel fun_spendAllowance [] (s₀, [var_owner, var_spender, var_value]) = s₉ → + Spec (A_fun_spendAllowance var_owner var_spender var_value) s₀ s₉ +:= λ h ↦ fun_spendAllowance_abs_of_concrete (fun_spendAllowance_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_spendAllowance_gen.lean b/Generated/erc20shim/ERC20Shim/fun_spendAllowance_gen.lean new file mode 100644 index 00000000..3e7e920d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_spendAllowance_gen.lean @@ -0,0 +1,152 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_allowance +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def fun_spendAllowance : FunctionDefinition := + +{ + let var_currentAllowance := fun_allowance(var_owner, var_spender) + let _1 := not(0) + let _2 := lt(var_currentAllowance, _1) + if _2 + { + let _3 := lt(var_currentAllowance, var_value) + if _3 + { + let expr := var_spender + let expr_1 := var_currentAllowance + let expr_2 := var_value + let _4 := 64 + let _5 := mload(_4) + let _6 := shl(225, 2110234841) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_address_uint256_uint256(_8, var_spender, var_currentAllowance, var_value) + let _10 := sub(_9, _5) + revert(_5, _10) + } + let expr_3 := var_owner + let expr_4 := var_spender + let _11 := 0 + let _12 := sub(var_currentAllowance, var_value) + fun__approve(var_owner, var_spender, _12, _11) + } +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_spendAllowance_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { var_owner var_spender var_value fuel}, + execCall fuel fun_spendAllowance [] (s₀, [var_owner, var_spender, var_value]) = s₉ → + Spec (C var_owner var_spender var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_owner var_spender var_value fuel + unfold fun_spendAllowance + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_allowance_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMNot'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMLt'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_8475192588736690919_abs_of_code if_8475192588736690919 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_spendAllowance_user.lean b/Generated/erc20shim/ERC20Shim/fun_spendAllowance_user.lean new file mode 100644 index 00000000..55a19320 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_spendAllowance_user.lean @@ -0,0 +1,56 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_allowance +import Generated.erc20shim.ERC20Shim.Common.if_8475192588736690919 +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.fun__approve + +import Generated.erc20shim.ERC20Shim.fun_spendAllowance_gen + +import Generated.erc20shim.ERC20Shim.Predicate + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_fun_spendAllowance (var_owner var_spender var_value : Literal) (s₀ s₉ : State) : Prop := + let owner_addr := Address.ofUInt256 var_owner + let spender_addr := Address.ofUInt256 var_spender + let transfer_value : UInt256 := var_value + s₉.isOk ∧ + (s₀.evm.isEVMState → s₉.evm.isEVMState) ∧ + ( + ∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState) → + let currentAllowance := (erc20.allowances.lookup (owner_addr, spender_addr)).getD 0 + -- Case: spendAllowance succeeds + ( + let allowances := update_allowances erc20 owner_addr spender_addr transfer_value + IsERC20 ({ erc20 with allowances }) s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.store = s₀.store ∧ + s₉.evm.reverted = false + ) + ∨ + -- Case: spendAllowance fails + ( + IsERC20 erc20 s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉ = s₀.setRevert ∧ + currentAllowance < transfer_value + ) + -- Case: Hash collision + ∨ s₉.evm.hash_collision = true + ) + ∧ (s₀.evm.hash_collision = true → s₉.evm.hash_collision = true) + +lemma fun_spendAllowance_abs_of_concrete {s₀ s₉ : State} { var_owner var_spender var_value} : + Spec (fun_spendAllowance_concrete_of_code.1 var_owner var_spender var_value) s₀ s₉ → + Spec (A_fun_spendAllowance var_owner var_spender var_value) s₀ s₉ := by + unfold fun_spendAllowance_concrete_of_code A_fun_spendAllowance + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_symbol.lean b/Generated/erc20shim/ERC20Shim/fun_symbol.lean new file mode 100644 index 00000000..26788630 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_symbol.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + +import Generated.erc20shim.ERC20Shim.fun_symbol_gen + +import Generated.erc20shim.ERC20Shim.fun_symbol_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_symbol_abs_of_code {s₀ s₉ : State} {var_mpos } {fuel : Nat} : + execCall fuel fun_symbol [var_mpos] (s₀, []) = s₉ → + Spec (A_fun_symbol var_mpos ) s₀ s₉ +:= λ h ↦ fun_symbol_abs_of_concrete (fun_symbol_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_symbol_gen.lean b/Generated/erc20shim/ERC20Shim/fun_symbol_gen.lean new file mode 100644 index 00000000..f0b703bc --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_symbol_gen.lean @@ -0,0 +1,102 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_symbol : FunctionDefinition := var_mpos + +{ + let _1 := 4 + var_mpos := copy_array_from_storage_to_memory_string(_1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_symbol_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var_mpos fuel}, + execCall fuel fun_symbol [var_mpos] (s₀, []) = s₉ → + Spec (C var_mpos ) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_mpos fuel + unfold fun_symbol + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (copy_array_from_storage_to_memory_string_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_symbol_user.lean b/Generated/erc20shim/ERC20Shim/fun_symbol_user.lean new file mode 100644 index 00000000..8c112209 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_symbol_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.copy_array_from_storage_to_memory_string + +import Generated.erc20shim.ERC20Shim.fun_symbol_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_symbol (var_mpos : Identifier) (s₀ s₉ : State) : Prop := sorry + +lemma fun_symbol_abs_of_concrete {s₀ s₉ : State} {var_mpos } : + Spec (fun_symbol_concrete_of_code.1 var_mpos ) s₀ s₉ → + Spec (A_fun_symbol var_mpos ) s₀ s₉ := by + unfold fun_symbol_concrete_of_code A_fun_symbol + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_totalSupply.lean b/Generated/erc20shim/ERC20Shim/fun_totalSupply.lean new file mode 100644 index 00000000..817f7966 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_totalSupply.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_totalSupply_gen + +import Generated.erc20shim.ERC20Shim.fun_totalSupply_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma fun_totalSupply_abs_of_code {s₀ s₉ : State} {var_ } {fuel : Nat} : + execCall fuel fun_totalSupply [var_] (s₀, []) = s₉ → + Spec (A_fun_totalSupply var_ ) s₀ s₉ +:= λ h ↦ fun_totalSupply_abs_of_concrete (fun_totalSupply_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_totalSupply_gen.lean b/Generated/erc20shim/ERC20Shim/fun_totalSupply_gen.lean new file mode 100644 index 00000000..9e6a199a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_totalSupply_gen.lean @@ -0,0 +1,94 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def fun_totalSupply : FunctionDefinition := var_ + +{ + let _1 := 2 + var_ := sload(_1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_totalSupply_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var_ fuel}, + execCall fuel fun_totalSupply [var_] (s₀, []) = s₉ → + Spec (C var_ ) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_ fuel + unfold fun_totalSupply + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_totalSupply_user.lean b/Generated/erc20shim/ERC20Shim/fun_totalSupply_user.lean new file mode 100644 index 00000000..611d39f1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_totalSupply_user.lean @@ -0,0 +1,45 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.fun_totalSupply_gen +import Generated.erc20shim.ERC20Shim.Predicate +import Generated.erc20shim.ERC20Shim.Variables + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_fun_totalSupply (var_ : Identifier) (s₀ s₉ : State) : Prop := + ∀ {erc20}, IsERC20 erc20 s₀ → + IsERC20 erc20 s₉ ∧ s₉ = s₀⟦var_ ↦ erc20.supply⟧ + +lemma fun_totalSupply_abs_of_concrete {s₀ s₉ : State} {var_ } : + Spec (fun_totalSupply_concrete_of_code.1 var_ ) s₀ s₉ → + Spec (A_fun_totalSupply var_ ) s₀ s₉ := by + unfold fun_totalSupply_concrete_of_code A_fun_totalSupply + rcases s₀ with ⟨evm, varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + intro hasFuel code erc20 is_erc20 + + unfold reviveJump at code + simp at code + rw [ ← State.insert_of_ok, ← State.insert_of_ok ] at code + rw [ ← State.insert_of_ok ] + clr_varstore, + + have := is_erc20.hasSupply + simp at this + rw [← Variables.totalSupply_def, this] at code + + apply And.intro + · rw [← code] + exact IsERC20_of_insert is_erc20 + · symm + assumption + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transfer.lean b/Generated/erc20shim/ERC20Shim/fun_transfer.lean new file mode 100644 index 00000000..aaa2415c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transfer.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun__transfer + +import Generated.erc20shim.ERC20Shim.fun_transfer_gen + +import Generated.erc20shim.ERC20Shim.fun_transfer_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_transfer_abs_of_code {s₀ s₉ : State} {var var_to var_value} {fuel : Nat} : + execCall fuel fun_transfer [var] (s₀, [var_to, var_value]) = s₉ → + Spec (A_fun_transfer var var_to var_value) s₀ s₉ +:= λ h ↦ fun_transfer_abs_of_concrete (fun_transfer_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transferFrom.lean b/Generated/erc20shim/ERC20Shim/fun_transferFrom.lean new file mode 100644 index 00000000..d6f0fbd0 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transferFrom.lean @@ -0,0 +1,25 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_spendAllowance +import Generated.erc20shim.ERC20Shim.fun__transfer + +import Generated.erc20shim.ERC20Shim.fun_transferFrom_gen + +import Generated.erc20shim.ERC20Shim.fun_transferFrom_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma fun_transferFrom_abs_of_code {s₀ s₉ : State} {var var_from var_to var_value} {fuel : Nat} : + execCall fuel fun_transferFrom [var] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (A_fun_transferFrom var var_from var_to var_value) s₀ s₉ +:= λ h ↦ fun_transferFrom_abs_of_concrete (fun_transferFrom_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transferFrom_gen.lean b/Generated/erc20shim/ERC20Shim/fun_transferFrom_gen.lean new file mode 100644 index 00000000..1b44f86f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transferFrom_gen.lean @@ -0,0 +1,136 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_spendAllowance +import Generated.erc20shim.ERC20Shim.fun__transfer + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_transferFrom : FunctionDefinition := var + +{ + let _1 := fun_msgSender() + fun_spendAllowance(var_from, _1, var_value) + fun__transfer(var_from, var_to, var_value) + var := 1 +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_transferFrom_concrete_of_code +: { + C : + _ → _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var var_from var_to var_value fuel}, + execCall fuel fun_transferFrom [var] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (C var var_from var_to var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var var_from var_to var_value fuel + unfold fun_transferFrom + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_msgSender_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_spendAllowance_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun__transfer_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transferFrom_user.lean b/Generated/erc20shim/ERC20Shim/fun_transferFrom_user.lean new file mode 100644 index 00000000..53b72860 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transferFrom_user.lean @@ -0,0 +1,500 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun_spendAllowance +import Generated.erc20shim.ERC20Shim.fun__transfer + +import Generated.erc20shim.ERC20Shim.fun_transferFrom_gen + +import Generated.erc20shim.ERC20Shim.Predicate + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_transferFrom (var : Identifier) (var_from var_to var_value : Literal) (s₀ s₉ : State) : Prop := + let sender := Address.ofUInt256 var_from + let recipient := Address.ofUInt256 var_to + let amount : UInt256 := var_value + ( + ∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState ∧ s₀.evm.reverted = false) → + -- Case: transferFrom succeeds + ( + let balances := update_balances erc20 sender recipient amount + let allowances := update_allowances erc20 sender s₀.evm.execution_env.source amount + IsERC20 ({ erc20 with balances, allowances }) s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + s₉[var]!! = 1 ∧ + s₉.evm.reverted = false + + ) + ∨ + -- Case: transferFrom fails + ( + let currentAllowance := (erc20.allowances.lookup (sender, s₀.evm.execution_env.source)).getD 0 + IsERC20 erc20 s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + s₉[var]!! = 1 ∧ + s₉.evm.reverted = true ∧ + (recipient.1 = 0 ∨ + sender.1 = 0 ∨ + balanceOf s₀.evm sender < amount ∨ + currentAllowance < amount) + ) + -- Case: Hash collision + ∨ s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 1500000 + +theorem Generated.erc20shim.ERC20Shim.extracted_1 {s₉ : State} {var : Identifier} {var_from var_to var_value : Literal} + (s0_evm : EVM) (s0_varstore : VarStore) (s_inhabited : State) + (s_inhabited_all : + Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧ = s_inhabited) + (s_inhabited_ok : s_inhabited.isOk) (hasFuel : ¬❓ s₉) (s s' s'' : State) {erc_20 : ERC20} (s₀ : State) + (s0_all : Ok s0_evm s0_varstore = s₀) (s0_isERC20 : IsERC20 erc_20 s₀) (evmState : isEVMState s₀.evm) + (s0_notReverted : s₀.evm.reverted = false) (s0_ok : s₀.isOk) + (s_inhabited_not_reverted : s_inhabited.evm.reverted = false) (s_ok : s.isOk) + (s_preserve_evmState : + isEVMState Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧.evm → + isEVMState s.evm) + (s_preserve_collision : + Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧.evm.hash_collision = true → + s.evm.hash_collision = true) + (s_source : + s.store = + Ok s0_evm + Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧⟦"_1"↦↑↑s0_evm.execution_env.source⟧.store) + (s_collision_false : s.evm.hash_collision = false) (s_evm : EVM) (s_varstore : VarStore) + (s_preservesEvm : preservesEvm (Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧) (Ok s_evm s_varstore)) + (s_all : s = Ok s_evm s_varstore) (s_not_reverted : s.evm.reverted = false) (s0_s_preservesEvm : preservesEvm s₀ s) + (s_erc20 : IsERC20 erc_20 s) (s_isEvmState : isEVMState s.evm) (s'_ok : s'.isOk) + (s'_isEVMState : isEVMState s.evm → isEVMState s'.evm) + (s'_pres_collision : s.evm.hash_collision = true → s'.evm.hash_collision = true) (s'_evm : EVM) + (s'_varstore : VarStore) (s'_all : s' = Ok s'_evm s'_varstore) (s''_ok : s''.isOk) + (s''_pres_collision : s'.evm.hash_collision = true → s''.evm.hash_collision = true) (s''_evm : EVM) + (s''_varstore : VarStore) (s''_all : s'' = Ok s''_evm s''_varstore) (s9_ok : s₉.isOk) + (code : Ok s''_evm s0_varstore⟦var↦ State.lookup! var (Ok s''_evm (Finmap.insert "var" 1 s''_varstore))⟧ = s₉) + (this : Preserved s''_evm s''_evm) (s9_preservesEvm : preservesEvm s'' s₉) + (s_values : + s₀.evm.execution_env.source = Address.ofUInt256 (s["_1"]!!) ∧ + var_value = s["var_value"]!! ∧ var_from = s["var_from"]!! ∧ var_to = s["var_to"]!!) + (s'_erc20 : IsERC20 erc_20 s') (s'_preservesEvm : preservesEvm s s') (s'_reverted : s' = s.setRevert) + (s'_source : + (Finmap.lookup (Address.ofUInt256 var_from, s₀.evm.execution_env.source) erc_20.allowances).getD 0 < var_value) + (isEvmState_s' : isEVMState s'.evm) (s'_store : s'.store = s.store) + (s'_values : var_to = s'["var_to"]!! ∧ var_value = s'["var_value"]!! ∧ var_from = s'["var_from"]!!) + (s''_erc20 : + IsERC20 + { supply := erc_20.supply, + balances := update_balances erc_20 (Address.ofUInt256 var_from) (Address.ofUInt256 var_to) var_value, + allowances := erc_20.allowances } + s'') + (s''_preservesEvm : preservesEvm s' s'') (s''_not_reverted : s''.evm.reverted = false) + (h : + ¬(Finmap.lookup (Address.ofUInt256 var_from, s₀.evm.execution_env.source) erc_20.allowances).getD 0 = + Fin.last UInt256.top) : + IsERC20 + { supply := erc_20.supply, + balances := update_balances erc_20 (Address.ofUInt256 var_from) (Address.ofUInt256 var_to) var_value, + allowances := + Finmap.insert (Address.ofUInt256 var_from, s₀.evm.execution_env.source) + ((Finmap.lookup (Address.ofUInt256 var_from, s₀.evm.execution_env.source) erc_20.allowances).getD 0 - + var_value) + erc_20.allowances } + s'' := by sorry + +lemma fun_transferFrom_abs_of_concrete {s₀ s₉ : State} {var var_from var_to var_value} : + Spec (fun_transferFrom_concrete_of_code.1 var var_from var_to var_value) s₀ s₉ → + Spec (A_fun_transferFrom var var_from var_to var_value) s₀ s₉ := by + + unfold fun_transferFrom_concrete_of_code A_fun_transferFrom + + -- Split s₀ into the 3 cases of OK, OutOfFuel, and Checkpoint + -- Immediately prove the latter cases with simp and aesop + -- Assign the initial state s₀ + rcases s₀ with ⟨s0_evm, s0_varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + -- applies the Spec + apply spec_eq + + -- Unfolds initcall and setStore + clr_funargs + + generalize s_inhabited_all : (Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧) = s_inhabited at * + have s_inhabited_ok : s_inhabited.isOk := by + aesop_spec + + -- s₀ --> s using call_msgSender + -- s --> s' using call_spendAllowance + -- s' --> s'' using call_transfer + -- s' --> s₉ using code + rintro hasFuel ⟨s, call_msgSender, ⟨s', call_spendAllowance, ⟨s'', call_transfer, code⟩⟩⟩ + + intro erc_20 s0_isERC20 evmState s0_notReverted + + -- Assign s₀ state to tidy up goal + generalize s0_all : Ok s0_evm s0_varstore = s₀ at * + have s0_ok : s₀.isOk := by + aesop + + have s_inhabited_not_reverted : s_inhabited.evm.reverted = false := by + aesop + + -- Clear specs at call_msgSender + unfold A_fun_msgSender at call_msgSender + clr_spec at call_msgSender + rw[←s_inhabited_all] at call_msgSender + + obtain ⟨s_preservesEvm, + ⟨s_ok, s_preserve_evmState, s_preserve_collision, + ⟨⟨s_source, s_collision_false⟩⟩⟩⟩ := call_msgSender + + · -- No collision at msgSender + + -- Combine state s in s_all + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have s_not_reverted : s.evm.reverted = false := by + rw [s_inhabited_all] at s_preservesEvm + have eq := preservesEvm_of_isOk s_inhabited_ok s_ok s_preservesEvm + rw [←eq.2.2.2.1] + exact s_inhabited_not_reverted + + rw [preservesEvm_of_insert, preservesEvm_of_insert, s_all] at s_preservesEvm + + -- Obtain hypotheses for state s from state s₀ + have s0_s_preservesEvm : preservesEvm s₀ s := by aesop (add simp preservesEvm) + have s_erc20 : IsERC20 erc_20 s := IsERC20_of_preservesEvm s0_s_preservesEvm s0_isERC20 + have s_isEvmState : isEVMState s.evm := by aesop + + unfold A_fun_spendAllowance at call_spendAllowance + clr_spec at call_spendAllowance + + unfold A_fun__transfer at call_transfer + clr_spec at call_transfer + + dsimp at call_spendAllowance + rcases call_spendAllowance with ⟨s'_ok, s'_isEVMState, spendAllowance_right, s'_pres_collision⟩ + obtain ⟨s'_evm, ⟨s'_varstore, s'_all⟩⟩ := State_of_isOk s'_ok + + dsimp at call_transfer + rcases call_transfer with ⟨s''_ok, transfer_right, s''_pres_collision⟩ + obtain ⟨s''_evm, ⟨s''_varstore, s''_all⟩⟩ := State_of_isOk s''_ok + + have s9_ok : s₉.isOk := by + aesop + + unfold reviveJump at code + simp [s''_all, ←s0_all] at code + rw [← State.insert_of_ok] at code + + have : Preserved s''_evm s''_evm := by aesop + have s9_preservesEvm : preservesEvm s'' s₉ := by + rw [s''_all, ←code] + apply this + + have s_values : s₀.evm.execution_env.source = Address.ofUInt256 (s["_1"]!!) ∧ + var_value = s["var_value"]!! ∧ + var_from = s["var_from"]!! ∧ + var_to = s["var_to"]!! := by + rw [s_all] + rw [s_all] at s_source + unfold store at s_source + unfold State.insert at s_source + simp at s_source + rw [s_source] + unfold lookup! + split_ands + · simp [←s0_all, Address.ofUInt256] + generalize eq₁ : s0_evm.execution_env.source = x + rw [ + Nat.mod_eq_of_lt (by rw [Nat.mod_eq_of_lt (Fin.val_lt_of_le _ (by decide))]; omega), + Nat.mod_eq_of_lt (Fin.val_lt_of_le _ (by decide)) + ] + rcases x with ⟨x, hx⟩ + simp [Fin.ofNat] + unfold Address.size at hx + omega + · aesop + · aesop + · aesop + + rw[←s_values.1, ←s_values.2.1, ←s_values.2.2.1] at spendAllowance_right + + specialize spendAllowance_right ⟨s_erc20, s_isEvmState⟩ + + obtain ⟨s'_erc20, s'_preservesEvm, s'_store, s'_not_reverted⟩ + | ⟨s'_erc20, s'_preservesEvm, s'_reverted, s'_source⟩ + | s'_collision + := spendAllowance_right + + · -- spendAllowance success + + have isEvmState_s' : isEVMState s'.evm := by + aesop + + have s'_values : var_to = s'["var_to"]!! ∧ + var_value = s'["var_value"]!! ∧ + var_from = s'["var_from"]!! := by + rw [s'_all] at s'_store + rw [s_all] at s'_store + unfold store at s'_store + aesop + + specialize transfer_right ⟨s'_erc20, isEvmState_s'⟩ + + obtain ⟨s''_erc20, s''_preservesEvm, s''_not_reverted⟩ + | ⟨s''_erc20, s''_preservesEvm, s''_reverted, s''_error⟩ + | s''_collision + := transfer_right + + · -- transfer success + left + + refine' ⟨?_ ,?_, ?_, ?_, (by aesop)⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + aesop + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · apply Utilities.preservesEvm_trans s'_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + have : s''.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s'_ok s''_ok) + aesop + aesop + + · rw [←code] + simp + unfold State.insert at code + unfold lookup! + simp + + · -- transfer fail + + right + left + + refine' ⟨?_, ?_, ?_, ?_, ?_, ?_⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + apply IsERC20_of_preservesEvm s''_preservesEvm + apply IsERC20_of_preservesEvm s'_preservesEvm + aesop + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · apply Utilities.preservesEvm_trans s'_ok + · aesop + · apply Utilities.preservesEvm_trans s''_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + have : s''.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s'_ok s''_ok) + aesop + rw [←code] + rw[s''_all] at this + rw[←this] + simp + + · rw [←code] + simp + unfold lookup! + simp + + · have : s''.evm.reverted = true := by + unfold setRevert at s''_reverted + aesop + rw [←code] + simp + rw[s''_all] at this + rw[<-this] + simp + + · rw [←s'_values.1, ←s'_values.2.1, ←s'_values.2.2] at s''_error + obtain zero_addr | balance_error := s''_error + · aesop + · right + right + left + have : s₀.evm.account_map = s'.evm.account_map := by + have := (preservesEvm_of_isOk s0_ok s'_ok) + have : preservesEvm s₀ s' := by + apply Utilities.preservesEvm_trans s_ok + · aesop + · aesop + aesop + unfold balanceOf + unfold balanceOf at balance_error + rw[this] + exact balance_error + + · -- collision at transfer + right + right + aesop + + · -- spendAllowance fail + + have isEvmState_s' : isEVMState s'.evm := by + aesop + + have s'_store : s'.store = s.store := by + rw[s'_reverted] + rw[s_all] + unfold setRevert + simp + unfold store + simp + + have s'_values : var_to = s'["var_to"]!! ∧ + var_value = s'["var_value"]!! ∧ + var_from = s'["var_from"]!! := by + rw [s'_all] at s'_store + rw [s_all] at s'_store + unfold store at s'_store + aesop + + specialize transfer_right ⟨s'_erc20, isEvmState_s'⟩ + + obtain ⟨s''_erc20, s''_preservesEvm, s''_not_reverted⟩ + | ⟨s''_erc20, s''_preservesEvm, s''_reverted, s''_error⟩ + | s''_collision + := transfer_right + + · -- transfer success + left + + refine' ⟨?_ ,?_, ?_, ?_, (by aesop)⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + + rw [←s'_values.1, ←s'_values.2.1, ←s'_values.2.2] at s''_erc20 + unfold update_allowances + simp + split + · exact s''_erc20 + · sorry + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · apply Utilities.preservesEvm_trans s'_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + have : s''.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s'_ok s''_ok) + aesop + aesop + + · rw [←code] + simp + unfold State.insert at code + unfold lookup! + simp + + · -- transfer fail + + right + left + + refine' ⟨?_, ?_, ?_, ?_, ?_, ?_⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + apply IsERC20_of_preservesEvm s''_preservesEvm + apply IsERC20_of_preservesEvm s'_preservesEvm + aesop + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · apply Utilities.preservesEvm_trans s'_ok + · aesop + · apply Utilities.preservesEvm_trans s''_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + have : s''.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s'_ok s''_ok) + aesop + rw [←code] + rw[s''_all] at this + rw[←this] + simp + + · rw [←code] + simp + unfold lookup! + simp + + · have : s''.evm.reverted = true := by + unfold setRevert at s''_reverted + aesop + rw [←code] + simp + rw[s''_all] at this + rw[<-this] + simp + + · rw [←s'_values.1, ←s'_values.2.1, ←s'_values.2.2] at s''_error + obtain zero_addr | balance_error := s''_error + · aesop + · right + right + left + have : s₀.evm.account_map = s'.evm.account_map := by + have := (preservesEvm_of_isOk s0_ok s'_ok) + have : preservesEvm s₀ s' := by + apply Utilities.preservesEvm_trans s_ok + · aesop + · aesop + aesop + unfold balanceOf + unfold balanceOf at balance_error + rw[this] + exact balance_error + + · --collision in spendAllowance + aesop + + · -- collision at msgSender + + rename_i s_collision + + right + right + + unfold A_fun_spendAllowance at call_spendAllowance + clr_spec at call_spendAllowance + unfold A_fun__transfer at call_transfer + clr_spec at call_transfer + + dsimp at call_transfer + rcases call_transfer with ⟨s''_ok, transfer_right, s''_pres_collision⟩ + obtain ⟨s''_evm, ⟨s''_varstore, s''_all⟩⟩ := State_of_isOk s''_ok + + aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transfer_gen.lean b/Generated/erc20shim/ERC20Shim/fun_transfer_gen.lean new file mode 100644 index 00000000..dc73a684 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transfer_gen.lean @@ -0,0 +1,119 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun__transfer + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def fun_transfer : FunctionDefinition := var + +{ + let _1 := fun_msgSender() + fun__transfer(_1, var_to, var_value) + var := 1 +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_transfer_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {var var_to var_value fuel}, + execCall fuel fun_transfer [var] (s₀, [var_to, var_value]) = s₉ → + Spec (C var var_to var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var var_to var_value fuel + unfold fun_transfer + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun_msgSender_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- simp [Var'] + -- simp [Var'] + -- simp [Var'] + try simp + + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (fun__transfer_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_transfer_user.lean b/Generated/erc20shim/ERC20Shim/fun_transfer_user.lean new file mode 100644 index 00000000..cfc7c712 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_transfer_user.lean @@ -0,0 +1,318 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.fun_msgSender +import Generated.erc20shim.ERC20Shim.fun__transfer + +import Generated.erc20shim.ERC20Shim.fun_transfer_gen + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_fun_transfer (var : Identifier) (var_to var_value : Literal) (s₀ s₉ : State) : Prop := + + let recipient := Address.ofUInt256 var_to + let amount : UInt256 := var_value + let sender := s₀.evm.execution_env.source + ( + ∀ {erc20}, (IsERC20 erc20 s₀ ∧ s₀.evm.isEVMState ∧ s₀.evm.reverted = false) → + -- Transfer succeeds + ( + let balances := update_balances erc20 sender recipient amount + IsERC20 ({ erc20 with balances }) s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + s₉[var]!! = 1 ∧ + s₉.evm.reverted = false + ) + ∨ + -- Transfer Fails + ( + IsERC20 erc20 s₉ ∧ + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + s₉[var]!! = 1 ∧ + s₉.evm.reverted = true ∧ + (recipient.1 = 0 ∨ balanceOf s₀.evm sender < amount) + ) + -- Hash Collision + ∨ s₉.evm.hash_collision = true + ) + +-- set_option pp.notation false in + +set_option maxHeartbeats 1000000 + +lemma fun_transfer_abs_of_concrete {s₀ s₉ : State} {var var_to var_value} : + Spec (fun_transfer_concrete_of_code.1 var var_to var_value) s₀ s₉ → + Spec (A_fun_transfer var var_to var_value) s₀ s₉ := by + + -- Unfold the definitions of the abstract and concrete specifications + unfold fun_transfer_concrete_of_code A_fun_transfer + -- Notice we now have two Specs in the tactic state - one for each specification + + -- Split s₀ into the 3 cases of OK, OutOfFuel, and Checkpoint + -- Immediately prove the latter cases with simp and aesop + -- Assign the initial state s₀ + rcases s₀ with ⟨s0_evm, s0_varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + -- applies the Spec + apply spec_eq + + -- Unfolds initcall and setStore + clr_funargs + + -- Assign s_inhabited state to tidy up goal + --set s_inhabited := (Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧) with eq1 + generalize s_inhabited_all : (Ok s0_evm Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧) = s_inhabited at * + -- Show state is Ok + have s_inhabited_ok : s_inhabited.isOk := by + aesop_spec + + -- s₀ --> s using call_msgSender + -- s --> s' using call_transfer + -- s' --> s₉ using code + rintro hasFuel ⟨s, call_msgSender, ⟨s', call_transfer, code⟩⟩ + + -- Introduce hypotheses for s₀ + intro erc_20 s0_isERC20 evmState s0_notReverted + + -- Assign s₀ state to tidy up goal + generalize s0_all : Ok s0_evm s0_varstore = s₀ at * + + have s0_ok : s₀.isOk := by + aesop + + have s_inhabited_not_reverted : s_inhabited.evm.reverted = false := by + aesop + + -- Clear specs at call_msgSender + unfold A_fun_msgSender at call_msgSender + clr_spec at call_msgSender + + rw[←s_inhabited_all] at call_msgSender + + obtain ⟨s_preservesEvm, + ⟨s_ok, s_preserve_evmState, s_preserve_collision, + ⟨⟨s_source, s_collision_false⟩⟩⟩⟩ := call_msgSender + + · -- No hash collision at state s + + -- Combine state s in s_all + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have s_not_reverted : s.evm.reverted = false := by + rw [s_inhabited_all] at s_preservesEvm + have eq := preservesEvm_of_isOk s_inhabited_ok s_ok s_preservesEvm + rw [←eq.2.2.2.1] + exact s_inhabited_not_reverted + + rw [preservesEvm_of_insert, preservesEvm_of_insert, s_all] at s_preservesEvm + + -- Obtain hypotheses for state s from state s₀ + have s0_s_preservesEvm : preservesEvm s₀ s := by aesop (add simp preservesEvm) + have s_isERC20 : IsERC20 erc_20 s := IsERC20_of_preservesEvm s0_s_preservesEvm s0_isERC20 + have isEvmState_s : isEVMState s.evm := by aesop + + unfold A_fun__transfer at call_transfer + clr_spec at call_transfer + + dsimp at call_transfer + rcases call_transfer with ⟨s'_ok, transfer_right, s'_collision⟩ + + obtain ⟨s'_evm, ⟨s'_varstore, s'_all⟩⟩ := State_of_isOk s'_ok + + have s9_ok : s₉.isOk := by + aesop + + unfold reviveJump at code + simp [s'_all, ←s0_all] at code + rw [← State.insert_of_ok] at code + + have s9_preserved : Preserved s'_evm s'_evm := by aesop + have s9_preservesEvm : preservesEvm s' s₉ := by + rw [s'_all, ←code] + apply s9_preserved + + have s_values : s₀.evm.execution_env.source = Address.ofUInt256 (s["_1"]!!) ∧ + var_value = s["var_value"]!! ∧ + var_to = s["var_to"]!! := by + rw [s_all] + rw [s_all] at s_source + unfold store at s_source + unfold State.insert at s_source + simp at s_source + rw [s_source] + unfold lookup! + split_ands + · simp [←s0_all, Address.ofUInt256] + generalize eq₁ : s0_evm.execution_env.source = x + rw [ + Nat.mod_eq_of_lt (by rw [Nat.mod_eq_of_lt (Fin.val_lt_of_le _ (by decide))]; omega), + Nat.mod_eq_of_lt (Fin.val_lt_of_le _ (by decide)) + ] + rcases x with ⟨x, hx⟩ + simp [Fin.ofNat] + unfold Address.size at hx + omega + · simp + rw [Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp) + , Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp)] + simp + · simp + rw [Finmap.lookup_insert_of_ne _ (by unfold Ne; apply String.ne_of_data_ne; simp)] + simp + + specialize transfer_right ⟨s_isERC20, isEvmState_s⟩ + + obtain ⟨s'_erc20, s'_preservesEvm, s'_not_reverted⟩ + | ⟨s'_erc20, s'_preservesEvm, s'_reverted, addr_balance_error⟩ + | s'_collision + := transfer_right + + · -- Transfer success case + left + + refine' ⟨?_ ,?_, ?_, ?_, (by aesop)⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + rw [←s_values.1, ←s_values.2.1, ←s_values.2.2] at s'_erc20 + exact s'_erc20 + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + aesop + + · rw [←code] + simp + unfold State.insert at code + unfold lookup! + simp + + · -- Transfer fail case + right + left + + have evm_revert : s'_evm = {s_evm with reverted := true} := by + unfold setRevert at s'_reverted + aesop + + have varstore_eq : s'_varstore = s_varstore := by + unfold setRevert at s'_reverted + aesop + + refine' ⟨?_, ?_, ?_, ?_, (by aesop), ?_⟩ + + · apply IsERC20_of_preservesEvm s9_preservesEvm + exact s'_erc20 + + · apply Utilities.preservesEvm_trans s_ok + · aesop + · aesop + + · have : s'.evm.hash_collision = false := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + aesop + + · rw [←code] + simp + unfold lookup! + simp + + · cases addr_balance_error + · aesop + · rename_i h + right + rw[s_values.1, s_values.2.1] + have : s.evm.account_map = s₀.evm.account_map := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + unfold balanceOf + unfold balanceOf at h + rw[←this] + exact h + + · -- collision at transfer + right + right + aesop + + · -- collision at msgSender + right + right + rename_i s_collision + + -- Combine state s in s_all + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + have s_not_reverted : s.evm.reverted = false := by + rw [s_inhabited_all] at s_preservesEvm + have eq := preservesEvm_of_isOk s_inhabited_ok s_ok s_preservesEvm + rw [←eq.2.2.2.1] + exact s_inhabited_not_reverted + + rw [preservesEvm_of_insert, preservesEvm_of_insert, s_all] at s_preservesEvm + + -- Obtain hypotheses for state s from state s₀ + have s0_s_preservesEvm : preservesEvm s₀ s := by aesop (add simp preservesEvm) + have s_isERC20 : IsERC20 erc_20 s := IsERC20_of_preservesEvm s0_s_preservesEvm s0_isERC20 + have isEvmState_s : isEVMState s.evm := by aesop + + unfold A_fun__transfer at call_transfer + clr_spec at call_transfer + + simp at call_transfer + rcases call_transfer with ⟨s'_ok, transfer_right, s'_collision⟩ + + obtain ⟨s'_evm, ⟨s'_varstore, s'_all⟩⟩ := State_of_isOk s'_ok + + have s9_ok : s₉.isOk := by + aesop + + unfold reviveJump at code + simp [s'_all, ←s0_all] at code + rw [← State.insert_of_ok] at code + + have s9_preserved : Preserved s'_evm s'_evm := by aesop + have s9_preservesEvm : preservesEvm s' s₉ := by + rw [s'_all, ←code] + apply s9_preserved + + specialize transfer_right s_isERC20 isEvmState_s + + obtain ⟨s'_erc20, s'_preservesEvm, s'_not_reverted⟩ + | ⟨s'_erc20, s'_preservesEvm, s'_reverted, addr_balance_error⟩ + | s'_collision + := transfer_right + + · -- transfer success + rw [←code] + simp + have : s.evm.hash_collision = true → s'.evm.hash_collision = true := by + have account_map_preservation := (preservesEvm_of_isOk s_ok s'_ok s'_preservesEvm).2.1 + aesop + aesop + + · -- transfer fail + rw [←code] + simp + have : s'.evm.hash_collision = true := by + have := (preservesEvm_of_isOk s_ok s'_ok) + aesop + rw[s'_all] at this + exact this + + · -- hash collision + aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_update.lean b/Generated/erc20shim/ERC20Shim/fun_update.lean new file mode 100644 index 00000000..a1efff82 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_update.lean @@ -0,0 +1,29 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.fun_update_gen + +import Generated.erc20shim.ERC20Shim.fun_update_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +lemma fun_update_abs_of_code {s₀ s₉ : State} { var_from var_to var_value} {fuel : Nat} : + execCall fuel fun_update [] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (A_fun_update var_from var_to var_value) s₀ s₉ +:= λ h ↦ fun_update_abs_of_concrete (fun_update_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_update_gen.lean b/Generated/erc20shim/ERC20Shim/fun_update_gen.lean new file mode 100644 index 00000000..c1e62be2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_update_gen.lean @@ -0,0 +1,254 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def fun_update : FunctionDefinition := + +{ + let expr := var_from + let _1 := sub(shl(160, 1), 1) + let _2 := and(var_from, _1) + let _3 := iszero(_2) + switch _3 case 0 { + let _4 := 0 + let _5 := mapping_index_access_mapping_address_uint256_of_address(_4, var_from) + let _6 := sload(_5) + let var_fromBalance := _6 + let _7 := lt(_6, var_value) + if _7 + { + let expr_1 := var_from + let expr_2 := _6 + let expr_3 := var_value + let _8 := 64 + let _9 := mload(_8) + let _10 := shl(226, 957625571) + mstore(_9, _10) + let _11 := 4 + let _12 := add(_9, _11) + let _13 := abi_encode_address_uint256_uint256(_12, var_from, _6, var_value) + let _14 := sub(_13, _9) + revert(_9, _14) + } + let expr_4 := sub(_6, var_value) + let _15 := _4 + let _16 := mapping_index_access_mapping_address_uint256_of_address(_4, var_from) + update_storage_value_offsett_uint256_to_uint256(_16, expr_4) + } + default + { + let _17 := 2 + let _18 := sload(_17) + let _19 := _18 + let _20 := checked_add_uint256(_18, var_value) + let _21 := _17 + update_storage_value_offsett_uint256_to_uint256(_17, _20) + } + let expr_5 := var_to + let _22 := _1 + let _23 := and(var_to, _1) + let _24 := iszero(_23) + switch _24 case 0 { + let expr_6 := var_value + let _25 := 0 + let _26 := mapping_index_access_mapping_address_uint256_of_address(_25, var_to) + let _27 := sload(_26) + let _28 := _27 + let _29 := add(_27, var_value) + update_storage_value_offsett_uint256_to_uint256(_26, _29) + } + default + { + let _30 := 2 + let _31 := sload(_30) + let _32 := _31 + let _33 := sub(_31, var_value) + let _34 := _30 + update_storage_value_offsett_uint256_to_uint256(_30, _33) + } + let expr_7 := var_from + let expr_8 := var_to + let expr_9 := var_value + let _35 := 100389287136786176327247604509743168900146139575972864366142685224231313322991 + let _36 := _2 + let _37 := _23 + let _38 := 64 + let _39 := mload(_38) + let _40 := abi_encode_uint256(_39, var_value) + let _41 := sub(_40, _39) + log3(_39, _41, _35, _2, _23) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def fun_update_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { var_from var_to var_value fuel}, + execCall fuel fun_update [] (s₀, [var_from, var_to, var_value]) = s₉ → + Spec (C var_from var_to var_value) s₀ s₉ + } := by + constructor + intros s₀ s₉ var_from var_to var_value fuel + unfold fun_update + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract switch_2364266820542243941_abs_of_code switch_2364266820542243941 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract switch_1041419350816529734_abs_of_code switch_1041419350816529734 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMMload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (abi_encode_uint256_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMLog3'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/fun_update_user.lean b/Generated/erc20shim/ERC20Shim/fun_update_user.lean new file mode 100644 index 00000000..ca1d68fb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/fun_update_user.lean @@ -0,0 +1,144 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.switch_2364266820542243941 +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address +import Generated.erc20shim.ERC20Shim.abi_encode_address_uint256_uint256 +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256 +import Generated.erc20shim.ERC20Shim.checked_add_uint256 +import Generated.erc20shim.ERC20Shim.Common.switch_1041419350816529734 +import Generated.erc20shim.ERC20Shim.abi_encode_uint256 + +import Generated.erc20shim.ERC20Shim.fun_update_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common Generated.erc20shim ERC20Shim + +def A_fun_update (var_from var_to var_value : Literal) (s₀ s₉ : State) : Prop := + let from_ := Address.ofUInt256 var_from + let to_ := Address.ofUInt256 var_to + let value_ : UInt256 := var_value + + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + ( -- Case 1.1 : _3 = 0 (Sender is not zero address) + (-- Case 1.1.1: _7 = 1 (Reversion) (Balance is less than transfer value) + ( -- Case 1.1.1.1: _24 = 0 (Receiver is not zero address) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ ≠ 0 ∧ + to_ ≠ 0 ∧ + s₉["var_fromBalance"]!! < value_ + ) + ∨ + ( -- Case 1.1.1.2: _24 ≠ 0 (Receiver is zero address) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ ≠ 0 ∧ + to_ = 0 ∧ + s₉["var_fromBalance"]!! < value_ + ) + ) + ∨ + (-- Case 1.1.2 _7 =/ 0 (Non Reversion) (balance ≥ trtansfer value ) + ( -- Case 1.1.2.1: _24 = 0 (Receiver is not zero address) + + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ ≠ 0 ∧ + to_ ≠ 0 ∧ + s₉["var_fromBalance"]!! ≥ value_ + ) + ∨ + ( -- Case 1.1.2.2: _24 ≠ 0 (receiver is zero address) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ ≠ 0 ∧ + to_ = 0 ∧ + s₉["var_fromBalance"]!! ≥ value_ + ) + ) + ) + ∨ + ( -- Case 1.2 : _3 ≠ 0 (Sender is zero address) + ( -- Case 1.2.1 _24 = 0 (Receiver is not zero address) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ = 0 ∧ + to_ ≠ 0 + ) + ∨ + ( -- Case 1.2.2 _24 ≠ 0 (Receiver is zero address) + preservesEvm s₀ s₉ ∧ + s₉.evm.hash_collision = false ∧ + from_ = 0 ∧ + to_ = 0 + ) + ) + ∨ + -- Case 1.3 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +set_option maxHeartbeats 2000000 +set_option maxRecDepth 1000 + +lemma fun_update_abs_of_concrete {s₀ s₉ : State} { var_from var_to var_value} : + Spec (fun_update_concrete_of_code.1 var_from var_to var_value) s₀ s₉ → + Spec (A_fun_update var_from var_to var_value) s₀ s₉ := by + unfold fun_update_concrete_of_code A_fun_update + + rcases s₀ with ⟨s0_evm, s0_varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + + apply spec_eq + clr_funargs + + + generalize s_inhabited_all : (Ok s0_evm + Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧⟦"expr"↦Ok + s0_evm + Inhabited.default⟦"var_value"↦var_value⟧⟦"var_to"↦var_to⟧⟦"var_from"↦var_from⟧["var_from"]!!⟧) = s_inhabited at * + have s_inhabited_ok : s_inhabited.isOk := by + aesop + + generalize s0__all : + (Finmap.lookup "var_from" + (Finmap.insert "_1" (Fin.shiftLeft 1 160 - 1) + (Finmap.insert "expr" var_from + (Finmap.insert "var_from" var_from + (Finmap.insert "var_to" var_to (Finmap.insert "var_value" var_value Inhabited.default)))))) = s0_ at * + + rintro hasFuel ⟨s, switch236, ⟨s', switch104, ⟨s'', encode, code⟩⟩⟩ + + unfold multifill at * + simp at * + + -- Assign s₀ state to tidy up goal + generalize s0_all : Ok s0_evm s0_varstore = s₀ at * + + unfold A_switch_2364266820542243941 at switch236 + unfold primCall at switch236 + simp[←s_inhabited_all] at switch236 + unfold State.insert lookup! at switch236 + simp at switch236 + + + + apply Spec_ok_unfold (by sorry) (by sorry) at switch236 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address.lean new file mode 100644 index 00000000..c3a29cad --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma mapping_index_access_mapping_address_mapping_address_uint256_of_address_abs_of_code {s₀ s₉ : State} {dataSlot slot key} {fuel : Nat} : + execCall fuel mapping_index_access_mapping_address_mapping_address_uint256_of_address [dataSlot] (s₀, [slot, key]) = s₉ → + Spec (A_mapping_index_access_mapping_address_mapping_address_uint256_of_address dataSlot slot key) s₀ s₉ +:= λ h ↦ mapping_index_access_mapping_address_mapping_address_uint256_of_address_abs_of_concrete (mapping_index_access_mapping_address_mapping_address_uint256_of_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen.lean new file mode 100644 index 00000000..466406c6 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen.lean @@ -0,0 +1,120 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def mapping_index_access_mapping_address_mapping_address_uint256_of_address : FunctionDefinition := dataSlot + +{ + let _1 := and(key, sub(shl(160, 1), 1)) + let _2 := 0 + mstore(_2, _1) + let _3 := 32 + mstore(_3, slot) + let _4 := 64 + let _5 := _2 + dataSlot := keccak256(_2, _4) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def mapping_index_access_mapping_address_mapping_address_uint256_of_address_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {dataSlot slot key fuel}, + execCall fuel mapping_index_access_mapping_address_mapping_address_uint256_of_address [dataSlot] (s₀, [slot, key]) = s₉ → + Spec (C dataSlot slot key) s₀ s₉ + } := by + constructor + intros s₀ s₉ dataSlot slot key fuel + unfold mapping_index_access_mapping_address_mapping_address_uint256_of_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMKeccak256'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_user.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_user.lean new file mode 100644 index 00000000..dc0b2cbe --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_mapping_address_uint256_of_address_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_mapping_address_uint256_of_address_gen +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_user + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_mapping_index_access_mapping_address_mapping_address_uint256_of_address (dataSlot : Identifier) (slot key : Literal) (s₀ s₉ : State) : Prop := + A_mapping_index_access_mapping_address_uint256_of_address dataSlot slot key s₀ s₉ + +lemma mapping_index_access_mapping_address_mapping_address_uint256_of_address_abs_of_concrete {s₀ s₉ : State} {dataSlot slot key} : + Spec (mapping_index_access_mapping_address_mapping_address_uint256_of_address_concrete_of_code.1 dataSlot slot key) s₀ s₉ → + Spec (A_mapping_index_access_mapping_address_mapping_address_uint256_of_address dataSlot slot key) s₀ s₉ := by + unfold mapping_index_access_mapping_address_mapping_address_uint256_of_address_concrete_of_code A_mapping_index_access_mapping_address_mapping_address_uint256_of_address + apply mapping_index_access_mapping_address_uint256_of_address_abs_of_concrete + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address.lean new file mode 100644 index 00000000..19867493 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_gen + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma mapping_index_access_mapping_address_uint256_of_address_abs_of_code {s₀ s₉ : State} {dataSlot slot key} {fuel : Nat} : + execCall fuel mapping_index_access_mapping_address_uint256_of_address [dataSlot] (s₀, [slot, key]) = s₉ → + Spec (A_mapping_index_access_mapping_address_uint256_of_address dataSlot slot key) s₀ s₉ +:= λ h ↦ mapping_index_access_mapping_address_uint256_of_address_abs_of_concrete (mapping_index_access_mapping_address_uint256_of_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_gen.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_gen.lean new file mode 100644 index 00000000..f2eae710 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_gen.lean @@ -0,0 +1,120 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def mapping_index_access_mapping_address_uint256_of_address : FunctionDefinition := dataSlot + +{ + let _1 := and(key, sub(shl(160, 1), 1)) + let _2 := 0 + mstore(_2, _1) + let _3 := 32 + mstore(_3, slot) + let _4 := 64 + let _5 := _2 + dataSlot := keccak256(_2, _4) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def mapping_index_access_mapping_address_uint256_of_address_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {dataSlot slot key fuel}, + execCall fuel mapping_index_access_mapping_address_uint256_of_address [dataSlot] (s₀, [slot, key]) = s₉ → + Spec (C dataSlot slot key) s₀ s₉ + } := by + constructor + intros s₀ s₉ dataSlot slot key fuel + unfold mapping_index_access_mapping_address_uint256_of_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMKeccak256'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_user.lean b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_user.lean new file mode 100644 index 00000000..dc08ce4e --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/mapping_index_access_mapping_address_uint256_of_address_user.lean @@ -0,0 +1,176 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.mapping_index_access_mapping_address_uint256_of_address_gen + +import Generated.erc20shim.ERC20Shim.Predicate +import Generated.erc20shim.ERC20Shim.Variables + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +abbrev AddressMap := Finmap (λ _ : Address ↦ UInt256) + +set_option linter.setOption false +set_option pp.coercions false + +def A_mapping_index_access_mapping_address_uint256_of_address (dataSlot : Identifier) (slot key : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk + ∧ + ( + ( + preservesEvm s₀ s₉ ∧ + (s₀.evm.isEVMState → s₉.evm.isEVMState) ∧ + (∃ keccak, + s₉.evm.keccak_map.lookup [ ↑(Address.ofUInt256 key), slot ] = some keccak ∧ + s₉.store = s₀⟦dataSlot ↦ keccak⟧.store + ) ∧ + s₉.evm.hash_collision = false + ) + ∨ s₉.evm.hash_collision = true + ) + ∧ + (s₀.evm.hash_collision = true → s₉.evm.hash_collision = true) + +-- Helper reifications +lemma shift_eq_size : Fin.shiftLeft (n := UInt256.size) 1 160 = Address.size := by + constructor + +lemma EVMAddrSize' {s : State} : (s, [Fin.shiftLeft 1 160]) = (s, [Address.size.toUInt256]) := by + simp + exact shift_eq_size + +lemma mapping_index_access_mapping_address_uint256_of_address_abs_of_concrete {s₀ s₉ : State} {dataSlot slot key} : + Spec (mapping_index_access_mapping_address_uint256_of_address_concrete_of_code.1 dataSlot slot key) s₀ s₉ → + Spec (A_mapping_index_access_mapping_address_uint256_of_address dataSlot slot key) s₀ s₉ := by + unfold mapping_index_access_mapping_address_uint256_of_address_concrete_of_code A_mapping_index_access_mapping_address_uint256_of_address + rcases s₀ with ⟨evm, varstore⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + intro hasFuel + clr_funargs + + rw [ EVMSub', EVMShl', EVMAddrSize' ]; simp + rw [ Address.and_size_eq_ofUInt256 ] + rw [ multifill_cons, multifill_nil ] + simp + + clr_varstore, + + generalize acconut_def : Address.ofUInt256 key = account + intro code + unfold reviveJump at code + + generalize prep_def : (mstore evm 0 ↑↑account).mstore 32 slot = state_prep at code + have Preserved_prep : Preserved evm state_prep := by + rw [← prep_def]; + exact Preserved.trans mstore_preserved mstore_preserved + + split at code + case h_1 _ res keccak_eq_some_res => + clr_match at code + rw [← code] + + have res_collision := hash_collision_of_keccak256_eq_some keccak_eq_some_res + have prep_collision : state_prep.hash_collision = evm.hash_collision := by + rw [← prep_def] + exact Eq.trans hash_collision_of_mstore hash_collision_of_mstore + + have preserves_collision : + evm.hash_collision = true → Ok res.2 varstore⟦dataSlot↦res.1⟧.evm.hash_collision = true := by + rw [State.insert_of_ok, get_evm_of_ok, res_collision, prep_collision] + intro h; exact h + + apply And.intro + + · aesop + · split_ands + · by_cases h : evm.hash_collision + · right + exact preserves_collision h + · + left; split_ands + · -- preservesEvm + rw [preservesEvm_of_insert'] + apply preservesEvm_of_preserved + rw [get_evm_of_ok, get_evm_of_ok] + exact Preserved.trans Preserved_prep (Preserved_of_keccek256 keccak_eq_some_res) + · -- s₉.evm.isEVMState + intro hIsEVMState + obtain ⟨res₁,res₂⟩ := res + simp + + have state_prep_isEVMState : isEVMState state_prep := by + rw [←prep_def] + + unfold isEVMState + split_ands + unfold isKeccakInjective + simp + intros a b h₁ h₂ + rw [mstore_preserves_keccak_map, mstore_preserves_keccak_map] at h₂ + unfold isEVMState at hIsEVMState + aesop + + unfold isKeccakUsedRange + simp + rw [mstore_preserves_keccak_map, mstore_preserves_keccak_map, + mstore_preserves_used_range, mstore_preserves_used_range] + unfold isEVMState at hIsEVMState + aesop + + apply @isEVMState_of_keccak256 ⟨state_prep, state_prep_isEVMState⟩ _ _ _ _ keccak_eq_some_res + + -- keccak + · use res.1 + split_ands + -- keccak lookup for last + rotate_left + -- varstore preservation + rw [State.insert_of_ok] + simp only [State.store] + rw [State.insert_of_ok, get_evm_of_ok] + unfold keccak256 at keccak_eq_some_res + rw [ interval'_eq_interval 2 two_ne_zero (by norm_cast) + , ← prep_def + , mstore_mstore_of_ne (by sorry) + , interval_of_mstore_eq_val_cons + , mstore_mstore_of_ne (by sorry) + , zero_add, interval_of_mstore_eq_val_cons + , interval_of_0_eq_nil + ] at keccak_eq_some_res + unfold_let at keccak_eq_some_res + + split at keccak_eq_some_res + case h_1 _ v h_lookup => + rw [Option.some_inj] at keccak_eq_some_res + rw [← keccak_eq_some_res] + exact h_lookup + case h_2 _ h_lookup => + split at keccak_eq_some_res + swap; contradiction + rw [Option.some_inj] at keccak_eq_some_res + rw [← keccak_eq_some_res] + simp only []; + rw [Finmap.lookup_insert] + + ·-- no hash collision + rw [State.insert_of_ok, get_evm_of_ok, res_collision, prep_collision] + rw [Bool.eq_false_eq_not_eq_true] at h; exact h + · aesop + case h_2 res keccak_eq_none => + clr_match at code + + have final_destination : s₉.evm.hash_collision := by + rw [← code, State.insert_of_ok, get_evm_of_ok] + exact hash_collision_of_addHashCollision state_prep + + apply And.intro + · aesop + · aesop + + end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x11.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x11.lean new file mode 100644 index 00000000..0a721415 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x11.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x11_gen + +import Generated.erc20shim.ERC20Shim.panic_error_0x11_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma panic_error_0x11_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel panic_error_0x11 [] (s₀, []) = s₉ → + Spec (A_panic_error_0x11 ) s₀ s₉ +:= λ h ↦ panic_error_0x11_abs_of_concrete (panic_error_0x11_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x11_gen.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x11_gen.lean new file mode 100644 index 00000000..56d8fbc2 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x11_gen.lean @@ -0,0 +1,121 @@ +import Clear.ReasoningPrinciple + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def panic_error_0x11 : FunctionDefinition := + +{ + let _1 := shl(224, 1313373041) + let _2 := 0 + mstore(_2, _1) + let _3 := 17 + let _4 := 4 + mstore(_4, _3) + let _5 := 36 + let _6 := _2 + revert(_2, _5) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def panic_error_0x11_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel panic_error_0x11 [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold panic_error_0x11 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x11_user.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x11_user.lean new file mode 100644 index 00000000..fbc0d52a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x11_user.lean @@ -0,0 +1,84 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x11_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_panic_error_0x11 (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + (-- Case 1.1 No hash collision in function + let s_evm := EVMState.mstore s₀.evm 0 (Fin.shiftLeft 1313373041 224) + let s'_evm := EVMState.mstore s_evm 4 17 + + preservesEvm s₀ s₉ ∧ + s'_evm.evm_revert 0 36 = s₉.evm ∧ + s₀.store = s₉.store ∧ + s₉.evm.hash_collision = false + ) + -- Case 1.2 collision in function + ∨ s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma panic_error_0x11_abs_of_concrete {s₀ s₉ : State} : + Spec (panic_error_0x11_concrete_of_code.1 ) s₀ s₉ → + Spec (A_panic_error_0x11 ) s₀ s₉ := by + unfold panic_error_0x11_concrete_of_code A_panic_error_0x11 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + simp + rintro hasFuel code + + unfold multifill at code + simp at code + unfold setEvm at code + simp at code + unfold State.insert at code + simp at code + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + have s0_evm : s₀.evm = evm₀ := by aesop + + split_ands + · aesop + · + intro h + left + split_ands + · rw[←code, ←s0_all] + have : Preserved evm₀ (((mstore evm₀ 0 (Fin.shiftLeft 1313373041 224)).mstore 4 17).evm_revert 0 36) := by + simp[Preserved_def] + unfold mstore updateMemory evm_revert evm_return + dsimp + simp + unfold preservesEvm + aesop + · aesop + · aesop + · rw[←code] + simp[s0_evm.symm] + unfold mstore updateMemory evm_revert evm_return + dsimp + aesop + · aesop + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x22.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x22.lean new file mode 100644 index 00000000..94f02645 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x22.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x22_gen + +import Generated.erc20shim.ERC20Shim.panic_error_0x22_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma panic_error_0x22_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel panic_error_0x22 [] (s₀, []) = s₉ → + Spec (A_panic_error_0x22 ) s₀ s₉ +:= λ h ↦ panic_error_0x22_abs_of_concrete (panic_error_0x22_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x22_gen.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x22_gen.lean new file mode 100644 index 00000000..fa5ab77b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x22_gen.lean @@ -0,0 +1,123 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def panic_error_0x22 : FunctionDefinition := + +{ + let _1 := shl(224, 1313373041) + let _2 := 0 + mstore(_2, _1) + let _3 := 34 + let _4 := 4 + mstore(_4, _3) + let _5 := 36 + let _6 := _2 + revert(_2, _5) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def panic_error_0x22_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel panic_error_0x22 [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold panic_error_0x22 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x22_user.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x22_user.lean new file mode 100644 index 00000000..5ad3b95a --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x22_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x22_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_panic_error_0x22 (s₀ s₉ : State) : Prop := sorry + +lemma panic_error_0x22_abs_of_concrete {s₀ s₉ : State} : + Spec (panic_error_0x22_concrete_of_code.1 ) s₀ s₉ → + Spec (A_panic_error_0x22 ) s₀ s₉ := by + unfold panic_error_0x22_concrete_of_code A_panic_error_0x22 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x41.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x41.lean new file mode 100644 index 00000000..b882fb48 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x41.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x41_gen + +import Generated.erc20shim.ERC20Shim.panic_error_0x41_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma panic_error_0x41_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel panic_error_0x41 [] (s₀, []) = s₉ → + Spec (A_panic_error_0x41 ) s₀ s₉ +:= λ h ↦ panic_error_0x41_abs_of_concrete (panic_error_0x41_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x41_gen.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x41_gen.lean new file mode 100644 index 00000000..df4993a4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x41_gen.lean @@ -0,0 +1,123 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def panic_error_0x41 : FunctionDefinition := + +{ + let _1 := shl(224, 1313373041) + let _2 := 0 + mstore(_2, _1) + let _3 := 65 + let _4 := 4 + mstore(_4, _3) + let _5 := 36 + let _6 := _2 + revert(_2, _5) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def panic_error_0x41_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel panic_error_0x41 [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold panic_error_0x41 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMShl'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMMstore'] + try simp + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/panic_error_0x41_user.lean b/Generated/erc20shim/ERC20Shim/panic_error_0x41_user.lean new file mode 100644 index 00000000..5e30215b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/panic_error_0x41_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.panic_error_0x41_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_panic_error_0x41 (s₀ s₉ : State) : Prop := sorry + +lemma panic_error_0x41_abs_of_concrete {s₀ s₉ : State} : + Spec (panic_error_0x41_concrete_of_code.1 ) s₀ s₉ → + Spec (A_panic_error_0x41 ) s₀ s₉ := by + unfold panic_error_0x41_concrete_of_code A_panic_error_0x41 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74.lean b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74.lean new file mode 100644 index 00000000..6d1bc5f1 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen + +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 [] (s₀, []) = s₉ → + Spec (A_revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 ) s₀ s₉ +:= λ h ↦ revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_abs_of_concrete (revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen.lean b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen.lean new file mode 100644 index 00000000..af0dad44 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen.lean @@ -0,0 +1,97 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 : FunctionDefinition := + +{ + let _1 := 0 + let _2 := _1 + revert(_1, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_user.lean b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_user.lean new file mode 100644 index 00000000..549228a4 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 (s₀ s₉ : State) : Prop := sorry + +lemma revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_abs_of_concrete {s₀ s₉ : State} : + Spec (revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_concrete_of_code.1 ) s₀ s₉ → + Spec (A_revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 ) s₀ s₉ := by + unfold revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74_concrete_of_code A_revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb.lean b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb.lean new file mode 100644 index 00000000..4a2bab6f --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen + +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb [] (s₀, []) = s₉ → + Spec (A_revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb ) s₀ s₉ +:= λ h ↦ revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_abs_of_concrete (revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen.lean b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen.lean new file mode 100644 index 00000000..81cb5885 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen.lean @@ -0,0 +1,97 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb : FunctionDefinition := + +{ + let _1 := 0 + let _2 := _1 + revert(_1, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_user.lean b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_user.lean new file mode 100644 index 00000000..573eac33 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb (s₀ s₉ : State) : Prop := sorry + +lemma revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_abs_of_concrete {s₀ s₉ : State} : + Spec (revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_concrete_of_code.1 ) s₀ s₉ → + Spec (A_revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb ) s₀ s₉ := by + unfold revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb_concrete_of_code A_revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b.lean b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b.lean new file mode 100644 index 00000000..c14848eb --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_abs_of_code {s₀ s₉ : State} {fuel : Nat} : + execCall fuel revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b [] (s₀, []) = s₉ → + Spec (A_revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b ) s₀ s₉ +:= λ h ↦ revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_abs_of_concrete (revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen.lean b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen.lean new file mode 100644 index 00000000..ebac60e7 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen.lean @@ -0,0 +1,97 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b : FunctionDefinition := + +{ + let _1 := 0 + let _2 := _1 + revert(_1, _1) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_concrete_of_code +: { + C : + + State → State → Prop + // ∀ {s₀ s₉ : State} { fuel}, + execCall fuel revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b [] (s₀, []) = s₉ → + Spec (C ) s₀ s₉ + } := by + constructor + intros s₀ s₉ fuel + unfold revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMRevert'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_user.lean b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_user.lean new file mode 100644 index 00000000..c3df60ec --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_user.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b (s₀ s₉ : State) : Prop := sorry + +lemma revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_abs_of_concrete {s₀ s₉ : State} : + Spec (revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_concrete_of_code.1 ) s₀ s₉ → + Spec (A_revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b ) s₀ s₉ := by + unfold revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b_concrete_of_code A_revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_byte_slice_shift.lean b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift.lean new file mode 100644 index 00000000..32894b7d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift.lean @@ -0,0 +1,22 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift_gen + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +lemma update_byte_slice_shift_abs_of_code {s₀ s₉ : State} {result value toInsert} {fuel : Nat} : + execCall fuel update_byte_slice_shift [result] (s₀, [value, toInsert]) = s₉ → + Spec (A_update_byte_slice_shift result value toInsert) s₀ s₉ +:= λ h ↦ update_byte_slice_shift_abs_of_concrete (update_byte_slice_shift_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_gen.lean b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_gen.lean new file mode 100644 index 00000000..10918a54 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_gen.lean @@ -0,0 +1,90 @@ +import Clear.ReasoningPrinciple + + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def update_byte_slice_shift : FunctionDefinition := result + +{ + toInsert := toInsert + result := toInsert +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def update_byte_slice_shift_concrete_of_code +: { + C : + _ → _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} {result value toInsert fuel}, + execCall fuel update_byte_slice_shift [result] (s₀, [value, toInsert]) = s₉ → + Spec (C result value toInsert) s₀ s₉ + } := by + constructor + intros s₀ s₉ result value toInsert fuel + unfold update_byte_slice_shift + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_user.lean b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_user.lean new file mode 100644 index 00000000..80d8342b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_byte_slice_shift_user.lean @@ -0,0 +1,73 @@ +import Clear.ReasoningPrinciple + + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities + +def A_update_byte_slice_shift (result : Identifier) (value toInsert : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + -- Case 1.1 : collision in function + ( + let s := s₀⟦result ↦ toInsert⟧ + s₀.evm = s₉.evm ∧ + s.store = s₉.store + ) + ∨ + -- Case 1.2 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma update_byte_slice_shift_abs_of_concrete {s₀ s₉ : State} {result value toInsert} : + Spec (update_byte_slice_shift_concrete_of_code.1 result value toInsert) s₀ s₉ → + Spec (A_update_byte_slice_shift result value toInsert) s₀ s₉ := by + unfold update_byte_slice_shift_concrete_of_code A_update_byte_slice_shift + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + clr_varstore, + rintro hasFuel code + generalize s_inhabited_all : + (Ok evm₀ + Inhabited.default⟦"toInsert"↦toInsert⟧⟦"value"↦value⟧⟦"toInsert"↦toInsert⟧⟦"result"↦toInsert⟧) + = s_inhab at * + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold reviveJump at code + simp [←s_inhabited_all, ←s0_all] at code + unfold State.insert at code + simp at code + + by_cases no_collision : s₀.evm.hash_collision = false + + · split_ands + · aesop + · simp [no_collision] + left + split_ands + · rw [←s0_all, ←code] + aesop + · aesop + · aesop + · aesop + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256.lean b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256.lean new file mode 100644 index 00000000..4839f245 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift + +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256_gen + +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +lemma update_storage_value_offsett_uint256_to_uint256_abs_of_code {s₀ s₉ : State} { slot value} {fuel : Nat} : + execCall fuel update_storage_value_offsett_uint256_to_uint256 [] (s₀, [slot, value]) = s₉ → + Spec (A_update_storage_value_offsett_uint256_to_uint256 slot value) s₀ s₉ +:= λ h ↦ update_storage_value_offsett_uint256_to_uint256_abs_of_concrete (update_storage_value_offsett_uint256_to_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_gen.lean new file mode 100644 index 00000000..aa76339b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_gen.lean @@ -0,0 +1,113 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def update_storage_value_offsett_uint256_to_uint256 : FunctionDefinition := + +{ + let _1 := sload(slot) + let _2 := update_byte_slice_shift(_1, value) + sstore(slot, _2) +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def update_storage_value_offsett_uint256_to_uint256_concrete_of_code +: { + C : + _ → _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { slot value fuel}, + execCall fuel update_storage_value_offsett_uint256_to_uint256 [] (s₀, [slot, value]) = s₉ → + Spec (C slot value) s₀ s₉ + } := by + constructor + intros s₀ s₉ slot value fuel + unfold update_storage_value_offsett_uint256_to_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSload'] + try simp + + rw [cons]; simp only [LetCall', AssignCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + try simp + generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro s (And.intro (update_byte_slice_shift_abs_of_code hs) ?_) + swap; clear hs + try revert h' + revert h + + rw [cons, ExprStmtPrimCall']; try simp only + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + -- EXPR  + rw [EVMSstore'] + try simp + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_user.lean b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_user.lean new file mode 100644 index 00000000..c89513bd --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/update_storage_value_offsett_uint256_to_uint256_user.lean @@ -0,0 +1,108 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.update_byte_slice_shift + +import Generated.erc20shim.ERC20Shim.update_storage_value_offsett_uint256_to_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities Generated.erc20shim ERC20Shim + +def A_update_storage_value_offsett_uint256_to_uint256 (slot value : Literal) (s₀ s₉ : State) : Prop := + s₉.isOk ∧ + + (--Case 1: No initial collision + s₀.evm.hash_collision = false → + ( + -- Case 1.1 : collision in function + ( + let s:= (Ok (sstore s₀.evm slot value) s₀.store) + preservesEvm s s₉ + ) + ∨ + -- Case 1.2 : Collision in function + s₉.evm.hash_collision = true + ) + ) + ∧ + (-- Case 2: existing initial collision + s₀.evm.hash_collision = true → + s₉.evm.hash_collision = true + ) + +lemma update_storage_value_offsett_uint256_to_uint256_abs_of_concrete {s₀ s₉ : State} { slot value} : + Spec (update_storage_value_offsett_uint256_to_uint256_concrete_of_code.1 slot value) s₀ s₉ → + Spec (A_update_storage_value_offsett_uint256_to_uint256 slot value) s₀ s₉ := by + unfold update_storage_value_offsett_uint256_to_uint256_concrete_of_code A_update_storage_value_offsett_uint256_to_uint256 + rcases s₀ with ⟨evm₀, varstore₀⟩ | _ | _ <;> [simp only; aesop_spec; aesop_spec] + apply spec_eq + clr_funargs + clr_varstore, + rintro hasFuel ⟨s, call_byte, code⟩ + generalize s_inhabited_all : + Ok evm₀ Inhabited.default⟦"value"↦value⟧⟦"slot"↦slot⟧ = s_inhab_all at * + have s_inhab_ok : s_inhab_all.isOk := by aesop + + generalize s0_all : + (Ok evm₀ varstore₀) = s₀ at * + + unfold reviveJump at code + unfold setEvm at code + + clr_spec at call_byte + unfold A_update_byte_slice_shift at call_byte + + obtain ⟨s_ok, ⟨sinhab_no_collision, sinhab_collision⟩⟩ + := call_byte + obtain ⟨s_evm, ⟨s_varstore, s_all⟩⟩ := State_of_isOk s_ok + + simp [s_all, ←s0_all] at code + + have sinhab_evm_eq : s_inhab_all⟦"_1"↦sload s_inhab_all.evm slot⟧.evm = s_inhab_all.evm := by + aesop + + have s0_sinhab_preservesEvm : preservesEvm s₀ s_inhab_all := by + simp [←s0_all, ←s_inhabited_all] + unfold preservesEvm + unfold State.insert + aesop + + have s0_sinhab__preservesEvm : preservesEvm s₀ (s_inhab_all⟦"_1"↦sload s_inhab_all.evm slot⟧) := + by aesop + + + by_cases collision_sinhab : s_inhab_all⟦"_1"↦sload s_inhab_all.evm slot⟧.evm.hash_collision = false + + · have: s_inhab_all.evm.hash_collision = false := by aesop + simp [this] at sinhab_no_collision + split_ands + · aesop + · intro h + cases sinhab_no_collision + · left + rw[←code] + unfold lookup! + simp + have t : (Finmap.lookup "slot" s_varstore).get! = slot ∧ + (Finmap.lookup "_2" s_varstore).get! = value := by aesop + rw[t.1, t.2] + aesop + · right + rw[←code] + simp + unfold sstore + aesop + · aesop + · simp at collision_sinhab + split_ands + · aesop + · aesop + · rw[←code] + unfold sstore + aesop +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_address.lean b/Generated/erc20shim/ERC20Shim/validator_revert_address.lean new file mode 100644 index 00000000..93f93f0b --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_address.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506 + +import Generated.erc20shim.ERC20Shim.validator_revert_address_gen + +import Generated.erc20shim.ERC20Shim.validator_revert_address_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +lemma validator_revert_address_abs_of_code {s₀ s₉ : State} { value} {fuel : Nat} : + execCall fuel validator_revert_address [] (s₀, [value]) = s₉ → + Spec (A_validator_revert_address value) s₀ s₉ +:= λ h ↦ validator_revert_address_abs_of_concrete (validator_revert_address_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_address_gen.lean b/Generated/erc20shim/ERC20Shim/validator_revert_address_gen.lean new file mode 100644 index 00000000..de38675c --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_address_gen.lean @@ -0,0 +1,130 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def validator_revert_address : FunctionDefinition := + +{ + let _1 := sub(shl(160, 1), 1) + let _2 := and(value, _1) + let _3 := eq(value, _2) + let _4 := iszero(_3) + if _4 + { + let _5 := 0 + let _6 := _5 + revert(_5, _5) + } +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def validator_revert_address_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value fuel}, + execCall fuel validator_revert_address [] (s₀, [value]) = s₉ → + Spec (C value) s₀ s₉ + } := by + constructor + intros s₀ s₉ value fuel + unfold validator_revert_address + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMSub'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMAnd'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMEq'] + try simp + + rw [cons]; simp only [LetPrimCall', AssignPrimCall'] + (try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil])) + rw [EVMIszero'] + try simp + + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_8073281237182003506_abs_of_code if_8073281237182003506 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_address_user.lean b/Generated/erc20shim/ERC20Shim/validator_revert_address_user.lean new file mode 100644 index 00000000..6853d66d --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_address_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_8073281237182003506 + +import Generated.erc20shim.ERC20Shim.validator_revert_address_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def A_validator_revert_address (value : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma validator_revert_address_abs_of_concrete {s₀ s₉ : State} { value} : + Spec (validator_revert_address_concrete_of_code.1 value) s₀ s₉ → + Spec (A_validator_revert_address value) s₀ s₉ := by + unfold validator_revert_address_concrete_of_code A_validator_revert_address + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_uint256.lean b/Generated/erc20shim/ERC20Shim/validator_revert_uint256.lean new file mode 100644 index 00000000..90229d77 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_uint256.lean @@ -0,0 +1,23 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229 + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256_gen + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256_user + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +lemma validator_revert_uint256_abs_of_code {s₀ s₉ : State} { value} {fuel : Nat} : + execCall fuel validator_revert_uint256 [] (s₀, [value]) = s₉ → + Spec (A_validator_revert_uint256 value) s₀ s₉ +:= λ h ↦ validator_revert_uint256_abs_of_concrete (validator_revert_uint256_concrete_of_code.2 h) + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_uint256_gen.lean b/Generated/erc20shim/ERC20Shim/validator_revert_uint256_gen.lean new file mode 100644 index 00000000..f3150ce9 --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_uint256_gen.lean @@ -0,0 +1,108 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229 + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def validator_revert_uint256 : FunctionDefinition := + +{ + let _1 := 0 + if _1 + { + let _2 := _1 + let _3 := _1 + revert(_1, _1) + } +} + +> + +set_option maxRecDepth 4000 +set_option maxHeartbeats 300000 + +def validator_revert_uint256_concrete_of_code +: { + C : + _ → + State → State → Prop + // ∀ {s₀ s₉ : State} { value fuel}, + execCall fuel validator_revert_uint256 [] (s₀, [value]) = s₉ → + Spec (C value) s₀ s₉ + } := by + constructor + intros s₀ s₉ value fuel + unfold validator_revert_uint256 + + unfold Spec + rcases s₀ with ⟨evm, store⟩ | _ | c <;> dsimp only + rotate_left 1 + · generalize Def _ _ _ = f; aesop + · generalize Def _ _ _ = f; aesop + swap + generalize hok : Ok evm store = s₀ + intros h _ + revert h + + unfold execCall + unfold call + unfold params body rets + conv => simp_match + conv => pattern List.map _ _; simp + conv => pattern mkOk _; rw [← hok]; simp + conv => pattern setStore _; rw [← hok]; simp + + generalize hs₁ : initcall _ _ _ = s₁ + let_unfold s₁ + generalize hbody : exec _ _ _ = s₂ + revert hbody + generalize hs₉ : multifill' _ _ = s₉' + + rw [cons]; simp only [LetEq', Assign', Lit', Var'] + -- abstraction offsetting + rw [cons] + generalize hxs : Block _ = xs + abstract if_1438067688173587229_abs_of_code if_1438067688173587229 with ss hs + try rw [← hs₁, hok] at hs + intros h + try intros h' + refine' Exists.intro ss (And.intro hs ?_) + swap; clear hs + try revert h' + revert h + subst xs + + try clr_varstore_target + -- finish offsetting + subst hs₉ + intros hbody + subst hbody + subst hs₁ + rw [← hok] + repeat {rw [lookup_insert' (by aesop)]} + repeat {rw [lookup_insert_of_ne (by decide)]} + try rw [lookup_initcall_1] + try rw [lookup_initcall_2 ?_] + try rw [lookup_initcall_3 ?_] + try rw [lookup_initcall_4 ?_] + try rw [lookup_initcall_5 ?_] + all_goals try decide + let_unfold s₂ + simp [multifill'] + try {rw [reviveJump_insert (by aesop)]} + repeat {rw [lookup_insert' (by aesop)]} + try simp + rw [hok] + intros h + exact h + + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/erc20shim/ERC20Shim/validator_revert_uint256_user.lean b/Generated/erc20shim/ERC20Shim/validator_revert_uint256_user.lean new file mode 100644 index 00000000..752829ae --- /dev/null +++ b/Generated/erc20shim/ERC20Shim/validator_revert_uint256_user.lean @@ -0,0 +1,24 @@ +import Clear.ReasoningPrinciple + +import Generated.erc20shim.ERC20Shim.Common.if_1438067688173587229 + +import Generated.erc20shim.ERC20Shim.validator_revert_uint256_gen + + +namespace Generated.erc20shim.ERC20Shim + +section + +open Clear EVMState Ast Expr Stmt FunctionDefinition State Interpreter ExecLemmas OutOfFuelLemmas Abstraction YulNotation PrimOps ReasoningPrinciple Utilities ERC20Shim.Common + +def A_validator_revert_uint256 (value : Literal) (s₀ s₉ : State) : Prop := sorry + +lemma validator_revert_uint256_abs_of_concrete {s₀ s₉ : State} { value} : + Spec (validator_revert_uint256_concrete_of_code.1 value) s₀ s₉ → + Spec (A_validator_revert_uint256 value) s₀ s₉ := by + unfold validator_revert_uint256_concrete_of_code A_validator_revert_uint256 + sorry + +end + +end Generated.erc20shim.ERC20Shim diff --git a/Generated/peano/Peano/Common/for_4806375509446804985_user.lean b/Generated/peano/Peano/Common/for_4806375509446804985_user.lean index 4955a57f..034b0c1f 100644 --- a/Generated/peano/Peano/Common/for_4806375509446804985_user.lean +++ b/Generated/peano/Peano/Common/for_4806375509446804985_user.lean @@ -49,7 +49,7 @@ lemma AOk_for_4806375509446804985 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isOk · split_ifs at h₅ · aesop_spec · simp only [h₇, h₅] at * - clr_varstore + clr_varstore, ring · have : isOk (s₂⟦"k"↦s₂["k"]!! - 1⟧) := by aesop simp [h₆.symm] at this diff --git a/Generated/peano/Peano/Common/for_727972558926940900_user.lean b/Generated/peano/Peano/Common/for_727972558926940900_user.lean index 714ec0c6..42d16908 100644 --- a/Generated/peano/Peano/Common/for_727972558926940900_user.lean +++ b/Generated/peano/Peano/Common/for_727972558926940900_user.lean @@ -55,7 +55,7 @@ lemma AOk_for_727972558926940900 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isOk s · clr_spec at h₇ split_ands <;> [skip; aesop_spec; tauto] by_cases eq : s₀["k"]!! = 0 <;> simp [eq] at h₅ <;> [simp [h₅] at h₂; skip] - rw [h₆] at h₇; rw [h₇.1, h₅]; clr_varstore + rw [h₆] at h₇; rw [h₇.1, h₅]; clr_varstore, have : ↑(s₀["k"]!! - 1) + 1 < UInt256.size := by simp_arith [fin_eq_lem eq]; zify; omega rw [mul_assoc, UInt256.UInt256_pow_succ this]; ring · have h : isOk (s₂⟦"k"↦(s₂["k"]!!) - 1⟧) := by aesop diff --git a/Generated/peano/Peano/Common/for_84821961910748561_user.lean b/Generated/peano/Peano/Common/for_84821961910748561_user.lean index 7e02a2cc..2cba5a34 100644 --- a/Generated/peano/Peano/Common/for_84821961910748561_user.lean +++ b/Generated/peano/Peano/Common/for_84821961910748561_user.lean @@ -46,7 +46,7 @@ lemma AOk_for_84821961910748561 : ∀ s₀ s₂ s₄ s₅, isOk s₀ → isOk s · clr_spec at h₇ split_ands <;> [skip; aesop_spec; tauto] by_cases eq : s₀["k"]!! = 0 <;> simp [eq] at h₅ <;> [simp [h₅] at h₂; skip] - rw [h₆] at h₇; rw [h₇.1.symm, h₅]; clr_varstore + rw [h₆] at h₇; rw [h₇.1.symm, h₅]; clr_varstore, ring · have h : isOk (s₂⟦"k"↦(s₂["k"]!!) - 1⟧) := by aesop simp [h₆.symm] at h diff --git a/out/erc20shim-generation.md b/out/erc20shim-generation.md new file mode 100644 index 00000000..259a698a --- /dev/null +++ b/out/erc20shim-generation.md @@ -0,0 +1,22 @@ +# How to generate `erc20shim.yul` + +1. Clone https://github.com/OpenZeppelin/openzeppelin-contracts +2. Checkout `v5.0.2` in openzeppelin-contracts +3. Create a new file called `erc20shim.sol` in the `contracts/mocks/token` directory with the following: +``` +pragma solidity ^0.8.20; + +import {ERC20} from "contracts/token/ERC20/ERC20.sol"; + +contract ERC20Shim is ERC20 { + constructor() ERC20("ERC20Shim", "E20S") {} +} +``` +4. Install `solc-select` to be able to select specific `solc` versions. See: https://github.com/crytic/solc-select or https://search.nixos.org/packages?channel=unstable&show=solc-select +5. Run `solc-select install 0.8.21` +6. From the `contracts` directory, run: +``` +SOLC_VERSION=0.8.21 solc --optimize --ir-optimized --yul-optimizations 'ho[esj]x[esVur]' contracts/mocks/token/erc20shim.sol > contracts/erc20shim.yul +``` + +You now have `erc20shim.yul` in the `contracts` directory. \ No newline at end of file diff --git a/out/erc20shim.yul b/out/erc20shim.yul new file mode 100644 index 00000000..c6b24ab7 --- /dev/null +++ b/out/erc20shim.yul @@ -0,0 +1,1312 @@ +Optimized IR: + +Optimized IR: + +Optimized IR: + +Optimized IR: +/// @use-src 0:"contracts/interfaces/draft-IERC6093.sol", 1:"contracts/mocks/token/ERC20Shim.sol", 2:"contracts/token/ERC20/ERC20.sol", 3:"contracts/token/ERC20/IERC20.sol", 4:"contracts/token/ERC20/extensions/IERC20Metadata.sol", 5:"contracts/utils/Context.sol" +object "ERC20Shim_14" { + code { + { + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _1 := memoryguard(0x80) + let _2 := 64 + mstore(_2, _1) + let _3 := callvalue() + if _3 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + constructor_ERC20Shim() + let _4 := _2 + let _5 := mload(_2) + let _6 := datasize("ERC20Shim_14_deployed") + let _7 := dataoffset("ERC20Shim_14_deployed") + codecopy(_5, _7, _6) + let _8 := _6 + return(_5, _6) + } + function revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + { + let _1 := 0 + let _2 := _1 + revert(_1, _1) + } + function panic_error_0x41() + { + let _1 := shl(224, 0x4e487b71) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x41 + let _4 := 4 + mstore(_4, _3) + let _5 := 0x24 + let _6 := _2 + revert(_2, _5) + } + function finalize_allocation(memPtr, size) + { + let _1 := not(31) + let _2 := 31 + let _3 := add(size, _2) + let _4 := and(_3, _1) + let newFreePtr := add(memPtr, _4) + let _5 := lt(newFreePtr, memPtr) + let _6 := sub(shl(64, 1), 1) + let _7 := gt(newFreePtr, _6) + let _8 := or(_7, _5) + if _8 { panic_error_0x41() } + let _9 := 64 + mstore(_9, newFreePtr) + } + function allocate_memory(size) -> memPtr + { + let _1 := 64 + memPtr := mload(_1) + finalize_allocation(memPtr, size) + } + function array_allocation_size_string(length) -> size + { + let _1 := sub(shl(64, 1), 1) + let _2 := gt(length, _1) + if _2 { panic_error_0x41() } + let _3 := not(31) + let _4 := 31 + let _5 := add(length, _4) + size := and(_5, _3) + let _6 := 0x20 + size := add(size, _6) + } + function allocate_memory_array_string(length) -> memPtr + { + let _1 := array_allocation_size_string(length) + memPtr := allocate_memory(_1) + mstore(memPtr, length) + } + function store_literal_in_memory_73d84741e39ae21500f019e1bd49b1509c4dad0285f14920732b98003dc4a297(memPtr) + { + let _1 := "ERC20Shim" + mstore(memPtr, _1) + } + function copy_literal_to_memory_73d84741e39ae21500f019e1bd49b1509c4dad0285f14920732b98003dc4a297() -> memPtr + { + let _1 := 9 + memPtr := allocate_memory_array_string(_1) + let _2 := 32 + let _3 := add(memPtr, _2) + store_literal_in_memory_73d84741e39ae21500f019e1bd49b1509c4dad0285f14920732b98003dc4a297(_3) + } + function store_literal_in_memory_654a20c509642b4486f3c0baf150dce7367ca9e5f6186c81edaf3f66a3f7c7a3(memPtr) + { + let _1 := "E20S" + mstore(memPtr, _1) + } + function copy_literal_to_memory_654a20c509642b4486f3c0baf150dce7367ca9e5f6186c81edaf3f66a3f7c7a3() -> memPtr + { + let _1 := 4 + memPtr := allocate_memory_array_string(_1) + let _2 := 32 + let _3 := add(memPtr, _2) + store_literal_in_memory_654a20c509642b4486f3c0baf150dce7367ca9e5f6186c81edaf3f66a3f7c7a3(_3) + } + /// @ast-id 13 @src 1:116:159 "constructor() ERC20(\"ERC20Shim\", \"E20S\") {}" + function constructor_ERC20Shim() + { + /// @src 1:136:147 "\"ERC20Shim\"" + let _mpos := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ copy_literal_to_memory_73d84741e39ae21500f019e1bd49b1509c4dad0285f14920732b98003dc4a297() + let _1 := copy_literal_to_memory_654a20c509642b4486f3c0baf150dce7367ca9e5f6186c81edaf3f66a3f7c7a3() + /// @src 1:116:159 "constructor() ERC20(\"ERC20Shim\", \"E20S\") {}" + constructor_ERC20(_mpos, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + } + function panic_error_0x22() + { + let _1 := shl(224, 0x4e487b71) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x22 + let _4 := 4 + mstore(_4, _3) + let _5 := 0x24 + let _6 := _2 + revert(_2, _5) + } + function extract_byte_array_length(data) -> length + { + let _1 := 1 + length := shr(_1, data) + let _2 := _1 + let outOfPlaceEncoding := and(data, _1) + let _3 := iszero(outOfPlaceEncoding) + if _3 + { + let _4 := 0x7f + length := and(length, _4) + } + let _5 := 32 + let _6 := lt(length, _5) + let _7 := eq(outOfPlaceEncoding, _6) + if _7 { panic_error_0x22() } + } + function array_dataslot_string_storage(ptr) -> data + { + let _1 := 0 + mstore(_1, ptr) + let _2 := 0x20 + let _3 := _1 + data := keccak256(_1, _2) + } + function update_byte_slice_dynamic32(value, shiftBytes, toInsert) -> result + { + let _1 := 3 + let shiftBits := shl(_1, shiftBytes) + let _2 := not(0) + let mask := shl(shiftBits, _2) + toInsert := shl(shiftBits, toInsert) + let _3 := not(mask) + value := and(value, _3) + let _4 := and(toInsert, mask) + result := or(value, _4) + } + function update_storage_value_uint256_to_uint256(slot, offset, value) + { + let _1 := sload(slot) + let _2 := update_byte_slice_dynamic32(_1, offset, value) + sstore(slot, _2) + } + function storage_set_to_zero_uint256(slot, offset) + { + let _1 := 0 + update_storage_value_uint256_to_uint256(slot, offset, _1) + } + function clear_storage_range_bytes1(start, end) + { + for { } + lt(start, end) + { + let _1 := 1 + start := add(start, _1) + } + { + let _2 := 0 + storage_set_to_zero_uint256(start, _2) + } + } + function clean_up_bytearray_end_slots_string_storage(array, len, startIndex) + { + let _1 := 31 + let _2 := gt(len, _1) + if _2 + { + let dataArea := array_dataslot_string_storage(array) + let _3 := _1 + let _4 := add(startIndex, _1) + let _5 := shr(5, _4) + let deleteStart := add(dataArea, _5) + let _6 := 32 + let _7 := lt(startIndex, _6) + if _7 { deleteStart := dataArea } + let _8 := _1 + let _9 := add(len, _1) + let _10 := shr(5, _9) + let _11 := add(dataArea, _10) + clear_storage_range_bytes1(deleteStart, _11) + } + } + function extract_used_part_and_set_length_of_short_byte_array(data, len) -> used + { + let _1 := not(0) + let _2 := 3 + let _3 := shl(_2, len) + let _4 := shr(_3, _1) + let _5 := not(_4) + data := and(data, _5) + let _6 := 1 + let _7 := shl(_6, len) + used := or(data, _7) + } + function copy_byte_array_to_storage_from_string_to_string(slot, src) + { + let newLen := mload(src) + let _1 := sub(shl(64, 1), 1) + let _2 := gt(newLen, _1) + if _2 { panic_error_0x41() } + let _3 := sload(slot) + let _4 := extract_byte_array_length(_3) + clean_up_bytearray_end_slots_string_storage(slot, _4, newLen) + let srcOffset := 0 + srcOffset := 0x20 + let _5 := 31 + let _6 := gt(newLen, _5) + switch _6 + case 1 { + let _7 := not(31) + let loopEnd := and(newLen, _7) + let dstPtr := array_dataslot_string_storage(slot) + let i := 0 + for { } + lt(i, loopEnd) + { + let _8 := 0x20 + i := add(i, _8) + } + { + let _9 := add(src, srcOffset) + let _10 := mload(_9) + sstore(dstPtr, _10) + let _11 := 1 + dstPtr := add(dstPtr, _11) + let _12 := 32 + srcOffset := add(srcOffset, _12) + } + let _13 := lt(loopEnd, newLen) + if _13 + { + let _14 := add(src, srcOffset) + let lastValue := mload(_14) + let _15 := not(0) + let _16 := and(shl(3, newLen), 248) + let _17 := shr(_16, _15) + let _18 := not(_17) + let _19 := and(lastValue, _18) + sstore(dstPtr, _19) + } + let _20 := 1 + let _21 := _20 + let _22 := shl(_20, newLen) + let _23 := add(_22, _20) + sstore(slot, _23) + } + default { + let value := 0 + if newLen + { + let _24 := add(src, srcOffset) + value := mload(_24) + } + let _25 := extract_used_part_and_set_length_of_short_byte_array(value, newLen) + sstore(slot, _25) + } + } + function update_storage_value_offsett_string_to_string(slot, value) + { + copy_byte_array_to_storage_from_string_to_string(slot, value) + } + /// @ast-id 66 @src 2:1601:1714 "constructor(string memory name_, string memory symbol_) {..." + function constructor_ERC20(var_name_mpos, var_symbol_mpos) + { + /// @src 2:1667:1680 "_name = name_" + let _1 := 0x03 + update_storage_value_offsett_string_to_string(_1, /** @src 2:1675:1680 "name_" */ var_name_mpos) + /// @src 2:1690:1707 "_symbol = symbol_" + let _2 := 0x04 + update_storage_value_offsett_string_to_string(_2, /** @src 2:1700:1707 "symbol_" */ var_symbol_mpos) + } + } + /// @use-src 1:"contracts/mocks/token/ERC20Shim.sol", 2:"contracts/token/ERC20/ERC20.sol", 5:"contracts/utils/Context.sol" + object "ERC20Shim_14_deployed" { + code { + { + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _1 := memoryguard(0x80) + let _2 := 64 + mstore(_2, _1) + let _3 := 4 + let _4 := calldatasize() + let _5 := lt(_4, _3) + let _6 := iszero(_5) + if _6 + { + let _7 := 0 + let _8 := calldataload(_7) + let _9 := 224 + let _10 := shr(_9, _8) + switch _10 + case 0x06fdde03 { external_fun_name() } + case 0x095ea7b3 { external_fun_approve() } + case 0x18160ddd { external_fun_totalSupply() } + case 0x23b872dd { external_fun_transferFrom() } + case 0x313ce567 { external_fun_decimals() } + case 0x70a08231 { external_fun_balanceOf() } + case 0x95d89b41 { external_fun_symbol() } + case 0xa9059cbb { external_fun_transfer() } + case 0xdd62ed3e { external_fun_allowance() } + } + revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74() + } + function revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + { + let _1 := 0 + let _2 := _1 + revert(_1, _1) + } + function revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + { + let _1 := 0 + let _2 := _1 + revert(_1, _1) + } + function abi_decode(headStart, dataEnd) + { + let _1 := 0 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + { + revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + } + } + function array_storeLengthForEncoding_string_fromStack(pos, length) -> updated_pos + { + mstore(pos, length) + let _1 := 0x20 + updated_pos := add(pos, _1) + } + function copy_memory_to_memory_with_cleanup(src, dst, length) + { + let i := 0 + for { } + lt(i, length) + { + let _1 := 32 + i := add(i, _1) + } + { + let _2 := add(src, i) + let _3 := mload(_2) + let _4 := add(dst, i) + mstore(_4, _3) + } + let _5 := 0 + let _6 := add(dst, length) + mstore(_6, _5) + } + function abi_encode_string_memory_ptr(value, pos) -> end + { + let length := mload(value) + pos := array_storeLengthForEncoding_string_fromStack(pos, length) + let _1 := 0x20 + let _2 := add(value, _1) + copy_memory_to_memory_with_cleanup(_2, pos, length) + let _3 := not(31) + let _4 := 31 + let _5 := add(length, _4) + let _6 := and(_5, _3) + end := add(pos, _6) + } + function abi_encode_string(headStart, value0) -> tail + { + let _1 := 32 + tail := add(headStart, _1) + let _2 := _1 + mstore(headStart, _1) + tail := abi_encode_string_memory_ptr(value0, tail) + } + function external_fun_name() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + abi_decode(_3, _2) + let ret := fun_name() + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_string(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function validator_revert_address(value) + { + let _1 := sub(shl(160, 1), 1) + let _2 := and(value, _1) + let _3 := eq(value, _2) + let _4 := iszero(_3) + if _4 + { + let _5 := 0 + let _6 := _5 + revert(_5, _5) + } + } + function abi_decode_address(offset, end) -> value + { + value := calldataload(offset) + validator_revert_address(value) + } + function validator_revert_uint256(value) + { + let _1 := 0 + if _1 + { + let _2 := _1 + let _3 := _1 + revert(_1, _1) + } + } + function abi_decode_uint256(offset, end) -> value + { + value := calldataload(offset) + validator_revert_uint256(value) + } + function abi_decode_addresst_uint256(headStart, dataEnd) -> value0, value1 + { + let _1 := 64 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + { + revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + } + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_uint256(_5, dataEnd) + } + function abi_encode_bool_to_bool(value, pos) + { + let _1 := iszero(value) + let _2 := iszero(_1) + mstore(pos, _2) + } + function abi_encode_bool(headStart, value0) -> tail + { + let _1 := 32 + tail := add(headStart, _1) + abi_encode_bool_to_bool(value0, headStart) + } + function external_fun_approve() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + let param, param_1 := abi_decode_addresst_uint256(_3, _2) + let ret := fun_approve(param, param_1) + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_bool(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function abi_encode_uint256_to_uint256(value, pos) + { mstore(pos, value) } + function abi_encode_uint256(headStart, value0) -> tail + { + let _1 := 32 + tail := add(headStart, _1) + abi_encode_uint256_to_uint256(value0, headStart) + } + function external_fun_totalSupply() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + abi_decode(_3, _2) + let ret := fun_totalSupply() + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_uint256(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function abi_decode_addresst_addresst_uint256(headStart, dataEnd) -> value0, value1, value2 + { + let _1 := 96 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + { + revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + } + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_address(_5, dataEnd) + let _6 := 64 + let _7 := add(headStart, _6) + value2 := abi_decode_uint256(_7, dataEnd) + } + function external_fun_transferFrom() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + let param, param_1, param_2 := abi_decode_addresst_addresst_uint256(_3, _2) + let ret := fun_transferFrom(param, param_1, param_2) + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_bool(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function abi_encode_uint8_to_uint8(value, pos) + { + let _1 := 0xff + let _2 := and(value, _1) + mstore(pos, _2) + } + function abi_encode_uint8(headStart, value0) -> tail + { + let _1 := 32 + tail := add(headStart, _1) + abi_encode_uint8_to_uint8(value0, headStart) + } + function external_fun_decimals() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + abi_decode(_3, _2) + let ret := fun_decimals() + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_uint8(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function abi_decode_tuple_address(headStart, dataEnd) -> value0 + { + let _1 := 32 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + { + revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + } + value0 := abi_decode_address(headStart, dataEnd) + } + function external_fun_balanceOf() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + let _4 := abi_decode_tuple_address(_3, _2) + let ret := fun_balanceOf(_4) + let _5 := 64 + let memPos := mload(_5) + let _6 := abi_encode_uint256(memPos, ret) + let _7 := sub(_6, memPos) + return(memPos, _7) + } + function external_fun_symbol() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + abi_decode(_3, _2) + let ret := fun_symbol() + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_string(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function external_fun_transfer() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + let param, param_1 := abi_decode_addresst_uint256(_3, _2) + let ret := fun_transfer(param, param_1) + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_bool(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function abi_decode_addresst_address(headStart, dataEnd) -> value0, value1 + { + let _1 := 64 + let _2 := sub(dataEnd, headStart) + let _3 := slt(_2, _1) + if _3 + { + revert_error_dbdddcbe895c83990c08b3492a0e83918d802a52331272ac6fdb6a7c4aea3b1b() + } + value0 := abi_decode_address(headStart, dataEnd) + let _4 := 32 + let _5 := add(headStart, _4) + value1 := abi_decode_address(_5, dataEnd) + } + function external_fun_allowance() + { + let _1 := callvalue() + if _1 + { + revert_error_ca66f745a3ce8ff40e2ccaf1ad45db7774001b90d25810abd9040049be7bf4bb() + } + let _2 := calldatasize() + let _3 := 4 + let param, param_1 := abi_decode_addresst_address(_3, _2) + let ret := fun_allowance(param, param_1) + let _4 := 64 + let memPos := mload(_4) + let _5 := abi_encode_uint256(memPos, ret) + let _6 := sub(_5, memPos) + return(memPos, _6) + } + function revert_error_42b3090547df1d2001c96683413b8cf91c1b902ef5e3cb8d9f6f304cf7446f74() + { + let _1 := 0 + let _2 := _1 + revert(_1, _1) + } + function panic_error_0x22() + { + let _1 := shl(224, 0x4e487b71) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x22 + let _4 := 4 + mstore(_4, _3) + let _5 := 0x24 + let _6 := _2 + revert(_2, _5) + } + function extract_byte_array_length(data) -> length + { + let _1 := 1 + length := shr(_1, data) + let _2 := _1 + let outOfPlaceEncoding := and(data, _1) + let _3 := iszero(outOfPlaceEncoding) + if _3 + { + let _4 := 0x7f + length := and(length, _4) + } + let _5 := 32 + let _6 := lt(length, _5) + let _7 := eq(outOfPlaceEncoding, _6) + if _7 { panic_error_0x22() } + } + function array_storeLengthForEncoding_string(pos, length) -> updated_pos + { + mstore(pos, length) + let _1 := 0x20 + updated_pos := add(pos, _1) + } + function array_dataslot_string_storage(ptr) -> data + { + let _1 := 0 + mstore(_1, ptr) + let _2 := 0x20 + let _3 := _1 + data := keccak256(_1, _2) + } + function abi_encode_string_storage(value, pos) -> ret + { + let slotValue := sload(value) + let length := extract_byte_array_length(slotValue) + pos := array_storeLengthForEncoding_string(pos, length) + let _1 := 1 + let _2 := and(slotValue, _1) + switch _2 + case 0 { + let _3 := not(255) + let _4 := and(slotValue, _3) + mstore(pos, _4) + let _5 := iszero(length) + let _6 := iszero(_5) + let _7 := shl(5, _6) + ret := add(pos, _7) + } + case 1 { + let dataPos := array_dataslot_string_storage(value) + let i := 0 + for { } + lt(i, length) + { + let _8 := 0x20 + i := add(i, _8) + } + { + let _9 := sload(dataPos) + let _10 := add(pos, i) + mstore(_10, _9) + let _11 := _1 + dataPos := add(dataPos, _1) + } + ret := add(pos, i) + } + } + function panic_error_0x41() + { + let _1 := shl(224, 0x4e487b71) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x41 + let _4 := 4 + mstore(_4, _3) + let _5 := 0x24 + let _6 := _2 + revert(_2, _5) + } + function finalize_allocation(memPtr, size) + { + let _1 := not(31) + let _2 := 31 + let _3 := add(size, _2) + let _4 := and(_3, _1) + let newFreePtr := add(memPtr, _4) + let _5 := lt(newFreePtr, memPtr) + let _6 := 0xffffffffffffffff + let _7 := gt(newFreePtr, _6) + let _8 := or(_7, _5) + if _8 { panic_error_0x41() } + let _9 := 64 + mstore(_9, newFreePtr) + } + function copy_array_from_storage_to_memory_string(slot) -> memPtr + { + let _1 := 64 + memPtr := mload(_1) + let _2 := abi_encode_string_storage(slot, memPtr) + let _3 := sub(_2, memPtr) + finalize_allocation(memPtr, _3) + } + /// @ast-id 75 @src 2:1779:1868 "function name() public view virtual returns (string memory) {..." + function fun_name() -> var__mpos + { + /// @src 2:1856:1861 "_name" + let _1 := 0x03 + /// @src 2:1849:1861 "return _name" + var__mpos := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ copy_array_from_storage_to_memory_string(/** @src 2:1856:1861 "_name" */ _1) + } + /// @ast-id 84 @src 2:1981:2074 "function symbol() public view virtual returns (string memory) {..." + function fun_symbol() -> var_mpos + { + /// @src 2:2060:2067 "_symbol" + let _1 := 0x04 + /// @src 2:2053:2067 "return _symbol" + var_mpos := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ copy_array_from_storage_to_memory_string(/** @src 2:2060:2067 "_symbol" */ _1) + } + /// @ast-id 93 @src 2:2707:2789 "function decimals() public view virtual returns (uint8) {..." + function fun_decimals() -> var + { + /// @src 2:2773:2782 "return 18" + var := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ 18 + } + /// @ast-id 102 @src 2:2849:2946 "function totalSupply() public view virtual returns (uint256) {..." + function fun_totalSupply() -> var_ + { + /// @src 2:2927:2939 "_totalSupply" + let _1 := 0x02 + /// @src 2:2920:2939 "return _totalSupply" + var_ := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ sload(/** @src 2:2927:2939 "_totalSupply" */ _1) + } + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + function mapping_index_access_mapping_address_uint256_of_address(slot, key) -> dataSlot + { + let _1 := and(key, sub(shl(160, 1), 1)) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x20 + mstore(_3, slot) + let _4 := 0x40 + let _5 := _2 + dataSlot := keccak256(_2, _4) + } + /// @ast-id 115 @src 2:3004:3120 "function balanceOf(address account) public view virtual returns (uint256) {..." + function fun_balanceOf(var_account) -> var + { + /// @src 2:3095:3104 "_balances" + let _1 := 0x00 + /// @src 2:3095:3113 "_balances[account]" + let _2 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:3095:3104 "_balances" */ _1, /** @src 2:3105:3112 "account" */ var_account) + /// @src 2:3088:3113 "return _balances[account]" + var := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ sload(/** @src 2:3095:3113 "_balances[account]" */ _2) + } + /// @ast-id 139 @src 2:3315:3493 "function transfer(address to, uint256 value) public virtual returns (bool) {..." + function fun_transfer(var_to, var_value) -> var + { + /// @src 2:3416:3428 "_msgSender()" + let _1 := fun_msgSender() + /// @src 2:3459:3464 "value" + fun__transfer(/** @src 2:3416:3428 "_msgSender()" */ _1, /** @src 2:3455:3457 "to" */ var_to, /** @src 2:3459:3464 "value" */ var_value) + /// @src 2:3475:3486 "return true" + var := /** @src 2:3482:3486 "true" */ 0x01 + } + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + function mapping_index_access_mapping_address_mapping_address_uint256_of_address(slot, key) -> dataSlot + { + let _1 := and(key, sub(shl(160, 1), 1)) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x20 + mstore(_3, slot) + let _4 := 0x40 + let _5 := _2 + dataSlot := keccak256(_2, _4) + } + /// @ast-id 156 @src 2:3551:3691 "function allowance(address owner, address spender) public view virtual returns (uint256) {..." + function fun_allowance(var_owner, var_spender) -> var + { + /// @src 2:3657:3668 "_allowances" + let _1 := 0x01 + /// @src 2:3657:3675 "_allowances[owner]" + let _2 := mapping_index_access_mapping_address_mapping_address_uint256_of_address(/** @src 2:3657:3668 "_allowances" */ _1, /** @src 2:3669:3674 "owner" */ var_owner) + /// @src 2:3657:3684 "_allowances[owner][spender]" + let _3 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:3657:3675 "_allowances[owner]" */ _2, /** @src 2:3676:3683 "spender" */ var_spender) + /// @src 2:3650:3684 "return _allowances[owner][spender]" + var := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ sload(/** @src 2:3657:3684 "_allowances[owner][spender]" */ _3) + } + /// @ast-id 180 @src 2:3998:4184 "function approve(address spender, uint256 value) public virtual returns (bool) {..." + function fun_approve(var_spender, var_value) -> var + { + /// @src 2:4103:4115 "_msgSender()" + let _1 := fun_msgSender() + /// @src 2:4150:4155 "value" + fun_approve_420(/** @src 2:4103:4115 "_msgSender()" */ _1, /** @src 2:4141:4148 "spender" */ var_spender, /** @src 2:4150:4155 "value" */ var_value) + /// @src 2:4166:4177 "return true" + var := /** @src 2:4173:4177 "true" */ 0x01 + } + /// @ast-id 212 @src 2:4776:5020 "function transferFrom(address from, address to, uint256 value) public virtual returns (bool) {..." + function fun_transferFrom(var_from, var_to, var_value) -> var + { + /// @src 2:4897:4909 "_msgSender()" + let _1 := fun_msgSender() + /// @src 2:4950:4955 "value" + fun_spendAllowance(/** @src 2:4935:4939 "from" */ var_from, /** @src 2:4897:4909 "_msgSender()" */ _1, /** @src 2:4950:4955 "value" */ var_value) + /// @src 2:4986:4991 "value" + fun__transfer(/** @src 2:4976:4980 "from" */ var_from, /** @src 2:4982:4984 "to" */ var_to, /** @src 2:4986:4991 "value" */ var_value) + /// @src 2:5002:5013 "return true" + var := /** @src 2:5009:5013 "true" */ 0x01 + } + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + function abi_encode_address(value, pos) + { + let _1 := sub(shl(160, 1), 1) + let _2 := and(value, _1) + mstore(pos, _2) + } + function abi_encode_tuple_address(headStart, value0) -> tail + { + let _1 := 32 + tail := add(headStart, _1) + abi_encode_address(value0, headStart) + } + /// @ast-id 259 @src 2:5393:5693 "function _transfer(address from, address to, uint256 value) internal {..." + function fun__transfer(var_from, var_to, var_value) + { + /// @src 2:5476:5480 "from" + let expr := var_from + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _1 := sub(shl(160, 1), 1) + let _2 := and(/** @src 2:5476:5494 "from == address(0)" */ var_from, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:5476:5494 "from == address(0)" + let _3 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _2) + /// @src 2:5472:5558 "if (from == address(0)) {..." + if /** @src 2:5476:5494 "from == address(0)" */ _3 + /// @src 2:5472:5558 "if (from == address(0)) {..." + { + /// @src 2:5536:5546 "address(0)" + let expr_1 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ 0 + let _4 := 64 + /// @src 2:5517:5547 "ERC20InvalidSender(address(0))" + let _5 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_4) + /// @src 2:5517:5547 "ERC20InvalidSender(address(0))" + let _6 := shl(225, 0x4b637e8f) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_tuple_address(_8, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ expr_1) + /// @src 2:5517:5547 "ERC20InvalidSender(address(0))" + let _10 := sub(_9, _5) + revert(_5, _10) + } + /// @src 2:5571:5573 "to" + let expr_2 := var_to + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _11 := _1 + let _12 := and(/** @src 2:5571:5587 "to == address(0)" */ var_to, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:5571:5587 "to == address(0)" + let _13 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _12) + /// @src 2:5567:5653 "if (to == address(0)) {..." + if /** @src 2:5571:5587 "to == address(0)" */ _13 + /// @src 2:5567:5653 "if (to == address(0)) {..." + { + /// @src 2:5631:5641 "address(0)" + let expr_3 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ 0 + let _14 := 64 + /// @src 2:5610:5642 "ERC20InvalidReceiver(address(0))" + let _15 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_14) + /// @src 2:5610:5642 "ERC20InvalidReceiver(address(0))" + let _16 := shl(224, 0xec442f05) + mstore(_15, _16) + let _17 := 4 + let _18 := add(_15, _17) + let _19 := abi_encode_tuple_address(_18, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ expr_3) + /// @src 2:5610:5642 "ERC20InvalidReceiver(address(0))" + let _20 := sub(_19, _15) + revert(_15, _20) + } + /// @src 2:5680:5685 "value" + fun_update(/** @src 2:5670:5674 "from" */ var_from, /** @src 2:5676:5678 "to" */ var_to, /** @src 2:5680:5685 "value" */ var_value) + } + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + function abi_encode_address_uint256_uint256(headStart, value0, value1, value2) -> tail + { + let _1 := 96 + tail := add(headStart, _1) + abi_encode_address(value0, headStart) + let _2 := 32 + let _3 := add(headStart, _2) + abi_encode_uint256_to_uint256(value1, _3) + let _4 := 64 + let _5 := add(headStart, _4) + abi_encode_uint256_to_uint256(value2, _5) + } + function update_byte_slice_shift(value, toInsert) -> result + { + toInsert := toInsert + result := toInsert + } + function update_storage_value_offsett_uint256_to_uint256(slot, value) + { + let _1 := sload(slot) + let _2 := update_byte_slice_shift(_1, value) + sstore(slot, _2) + } + function panic_error_0x11() + { + let _1 := shl(224, 0x4e487b71) + let _2 := 0 + mstore(_2, _1) + let _3 := 0x11 + let _4 := 4 + mstore(_4, _3) + let _5 := 0x24 + let _6 := _2 + revert(_2, _5) + } + function checked_add_uint256(x, y) -> sum + { + x := x + y := y + sum := add(x, y) + let _1 := gt(x, sum) + if _1 { panic_error_0x11() } + } + /// @ast-id 336 @src 2:6008:7115 "function _update(address from, address to, uint256 value) internal virtual {..." + function fun_update(var_from, var_to, var_value) + { + /// @src 2:6097:6101 "from" + let expr := var_from + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _1 := sub(shl(160, 1), 1) + let _2 := and(/** @src 2:6097:6115 "from == address(0)" */ var_from, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:6097:6115 "from == address(0)" + let _3 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _2) + /// @src 2:6093:6633 "if (from == address(0)) {..." + switch /** @src 2:6097:6115 "from == address(0)" */ _3 + case /** @src 2:6093:6633 "if (from == address(0)) {..." */ 0 { + /// @src 2:6307:6316 "_balances" + let _4 := 0x00 + /// @src 2:6307:6322 "_balances[from]" + let _5 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:6307:6316 "_balances" */ _4, /** @src 2:6317:6321 "from" */ var_from) + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _6 := sload(/** @src 2:6307:6322 "_balances[from]" */ _5) + /// @src 2:6285:6322 "uint256 fromBalance = _balances[from]" + let var_fromBalance := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _6 + /// @src 2:6340:6359 "fromBalance < value" + let _7 := lt(/** @src 2:6340:6351 "fromBalance" */ _6, /** @src 2:6354:6359 "value" */ var_value) + /// @src 2:6336:6451 "if (fromBalance < value) {..." + if /** @src 2:6340:6359 "fromBalance < value" */ _7 + /// @src 2:6336:6451 "if (fromBalance < value) {..." + { + /// @src 2:6411:6415 "from" + let expr_1 := var_from + /// @src 2:6417:6428 "fromBalance" + let expr_2 := _6 + /// @src 2:6430:6435 "value" + let expr_3 := var_value + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _8 := 64 + /// @src 2:6386:6436 "ERC20InsufficientBalance(from, fromBalance, value)" + let _9 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_8) + /// @src 2:6386:6436 "ERC20InsufficientBalance(from, fromBalance, value)" + let _10 := shl(226, 0x391434e3) + mstore(_9, _10) + let _11 := 4 + let _12 := add(_9, _11) + let _13 := abi_encode_address_uint256_uint256(_12, var_from, _6, var_value) + let _14 := sub(_13, _9) + revert(_9, _14) + } + /// @src 2:6589:6608 "fromBalance - value" + let expr_4 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ sub(/** @src 2:6589:6600 "fromBalance" */ _6, /** @src 2:6603:6608 "value" */ var_value) + /// @src 2:6571:6580 "_balances" + let _15 := _4 + /// @src 2:6571:6586 "_balances[from]" + let _16 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:6571:6580 "_balances" */ _4, /** @src 2:6581:6585 "from" */ var_from) + /// @src 2:6571:6608 "_balances[from] = fromBalance - value" + update_storage_value_offsett_uint256_to_uint256(/** @src 2:6571:6586 "_balances[from]" */ _16, /** @src 2:6571:6608 "_balances[from] = fromBalance - value" */ expr_4) + } + default /// @src 2:6093:6633 "if (from == address(0)) {..." + { + /// @src 2:6233:6254 "_totalSupply += value" + let _17 := 0x02 + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _18 := sload(/** @src 2:6233:6254 "_totalSupply += value" */ _17) + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _19 := _18 + /// @src 2:6233:6254 "_totalSupply += value" + let _20 := checked_add_uint256(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _18, /** @src 2:6249:6254 "value" */ var_value) + /// @src 2:6233:6254 "_totalSupply += value" + let _21 := _17 + update_storage_value_offsett_uint256_to_uint256(_17, _20) + } + /// @src 2:6647:6649 "to" + let expr_5 := var_to + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _22 := _1 + let _23 := and(/** @src 2:6647:6663 "to == address(0)" */ var_to, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:6647:6663 "to == address(0)" + let _24 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _23) + /// @src 2:6643:7068 "if (to == address(0)) {..." + switch /** @src 2:6647:6663 "to == address(0)" */ _24 + case /** @src 2:6643:7068 "if (to == address(0)) {..." */ 0 { + /// @src 2:7038:7043 "value" + let expr_6 := var_value + /// @src 2:7021:7030 "_balances" + let _25 := 0x00 + /// @src 2:7021:7034 "_balances[to]" + let _26 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:7021:7030 "_balances" */ _25, /** @src 2:7031:7033 "to" */ var_to) + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _27 := sload(/** @src 2:7021:7043 "_balances[to] += value" */ _26) + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _28 := _27 + let _29 := add(_27, /** @src 2:7021:7043 "_balances[to] += value" */ var_value) + update_storage_value_offsett_uint256_to_uint256(_26, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _29) + } + default /// @src 2:6643:7068 "if (to == address(0)) {..." + { + /// @src 2:6810:6831 "_totalSupply -= value" + let _30 := 0x02 + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _31 := sload(/** @src 2:6810:6831 "_totalSupply -= value" */ _30) + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _32 := _31 + let _33 := sub(_31, /** @src 2:6826:6831 "value" */ var_value) + /// @src 2:6810:6831 "_totalSupply -= value" + let _34 := _30 + update_storage_value_offsett_uint256_to_uint256(_30, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _33) + } + /// @src 2:7092:7096 "from" + let expr_7 := var_from + /// @src 2:7098:7100 "to" + let expr_8 := var_to + /// @src 2:7102:7107 "value" + let expr_9 := var_value + /// @src 2:7083:7108 "Transfer(from, to, value)" + let _35 := 0xddf252ad1be2c89b69c2b068fc378daa952ba7f163c4a11628f55a4df523b3ef + let _36 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _2 + /// @src 2:7083:7108 "Transfer(from, to, value)" + let _37 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _23 + let _38 := 64 + /// @src 2:7083:7108 "Transfer(from, to, value)" + let _39 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_38) + /// @src 2:7083:7108 "Transfer(from, to, value)" + let _40 := abi_encode_uint256(_39, var_value) + let _41 := sub(_40, _39) + log3(_39, _41, _35, _2, _23) + } + /// @ast-id 420 @src 2:8726:8854 "function _approve(address owner, address spender, uint256 value) internal {..." + function fun_approve_420(var_owner, var_spender, var_value) + { + /// @src 2:8819:8824 "owner" + let expr := var_owner + /// @src 2:8842:8846 "true" + let _1 := 0x01 + fun__approve(var_owner, /** @src 2:8826:8833 "spender" */ var_spender, /** @src 2:8835:8840 "value" */ var_value, /** @src 2:8842:8846 "true" */ _1) + } + /// @ast-id 480 @src 2:9701:10133 "function _approve(address owner, address spender, uint256 value, bool emitEvent) internal virtual {..." + function fun__approve(var_owner, var_spender, var_value, var_emitEvent) + { + /// @src 2:9813:9818 "owner" + let expr := var_owner + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _1 := sub(shl(160, 1), 1) + let _2 := and(/** @src 2:9813:9832 "owner == address(0)" */ var_owner, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:9813:9832 "owner == address(0)" + let _3 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _2) + /// @src 2:9809:9898 "if (owner == address(0)) {..." + if /** @src 2:9813:9832 "owner == address(0)" */ _3 + /// @src 2:9809:9898 "if (owner == address(0)) {..." + { + /// @src 2:9876:9886 "address(0)" + let expr_1 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ 0 + let _4 := 64 + /// @src 2:9855:9887 "ERC20InvalidApprover(address(0))" + let _5 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_4) + /// @src 2:9855:9887 "ERC20InvalidApprover(address(0))" + let _6 := shl(224, 0xe602df05) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_tuple_address(_8, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ expr_1) + /// @src 2:9855:9887 "ERC20InvalidApprover(address(0))" + let _10 := sub(_9, _5) + revert(_5, _10) + } + /// @src 2:9911:9918 "spender" + let expr_2 := var_spender + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _11 := _1 + let _12 := and(/** @src 2:9911:9932 "spender == address(0)" */ var_spender, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _1) + /// @src 2:9911:9932 "spender == address(0)" + let _13 := iszero(/** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _12) + /// @src 2:9907:9997 "if (spender == address(0)) {..." + if /** @src 2:9911:9932 "spender == address(0)" */ _13 + /// @src 2:9907:9997 "if (spender == address(0)) {..." + { + /// @src 2:9975:9985 "address(0)" + let expr_3 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ 0 + let _14 := 64 + /// @src 2:9955:9986 "ERC20InvalidSpender(address(0))" + let _15 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_14) + /// @src 2:9955:9986 "ERC20InvalidSpender(address(0))" + let _16 := shl(225, 0x4a1406b1) + mstore(_15, _16) + let _17 := 4 + let _18 := add(_15, _17) + let _19 := abi_encode_tuple_address(_18, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ expr_3) + /// @src 2:9955:9986 "ERC20InvalidSpender(address(0))" + let _20 := sub(_19, _15) + revert(_15, _20) + } + /// @src 2:10036:10041 "value" + let expr_4 := var_value + /// @src 2:10006:10017 "_allowances" + let _21 := 0x01 + /// @src 2:10006:10024 "_allowances[owner]" + let _22 := mapping_index_access_mapping_address_mapping_address_uint256_of_address(/** @src 2:10006:10017 "_allowances" */ _21, /** @src 2:10018:10023 "owner" */ var_owner) + /// @src 2:10006:10033 "_allowances[owner][spender]" + let _23 := mapping_index_access_mapping_address_uint256_of_address(/** @src 2:10006:10024 "_allowances[owner]" */ _22, /** @src 2:10025:10032 "spender" */ var_spender) + /// @src 2:10006:10041 "_allowances[owner][spender] = value" + update_storage_value_offsett_uint256_to_uint256(/** @src 2:10006:10033 "_allowances[owner][spender]" */ _23, /** @src 2:10006:10041 "_allowances[owner][spender] = value" */ var_value) + /// @src 2:10051:10127 "if (emitEvent) {..." + if /** @src 2:10055:10064 "emitEvent" */ var_emitEvent + /// @src 2:10051:10127 "if (emitEvent) {..." + { + /// @src 2:10094:10099 "owner" + let expr_5 := var_owner + /// @src 2:10101:10108 "spender" + let expr_6 := var_spender + /// @src 2:10110:10115 "value" + let expr_7 := var_value + /// @src 2:10085:10116 "Approval(owner, spender, value)" + let _24 := 0x8c5be1e5ebec7d5bd14f71427d1e84f3dd0314c0f7b2291e5b200ac8c7c3b925 + let _25 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _2 + /// @src 2:10085:10116 "Approval(owner, spender, value)" + let _26 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _12 + let _27 := 64 + /// @src 2:10085:10116 "Approval(owner, spender, value)" + let _28 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_27) + /// @src 2:10085:10116 "Approval(owner, spender, value)" + let _29 := abi_encode_uint256(_28, var_value) + let _30 := sub(_29, _28) + log3(_28, _30, _24, _2, _12) + } + } + /// @ast-id 528 @src 2:10415:10891 "function _spendAllowance(address owner, address spender, uint256 value) internal virtual {..." + function fun_spendAllowance(var_owner, var_spender, var_value) + { + /// @src 2:10514:10566 "uint256 currentAllowance = allowance(owner, spender)" + let var_currentAllowance := /** @src 2:10541:10566 "allowance(owner, spender)" */ fun_allowance(/** @src 2:10551:10556 "owner" */ var_owner, /** @src 2:10558:10565 "spender" */ var_spender) + /// @src 2:10599:10616 "type(uint256).max" + let _1 := not(0) + /// @src 2:10580:10616 "currentAllowance < type(uint256).max" + let _2 := lt(/** @src 2:10580:10596 "currentAllowance" */ var_currentAllowance, /** @src 2:10599:10616 "type(uint256).max" */ _1) + /// @src 2:10576:10885 "if (currentAllowance < type(uint256).max) {..." + if /** @src 2:10580:10616 "currentAllowance < type(uint256).max" */ _2 + /// @src 2:10576:10885 "if (currentAllowance < type(uint256).max) {..." + { + /// @src 2:10636:10660 "currentAllowance < value" + let _3 := lt(/** @src 2:10636:10652 "currentAllowance" */ var_currentAllowance, /** @src 2:10655:10660 "value" */ var_value) + /// @src 2:10632:10762 "if (currentAllowance < value) {..." + if /** @src 2:10636:10660 "currentAllowance < value" */ _3 + /// @src 2:10632:10762 "if (currentAllowance < value) {..." + { + /// @src 2:10714:10721 "spender" + let expr := var_spender + /// @src 2:10723:10739 "currentAllowance" + let expr_1 := var_currentAllowance + /// @src 2:10741:10746 "value" + let expr_2 := var_value + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _4 := 64 + /// @src 2:10687:10747 "ERC20InsufficientAllowance(spender, currentAllowance, value)" + let _5 := /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ mload(_4) + /// @src 2:10687:10747 "ERC20InsufficientAllowance(spender, currentAllowance, value)" + let _6 := shl(225, 0x7dc7a0d9) + mstore(_5, _6) + let _7 := 4 + let _8 := add(_5, _7) + let _9 := abi_encode_address_uint256_uint256(_8, var_spender, var_currentAllowance, var_value) + let _10 := sub(_9, _5) + revert(_5, _10) + } + /// @src 2:10812:10817 "owner" + let expr_3 := var_owner + /// @src 2:10819:10826 "spender" + let expr_4 := var_spender + /// @src 2:10854:10859 "false" + let _11 := 0x00 + /// @src 1:82:161 "contract ERC20Shim is ERC20 {..." + let _12 := sub(/** @src 2:10828:10844 "currentAllowance" */ var_currentAllowance, /** @src 2:10847:10852 "value" */ var_value) + /// @src 2:10854:10859 "false" + fun__approve(var_owner, var_spender, /** @src 1:82:161 "contract ERC20Shim is ERC20 {..." */ _12, /** @src 2:10854:10859 "false" */ _11) + } + } + /// @ast-id 782 @src 5:656:752 "function _msgSender() internal view virtual returns (address) {..." + function fun_msgSender() -> var + { + /// @src 5:728:745 "return msg.sender" + var := /** @src 5:735:745 "msg.sender" */ caller() + } + } + data ".metadata" hex"a2646970667358221220e124d3304315e49a13a11d4379533b7d9c2fb14642277dba92735950eb596d5e64736f6c63430008150033" + } +} + +Optimized IR: + +Optimized IR: + +Optimized IR: + +Optimized IR: + diff --git a/vc/src/Main.hs b/vc/src/Main.hs index 6c76fefc..e33cf2f9 100644 --- a/vc/src/Main.hs +++ b/vc/src/Main.hs @@ -259,7 +259,7 @@ fillInFunction topLevelContract file imports (FuncDef _ contract fargs ret body) funcArgs = generateGuarded (null fargs) $ "(" ++ unwords fargs ++ " : Literal)" opens = opensOfImports topLevelContract imports retVals = generateGuarded (null ret) $ "(" ++ unwords ret ++ " : Identifier)" - rValsAndArgs = generateGuarded (null (ret ++ fargs)) "{" ++ unwords ret ++ " " ++ argsSepSpace ++ "}" + rValsAndArgs = generateGuarded (null (ret ++ fargs)) $ "{" ++ unwords ret ++ " " ++ argsSepSpace ++ "}" replaceIn ttype = replaceMany [ ("\\", leanImports ++ internalImports topLevelContract contract file ttype), diff --git a/vc/src/ProofGenerator.hs b/vc/src/ProofGenerator.hs index dd2c9cb8..412feb36 100644 --- a/vc/src/ProofGenerator.hs +++ b/vc/src/ProofGenerator.hs @@ -17,12 +17,12 @@ tacticsOfExpr (Var {}) = "-- simp [Var']" tacticsOfExpr (Lit {}) = "-- simp [Lit']" tacticsOfCond :: String -tacticsOfCond = "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]" +tacticsOfCond = "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))" assignCall :: String -> String assignCall name = unlines [ "rw [cons]; simp only [LetCall', AssignCall']", - "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]", + "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))", "-- EXPR \6", "try simp", "generalize hs : execCall _ _ _ _ = s; try rw [← hs₁, hok] at hs", @@ -54,6 +54,7 @@ rwPrimop primop = if primop == "delegatecall" then "-- delegate call" else "rw [ finish :: String finish = unlines [ + "try clr_varstore_target", "-- finish offsetting", "subst hs₉", "intros hbody", @@ -84,7 +85,7 @@ tacticsOfStmt' _ (LetInit _ (Call f _)) = if f `elem` yulPrimOps then unlines [ "rw [cons]; simp only [LetPrimCall', AssignPrimCall']", - "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]", + "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))", rwPrimop f, "try simp"] else assignCall f @@ -93,7 +94,7 @@ tacticsOfStmt' _ (Assignment _ (Call f _)) = if f `elem` yulPrimOps then unlines [ "rw [cons]; simp only [LetPrimCall', AssignPrimCall']", - "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]", + "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))", rwPrimop f, "try simp"] else assignCall f @@ -103,13 +104,13 @@ tacticsOfStmt' _ (ExpressionStmt (Call f args)) = if f `elem` yulPrimOps then unlines [ "rw [cons, ExprStmtPrimCall']; try simp only", - "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]", + "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))", "-- EXPR \4", rwPrimop f, "try simp"] else let preamble = unlines [ "rw [cons, ExprStmtCall']; try simp only", - "simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]"] + "(try (simp only [Fin.isValue])); (try (rw [List.foldr_cons])); (try (rw [List.foldr_nil])); simp [evalArgs, head', reverse', multifill', PrimCall', Lit', Var', execPrimCall, evalPrimCall]; (try (rewrite [List.foldr_nil]))"] postamble = unlines [ "try simp", "", @@ -131,9 +132,9 @@ tacticsOfStmt' abs node@(Switch c legs dflt) = "unfold execSwitchCases", tacticsOfCond, tacticsOfExpr c, - concatMap ((tacticsOfStmt' abs . Block) . snd) legs, + concatMap ((("(try (unfold execSwitchCases))\n" ++) . tacticsOfStmt' abs . Block) . snd) legs, "generalize hdefault : exec _ _ _ = sdef", - "unfold execSwitchCases", + "(try (unfold execSwitchCases))", "subst hdefault", tacticsOfStmt' abs (Block dflt)] tacticsOfStmt' abs node@(For {}) = diff --git a/vc/stack.yaml b/vc/stack.yaml index 4d91b545..b51bbf92 100644 --- a/vc/stack.yaml +++ b/vc/stack.yaml @@ -17,8 +17,8 @@ # # resolver: ./custom-snapshot.yaml # resolver: https://example.com/snapshots/2018-01-01.yaml -resolver: - url: https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/20/11.yaml +resolver: lts-20.11 +# https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/20/11.yaml # User packages to be built. # Various formats can be used as shown in the example below. @@ -66,5 +66,3 @@ packages: # Allow a newer minor version of GHC than the snapshot specifies # compiler-check: newer-minor -configure-options: - $targets: [] diff --git a/vc/stack.yaml.lock b/vc/stack.yaml.lock index 315a1143..90e049cb 100644 --- a/vc/stack.yaml.lock +++ b/vc/stack.yaml.lock @@ -9,5 +9,4 @@ snapshots: sha256: adbc602422dde10cc330175da7de8609e70afc41449a7e2d6e8b1827aa0e5008 size: 649342 url: https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/20/11.yaml - original: - url: https://raw.githubusercontent.com/commercialhaskell/stackage-snapshots/master/lts/20/11.yaml + original: lts-20.11