|
1 |
| -use std::collections::HashMap; |
| 1 | +use std::collections::{HashMap, HashSet}; |
2 | 2 | use std::sync::{Arc, LazyLock};
|
3 | 3 |
|
4 | 4 | use blockifier::abi::constants::STORED_BLOCK_HASH_BUFFER;
|
5 | 5 | use blockifier::blockifier_versioned_constants::VersionedConstants;
|
6 | 6 | use blockifier::test_utils::dict_state_reader::DictStateReader;
|
| 7 | +use blockifier::test_utils::ALIAS_CONTRACT_ADDRESS; |
7 | 8 | use blockifier::transaction::test_utils::ExpectedExecutionInfo;
|
8 | 9 | use blockifier_test_utils::cairo_versions::{CairoVersion, RunnableCairo1};
|
9 | 10 | use blockifier_test_utils::calldata::create_calldata;
|
@@ -1925,3 +1926,84 @@ async fn test_deprecated_tx_info() {
|
1925 | 1926 | test_output.assert_account_balance_change(tx_info_account_address);
|
1926 | 1927 | test_output.assert_account_balance_change(contract_address!(TEST_SEQUENCER_ADDRESS));
|
1927 | 1928 | }
|
| 1929 | + |
| 1930 | +#[rstest] |
| 1931 | +#[tokio::test] |
| 1932 | +async fn test_deploy_syscall() { |
| 1933 | + let test_contract = FeatureContract::TestContract(CairoVersion::Cairo0); |
| 1934 | + let empty_contract = FeatureContract::Empty(CairoVersion::Cairo0); |
| 1935 | + let class_hash = get_class_hash_of_feature_contract(test_contract); |
| 1936 | + let empty_class_hash = get_class_hash_of_feature_contract(empty_contract); |
| 1937 | + // Initialize the test manager with the test contract and empty contract already declared. |
| 1938 | + // We can ignore the addresses of the deployed instances. |
| 1939 | + let (mut test_manager, mut nonce_manager, _) = |
| 1940 | + TestManager::<DictStateReader>::new_with_default_initial_state([ |
| 1941 | + (test_contract, calldata![Felt::ZERO, Felt::ZERO]), |
| 1942 | + (empty_contract, calldata![]), |
| 1943 | + ]) |
| 1944 | + .await; |
| 1945 | + |
| 1946 | + let ctor_calldata = vec![Felt::from(1979), Felt::from(1989)]; |
| 1947 | + let salt = Felt::from(12); |
| 1948 | + |
| 1949 | + // Call deploy_contract(...). |
| 1950 | + let (deploy_tx, deployed_test_address) = get_deploy_contract_tx_and_address_with_salt( |
| 1951 | + class_hash, |
| 1952 | + Calldata(Arc::new(ctor_calldata.clone())), |
| 1953 | + nonce_manager.next(*FUNDED_ACCOUNT_ADDRESS), |
| 1954 | + *NON_TRIVIAL_RESOURCE_BOUNDS, |
| 1955 | + salt, |
| 1956 | + ); |
| 1957 | + test_manager.add_invoke_tx(deploy_tx, None); |
| 1958 | + let expected_storage_updates = HashMap::from([( |
| 1959 | + deployed_test_address, |
| 1960 | + HashMap::from([( |
| 1961 | + StarknetStorageKey(ctor_calldata[0].try_into().unwrap()), |
| 1962 | + StarknetStorageValue(ctor_calldata[1]), |
| 1963 | + )]), |
| 1964 | + )]); |
| 1965 | + |
| 1966 | + // Deploy a contract with no constructor using deploy syscall. |
| 1967 | + let invoke_args = invoke_tx_args! { |
| 1968 | + sender_address: *FUNDED_ACCOUNT_ADDRESS, |
| 1969 | + nonce: nonce_manager.next(*FUNDED_ACCOUNT_ADDRESS), |
| 1970 | + calldata: create_calldata( |
| 1971 | + *FUNDED_ACCOUNT_ADDRESS, |
| 1972 | + "deploy_contract", |
| 1973 | + &[empty_class_hash.0, salt, Felt::ZERO], |
| 1974 | + ), |
| 1975 | + resource_bounds: *NON_TRIVIAL_RESOURCE_BOUNDS, |
| 1976 | + }; |
| 1977 | + test_manager.add_invoke_tx_from_args(invoke_args, &CHAIN_ID_FOR_TESTS, None); |
| 1978 | + |
| 1979 | + // Run the test and verify storage changes. |
| 1980 | + let test_output = |
| 1981 | + test_manager.execute_test_with_default_block_contexts(&TestParameters::default()).await; |
| 1982 | + let perform_global_validations = true; |
| 1983 | + test_output.perform_validations( |
| 1984 | + perform_global_validations, |
| 1985 | + Some(&StateDiff { storage_updates: expected_storage_updates, ..Default::default() }), |
| 1986 | + ); |
| 1987 | + |
| 1988 | + // Make sure only the newly deployed contract and the fee contract have changed storage. |
| 1989 | + let block_hash_contract_address = ContractAddress( |
| 1990 | + Const::BlockHashContractAddress.fetch_from_os_program().unwrap().try_into().unwrap(), |
| 1991 | + ); |
| 1992 | + let allowed_changed_addresses = HashSet::from([ |
| 1993 | + &deployed_test_address, |
| 1994 | + &*STRK_FEE_TOKEN_ADDRESS, |
| 1995 | + &*ALIAS_CONTRACT_ADDRESS, |
| 1996 | + &block_hash_contract_address, |
| 1997 | + ]); |
| 1998 | + assert!( |
| 1999 | + HashSet::from_iter( |
| 2000 | + test_output |
| 2001 | + .decompressed_state_diff |
| 2002 | + .storage_updates |
| 2003 | + .into_keys() |
| 2004 | + .collect::<Vec<_>>() |
| 2005 | + .iter() |
| 2006 | + ) |
| 2007 | + .is_subset(&allowed_changed_addresses) |
| 2008 | + ); |
| 2009 | +} |
0 commit comments