Skip to content

Commit

Permalink
Add large calldata test (#391)
Browse files Browse the repository at this point in the history
* Call data size test

* Addition of large call data test
  • Loading branch information
moraygrieve authored Dec 17, 2024
1 parent 0c2b5b6 commit fa40674
Show file tree
Hide file tree
Showing 6 changed files with 119 additions and 6 deletions.
10 changes: 5 additions & 5 deletions src/python/ten/test/baserunner.py
Original file line number Diff line number Diff line change
Expand Up @@ -251,11 +251,11 @@ def __print_cost(self, runner, url, web3, user_id, eth_price):
pass

def get_eth_price(self):
url = "https://min-api.cryptocompare.com/data/price?fsym=ETH&tsyms=USD"
response = requests.get(url)

if response.status_code == 200:
return float(response.json()['USD'])
try:
url = "https://min-api.cryptocompare.com/data/price?fsym=ETH&tsyms=USD"
response = requests.get(url)
if response.status_code == 200: return float(response.json()['USD'])
except: return None
return None

@staticmethod
Expand Down
5 changes: 5 additions & 0 deletions src/python/ten/test/contracts/calldata.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,11 @@
from ten.test.contracts.default import DefaultContract


class CallData(DefaultContract):
SOURCE = os.path.join(PROJECT.root, 'src', 'solidity', 'contracts', 'calldata', 'CallData.sol')
CONTRACT = 'CallData'


class CallDataTwoPhase(DefaultContract):
SOURCE = os.path.join(PROJECT.root, 'src', 'solidity', 'contracts', 'calldata', 'CallDataTwoPhase.sol')
CONTRACT = 'CallDataTwoPhase'
Expand Down
19 changes: 19 additions & 0 deletions src/solidity/contracts/calldata/CallData.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
// SPDX-License-Identifier: GPL-3.0
pragma solidity ^0.8.0;

contract CallData {
uint256 public lastSum;

function processLargeData(uint256[] memory data) public {
uint256 sum = 0;
for (uint256 i = 0; i < data.length; i++) {
sum += data[i];
}
lastSum = sum;
}

function getLastSum() public view returns (uint256) {
return lastSum;
}
}

38 changes: 38 additions & 0 deletions tests/generic/gen_cor_134/pysystest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
<?xml version="1.0" encoding="utf-8"?>
<pysystest type="auto">

<description>
<title>Gas: Large call data</title>
<purpose><![CDATA[
Perform some tx calls with large call data, where we expect the tx to both fail and succeed depending on the call data
size.
]]>
</purpose>
</description>

<classification>
<groups inherit="true">
<group>gas</group>
</groups>
<modes inherit="true">
<mode>ten.sepolia</mode>
<mode>ten.uat</mode>
<mode>ten.dev</mode>
<mode>ten.local</mode>
<mode>ten.sim</mode>
<mode>arbitrum.sepolia</mode>
<mode>ganache</mode>
<mode>sepolia</mode>
</modes>
</classification>

<data>
<class name="PySysTest" module="run"/>
</data>

<traceability>
<requirements>
<requirement id=""/>
</requirements>
</traceability>
</pysystest>
51 changes: 51 additions & 0 deletions tests/generic/gen_cor_134/run.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,51 @@
from pysys.constants import FAILED, PASSED
from ten.test.basetest import TenNetworkTest
from ten.test.utils.properties import Properties
from ten.test.contracts.calldata import CallData


class PySysTest(TenNetworkTest):

def execute(self):
# connect to the network (use an ephemeral account)
network = self.get_network_connection()
web3, account = network.connect(self, private_key=self.get_ephemeral_pk(), check_funds=False)
self.distribute_native(account, network.ETH_ALLOC)

# deploy the contract
calldata = CallData(self, web3, Properties().L2PublicCallbacks)
calldata.deploy(network, account)

# transact (the first should be rejected so we just check later ones go through)
self.transact(calldata, web3, account, limit=5000, expect_pass=False)
self.transact(calldata, web3, account, limit=1000)
self.transact(calldata, web3, account, limit=500)

def transact(self, calldata, web3, account, limit, expect_pass=True):
# build the transaction
large_array = [i for i in range(limit)]
target = calldata.contract.functions.processLargeData(large_array)
nonce = web3.eth.get_transaction_count(account.address)
params = {'nonce': nonce,
'chainId': web3.eth.chain_id,
'gasPrice': web3.eth.gas_price}
params['gas'] = int(1.1 * target.estimate_gas(params))
build_tx = target.build_transaction(params)

# sign, send and wait
try:
signed_tx = account.sign_transaction(build_tx)
tx_hash = web3.eth.send_raw_transaction(signed_tx.rawTransaction)
tx_receipt = web3.eth.wait_for_transaction_receipt(tx_hash)
if tx_receipt.status == 1:
self.log.info('Transaction confirmed')
self.log.info('Expected sum: %d' % sum(large_array))
self.log.info('Call shows value: %d', calldata.contract.functions.getLastSum().call())
self.assertTrue(calldata.contract.functions.getLastSum().call() == sum(large_array))
else:
self.log.error('Transaction failed')
if expect_pass: self.addOutcome(FAILED,outcomeReason='Expected tx to succeed')
except Exception as e:
self.log.error('Error %s' % e)
if expect_pass: self.addOutcome(FAILED,outcomeReason='Expected tx to succeed')
else: self.addOutcome(PASSED,outcomeReason='Expected tx to fail')
2 changes: 1 addition & 1 deletion tests/ten/ten_cor_117/pysystest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
<title>Callbacks: privacy callback with large call data</title>
<purpose><![CDATA[
Uses a contract that processes large call data via a two phase commit (the public call back). The test first sends
such the tx has oversized data, then sends two other transactions under the limit.
such that the tx has oversized data, it then sends two other transactions under the limit.
]]>
</purpose>
</description>
Expand Down

0 comments on commit fa40674

Please sign in to comment.