mirror of
https://github.com/datahaven-xyz/datahaven
synced 2026-05-24 01:38:32 +00:00
## Summary This PR adds Moonbeam's Batch precompile to DataHaven, enabling efficient batching of multiple EVM transactions in a single call. This implementation follows Moonbeam's exact architecture and provides significant gas savings for batch operations. ## Key Features ### Batch Precompile Functions - **`batchSome(address[], uint256[], bytes[], uint64[])`**: Execute multiple calls, continuing on failures - **`batchSomeUntilFailure(address[], uint256[], bytes[], uint64[])`**: Execute calls until first failure - **`batchAll(address[], uint256[], bytes[], uint64[])`**: Execute all calls, reverting if any fail ### Technical Implementation - **Address**: `0x0808` (2056 in decimal) - **Access Control**: Restricted nesting with `SubcallWithMaxNesting<2>` - **Self-recursion**: Only the Batch precompile can call itself (`OnlyFrom<AddressU64<2056>>`) - **Gas Management**: Proper gas estimation and refund handling - **Error Handling**: Comprehensive revert reasons and event logging Depends on #137 --------- Co-authored-by: Ahmad Kaouk <ahmadkaouk.93@gmail.com>
82 lines
3.7 KiB
Solidity
82 lines
3.7 KiB
Solidity
// SPDX-License-Identifier: GPL-3.0-only
|
|
pragma solidity >=0.8.3;
|
|
|
|
/// @dev The Batch contract's address.
|
|
address constant BATCH_ADDRESS = 0x0000000000000000000000000000000000000808;
|
|
|
|
/// @dev The Batch contract's instance.
|
|
Batch constant BATCH_CONTRACT = Batch(BATCH_ADDRESS);
|
|
|
|
/// @author The Moonbeam Team
|
|
/// @title Batch precompile
|
|
/// @dev Allows to perform multiple calls throught one call to the precompile.
|
|
/// Can be used by EOA to do multiple calls in a single transaction.
|
|
/// @custom:address 0x0000000000000000000000000000000000000808
|
|
interface Batch {
|
|
/// @dev Batch multiple calls into a single transaction.
|
|
/// All calls are performed from the address calling this precompile.
|
|
///
|
|
/// In case of one subcall reverting following subcalls will still be attempted.
|
|
///
|
|
/// @param to List of addresses to call.
|
|
/// @param value List of values for each subcall. If array is shorter than "to" then additional
|
|
/// calls will be performed with a value of 0.
|
|
/// @param callData Call data for each `to` address. If array is shorter than "to" then
|
|
/// additional calls will be performed with an empty call data.
|
|
/// @param gasLimit Gas limit for each `to` address. Use 0 to forward all the remaining gas.
|
|
/// If array is shorter than "to" then the remaining gas available will be used.
|
|
/// @custom:selector 79df4b9c
|
|
function batchSome(
|
|
address[] memory to,
|
|
uint256[] memory value,
|
|
bytes[] memory callData,
|
|
uint64[] memory gasLimit
|
|
) external;
|
|
|
|
/// @dev Batch multiple calls into a single transaction.
|
|
/// All calls are performed from the address calling this precompile.
|
|
///
|
|
/// In case of one subcall reverting, no more subcalls will be executed but
|
|
/// the batch transaction will succeed. Use batchAll to revert on any subcall revert.
|
|
///
|
|
/// @param to List of addresses to call.
|
|
/// @param value List of values for each subcall. If array is shorter than "to" then additional
|
|
/// calls will be performed with a value of 0.
|
|
/// @param callData Call data for each `to` address. If array is shorter than "to" then
|
|
/// additional calls will be performed with an empty call data.
|
|
/// @param gasLimit Gas limit for each `to` address. Use 0 to forward all the remaining gas.
|
|
/// If array is shorter than "to" then the remaining gas available will be used.
|
|
/// @custom:selector cf0491c7
|
|
function batchSomeUntilFailure(
|
|
address[] memory to,
|
|
uint256[] memory value,
|
|
bytes[] memory callData,
|
|
uint64[] memory gasLimit
|
|
) external;
|
|
|
|
/// @dev Batch multiple calls into a single transaction.
|
|
/// All calls are performed from the address calling this precompile.
|
|
///
|
|
/// In case of one subcall reverting, the entire batch will revert.
|
|
///
|
|
/// @param to List of addresses to call.
|
|
/// @param value List of values for each subcall. If array is shorter than "to" then additional
|
|
/// calls will be performed with a value of 0.
|
|
/// @param callData Call data for each `to` address. If array is shorter than "to" then
|
|
/// additional calls will be performed with an empty call data.
|
|
/// @param gasLimit Gas limit for each `to` address. Use 0 to forward all the remaining gas.
|
|
/// If array is shorter than "to" then the remaining gas available will be used.
|
|
/// @custom:selector 96e292b8
|
|
function batchAll(
|
|
address[] memory to,
|
|
uint256[] memory value,
|
|
bytes[] memory callData,
|
|
uint64[] memory gasLimit
|
|
) external;
|
|
|
|
/// Emitted when a subcall succeeds.
|
|
event SubcallSucceeded(uint256 index);
|
|
|
|
/// Emitted when a subcall fails.
|
|
event SubcallFailed(uint256 index);
|
|
}
|