Cartesi Rollups Contracts
The Cartesi Rollups Contracts are a set of Solidity smart contracts that provide Data Availability, Consensus and Settlement to Cartesi Rollups applications. They are completely permissionless, and can be deployed by anyone to any EVM-compatible chain. Nevertheless, the Cartesi Foundation, as a form of public good, kindly deploys them to Ethereum, Arbitrum, Optimism, Base, and their respective testnets.
Data Availability of user transactions and Consensus over their order is provided by the InputBox contract,
while Settlement is provided by the Application contract in conjunction with a settlement module.
Currently, we have implemented an authority-based module (Authority) and a quorum-based module (Quorum).
We also support a tournament-based module (DaveConsensus), which is hosted on the Dave repository.
The Cartesi Rollups Contracts are an integral part of the Cartesi Rollups SDK, and are used by the Cartesi Rollups Node, the Cartesi Rollups Explorer, and, of course, by Cartesi Rollups applications. Through simple Solidity interfaces, one can easily send and list user transactions, deposit assets, submit claims, execute asset withdrawal orders, and more.
Features
- Supports deposits and withdrawals of several types of assets:
- Supports the validation of outputs and output hashes
- Supports the execution of
CALLandDELEGATECALLvouchers - Supports Quorum and Authority-based settlement models
- Includes factory contracts for easy deployment
Getting started
First, clone this repository.
git clone https://github.com/cartesi/rollups-contracts.git
Then, make sure the correct version of Foundry is installed.
make check-foundry-version
Having done that, you can build a local devnet.
The following Makefile target dumps the Anvil state into a state.json file
and the deployment addresses into the deployments/31337 directory.
make devnet
Once built, you can run the local devnet with Anvil.
anvil --load-state state.json
You can then interact with the contracts with Cast.
The following command, for example,
calls the getDeploymentBlockNumber function
of the InputBox contract
deployed to the local devnet.
cast call $(cat deployments/31337/InputBox.txt) 'getDeploymentBlockNumber()(uint256)'
Deployment
If you wish to deploy the contracts to a live network, we may suggest our deployment guide.
Verification
If you wish to verify contracts deployed to a live network, we may suggest our verification guide.
Documentation
A more in-depth documentation on the contracts can be found here.
Use cases
The Cartesi Rollups Contracts are used by the Cartesi Rollups SDK. They offer an extensible framework for input relays and output execution. Here are some examples of use cases:
- Trustless relaying of on-chain information
- Trustless locking of on-chain assets
- Withdrawal of on-chain assets
- Minting of on-chain assets
- Scheduling of on-chain actions
- Liquidity for on-chain assets
Related projects
The contracts are used by several other projects in the Cartesi ecosystem:
Authors
- Guilherme Dantas (guidanoli)
- Pedro Argento (pedroargento)
- Zehui Zheng (ZzzzHui)
License
The project is licensed under Apache-2.0.
Contents
IOwnable
The interface of OpenZeppelin's Ownable contract.
Functions
owner
function owner() external view returns (address);
renounceOwnership
function renounceOwnership() external;
transferOwnership
function transferOwnership(address newOwner) external;
Contents
- AccountValidityProof
- AddressErrors
- BinaryMerkleTreeErrors
- CanonicalMachine
- DelegateCallVoucher
- Erc1155BatchDeposit
- Erc1155SingleDeposit
- Erc20Deposit
- Erc721Deposit
- EtherDeposit
- IVersionGetter
- InputEncoding
- Inputs
- LeafProof
- MachineValidationErrors
- MachineValidityProof
- OutputValidityProof
- Outputs
- RollupsContract
- Version constants
- Voucher
- WithdrawalConfig
AccountValidityProof
Proof of inclusion of an account in the accounts drive.
From the index and siblings, one can calculate the accounts drive root.
The siblings array should have size equal to the log2 of the maximum number of accounts.
struct AccountValidityProof {
uint64 accountIndex;
bytes32[] accountRootSiblings;
}
Properties
| Name | Type | Description |
|---|---|---|
accountIndex | uint64 | Index of account in the accounts drive |
accountRootSiblings | bytes32[] | Siblings of the account root in the accounts drive |
AddressErrors
Errors
InsufficientFunds
Could not execute an output, because the application contract doesn't have enough Ether.
error InsufficientFunds(uint256 value, uint256 balance);
Parameters
| Name | Type | Description |
|---|---|---|
value | uint256 | The amount of Wei necessary for the execution of the output |
balance | uint256 | The current application contract balance |
TargetHasNoCode
Could not execute an output, because the target account doesn't have any code.
error TargetHasNoCode(address target);
Parameters
| Name | Type | Description |
|---|---|---|
target | address | The target account address |
BinaryMerkleTreeErrors
Errors
InvalidNodeIndex
The provided node index is invalid.
The node index should be less than 2^{height}.
error InvalidNodeIndex(uint256 nodeIndex, uint256 height);
Parameters
| Name | Type | Description |
|---|---|---|
nodeIndex | uint256 | The node index in its level |
height | uint256 | The binary Merkle tree height |
DriveTooLarge
A drive size too large was provided.
error DriveTooLarge(uint256 log2DriveSize, uint256 maxLog2DriveSize);
Parameters
| Name | Type | Description |
|---|---|---|
log2DriveSize | uint256 | The log2 size of the drive |
maxLog2DriveSize | uint256 | The maximum log2 size of a drive |
DataBlockTooLarge
A data block size too large was provided.
error DataBlockTooLarge(uint256 log2DataBlockSize, uint256 maxLog2DataBlockSize);
Parameters
| Name | Type | Description |
|---|---|---|
log2DataBlockSize | uint256 | The log2 size of the data block |
maxLog2DataBlockSize | uint256 | The maximum log2 size of a data block |
DriveSmallerThanDataBlock
A drive size smaller than the data block size was provided.
error DriveSmallerThanDataBlock(uint256 log2DriveSize, uint256 log2DataBlockSize);
Parameters
| Name | Type | Description |
|---|---|---|
log2DriveSize | uint256 | The log2 size of the drive |
log2DataBlockSize | uint256 | The log2 size of the data block |
DriveSmallerThanData
A drive too small to fit the data was provided.
error DriveSmallerThanData(uint256 driveSize, uint256 dataSize);
Parameters
| Name | Type | Description |
|---|---|---|
driveSize | uint256 | The size of the drive |
dataSize | uint256 | The size of the data |
UnexpectedFinalStackDepth
An unexpected stack error occurred.
Expected final stack depth to be 1.
error UnexpectedFinalStackDepth(uint256 stackDepth);
Parameters
| Name | Type | Description |
|---|---|---|
stackDepth | uint256 | The final stack depth |
CanonicalMachine
Title: Canonical Machine Constants Library
Defines several constants related to the reference implementation of the RISC-V machine that runs Linux, also known as the "Cartesi Machine".
State Variables
INPUT_MAX_SIZE
Maximum input size (64 kilobytes).
uint64 constant INPUT_MAX_SIZE = 1 << 16
LOG2_MEMORY_SIZE
Log2 of memory size.
uint8 constant LOG2_MEMORY_SIZE = 64
LOG2_MAX_OUTPUTS
Log2 of maximum number of outputs.
uint64 constant LOG2_MAX_OUTPUTS = EmulatorConstants.ROLLUP_LOG2_MAX_OUTPUT_COUNT
LOG2_DATA_BLOCK_SIZE
Log2 of data block size.
uint8 constant LOG2_DATA_BLOCK_SIZE = Memory.LOG2_LEAF
DATA_BLOCK_MASK
Data block mask.
uint64 constant DATA_BLOCK_MASK = Memory.LEAF_MASK
MEMORY_TREE_HEIGHT
Log2 of memory tree height.
uint8 constant MEMORY_TREE_HEIGHT = LOG2_MEMORY_SIZE - LOG2_DATA_BLOCK_SIZE
TX_BUFFER_START
TX buffer start.
uint64 constant TX_BUFFER_START = EmulatorConstants.AR_CMIO_TX_BUFFER_START
IFLAGS_Y_ADDRESS
Internal Y flag address.
uint64 constant IFLAGS_Y_ADDRESS = EmulatorConstants.IFLAGS_Y_ADDRESS
HTIF_TOHOST_ADDRESS
HTIF tohost address.
uint64 constant HTIF_TOHOST_ADDRESS = EmulatorConstants.HTIF_TOHOST_ADDRESS
DelegateCallVoucher
A delegate-call voucher
struct DelegateCallVoucher {
address destination;
bytes payload;
}
Properties
| Name | Type | Description |
|---|---|---|
destination | address | The destination address |
payload | bytes | The delegate-call payload |
Erc1155BatchDeposit
An ERC-1155 batch token deposit
struct Erc1155BatchDeposit {
IERC1155 token;
address sender;
uint256[] tokenIds;
uint256[] values;
}
Properties
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The token contract |
sender | address | The token sender |
tokenIds | uint256[] | The token identifiers |
values | uint256[] | The token amounts per token type |
Erc1155SingleDeposit
An ERC-1155 single token deposit
struct Erc1155SingleDeposit {
IERC1155 token;
address sender;
uint256 tokenId;
uint256 value;
}
Properties
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The token contract |
sender | address | The token sender |
tokenId | uint256 | The token identifier |
value | uint256 | The token amount |
Erc20Deposit
An ERC-20 token deposit
struct Erc20Deposit {
IERC20 token;
address sender;
uint256 value;
}
Properties
| Name | Type | Description |
|---|---|---|
token | IERC20 | The token contract |
sender | address | The token sender |
value | uint256 | The token amount |
Erc721Deposit
An ERC-721 token deposit
struct Erc721Deposit {
IERC721 token;
address sender;
uint256 tokenId;
}
Properties
| Name | Type | Description |
|---|---|---|
token | IERC721 | The token contract |
sender | address | The token sender |
tokenId | uint256 | The token identifier |
EtherDeposit
An Ether token deposit
struct EtherDeposit {
address sender;
uint256 value;
}
Properties
| Name | Type | Description |
|---|---|---|
sender | address | The Ether sender |
value | uint256 | The Ether amount (in Wei) |
IVersionGetter
Functions
version
Get the version of the smart contract project.
Examples:
- 1.2.3 --> (1, 2, 3, "", "" )
- 1.2.3-alpha.0 --> (1, 2, 3, "alpha.0", "" )
- 1.2.3+sha.a1b2c3 --> (1, 2, 3, "", "sha.a1b2c3")
- 1.2.3-alpha.0+sha.a1b2c3 --> (1, 2, 3, "alpha.0", "sha.a1b2c3") You can learn more about semantic versioning at <semver.org>.
function version()
external
view
returns (
uint64 major,
uint64 minor,
uint64 patch,
string memory preRelease,
string memory buildMetadata
);
Returns
| Name | Type | Description |
|---|---|---|
major | uint64 | The major version |
minor | uint64 | The minor version |
patch | uint64 | The patch version |
preRelease | string | The pre-release version (can be empty) |
buildMetadata | string | The build metadata (can be empty) |
InputEncoding
Title: Input Encoding Library
Defines the encoding of inputs added by core trustless and permissionless contracts, such as portals.
Functions
encodeEtherDeposit
Encode an Ether deposit.
function encodeEtherDeposit(
address sender,
uint256 value,
bytes calldata execLayerData
) internal pure returns (bytes memory);
Parameters
| Name | Type | Description |
|---|---|---|
sender | address | The Ether sender |
value | uint256 | The amount of Wei being sent |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes | The encoded input payload |
decodeEtherDeposit
Decode an Ether deposit.
function decodeEtherDeposit(bytes calldata payload)
internal
pure
returns (EtherDeposit memory deposit);
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | The encoded input payload |
Returns
| Name | Type | Description |
|---|---|---|
deposit | EtherDeposit | The decoded Ether deposit |
encodeErc20Deposit
Encode an ERC-20 token deposit.
function encodeErc20Deposit(
IERC20 token,
address sender,
uint256 value,
bytes calldata execLayerData
) internal pure returns (bytes memory);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC20 | The token contract |
sender | address | The token sender |
value | uint256 | The amount of tokens being sent |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes | The encoded input payload |
decodeErc20Deposit
Decode an ERC-20 token deposit.
function decodeErc20Deposit(bytes calldata payload)
internal
pure
returns (Erc20Deposit memory deposit);
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | The encoded input payload |
Returns
| Name | Type | Description |
|---|---|---|
deposit | Erc20Deposit | The decoded ERC-20 token deposit |
encodeErc721Deposit
Encode an ERC-721 token deposit.
baseLayerData should be forwarded to token.
function encodeErc721Deposit(
IERC721 token,
address sender,
uint256 tokenId,
bytes calldata baseLayerData,
bytes calldata execLayerData
) internal pure returns (bytes memory);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC721 | The token contract |
sender | address | The token sender |
tokenId | uint256 | The token identifier |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes | The encoded input payload |
decodeErc721Deposit
Decode an ERC-721 token deposit.
function decodeErc721Deposit(bytes calldata payload)
internal
pure
returns (Erc721Deposit memory deposit);
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | The encoded input payload |
Returns
| Name | Type | Description |
|---|---|---|
deposit | Erc721Deposit | The decoded ERC-721 token deposit |
encodeSingleErc1155Deposit
Encode an ERC-1155 single token deposit.
baseLayerData should be forwarded to token.
function encodeSingleErc1155Deposit(
IERC1155 token,
address sender,
uint256 tokenId,
uint256 value,
bytes calldata baseLayerData,
bytes calldata execLayerData
) internal pure returns (bytes memory);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The ERC-1155 token contract |
sender | address | The token sender |
tokenId | uint256 | The identifier of the token being transferred |
value | uint256 | Transfer amount |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes | The encoded input payload |
decodeErc1155SingleDeposit
Decode an ERC-1155 single token deposit.
function decodeErc1155SingleDeposit(bytes calldata payload)
internal
pure
returns (Erc1155SingleDeposit memory deposit);
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | The encoded input payload |
Returns
| Name | Type | Description |
|---|---|---|
deposit | Erc1155SingleDeposit | The decoded ERC-1155 single token deposit |
encodeBatchErc1155Deposit
Encode an ERC-1155 batch token deposit.
baseLayerData should be forwarded to token.
function encodeBatchErc1155Deposit(
IERC1155 token,
address sender,
uint256[] calldata tokenIds,
uint256[] calldata values,
bytes calldata baseLayerData,
bytes calldata execLayerData
) internal pure returns (bytes memory);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The ERC-1155 token contract |
sender | address | The token sender |
tokenIds | uint256[] | The identifiers of the tokens being transferred |
values | uint256[] | Transfer amounts per token type |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes | The encoded input payload |
decodeErc1155BatchDeposit
Decode an ERC-1155 batch token deposit.
function decodeErc1155BatchDeposit(bytes calldata payload)
internal
pure
returns (Erc1155BatchDeposit memory deposit);
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | The encoded input payload |
Returns
| Name | Type | Description |
|---|---|---|
deposit | Erc1155BatchDeposit | The decoded ERC-1155 batch token deposit |
Inputs
Title: Inputs
forge-lint: disable-start(mixed-case-function)
Defines the signatures of inputs.
Functions
EvmAdvance
An advance request from an EVM-compatible blockchain to a Cartesi Machine.
See EIP-4399 for safe usage of prevRandao.
function EvmAdvance(
uint256 chainId,
address appContract,
address msgSender,
uint256 blockNumber,
uint256 blockTimestamp,
uint256 prevRandao,
uint256 index,
bytes calldata payload
) external;
Parameters
| Name | Type | Description |
|---|---|---|
chainId | uint256 | The chain ID |
appContract | address | The application contract address |
msgSender | address | The address of whoever sent the input |
blockNumber | uint256 | The number of the block in which the input was added |
blockTimestamp | uint256 | The timestamp of the block in which the input was added |
prevRandao | uint256 | The latest RANDAO mix of the post beacon state of the previous block |
index | uint256 | The index of the input in the input box |
payload | bytes | The payload provided by the message sender |
LeafProof
Proves a data block at a known offset in the machine.
struct LeafProof {
bytes32 dataBlock;
bytes32[] siblings;
}
Properties
| Name | Type | Description |
|---|---|---|
dataBlock | bytes32 | The 32-byte data block at the known offset |
siblings | bytes32[] | The bottom-up siblings of the leaf node |
MachineValidationErrors
Errors
InvalidSiblingsArrayLength
A siblings array has an invalid length. A leaf proof siblings array has
an expected length given by the log2 of the machine memory space - the log2 of
the machine data block size (in bytes). See the CanonicalMachine library for
the value of these constants. This is most likely an issue on the claim submitter
code rather than on the application.
error InvalidSiblingsArrayLength();
InvalidMachineMerkleProof
The machine Merkle root produced by a Merkle proof differs from the one provided separately. This indicates that either the leaf proof data block, the leaf proof siblings array, or the machine Merkle root is incorrect. This is most likely an issue on the claim submitter code rather than on the application.
error InvalidMachineMerkleProof();
InvalidPostEpochMachineIflagsYRegister
The post-epoch machine iflags_Y register is unset (zero) and therefore unsuitable for finalization. This may suggest that the machine has reached an unrecoverable state and that the application should be foreclosed to unlock user funds through emergency withdrawals and non-finalized deposit refunds.
error InvalidPostEpochMachineIflagsYRegister();
InvalidPostEpochMachineHtifTohostRegister
The post-epoch machine HTIF tohost register does not signal that the machine is manually yielded with 'rx accepted' reason. This may suggest that the machine has reached an unrecoverable state and that the application should be foreclosed to unlock user funds through emergency withdrawals and non-finalized deposit refunds.
error InvalidPostEpochMachineHtifTohostRegister();
MachineValidityProof
Contains information used to prove the validity of a post-epoch machine state (yielded manually with an 'rx accepted' reason) and its outputs Merkle root (stored at the start of the tx buffer).
struct MachineValidityProof {
LeafProof iflagsYProof;
LeafProof htifTohostProof;
LeafProof txBufferProof;
}
Properties
| Name | Type | Description |
|---|---|---|
iflagsYProof | LeafProof | Proves the iflags_Y register |
htifTohostProof | LeafProof | Proves the HTIF tohost register |
txBufferProof | LeafProof | Proves the first data block of the CMIO tx buffer |
OutputValidityProof
Proof of inclusion of an output in the output Merkle tree.
From the index and siblings, one can calculate the root of the Merkle tree.
The siblings array should have size equal to the log2 of the maximum number of outputs.
See the CanonicalMachine library for constants.
struct OutputValidityProof {
uint64 outputIndex;
bytes32[] outputHashesSiblings;
}
Properties
| Name | Type | Description |
|---|---|---|
outputIndex | uint64 | Index of output in the Merkle tree |
outputHashesSiblings | bytes32[] | Siblings of the output in the Merkle tree |
Outputs
Title: Outputs
forge-lint: disable-start(mixed-case-function)
Defines the signatures of outputs that can be generated by the off-chain machine and verified by the on-chain contracts.
Functions
Notice
A piece of verifiable information.
function Notice(bytes calldata payload) external;
Parameters
| Name | Type | Description |
|---|---|---|
payload | bytes | An arbitrary payload. |
Voucher
A single-use permission to execute a specific message call from the context of the application contract.
function Voucher(address destination, uint256 value, bytes calldata payload) external;
Parameters
| Name | Type | Description |
|---|---|---|
destination | address | The address that will be called |
value | uint256 | The amount of Wei to be transferred through the call |
payload | bytes | The payload, which—in the case of Solidity contracts—encodes a function call |
DelegateCallVoucher
A single-use permission to execute a specific delegate call from the context of the application contract.
function DelegateCallVoucher(address destination, bytes calldata payload) external;
Parameters
| Name | Type | Description |
|---|---|---|
destination | address | The address that will be called |
payload | bytes | The payload, which—in the case of Solidity libraries—encodes a function call |
RollupsContract
Inherits: IVersionGetter
Functions
version
function version()
external
pure
override
returns (
uint64 major,
uint64 minor,
uint64 patch,
string memory preRelease,
string memory buildMetadata
);
Constants
MAJOR
uint64 constant MAJOR = 3
MINOR
uint64 constant MINOR = 0
PATCH
uint64 constant PATCH = 0
PRE_RELEASE
string constant PRE_RELEASE = "alpha.10"
BUILD_METADATA
string constant BUILD_METADATA = ""
Voucher
A voucher
struct Voucher {
address destination;
uint256 value;
bytes payload;
}
Properties
| Name | Type | Description |
|---|---|---|
destination | address | The destination address |
value | uint256 | The Ether amount (in Wei) |
payload | bytes | The call payload |
WithdrawalConfig
struct WithdrawalConfig {
address guardian;
uint8 log2LeavesPerAccount;
uint8 log2MaxNumOfAccounts;
uint64 accountsDriveStartIndex;
IWithdrawalOutputBuilder withdrawalOutputBuilder;
}
Contents
Contents
Authority
Inherits: IAuthority, AbstractConsensus, Ownable
A consensus contract controlled by a single address, the owner.
This contract inherits from OpenZeppelin's Ownable contract.
For more information on Ownable, please consult OpenZeppelin's official documentation.
State Variables
_validatedEpochs
Epochs with a submitted (and staged) claim, per application.
Epochs are stored in bitmap structure by their number (last processed block number / epoch length).
mapping(address => BitMaps.BitMap) _validatedEpochs
Functions
constructor
Reverts if the epoch length is zero.
constructor(address initialOwner, uint256 epochLength, uint256 claimStagingPeriod)
AbstractConsensus(epochLength, claimStagingPeriod)
Ownable(initialOwner);
Parameters
| Name | Type | Description |
|---|---|---|
initialOwner | address | The initial contract owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
submitClaim
Submit a claim to the consensus.
MUST fire a ClaimSubmitted event.
function submitClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
MachineValidityProof calldata proof
) external override onlyOwner;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
proof | MachineValidityProof | The machine validity proof |
owner
Returns the address of the current owner.
function owner() public view override(IOwnable, Ownable) returns (address);
renounceOwnership
Leaves the contract without owner. It will not be possible to call
onlyOwner functions. Can only be called by the current owner.
NOTE: Renouncing ownership will leave the contract without an owner,
thereby disabling any functionality that is only available to the owner.
function renounceOwnership() public override(IOwnable, Ownable);
transferOwnership
Transfers ownership of the contract to a new account (newOwner).
Can only be called by the current owner.
function transferOwnership(address newOwner) public override(IOwnable, Ownable);
supportsInterface
function supportsInterface(bytes4 interfaceId)
public
view
override(IERC165, AbstractConsensus)
returns (bool);
AuthorityFactory
Inherits: IAuthorityFactory, RollupsContract
Title: Authority Factory
Allows anyone to reliably deploy a new IAuthority contract.
Functions
newAuthority
function newAuthority(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod
) external override returns (IAuthority authority);
newAuthority
function newAuthority(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external override returns (IAuthority authority);
calculateAuthorityAddress
function calculateAuthorityAddress(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external view override returns (address);
IAuthority
Inherits: IConsensus, IOwnable
A consensus contract controlled by a single address, the owner.
IAuthorityFactory
Inherits: IVersionGetter, IConsensusFactoryErrors
Title: Authority Factory interface
Functions
newAuthority
Deploy a new authority.
On success, MUST emit an AuthorityCreated event.
Reverts if the authority owner address is zero.
Reverts if the epoch length is zero.
function newAuthority(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod
) external returns (IAuthority);
Parameters
| Name | Type | Description |
|---|---|---|
authorityOwner | address | The initial authority owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IAuthority | The authority |
newAuthority
Deploy a new authority deterministically.
On success, MUST emit an AuthorityCreated event.
Reverts if the authority owner address is zero.
Reverts if the epoch length is zero.
function newAuthority(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external returns (IAuthority);
Parameters
| Name | Type | Description |
|---|---|---|
authorityOwner | address | The initial authority owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
salt | bytes32 | The salt used to deterministically generate the authority address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IAuthority | The authority |
calculateAuthorityAddress
Calculate the address of an authority to be deployed deterministically.
Beware that only the newAuthority function with the salt parameter
is able to deterministically deploy an authority.
function calculateAuthorityAddress(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external view returns (address);
Parameters
| Name | Type | Description |
|---|---|---|
authorityOwner | address | The initial authority owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
salt | bytes32 | The salt used to deterministically generate the authority address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | address | The deterministic authority address |
Events
AuthorityCreated
A new authority was deployed.
MUST be triggered on a successful call to newAuthority.
event AuthorityCreated(IAuthority authority);
Parameters
| Name | Type | Description |
|---|---|---|
authority | IAuthority | The authority |
Contents
IQuorum
Inherits: IConsensus
A consensus model controlled by a small, immutable set of n (>= 1) validators.
You can know the value of n by calling the numOfValidators function.
Upon construction, each validator is assigned a unique number between 1 and n.
These numbers are used internally instead of addresses for gas optimization reasons.
You can list the validators in the quorum by calling the validatorById
function for each ID from 1 to n.
Functions
numOfValidators
Get the number of validators.
The number of validators is greater than or equal to 1.
function numOfValidators() external view returns (uint256);
validatorId
Get the ID of a validator.
Validators are assigned IDs between 1 and N, the total number of validators.
Non-validators are assigned to ID zero.
function validatorId(address validator) external view returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
validator | address | The validator address |
validatorById
Get the address of a validator by its ID.
Validator IDs range from 1 to N, the total number of validators.
Valid IDs do not map to address zero.
Invalid IDs map to address zero.
function validatorById(uint256 id) external view returns (address);
Parameters
| Name | Type | Description |
|---|---|---|
id | uint256 | The validator ID |
numOfValidatorsInFavorOfAnyClaimInEpoch
Get the number of validators in favor of any claim in a given epoch.
function numOfValidatorsInFavorOfAnyClaimInEpoch(
address appContract,
uint256 lastProcessedBlockNumber
) external view returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
Returns
| Name | Type | Description |
|---|---|---|
<none> | uint256 | Number of validators in favor of any claim in the epoch |
isValidatorInFavorOfAnyClaimInEpoch
Check whether a validator is in favor of any claim in a given epoch.
Assumes the provided ID is valid.
function isValidatorInFavorOfAnyClaimInEpoch(
address appContract,
uint256 lastProcessedBlockNumber,
uint256 id
) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
id | uint256 | The ID of the validator |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether validator is in favor of any claim in the epoch |
numOfValidatorsInFavorOf
Get the number of validators in favor of a claim.
function numOfValidatorsInFavorOf(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) external view returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
<none> | uint256 | Number of validators in favor of claim |
isValidatorInFavorOf
Check whether a validator is in favor of a claim.
Assumes the provided ID is valid.
function isValidatorInFavorOf(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
uint256 id
) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
id | uint256 | The ID of the validator |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether validator is in favor of claim |
Errors
CallerIsNotValidator
This error is raised whenever submitClaim is called by
someone who is not a validator.
error CallerIsNotValidator(address caller);
Parameters
| Name | Type | Description |
|---|---|---|
caller | address | The caller address |
IQuorumFactory
Inherits: IVersionGetter, IConsensusFactoryErrors, IQuorumFactoryErrors
Title: Quorum Factory interface
Functions
newQuorum
Deploy a new quorum.
On success, MUST emit a QuorumCreated event.
Duplicates in the validators array are ignored.
Reverts if the epoch length is zero.
function newQuorum(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod
) external returns (IQuorum);
Parameters
| Name | Type | Description |
|---|---|---|
validators | address[] | the list of validators |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IQuorum | The quorum |
newQuorum
Deploy a new quorum deterministically.
On success, MUST emit a QuorumCreated event.
Duplicates in the validators array are ignored.
Reverts if the epoch length is zero.
function newQuorum(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external returns (IQuorum);
Parameters
| Name | Type | Description |
|---|---|---|
validators | address[] | the list of validators |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
salt | bytes32 | The salt used to deterministically generate the quorum address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IQuorum | The quorum |
calculateQuorumAddress
Calculate the address of a quorum to be deployed deterministically.
Beware that only the newQuorum function with the salt parameter
is able to deterministically deploy a quorum.
function calculateQuorumAddress(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external view returns (address);
Parameters
| Name | Type | Description |
|---|---|---|
validators | address[] | the list of validators |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
salt | bytes32 | The salt used to deterministically generate the quorum address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | address | The deterministic quorum address |
Events
QuorumCreated
A new quorum was deployed.
MUST be triggered on a successful call to newQuorum.
event QuorumCreated(IQuorum quorum);
Parameters
| Name | Type | Description |
|---|---|---|
quorum | IQuorum | The quorum |
IQuorumFactoryErrors
Errors
ZeroAddressValidator
This error is raised whenever one tries to deploy a Quorum
with the zero address as one of the validators. This is forbidden
because we reserve the zero address as a sentinel value for
non-validators (when consulting the validatorById function).
error ZeroAddressValidator();
EmptyQuorum
This error is raised whenever someone deploys a Quorum with an empty array of validators. This is forbidden because without validators, the Quorum contract would be essentially dead, indicating a mistake from the deployer.
error EmptyQuorum();
Quorum
Inherits: IQuorum, AbstractConsensus
State Variables
NUM_OF_VALIDATORS
The total number of validators.
See the numOfValidators function.
uint256 immutable NUM_OF_VALIDATORS
_validatorId
Validator IDs indexed by address.
See the validatorId function.
Non-validators are assigned to ID zero.
Validators have IDs greater than zero.
mapping(address => uint256) private _validatorId
_validatorById
Validator addresses indexed by ID.
See the validatorById function.
Invalid IDs map to address zero.
mapping(uint256 => address) private _validatorById
_allVotes
Votes indexed by application contract address, and last processed block number.
See the numOfValidatorsInFavorOfAnyClaimInEpoch
and isValidatorInFavorOfAnyClaimInEpoch functions.
mapping(address => mapping(uint256 => Votes)) private _allVotes
_votes
Votes indexed by application contract address, last processed block number and machine Merkle root.
See the numOfValidatorsInFavorOf and isValidatorInFavorOf functions.
mapping(address => mapping(uint256 => mapping(bytes32 => Votes))) private _votes
Functions
constructor
Duplicates in the validators array are ignored.
Zero addresses in the validators array are prohibited.
Reverts if the epoch length is zero.
Reverts if the quorum would contain zero validators.
constructor(
address[] memory validators,
uint256 epochLength,
uint256 claimStagingPeriod
) AbstractConsensus(epochLength, claimStagingPeriod);
Parameters
| Name | Type | Description |
|---|---|---|
validators | address[] | The array of validator addresses |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
submitClaim
function submitClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
MachineValidityProof calldata proof
) external override;
numOfValidators
function numOfValidators() external view override returns (uint256);
validatorId
function validatorId(address validator) external view override returns (uint256);
validatorById
function validatorById(uint256 id) external view override returns (address);
numOfValidatorsInFavorOfAnyClaimInEpoch
function numOfValidatorsInFavorOfAnyClaimInEpoch(
address appContract,
uint256 lastProcessedBlockNumber
) external view override returns (uint256);
isValidatorInFavorOfAnyClaimInEpoch
function isValidatorInFavorOfAnyClaimInEpoch(
address appContract,
uint256 lastProcessedBlockNumber,
uint256 id
) external view override returns (bool);
numOfValidatorsInFavorOf
function numOfValidatorsInFavorOf(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) external view override returns (uint256);
isValidatorInFavorOf
function isValidatorInFavorOf(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
uint256 id
) external view override returns (bool);
_getAllVotes
Get a Votes structure from storage from a given epoch.
function _getAllVotes(address appContract, uint256 lastProcessedBlockNumber)
internal
view
returns (Votes storage);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
Returns
| Name | Type | Description |
|---|---|---|
<none> | Votes | The Votes structure related to all claims in a given epoch |
_getVotes
Get a Votes structure from storage from a given claim.
function _getVotes(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) internal view returns (Votes storage);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
<none> | Votes | The Votes structure related to a given claim |
supportsInterface
function supportsInterface(bytes4 interfaceId)
public
view
override(IERC165, AbstractConsensus)
returns (bool);
Structs
Votes
Votes in favor of a particular claim.
inFavorById is a bitmap indexed by validator IDs.
struct Votes {
uint256 inFavorCount;
BitMaps.BitMap inFavorById;
}
Properties
| Name | Type | Description |
|---|---|---|
inFavorCount | uint256 | The number of validators in favor of the claim |
inFavorById | BitMaps.BitMap | The set of validators in favor of the claim |
QuorumFactory
Inherits: IQuorumFactory, RollupsContract
Title: Quorum Factory
Allows anyone to reliably deploy a new IQuorum contract.
Functions
newQuorum
function newQuorum(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod
) external override returns (IQuorum quorum);
newQuorum
function newQuorum(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external override returns (IQuorum quorum);
calculateQuorumAddress
function calculateQuorumAddress(
address[] calldata validators,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 salt
) external view override returns (address);
AbstractConsensus
Inherits: IConsensus, ERC165, ApplicationChecker, RollupsContract
Abstract implementation of IConsensus
State Variables
EPOCH_LENGTH
The epoch length
uint256 immutable EPOCH_LENGTH
CLAIM_STAGING_PERIOD
The claim staging period
uint256 immutable CLAIM_STAGING_PERIOD
_validOutputsMerkleRoots
Indexes valid outputs Merkle roots by application contract address.
mapping(address => mapping(bytes32 => bool)) private _validOutputsMerkleRoots
_claims
Indexes claim information by application contract address, last-processed block number, and machine Merkle root.
mapping(address => mapping(uint256 => mapping(bytes32 => Claim))) private _claims
_firstUnprocessedBlockNumbers
Indexes number of the first unprocessed block by application contract address.
mapping(address => uint256) private _firstUnprocessedBlockNumbers
_lastFinalizedMachineMerkleRoots
Indexes machine merkle root of the most recently accepted claim by application contract address.
mapping(address => bytes32) private _lastFinalizedMachineMerkleRoots
_numOfAcceptedClaims
Indexes number of accepted claims by application contract address.
Must be monotonically non-decreasing in time
mapping(address => uint256) private _numOfAcceptedClaims
_numOfStagedClaims
Indexes number of staged claims by application contract address.
Must be monotonically non-decreasing in time
mapping(address => uint256) private _numOfStagedClaims
_numOfSubmittedClaims
Indexes number of submitted claims by application contract address.
Must be monotonically non-decreasing in time
mapping(address => uint256) private _numOfSubmittedClaims
Functions
constructor
Reverts if the epoch length is zero.
constructor(uint256 epochLength, uint256 claimStagingPeriod) ;
Parameters
| Name | Type | Description |
|---|---|---|
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
isOutputsMerkleRootValid
Check whether an outputs Merkle root is valid.
function isOutputsMerkleRootValid(address appContract, bytes32 outputsMerkleRoot)
public
view
override
returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
outputsMerkleRoot | bytes32 | The outputs Merkle root |
getLastFinalizedMachineMerkleRoot
function getLastFinalizedMachineMerkleRoot(address appContract)
public
view
override
returns (bytes32);
wasInputFinalized
function wasInputFinalized(address appContract, uint256, uint256 blockNumber)
public
view
override
returns (bool);
getEpochLength
Get the epoch length, in number of base-layer blocks.
The epoch number of a block is defined as the integer division of the block number by the epoch length.
function getEpochLength() public view override returns (uint256);
getClaimStagingPeriod
function getClaimStagingPeriod() public view override returns (uint256);
getNumberOfAcceptedClaims
Get the number of claims accepted by the consensus regarding a specific app.
function getNumberOfAcceptedClaims(address appContract)
external
view
override
returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getNumberOfStagedClaims
function getNumberOfStagedClaims(address appContract)
external
view
override
returns (uint256);
getNumberOfSubmittedClaims
Get the number of claims submitted to the consensus regarding a specific app.
function getNumberOfSubmittedClaims(address appContract)
external
view
override
returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
supportsInterface
See {IERC165-supportsInterface}.
function supportsInterface(bytes4 interfaceId)
public
view
virtual
override(IERC165, ERC165)
returns (bool);
getClaim
function getClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) public view override returns (Claim memory claim);
acceptClaim
function acceptClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) external override notForeclosed(appContract);
_validateLastProcessedBlockNumber
Validate a last processed block number.
function _validateLastProcessedBlockNumber(uint256 lastProcessedBlockNumber)
internal
view;
Parameters
| Name | Type | Description |
|---|---|---|
lastProcessedBlockNumber | uint256 | The number of the last processed block |
_submitClaim
Submit a claim.
Assumes the machine is proven to be manually yielded with an 'rx accepted' reason.
Assumes outputs Merkle root is proven to be at the start of the machine TX buffer.
Assumes the last processed block number is valid.
Checks whether the app is foreclosed.
Emits a ClaimSubmitted event.
function _submitClaim(
address submitter,
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 outputsMerkleRoot,
bytes32 machineMerkleRoot
) internal notForeclosed(appContract);
Parameters
| Name | Type | Description |
|---|---|---|
submitter | address | The submitter address |
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
outputsMerkleRoot | bytes32 | The output Merkle root |
machineMerkleRoot | bytes32 | The machine Merkle root |
_stageClaim
Stage a claim (if unstaged).
Assumes the machine is proven to be manually yielded with an 'rx accepted' reason.
Assumes outputs Merkle root is proven to be at the start of the machine TX buffer.
Assumes the last processed block number is valid.
Assumes the claim was previously submitted.
Checks whether the app is foreclosed.
Marks the claim as staged (if unstaged).
Emits a ClaimStaged event (if unstaged).
function _stageClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 outputsMerkleRoot,
bytes32 machineMerkleRoot
) internal notForeclosed(appContract);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
outputsMerkleRoot | bytes32 | The output Merkle root |
machineMerkleRoot | bytes32 | The machine Merkle root |
_validateMachine
Validates a machine given its Merkle root and a validity proof.
function _validateMachine(
bytes32 machineMerkleRoot,
MachineValidityProof calldata proof
) internal pure returns (bytes32 outputsMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
machineMerkleRoot | bytes32 | The machine Merkle root |
proof | MachineValidityProof | The machine validity proof |
Returns
| Name | Type | Description |
|---|---|---|
outputsMerkleRoot | bytes32 | The proven outputs Merkle root |
IConsensus
Inherits: IOutputsMerkleRootValidator, IApplicationChecker, IVersionGetter, MachineValidationErrors
This interface defines functions for submitting and accepting claims about
the state of multiple Cartesi Rollups applications with a single fixed epoch length.
Each application has its own stream of inputs, which is split into epochs. The index
of the epoch of an input is determined by the integer division of the number of the
base-layer block in which the input was added by the epoch length (see
getEpochLength function).
After every epoch, each validator can submit a claim about the post-epoch state of
the application (summarized by a machine Merkle root), while also proving the set of
all outputs ever emitted by the application up until that point (summarized by an
outputs Merkle root, which is written at a known address in the machine memory, and
proved on-chain through a Merkle proof). Naturally, some epochs might be empty (i.e.
they contain no input), in which case the state of the application remains unchanged.
Validators can save on base-layer fees by not submitting claims for empty epochs.
If a claim meets the staging criteria of the consensus model, the claim is staged.
The criteria for a claim to be staged is outside the scope of this interface, but
for example, a claim may be staged if it was...
- submitted by an authority or;
- submitted by the majority of a quorum or;
- submitted and not proven wrong after some period of time or;
- submitted and proven correct through an on-chain tournament.
When a claim is staged, its effects are not instant. Validators must wait for the
claim staging period (see
getClaimStagingPeriodfunction) to elapse before it can be accepted by the consensus. This delay serves as a layer of protection against malicious validators, private-key leakage, smart-contract bugs, and other issues. If a malicious claim is ever staged, the application guardian should have enough time to foreclose the application, preventing the claim from ever being accepted, and allowing users to withdraw their funds from the last-finalized machine Merkle root. If the claim staging period is elapsed, and the application was not foreclosed, the claim can be finally accepted, and any outputs generated during that epoch can now be validated on-chain.
Functions
submitClaim
Submit a claim to the consensus.
MUST fire a ClaimSubmitted event.
MAY fire a ClaimStaged event, if the staging criteria is met.
function submitClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
MachineValidityProof calldata proof
) external;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
proof | MachineValidityProof | The machine validity proof |
acceptClaim
Accept a staged claim whose staging period has elapsed.
MUST fire a ClaimAccepted event.
function acceptClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) external;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
getEpochLength
Get the epoch length, in number of base-layer blocks.
The epoch number of a block is defined as the integer division of the block number by the epoch length.
function getEpochLength() external view returns (uint256);
getClaimStagingPeriod
Get the number of base-layer blocks after which a staged claim can be accepted.
function getClaimStagingPeriod() external view returns (uint256);
getNumberOfAcceptedClaims
Get the number of claims accepted by the consensus regarding a specific app.
function getNumberOfAcceptedClaims(address appContract)
external
view
returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getNumberOfStagedClaims
Get the number of claims staged by the consensus regarding a specific app.
function getNumberOfStagedClaims(address appContract) external view returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getNumberOfSubmittedClaims
Get the number of claims submitted to the consensus regarding a specific app.
function getNumberOfSubmittedClaims(address appContract)
external
view
returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getClaim
Get information about a claim.
function getClaim(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot
) external view returns (Claim memory claim);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
claim | Claim | Information about the claim |
Events
ClaimSubmitted
MUST trigger when a claim is submitted.
event ClaimSubmitted(
address indexed submitter,
address indexed appContract,
uint256 lastProcessedBlockNumber,
bytes32 outputsMerkleRoot,
bytes32 machineMerkleRoot
);
Parameters
| Name | Type | Description |
|---|---|---|
submitter | address | The submitter address |
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
outputsMerkleRoot | bytes32 | The outputs Merkle root |
machineMerkleRoot | bytes32 | The machine Merkle root |
ClaimStaged
MUST trigger when a claim is staged.
For each application and lastProcessedBlockNumber, there can be at most one staged claim.
event ClaimStaged(
address indexed appContract,
uint256 lastProcessedBlockNumber,
bytes32 outputsMerkleRoot,
bytes32 machineMerkleRoot
);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
outputsMerkleRoot | bytes32 | The outputs Merkle root |
machineMerkleRoot | bytes32 | The machine Merkle root |
ClaimAccepted
MUST trigger when a claim is accepted.
For each application and lastProcessedBlockNumber, there can be at most one accepted claim.
event ClaimAccepted(
address indexed appContract,
uint256 lastProcessedBlockNumber,
bytes32 outputsMerkleRoot,
bytes32 machineMerkleRoot
);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
outputsMerkleRoot | bytes32 | The outputs Merkle root |
machineMerkleRoot | bytes32 | The machine Merkle root |
Errors
NotEpochFinalBlock
The claim contains the number of a block that is not at the end of an epoch (its modulo epoch length is not epoch length - 1).
error NotEpochFinalBlock(uint256 lastProcessedBlockNumber, uint256 epochLength);
Parameters
| Name | Type | Description |
|---|---|---|
lastProcessedBlockNumber | uint256 | The number of the last processed block |
epochLength | uint256 | The epoch length |
NotPastBlock
The claim contains the number of a block in the future (it is greater or equal to the current block number).
error NotPastBlock(uint256 lastProcessedBlockNumber, uint256 currentBlockNumber);
Parameters
| Name | Type | Description |
|---|---|---|
lastProcessedBlockNumber | uint256 | The number of the last processed block |
currentBlockNumber | uint256 | The number of the current block |
NotFirstClaim
A claim for that application and epoch was already submitted by the validator.
error NotFirstClaim(address appContract, uint256 lastProcessedBlockNumber);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
ClaimNotStaged
The claim was not staged and therefore cannot be accepted.
error ClaimNotStaged(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
ClaimStatus claimStatus
);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
claimStatus | ClaimStatus | The status of the claim |
ClaimStagingPeriodNotOverYet
The claim was staged but its staging period is not over yet.
error ClaimStagingPeriodNotOverYet(
address appContract,
uint256 lastProcessedBlockNumber,
bytes32 machineMerkleRoot,
uint256 numberOfBlocksAfterStaging,
uint256 claimStagingPeriod
);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
lastProcessedBlockNumber | uint256 | The number of the last processed block |
machineMerkleRoot | bytes32 | The machine Merkle root |
numberOfBlocksAfterStaging | uint256 | The number of blocks since the claim was staged |
claimStagingPeriod | uint256 | The claim staging period, in number of blocks |
Structs
Claim
Information about a claim.
The values of the fields stagingBlockNumber and stagedOutputsMerkleRoot
only have meaning if the claim was staged. Otherwise, they are meaningless.
struct Claim {
ClaimStatus status;
uint256 stagingBlockNumber;
bytes32 stagedOutputsMerkleRoot;
}
Properties
| Name | Type | Description |
|---|---|---|
status | ClaimStatus | The status of the claim |
stagingBlockNumber | uint256 | The number of the block in which the claim was staged |
stagedOutputsMerkleRoot | bytes32 | The outputs Merkle root that was proven on staging |
Enums
ClaimStatus
The status of a claim.
enum ClaimStatus {
UNSTAGED,
STAGED,
ACCEPTED
}
Variants
| Name | Description |
|---|---|
UNSTAGED | The claim was neither staged nor accepted |
STAGED | The claim was staged but not accepted |
ACCEPTED | The claim was staged and accepted |
IConsensusFactoryErrors
Errors
ZeroEpochLength
This error is raised whenever a consensus would be deployed
with zero as epoch length. This is forbidden because this would lead
to a division-by-zero error when calculating the epoch index of any
given block number, which is given by block.number / epochLength.
error ZeroEpochLength();
IOutputsMerkleRootValidator
Inherits: IERC165
Provides valid outputs Merkle roots for validation.
ERC-165 can be used to determine whether this contract also supports any other interface (e.g. for submitting claims).
Functions
isOutputsMerkleRootValid
Check whether an outputs Merkle root is valid.
function isOutputsMerkleRootValid(address appContract, bytes32 outputsMerkleRoot)
external
view
returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
outputsMerkleRoot | bytes32 | The outputs Merkle root |
getLastFinalizedMachineMerkleRoot
Get the last finalized machine Merkle root.
Returns zero if no machine merkle root has been finalized yet for that particular application. This should not be a problem given that the pre-image Keccak-256 hash of zero is unknown.
function getLastFinalizedMachineMerkleRoot(address appContract)
external
view
returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
wasInputFinalized
Check whether an input was finalized.
This function assumes that an input with such an index exists in the input box of the application, and that it was added in such a base-layer block. Foreclosed applications can use this function to issue refunds for deposit inputs that were not finalized.
function wasInputFinalized(
address appContract,
uint256 inputIndex,
uint256 blockNumber
) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
inputIndex | uint256 | The index of the input in the application's input box |
blockNumber | uint256 | The number of the base-layer block in which the input was added |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether the input was finalized |
Contents
- Application
- ApplicationChecker
- ApplicationFactory
- IApplication
- IApplicationChecker
- IApplicationFactory
- IApplicationFactoryErrors
- ISelfHostedApplicationFactory
- SelfHostedApplicationFactory
Application
Inherits: IApplication, Ownable, ERC721Holder, ERC1155Holder, RollupsContract
State Variables
DEPLOYMENT_BLOCK_NUMBER
Deployment block number
uint256 immutable DEPLOYMENT_BLOCK_NUMBER = block.number
TEMPLATE_HASH
The initial machine state hash.
See the getTemplateHash function.
bytes32 immutable TEMPLATE_HASH
INPUT_BOX
The input box contract.
See the getInputBox function.
IInputBox immutable INPUT_BOX
GUARDIAN
The guardian address.
See the getGuardian function.
address immutable GUARDIAN
LOG2_LEAVES_PER_ACCOUNT
The base-2 log of leaves per account.
See the getLog2LeavesPerAccount function.
uint8 immutable LOG2_LEAVES_PER_ACCOUNT
LOG2_MAX_NUM_OF_ACCOUNTS
The base-2 log of max. num. of accounts.
See the getLog2MaxNumOfAccounts function.
uint8 immutable LOG2_MAX_NUM_OF_ACCOUNTS
ACCOUNTS_DRIVE_START_INDEX
The offset of the accounts drive.
See the getAccountsDriveStartIndex function.
uint64 immutable ACCOUNTS_DRIVE_START_INDEX
REFUND_OUTPUT_BUILDER
The refund output builder contract.
See the getRefundOutputBuilder function.
IRefundOutputBuilder immutable REFUND_OUTPUT_BUILDER
WITHDRAWAL_OUTPUT_BUILDER
The withdrawal output builder contract.
See the getWithdrawalOutputBuilder function.
IWithdrawalOutputBuilder immutable WITHDRAWAL_OUTPUT_BUILDER
_executed
Keeps track of which outputs have been executed.
See the wasOutputExecuted function.
BitMaps.BitMap internal _executed
_refunded
Keeps track of which inputs have been refunded.
See the wasRefundForInputIssued function.
BitMaps.BitMap internal _refunded
_withdrawn
Keeps track of which accounts have been withdrawn.
See the wereAccountFundsWithdrawn function.
BitMaps.BitMap internal _withdrawn
_outputsMerkleRootValidator
The current outputs Merkle root validator contract.
See the getOutputsMerkleRootValidator and migrateToOutputsMerkleRootValidator functions.
IOutputsMerkleRootValidator internal _outputsMerkleRootValidator
_isForeclosed
Whether the application has been foreclosed by the guardian.
See the isForeclosed function.
bool internal _isForeclosed
_wasAccountsDriveMerkleRootProved
Whether the accounts drive Merkle root was proved.
See the getAccountsDriveMerkleRoot and
proveAccountsDriveMerkleRoot functions.
bool internal _wasAccountsDriveMerkleRootProved
_accountsDriveMerkleRoot
The accounts drive Merkle root.
See the getAccountsDriveMerkleRoot and
proveAccountsDriveMerkleRoot functions.
bytes32 internal _accountsDriveMerkleRoot
_numOfExecutedOutputs
The number of outputs executed by the application.
See the getNumberOfExecutedOutputs function.
uint256 _numOfExecutedOutputs
_numOfIssuedRefunds
The number of refunds issued by the application.
See the getNumberOfIssuedRefunds function.
uint256 _numOfIssuedRefunds
_numOfWithdrawals
The number of withdrawals from the application.
See the getNumberOfWithdrawals function.
uint256 _numOfWithdrawals
Functions
constructor
Creates an Application contract.
Reverts if the initial application owner address is zero.
constructor(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address initialOwner,
bytes32 templateHash,
IInputBox inputBox,
IRefundOutputBuilder refundOutputBuilder,
WithdrawalConfig memory withdrawalConfig
) Ownable(initialOwner);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRootValidator | IOutputsMerkleRootValidator | The initial outputs Merkle root validator contract |
initialOwner | address | The initial application owner |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
refundOutputBuilder | IRefundOutputBuilder | The refund output builder |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
receive
Accept Ether transfers.
If you wish to transfer Ether to an application while informing the backend of it, then please do so through the Ether portal contract.
receive() external payable;
executeOutput
Execute an output.
On a successful execution, emits a OutputExecuted event.
function executeOutput(bytes calldata output, OutputValidityProof calldata proof)
external
override;
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
issueRefund
function issueRefund(uint256 inputIndex, bytes calldata input)
external
override
onlyForeclosed;
proveAccountsDriveMerkleRoot
function proveAccountsDriveMerkleRoot(
bytes32 accountsDriveMerkleRoot,
bytes32[] calldata proof
) external override onlyForeclosed;
withdraw
function withdraw(bytes calldata account, AccountValidityProof calldata proof)
external
override
onlyForeclosed;
migrateToOutputsMerkleRootValidator
Migrate the application to a new outputs Merkle root validator.
Can only be called by the application owner.
May raise OwnableUnauthorizedAccount or Foreclosed.
function migrateToOutputsMerkleRootValidator(IOutputsMerkleRootValidator newOutputsMerkleRootValidator)
external
override
onlyOwner
notForeclosed
onDeploymentBlock;
Parameters
| Name | Type | Description |
|---|---|---|
newOutputsMerkleRootValidator | IOutputsMerkleRootValidator | The new outputs Merkle root validator |
foreclose
function foreclose() external override onlyGuardian notForeclosed;
wasOutputExecuted
Check whether an output has been executed.
function wasOutputExecuted(uint256 outputIndex)
external
view
override
returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
outputIndex | uint256 | The index of output |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether the output has been executed before or is currently being executed (in the current transaction) |
wasRefundForInputIssued
function wasRefundForInputIssued(uint256 inputIndex)
external
view
override
returns (bool);
wereAccountFundsWithdrawn
function wereAccountFundsWithdrawn(uint256 accountIndex)
external
view
returns (bool);
validateOutput
Validate an output.
May raise any of the errors raised by validateOutputHash.
function validateOutput(bytes calldata output, OutputValidityProof calldata proof)
public
view
override;
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
validateOutputHash
Validate an output hash.
May raise InvalidOutputHashesSiblingsArrayLength
or InvalidOutputsMerkleRoot.
function validateOutputHash(bytes32 outputHash, OutputValidityProof calldata proof)
public
view
override;
Parameters
| Name | Type | Description |
|---|---|---|
outputHash | bytes32 | The output hash |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
validateInput
function validateInput(uint256 inputIndex, bytes calldata input)
public
view
override
returns (uint256 blockNumber, address inputSender, bytes memory inputPayload);
validateInputHash
function validateInputHash(uint256 inputIndex, bytes32 inputHash)
public
view
override;
validateAccount
function validateAccount(bytes calldata account, AccountValidityProof calldata proof)
public
view
override;
validateAccountMerkleRoot
function validateAccountMerkleRoot(
bytes32 accountMerkleRoot,
AccountValidityProof calldata proof
) public view override;
getTemplateHash
Get the application's template hash.
function getTemplateHash() public view override returns (bytes32);
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes32 | The application's template hash |
getOutputsMerkleRootValidator
Get the current outputs Merkle root validator.
function getOutputsMerkleRootValidator()
public
view
override
returns (IOutputsMerkleRootValidator);
Returns
| Name | Type | Description |
|---|---|---|
<none> | IOutputsMerkleRootValidator | The current outputs Merkle root validator |
getInputBox
function getInputBox() public view override returns (IInputBox);
getDeploymentBlockNumber
Get number of block in which contract was deployed
function getDeploymentBlockNumber() external view override returns (uint256);
getNumberOfExecutedOutputs
Get number of outputs executed by the application.
function getNumberOfExecutedOutputs() external view override returns (uint256);
getNumberOfIssuedRefunds
function getNumberOfIssuedRefunds() external view override returns (uint256);
getNumberOfWithdrawals
function getNumberOfWithdrawals() external view override returns (uint256);
getLog2LeavesPerAccount
function getLog2LeavesPerAccount() public view override returns (uint8);
getLog2MaxNumOfAccounts
function getLog2MaxNumOfAccounts() public view override returns (uint8);
getAccountsDriveStartIndex
function getAccountsDriveStartIndex() public view override returns (uint64);
getGuardian
function getGuardian() public view override returns (address);
getRefundOutputBuilder
function getRefundOutputBuilder()
public
view
override
returns (IRefundOutputBuilder);
getWithdrawalOutputBuilder
function getWithdrawalOutputBuilder()
public
view
override
returns (IWithdrawalOutputBuilder);
isForeclosed
function isForeclosed() public view override returns (bool);
getWithdrawalConfig
function getWithdrawalConfig()
external
view
override
returns (WithdrawalConfig memory withdrawalConfig);
getAccountsDriveMerkleRoot
function getAccountsDriveMerkleRoot()
external
view
override
returns (bool wasAccountsDriveMerkleRootProved, bytes32 accountsDriveMerkleRoot);
owner
Returns the address of the current owner.
function owner() public view override(IOwnable, Ownable) returns (address);
renounceOwnership
Leaves the contract without owner. It will not be possible to call
onlyOwner functions. Can only be called by the current owner.
NOTE: Renouncing ownership will leave the contract without an owner,
thereby disabling any functionality that is only available to the owner.
function renounceOwnership() public override(IOwnable, Ownable);
transferOwnership
Transfers ownership of the contract to a new account (newOwner).
Can only be called by the current owner.
function transferOwnership(address newOwner) public override(IOwnable, Ownable);
onlyGuardian
modifier onlyGuardian() ;
notForeclosed
modifier notForeclosed() ;
onlyForeclosed
modifier onlyForeclosed() ;
onDeploymentBlock
modifier onDeploymentBlock() ;
_getLog2AccountsDriveSize
Get the log (base 2) of the number of bytes in the machine memory that are reserved for the accounts drive.
function _getLog2AccountsDriveSize() internal view returns (uint8);
_isOutputsMerkleRootValid
Check if an outputs Merkle root is valid, according to the current outputs Merkle root validator.
function _isOutputsMerkleRootValid(bytes32 outputsMerkleRoot)
internal
view
returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRoot | bytes32 | The output Merkle root |
_getLastFinalizedMachineMerkleRoot
Get the last finalized machine Merkle root, according to the current outputs Merkle root validator.
If the outputs Merkle root validator returns a zeroed bytes32 value, signaling that no machine Merkle root has been finalized yet, we instead use the immutable template hash value set at construction time.
function _getLastFinalizedMachineMerkleRoot()
internal
view
returns (bytes32 lastFinalizedMachineMerkleRoot);
Returns
| Name | Type | Description |
|---|---|---|
lastFinalizedMachineMerkleRoot | bytes32 | The last finalized machine Merkle root |
_wasInputFinalized
Check if an input was finalized, according to the current outputs Merkle root validator.
function _wasInputFinalized(uint256 inputIndex, uint256 blockNumber)
internal
view
returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input in the application's input box |
blockNumber | uint256 | The number of the base-layer block in which the input was added |
_buildRefundOutput
Build a refund output from an input, using the refund output builder contract.
function _buildRefundOutput(address sender, bytes memory payload)
internal
view
returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
sender | address | The input sender |
payload | bytes | The input payload |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The refund output |
_buildWithdrawalOutput
Build a withdrawal output from an account, using the withdrawal output builder contract.
function _buildWithdrawalOutput(bytes calldata account)
internal
view
returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
account | bytes | The account |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The withdrawal output |
_executeOutput
Executes an output
function _executeOutput(bytes memory output) internal;
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
_executeVoucher
Executes a voucher
function _executeVoucher(bytes memory arguments) internal;
Parameters
| Name | Type | Description |
|---|---|---|
arguments | bytes | ABI-encoded arguments |
_executeDelegateCallVoucher
Executes a delegatecall voucher
function _executeDelegateCallVoucher(bytes memory arguments) internal;
Parameters
| Name | Type | Description |
|---|---|---|
arguments | bytes | ABI-encoded arguments |
_ensureMsgSenderIsGuardian
Ensures the message sender is the guardian.
function _ensureMsgSenderIsGuardian() internal view;
_ensureAppIsNotForeclosed
Ensures the application is not foreclosed.
function _ensureAppIsNotForeclosed() internal view;
_ensureAppIsForeclosed
Ensures the application is foreclosed.
function _ensureAppIsForeclosed() internal view;
_ensureOnDeploymentBlock
Ensures the current block is the deployment block.
function _ensureOnDeploymentBlock() internal view;
ApplicationChecker
Inherits: IApplicationChecker
Functions
_ensureIsNotForeclosed
Ensure that a given application is not foreclosed.
function _ensureIsNotForeclosed(address appContract) internal view;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
notForeclosed
A modifier that ensures an application is not foreclosed.
modifier notForeclosed(address appContract) ;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
ApplicationFactory
Inherits: IApplicationFactory, RollupsContract
Title: Application Factory
Allows anyone to reliably deploy a new IApplication contract.
State Variables
REFUND_OUTPUT_BUILDER
IRefundOutputBuilder immutable REFUND_OUTPUT_BUILDER
Functions
constructor
Creates an ApplicationFactory contract.
constructor(IRefundOutputBuilder refundOutputBuilder) ;
Parameters
| Name | Type | Description |
|---|---|---|
refundOutputBuilder | IRefundOutputBuilder | The refund output builder |
newApplication
function newApplication(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig
) external override returns (IApplication appContract);
newApplication
function newApplication(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external override returns (IApplication appContract);
calculateApplicationAddress
function calculateApplicationAddress(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external view override returns (address);
IApplication
Inherits: IOwnable, AddressErrors, BinaryMerkleTreeErrors, IRefundOutputBuilderErrors, IWithdrawalOutputBuilderErrors, IVersionGetter
The base layer incarnation of an application running on the execution layer.
The state of the application advances through inputs sent to an IInputBox contract.
These inputs can be sent either directly, or indirectly through portals.
Reader nodes can retrieve inputs sent to the IInputBox contract through events, and feed them into the machine.
Validator nodes can also submit claims to the IOutputsMerkleRootValidator contract (see the getOutputsMerkleRootValidator function).
Once accepted, claims can be used to validate outputs generated by the machine.
Some outputs are executable, which means they can have on-chain side effects.
Every application is subscribed to some outputs Merkle root validator, and may be governed by some owner. The outputs Merkle root validator has the power to accept claims, which, in turn, are used to validate outputs. Meanwhile, the owner can replace the outputs Merkle root validator at any time. Therefore, the users of an application must trust both the outputs Merkle root validator and the application owner.
There are several ownership models to choose from:
- no owner (address zero)
- individual signer (externally-owned account)
- multiple signers (multi-sig)
- DAO (decentralized autonomous organization)
- self-owned application (off-chain governance logic)
Functions
migrateToOutputsMerkleRootValidator
Migrate the application to a new outputs Merkle root validator.
Can only be called by the application owner.
May raise OwnableUnauthorizedAccount or Foreclosed.
function migrateToOutputsMerkleRootValidator(IOutputsMerkleRootValidator newOutputsMerkleRootValidator)
external;
Parameters
| Name | Type | Description |
|---|---|---|
newOutputsMerkleRootValidator | IOutputsMerkleRootValidator | The new outputs Merkle root validator |
foreclose
Forecloses the application, allowing users to withdraw their funds by providing Merkle proofs of their in-app accounts.
Can only be called by the application guardian.
May raise NotGuardian or Foreclosed.
function foreclose() external;
executeOutput
Execute an output.
On a successful execution, emits a OutputExecuted event.
May raise any of the errors raised by validateOutput,
as well as OutputNotExecutable and OutputNotReexecutable.
function executeOutput(bytes calldata output, OutputValidityProof calldata proof)
external;
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
issueRefund
Issue a refund for an unprocessed input.
May raise CannotRefundFinalizedInput, RefundAlreadyIssued,
UnknownInputSender, as well as any of the errors raised by validateInput.
On success, marks the input as refunded, and emits a RefundIssued event.
function issueRefund(uint256 inputIndex, bytes calldata input) external;
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input in the application's input box. |
input | bytes | The input that was sent to the application |
proveAccountsDriveMerkleRoot
Prove the accounts drive Merkle root in the last-finalized machine state provided by the application's outputs Merkle root validator or in the initial machine Merkle root (template hash) if no machine Merkle root has been finalized yet. This function can be called by anyone after the app is foreclosed so that accounts can be validated and their funds can be withdrawn.
May raise NotForeclosed, AccountsDriveMerkleRootAlreadyProved,
InvalidAccountsDriveMerkleRootProofSize or InvalidMachineMerkleRoot.
On success, stores the proved accounts drive Merkle root and emits an
AccountsDriveMerkleRootProved event.
function proveAccountsDriveMerkleRoot(
bytes32 accountsDriveMerkleRoot,
bytes32[] calldata proof
) external;
Parameters
| Name | Type | Description |
|---|---|---|
accountsDriveMerkleRoot | bytes32 | The accounts drive Merkle root |
proof | bytes32[] | Siblings of the accounts drive Merkle root in the machine |
withdraw
Withdraw the funds of an account from the foreclosed application. First, the account is validated against the proved accounts drive Merkle root. Then, a withdrawal output is built from the account, and executed.
May raise NotForeclosed, AccountFundsAlreadyWithdrawn,
as well as any of the errors raised by validateAccount.
On success, marks the account funds as withdrawn, and emits a Withdrawal event.
function withdraw(bytes calldata account, AccountValidityProof calldata proof)
external;
Parameters
| Name | Type | Description |
|---|---|---|
account | bytes | The account |
proof | AccountValidityProof | The proof used to validate the account |
wasOutputExecuted
Check whether an output has been executed.
function wasOutputExecuted(uint256 outputIndex) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
outputIndex | uint256 | The index of output |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether the output has been executed before or is currently being executed (in the current transaction) |
validateOutput
Validate an output.
May raise any of the errors raised by validateOutputHash.
function validateOutput(bytes calldata output, OutputValidityProof calldata proof)
external
view;
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
validateOutputHash
Validate an output hash.
May raise InvalidOutputHashesSiblingsArrayLength
or InvalidOutputsMerkleRoot.
function validateOutputHash(bytes32 outputHash, OutputValidityProof calldata proof)
external
view;
Parameters
| Name | Type | Description |
|---|---|---|
outputHash | bytes32 | The output hash |
proof | OutputValidityProof | The proof used to validate the output against a claim accepted to the current outputs Merkle root validator contract |
getTemplateHash
Get the application's template hash.
function getTemplateHash() external view returns (bytes32);
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes32 | The application's template hash |
getOutputsMerkleRootValidator
Get the current outputs Merkle root validator.
function getOutputsMerkleRootValidator()
external
view
returns (IOutputsMerkleRootValidator);
Returns
| Name | Type | Description |
|---|---|---|
<none> | IOutputsMerkleRootValidator | The current outputs Merkle root validator |
getInputBox
Get the input box contract used by application.
function getInputBox() external view returns (IInputBox);
getDeploymentBlockNumber
Get number of block in which contract was deployed
function getDeploymentBlockNumber() external view returns (uint256);
getNumberOfExecutedOutputs
Get number of outputs executed by the application.
function getNumberOfExecutedOutputs() external view returns (uint256);
isForeclosed
Check whether the application has been foreclosed. An application that has been foreclosed will remain so.
function isForeclosed() external view returns (bool);
getGuardian
Get the address of the guardian, which has the power to foreclose the application.
function getGuardian() external view returns (address);
getWithdrawalConfig
Get the withdrawal configuration set upon construction.
function getWithdrawalConfig()
external
view
returns (WithdrawalConfig memory withdrawalConfig);
Returns
| Name | Type | Description |
|---|---|---|
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
getNumberOfIssuedRefunds
Get the number of issued refunds.
Useful for fast-syncing RefundIssued events.
function getNumberOfIssuedRefunds() external view returns (uint256);
wasRefundForInputIssued
Check whether a refund had been issued for an input.
function wasRefundForInputIssued(uint256 inputIndex) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input in the application's input box |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether a refund for the input has been issued before or is currently being issued (in the current transaction) |
getAccountsDriveMerkleRoot
Check whether the accounts drive Merkle root was proved and its value.
function getAccountsDriveMerkleRoot()
external
view
returns (bool wasAccountsDriveMerkleRootProved, bytes32 accountsDriveMerkleRoot);
Returns
| Name | Type | Description |
|---|---|---|
wasAccountsDriveMerkleRootProved | bool | Whether the accounts drive Merkle root was proved |
accountsDriveMerkleRoot | bytes32 | The accounts drive Merkle root (if proved) |
getNumberOfWithdrawals
Get the number of withdrawals.
Useful for fast-syncing Withdrawal events.
function getNumberOfWithdrawals() external view returns (uint256);
wereAccountFundsWithdrawn
Check whether an account had its funds withdrawn.
function wereAccountFundsWithdrawn(uint256 accountIndex) external view returns (bool);
Parameters
| Name | Type | Description |
|---|---|---|
accountIndex | uint256 | The index of the account in the accounts drive. |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bool | Whether the account funds have been withdrawn before or are currently being withdrawn (in the current transaction) |
getLog2LeavesPerAccount
Get the log (base 2) of the number of leaves in the machine state tree that are reserved for each account in the accounts drive.
function getLog2LeavesPerAccount() external view returns (uint8);
getLog2MaxNumOfAccounts
Get the log (base 2) of the maximum number of accounts that can be stored in the accounts drive.
This is equivalent to the depth of the accounts drive tree whose leaves are the account roots.
function getLog2MaxNumOfAccounts() external view returns (uint8);
getAccountsDriveStartIndex
Get the factor that, when multiplied by the size of the accounts drive, yields the start memory address of the accounts drive.
If a = getLog2LeavesPerAccount() b = getLog2MaxNumOfAccounts(),
and c = getAccountsDriveStartIndex(), then the accounts drive starts
at memory address c*2^{a+b+5} and has 2^{a+b+5} bytes in size.
function getAccountsDriveStartIndex() external view returns (uint64);
getRefundOutputBuilder
Get the refund output builder, which gets static-called whenever a deposit is to be refunded to the original depositor.
function getRefundOutputBuilder() external view returns (IRefundOutputBuilder);
validateInput
Validates an input that was sent to the application.
May raise IllFormedInput as well as any of the errors raised by validateInputHash.
function validateInput(uint256 inputIndex, bytes calldata input)
external
view
returns (uint256 blockNumber, address inputSender, bytes memory inputPayload);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input in the application's input box. |
input | bytes | The input that was sent to the application |
Returns
| Name | Type | Description |
|---|---|---|
blockNumber | uint256 | The number of the base-layer block in which the input was added |
inputSender | address | The input sender |
inputPayload | bytes | The input payload |
validateInputHash
Validates an input that was sent to the application.
May raise InvalidInputIndex or InvalidInputHash.
function validateInputHash(uint256 inputIndex, bytes32 inputHash) external view;
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input in the application's input box. |
inputHash | bytes32 | The hash of the input that was sent to the application |
getWithdrawalOutputBuilder
Get the withdrawal output builder, which gets static-called whenever the funds of an account are to be withdrawn.
function getWithdrawalOutputBuilder() external view returns (IWithdrawalOutputBuilder);
validateAccount
Validate the existence of an account at a given index
on the accounts drive given a Merkle proof of the account root,
according to the accounts drive Merkle root proved through the
proveAccountsDriveMerkleRoot function.
May raise any of the errors raised by validateAccountMerkleRoot,
as well as DriveSmallerThanData (if the provided account is too large).
function validateAccount(bytes calldata account, AccountValidityProof calldata proof)
external
view;
Parameters
| Name | Type | Description |
|---|---|---|
account | bytes | The account |
proof | AccountValidityProof | The proof used to validate the account |
validateAccountMerkleRoot
Validate the existence of an account at a given index
on the accounts drive given a Merkle proof of the account root,
according to the accounts drive Merkle root proved through the
proveAccountsDriveMerkleRoot function.
May raise InvalidAccountRootSiblingsArrayLength, InvalidNodeIndex
(if the account index is outside the boundaries of the accounts drive),
AccountsDriveMerkleRootNotProved or InvalidAccountsDriveMerkleRoot.
function validateAccountMerkleRoot(
bytes32 accountMerkleRoot,
AccountValidityProof calldata proof
) external view;
Parameters
| Name | Type | Description |
|---|---|---|
accountMerkleRoot | bytes32 | The account Merkle root |
proof | AccountValidityProof | The proof used to validate the account |
Events
OutputsMerkleRootValidatorChanged
MUST trigger when a new outputs Merkle root validator is chosen.
event OutputsMerkleRootValidatorChanged(IOutputsMerkleRootValidator newOutputsMerkleRootValidator);
Parameters
| Name | Type | Description |
|---|---|---|
newOutputsMerkleRootValidator | IOutputsMerkleRootValidator | The new outputs Merkle root validator |
OutputExecuted
MUST trigger when an output is executed.
event OutputExecuted(uint64 indexed outputIndex, bytes output);
Parameters
| Name | Type | Description |
|---|---|---|
outputIndex | uint64 | The index of the output |
output | bytes | The output |
Foreclosure
MUST trigger when the application is foreclosed.
event Foreclosure();
RefundIssued
MUST trigger when a refund for an input is issued.
event RefundIssued(uint256 indexed inputIndex, bytes input, bytes output);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The index of the input |
input | bytes | The input |
output | bytes | The refund output |
AccountsDriveMerkleRootProved
MUST trigger when the accounts drive Merkle root is proved.
event AccountsDriveMerkleRootProved(bytes32 accountsDriveMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
accountsDriveMerkleRoot | bytes32 | The accounts drive Merkle root |
Withdrawal
MUST trigger when the funds of an account are withdrawn.
event Withdrawal(uint64 indexed accountIndex, bytes account, bytes output);
Parameters
| Name | Type | Description |
|---|---|---|
accountIndex | uint64 | The account index in the accounts drive |
account | bytes | The account as encoded in the accounts drive |
output | bytes | The withdrawal output |
Errors
OutputNotExecutable
Could not execute an output, because the application contract doesn't know how to.
error OutputNotExecutable(bytes output);
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
OutputNotReexecutable
Could not execute an output, because it was already executed.
error OutputNotReexecutable(bytes output);
Parameters
| Name | Type | Description |
|---|---|---|
output | bytes | The output |
InvalidOutputHashesSiblingsArrayLength
Raised when the output hashes siblings array has an invalid size.
Please consult CanonicalMachine for the maximum number of outputs.
error InvalidOutputHashesSiblingsArrayLength();
InvalidOutputsMerkleRoot
Raised when the computed outputs Merkle root is invalid, according to the current outputs Merkle root validator.
error InvalidOutputsMerkleRoot(bytes32 outputsMerkleRoot);
NotGuardian
Raised when a function that can only be called by the application guardian is called by some other account.
error NotGuardian();
NotForeclosed
Raised when the application has not yet been foreclosed and therefore withdrawal-related actions cannot be performed yet.
error NotForeclosed();
Foreclosed
Raised when the application has been foreclosed and therefore some actions cannot be performed anymore.
error Foreclosed();
InvalidInputIndex
Raised when trying to validate an input with an invalid index.
This error is raised when invalidInputIndex >= numOfInputs.
error InvalidInputIndex(uint256 invalidInputIndex, uint256 numOfInputs);
Parameters
| Name | Type | Description |
|---|---|---|
invalidInputIndex | uint256 | The invalid input index provided for validation |
numOfInputs | uint256 | The actual number of inputs to the application |
InvalidInputHash
Raised when trying to validate an input with an invalid hash.
This error is raised when storedInputHash != invalidInputHash.
error InvalidInputHash(bytes32 storedInputHash, bytes32 invalidInputHash);
Parameters
| Name | Type | Description |
|---|---|---|
storedInputHash | bytes32 | The hash of the input stored in the input box |
invalidInputHash | bytes32 | The invalid input hash provided for validation |
IllFormedInput
Raised when decoding an ill-formed input.
This error should never be raised if the application uses the canonical input box contract.
error IllFormedInput();
CannotRefundFinalizedInput
Raised when trying to issue a refund for a finalized input.
error CannotRefundFinalizedInput(uint256 inputIndex);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The input index |
RefundAlreadyIssued
Raised when trying to re-issue a refund for the same input.
error RefundAlreadyIssued(uint256 inputIndex);
Parameters
| Name | Type | Description |
|---|---|---|
inputIndex | uint256 | The input index |
InvalidAccountsDriveMerkleRootProofSize
Raised when the accounts drive Merkle root proof size is invalid.
The array length should be log2 of the machine memory size - log2 of the
accounts drive size. See the CanonicalMachine library and the
getLog2MaxNumOfAccounts and getLog2LeavesPerAccount functions.
error InvalidAccountsDriveMerkleRootProofSize();
AccountsDriveMerkleRootAlreadyProved
Raised when someone tries to prove the accounts drive Merkle root but it
has already been proved. This error adds an extra layer of protection against
consensus-takeover attacks in which getLastFinalizedMachineMerkleRoot returns
a different value after the application is foreclosed.
error AccountsDriveMerkleRootAlreadyProved();
AccountsDriveMerkleRootNotProved
Raised when someone tries to validate an accounts Merkle root but the
accounts drive Merkle root has not yet been proved through the
proveAccountsDriveMerkleRoot function.
error AccountsDriveMerkleRootNotProved();
InvalidAccountRootSiblingsArrayLength
Raised when the account root siblings array has an invalid length.
The array length should be log2 of the maximum number of accounts. See the
getLog2MaxNumOfAccounts function.
error InvalidAccountRootSiblingsArrayLength();
InvalidMachineMerkleRoot
Raised when the computed machine Merkle root differs from the last-finalized machine Merkle root provided by the outputs Merkle root validator or from the initial machine Merkle root (template hash) if no machine Merkle root has been finalized yet.
error InvalidMachineMerkleRoot(bytes32 machineMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
machineMerkleRoot | bytes32 | The computed machine Merkle root |
InvalidAccountsDriveMerkleRoot
Raised when the computed accounts drive Merkle root differs
from the one proved through the proveAccountsDriveMerkleRoot function.
error InvalidAccountsDriveMerkleRoot(bytes32 accountsDriveMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
accountsDriveMerkleRoot | bytes32 | The computed accounts drive Merkle root |
AccountFundsAlreadyWithdrawn
Raised when trying to withdraw funds of an account whose funds have already been withdrawn.
error AccountFundsAlreadyWithdrawn(uint64 accountIndex);
Parameters
| Name | Type | Description |
|---|---|---|
accountIndex | uint64 | The account index |
NotDeploymentBlock
Raised when the application owner tries to migrate the application to another outputs Merkle root validator in a block that is not the deployment block.
This restriction protects users from malicious application owners that, by swapping the outputs Merkle root validator, can take control of user funds locked in the application contract. Rather, the application owner serves merely as an implementation detail that enables application-consensus factory contracts to deploy application-consensus pairs in the same transaction.
error NotDeploymentBlock();
IApplicationChecker
Errors
ApplicationNotDeployed
The application contract address contains no code.
error ApplicationNotDeployed(address appContract);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
ApplicationReverted
The call to the application contract reverted with an error.
error ApplicationReverted(address appContract, bytes error);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
error | bytes | The error raised by the application contract |
IllformedApplicationReturnData
The call to the application contract returned ill-formed data.
error IllformedApplicationReturnData(address appContract, bytes data);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
data | bytes | The data returned by the application contract |
InputBoxNotDeployed
The input box address contains no code.
error InputBoxNotDeployed(address inputBox);
Parameters
| Name | Type | Description |
|---|---|---|
inputBox | address | The input box contract address |
ApplicationForeclosed
Application was foreclosed.
error ApplicationForeclosed(address appContract);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
IApplicationFactory
Inherits: IVersionGetter, IApplicationFactoryErrors
Title: Application Factory interface
Functions
newApplication
Deploy a new application.
On success, MUST emit an ApplicationCreated event.
Reverts if the application owner address is zero.
function newApplication(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig
) external returns (IApplication);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRootValidator | IOutputsMerkleRootValidator | The initial outputs Merkle root validator contract |
appOwner | address | The initial application owner |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IApplication | The application |
newApplication
Deploy a new application deterministically.
On success, MUST emit an ApplicationCreated event.
Reverts if the application owner address is zero.
function newApplication(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external returns (IApplication);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRootValidator | IOutputsMerkleRootValidator | The initial outputs Merkle root validator contract |
appOwner | address | The initial application owner |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
salt | bytes32 | The salt used to deterministically generate the application contract address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IApplication | The application |
calculateApplicationAddress
Calculate the address of an application contract to be deployed deterministically.
Beware that only the newApplication function with the salt parameter
is able to deterministically deploy an application.
function calculateApplicationAddress(
IOutputsMerkleRootValidator outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external view returns (address);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRootValidator | IOutputsMerkleRootValidator | The initial outputs Merkle root validator contract |
appOwner | address | The initial application owner |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
salt | bytes32 | The salt used to deterministically generate the application contract address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | address | The deterministic application contract address |
Events
ApplicationCreated
A new application was deployed.
MUST be triggered on a successful call to newApplication.
event ApplicationCreated(
IOutputsMerkleRootValidator indexed outputsMerkleRootValidator,
address appOwner,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig withdrawalConfig,
IApplication appContract
);
Parameters
| Name | Type | Description |
|---|---|---|
outputsMerkleRootValidator | IOutputsMerkleRootValidator | The initial outputs Merkle root validator contract |
appOwner | address | The initial application owner |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | |
appContract | IApplication | The application contract |
IApplicationFactoryErrors
Errors
InvalidWithdrawalConfig
This error is raised when someone tries to deploy an application with invalid withdrawal configuration, in which the accounts drive is outside the bounds of the machine memory. This is forbidden at the contract level so that users and the node don't need to make this sanity check.
error InvalidWithdrawalConfig(WithdrawalConfig withdrawalConfig);
Parameters
| Name | Type | Description |
|---|---|---|
withdrawalConfig | WithdrawalConfig | The invalid withdrawal configuration |
ISelfHostedApplicationFactory
Inherits: IVersionGetter, IConsensusFactoryErrors, IApplicationFactoryErrors
Title: Self-hosted Application Factory interface
Functions
getAuthorityFactory
Get the factory used to deploy IAuthority contracts
function getAuthorityFactory() external view returns (IAuthorityFactory);
Returns
| Name | Type | Description |
|---|---|---|
<none> | IAuthorityFactory | The authority factory |
getApplicationFactory
Get the factory used to deploy IApplication contracts
function getApplicationFactory() external view returns (IApplicationFactory);
Returns
| Name | Type | Description |
|---|---|---|
<none> | IApplicationFactory | The application factory |
deployContracts
Deploy new application and authority contracts deterministically.
Reverts if the authority owner address is zero.
Reverts if the epoch length is zero.
function deployContracts(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external returns (IApplication, IAuthority);
Parameters
| Name | Type | Description |
|---|---|---|
authorityOwner | address | The initial authority owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
salt | bytes32 | The salt used to deterministically generate the addresses |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IApplication | The application contract |
<none> | IAuthority | The authority contract |
calculateAddresses
Calculate the addresses of the application and authority contracts to be deployed deterministically.
function calculateAddresses(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external view returns (address, address);
Parameters
| Name | Type | Description |
|---|---|---|
authorityOwner | address | The initial authority owner |
epochLength | uint256 | The epoch length |
claimStagingPeriod | uint256 | The claim staging period |
templateHash | bytes32 | The initial machine state hash |
inputBox | IInputBox | The input box contract |
withdrawalConfig | WithdrawalConfig | The withdrawal configuration |
salt | bytes32 | The salt used to deterministically generate the addresses |
Returns
| Name | Type | Description |
|---|---|---|
<none> | address | The application address |
<none> | address | The authority address |
SelfHostedApplicationFactory
Inherits: ISelfHostedApplicationFactory, RollupsContract
Title: Self-hosted Application Factory
Allows anyone to reliably deploy a new IAuthority contract, along with an IApplication contract already linked to it.
State Variables
AUTHORITY_FACTORY
IAuthorityFactory immutable AUTHORITY_FACTORY
APPLICATION_FACTORY
IApplicationFactory immutable APPLICATION_FACTORY
Functions
constructor
constructor(
IAuthorityFactory authorityFactory,
IApplicationFactory applicationFactory
) ;
Parameters
| Name | Type | Description |
|---|---|---|
authorityFactory | IAuthorityFactory | The authority factory |
applicationFactory | IApplicationFactory | The application factory |
getAuthorityFactory
function getAuthorityFactory() external view override returns (IAuthorityFactory);
getApplicationFactory
function getApplicationFactory()
external
view
override
returns (IApplicationFactory);
deployContracts
function deployContracts(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external returns (IApplication application, IAuthority authority);
calculateAddresses
function calculateAddresses(
address authorityOwner,
uint256 epochLength,
uint256 claimStagingPeriod,
bytes32 templateHash,
IInputBox inputBox,
WithdrawalConfig calldata withdrawalConfig,
bytes32 salt
) external view returns (address application, address authority);
Contents
ISafeErc20Transfer
Inherits: IVersionGetter
Functions
safeTransfer
Safely transfer ERC-20 tokens.
function safeTransfer(IERC20 token, address to, uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC20 | The ERC-20 token contract |
to | address | The token recipient address |
value | uint256 | The amount of tokens |
SafeErc20Transfer
Inherits: ISafeErc20Transfer, RollupsContract
Functions
safeTransfer
function safeTransfer(IERC20 token, address to, uint256 value) external override;
Contents
BaseTestFungibleToken
Inherits: ERC20
Functions
mint
Mint fungible tokens for oneself.
function mint(uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
value | uint256 | The amount of fungible tokens to mint |
mint
Mint fungible tokens.
Compatible with cast erc20 mint <TOKEN> <TO> <VALUE>.
function mint(address to, uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
to | address | The account that will receive the tokens |
value | uint256 | The amount of fungible tokens to mint |
burn
Burn fungible tokens from one's balance.
Compatible with cast erc20 burn <TOKEN> <VALUE>.
function burn(uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
value | uint256 | The amount of fungible tokens to burn |
TestFungibleToken
Inherits: BaseTestFungibleToken
Functions
constructor
constructor() ERC20("Fungible", "FUN");
TestMultiToken
Inherits: ERC1155
Functions
constructor
constructor() ERC1155("https://test-multi-token.com/{id}.json");
mint
Mint multi-tokens for oneself.
function mint(uint256 tokenId, uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
tokenId | uint256 | The multi-token ID |
value | uint256 | The amount of fungible tokens to mint |
mintBatch
Mint a batch of multi-tokens for oneself.
function mintBatch(uint256[] calldata tokenIds, uint256[] calldata values) external;
Parameters
| Name | Type | Description |
|---|---|---|
tokenIds | uint256[] | The multi-token IDs |
values | uint256[] | The amounts of fungible tokens to mint |
mint
Mint multi-tokens.
function mint(address to, uint256 tokenId, uint256 value) external;
Parameters
| Name | Type | Description |
|---|---|---|
to | address | The account that will receive the tokens |
tokenId | uint256 | The multi-token ID |
value | uint256 | The amount of fungible tokens to mint |
mintBatch
Mint a batch of multi-tokens.
function mintBatch(address to, uint256[] calldata tokenIds, uint256[] calldata values)
external;
Parameters
| Name | Type | Description |
|---|---|---|
to | address | The account that will receive the tokens |
tokenIds | uint256[] | The multi-token IDs |
values | uint256[] | The amounts of fungible tokens to mint |
TestNonFungibleToken
Inherits: ERC721
Functions
constructor
constructor() ERC721("Non-fungible", "NFT");
mint
Mint a non-fungible token for oneself.
function mint(uint256 tokenId) external;
Parameters
| Name | Type | Description |
|---|---|---|
tokenId | uint256 | The non-fungible token ID |
mint
Mint a non-fungible token.
function mint(address to, uint256 tokenId) external;
Parameters
| Name | Type | Description |
|---|---|---|
to | address | The account that will receive the token |
tokenId | uint256 | The non-fungible token ID |
TestUsdc
Inherits: ERC20, BaseTestFungibleToken
Functions
constructor
constructor() ERC20("USD Coin", "USDC");
decimals
Overrides the default value of 18 from OpenZeppelin to better simulate the original USDC token on front-ends.
function decimals() public pure override returns (uint8);
Contents
IInputBox
Inherits: IVersionGetter, IApplicationChecker
Provides data availability of inputs for applications.
Each application has its own append-only list of inputs.
Off-chain, inputs can be retrieved via events.
On-chain, only the input hashes are stored.
See LibInput for more details on how such hashes are computed.
Functions
addInput
Send an input to an application.
MUST fire an InputAdded event.
function addInput(address appContract, bytes calldata payload)
external
returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
payload | bytes | The input payload |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes32 | The hash of the input blob |
getNumberOfInputs
Get the number of inputs sent to an application.
function getNumberOfInputs(address appContract) external view returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getInputHash
Get the hash of an input in an application's input box.
The provided index must be valid.
function getInputHash(address appContract, uint256 index)
external
view
returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
index | uint256 | The input index |
getDeploymentBlockNumber
Get number of block in which contract was deployed
function getDeploymentBlockNumber() external view returns (uint256);
Events
InputAdded
MUST trigger when an input is added.
event InputAdded(address indexed appContract, uint256 indexed index, bytes input);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
index | uint256 | The input index |
input | bytes | The input blob |
Errors
InputTooLarge
Input is too large.
error InputTooLarge(address appContract, uint256 inputLength, uint256 maxInputLength);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
inputLength | uint256 | The input length |
maxInputLength | uint256 | The maximum input length |
InputBox
Inherits: IInputBox, RollupsContract, ApplicationChecker
State Variables
DEPLOYMENT_BLOCK_NUMBER
Deployment block number
uint256 immutable DEPLOYMENT_BLOCK_NUMBER = block.number
_inputBoxes
Mapping of application contract addresses to arrays of input hashes.
mapping(address => bytes32[]) private _inputBoxes
Functions
addInput
Send an input to an application.
MUST fire an InputAdded event.
function addInput(address appContract, bytes calldata payload)
external
override
notForeclosed(appContract)
returns (bytes32 inputHash);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
payload | bytes | The input payload |
Returns
| Name | Type | Description |
|---|---|---|
inputHash | bytes32 | The hash of the input blob |
getNumberOfInputs
Get the number of inputs sent to an application.
function getNumberOfInputs(address appContract)
external
view
override
returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
getInputHash
Get the hash of an input in an application's input box.
The provided index must be valid.
function getInputHash(address appContract, uint256 index)
external
view
override
returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
index | uint256 | The input index |
getDeploymentBlockNumber
Get number of block in which contract was deployed
function getDeploymentBlockNumber() external view override returns (uint256);
Contents
- LibAccountValidityProof
- LibAddress
- LibBinaryMerkleTree
- LibBytes
- LibDelegateCallVoucher
- LibErc1155BatchDeposit
- LibErc1155SingleDeposit
- LibErc20Deposit
- IErc721SafeTransferFromWithoutData
- LibErc721Deposit
- LibError
- LibEtherDeposit
- LibKeccak256
- LibLeafProof
- LibMachineValidityProof
- LibMath
- LibOutputValidityProof
- LibUsdAccount
- LibVoucher
- LibWithdrawalConfig
LibAccountValidityProof
Functions
isSiblingsArrayLengthValid
function isSiblingsArrayLengthValid(
AccountValidityProof calldata v,
uint8 log2MaxNumOfAccounts
) internal pure returns (bool);
computeAccountsDriveMerkleRoot
function computeAccountsDriveMerkleRoot(
AccountValidityProof calldata v,
bytes32 accountMerkleRoot
) internal pure returns (bytes32);
LibAddress
Functions
safeCall
Perform a low level call and raise error if failed
Can be used to transfer Ether to EOAs by passing a non-zero value and an empty payload. Solidity contracts will accept such message calls through the receive() payable entrypoint.
function safeCall(address destination, uint256 value, bytes memory payload) internal;
Parameters
| Name | Type | Description |
|---|---|---|
destination | address | The address that will be called |
value | uint256 | The amount of Wei to be transferred through the call |
payload | bytes | The payload, which—in the case of Solidity contracts—encodes a function call |
safeDelegateCall
Perform a delegate call and raise error if failed
function safeDelegateCall(address destination, bytes memory payload) internal;
Parameters
| Name | Type | Description |
|---|---|---|
destination | address | The address that will be called |
payload | bytes | The payload, which—in the case of Solidity libraries—encodes a function call |
LibBinaryMerkleTree
State Variables
LOG2_MAX_DATA_BLOCK_SIZE
Log2 of the maximum data block size.
The data block must still be smaller than the drive. We limit the size of data blocks because of the block gas limit.
uint256 constant LOG2_MAX_DATA_BLOCK_SIZE = 12
Functions
merkleRootAfterReplacement
Compute the root of a Merkle tree after replacing one of its nodes.
Level of node is deduced by the length of the siblings array.
Raises an InvalidNodeIndex error if an invalid node index is provided.
function merkleRootAfterReplacement(
bytes32[] calldata sibs,
uint256 nodeIndex,
bytes32 node,
function(bytes32, bytes32) pure returns (bytes32) nodeFromChildren
) internal pure returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
sibs | bytes32[] | The siblings of the node in bottom-up order |
nodeIndex | uint256 | The index of the node |
node | bytes32 | The new node |
nodeFromChildren | function (bytes32, bytes32) pure returns (bytes32) | The function that computes nodes from their children |
Returns
| Name | Type | Description |
|---|---|---|
<none> | bytes32 | The root hash of the new Merkle tree |
merkleRoot
Get the Merkle root of a byte array.
Data blocks are right-padded with zeros if necessary.
leafFromDataAt receives the data, the block index, and the block size
function merkleRoot(
bytes memory data,
uint256 log2DriveSize,
uint256 log2DataBlockSize,
function(bytes memory, uint256, uint256) pure returns (bytes32) leafFromDataAt,
function(bytes32, bytes32) pure returns (bytes32) nodeFromChildren
) internal pure returns (bytes32);
Parameters
| Name | Type | Description |
|---|---|---|
data | bytes | The byte array |
log2DriveSize | uint256 | The log2 of the drive size |
log2DataBlockSize | uint256 | The log2 of the data block size |
leafFromDataAt | function (bytes memory, uint256, uint256) pure returns (bytes32) | The function that computes leaves from data blocks |
nodeFromChildren | function (bytes32, bytes32) pure returns (bytes32) | The function that computes nodes from their children |
LibBytes
Functions
consumeBytes4
function consumeBytes4(bytes memory buffer)
internal
pure
returns (bool isBufferValid, bytes4 selector, bytes memory arguments);
LibDelegateCallVoucher
Functions
encode
Encode a delegate-call voucher as an output.
function encode(DelegateCallVoucher memory v)
internal
pure
returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
v | DelegateCallVoucher | The delegate-call voucher |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The encoded delegate-call voucher |
LibErc1155BatchDeposit
Functions
buildRefund
function buildRefund(Erc1155BatchDeposit memory deposit, address appContract)
internal
pure
returns (Voucher memory voucher);
LibErc1155SingleDeposit
Functions
buildRefund
function buildRefund(Erc1155SingleDeposit memory deposit, address appContract)
internal
pure
returns (Voucher memory voucher);
LibErc20Deposit
Functions
buildRefund
function buildRefund(Erc20Deposit memory deposit, ISafeErc20Transfer safeTransfer)
internal
pure
returns (DelegateCallVoucher memory delegateCallVoucher);
IErc721SafeTransferFromWithoutData
Title: Auxiliary interface for encoding calls to ERC-721 safeTransferFrom with abi.encodeCall (which leverages Solidity type checker) instead of abi.encodeWithSignature (which does not type-check call arguments).
See https://github.com/argotorg/solidity/issues/3556
Functions
safeTransferFrom
function safeTransferFrom(address, address, uint256) external;
LibErc721Deposit
Functions
buildRefund
function buildRefund(Erc721Deposit memory deposit, address appContract)
internal
pure
returns (Voucher memory voucher);
LibError
Functions
raise
Raise error data
function raise(bytes memory errordata) internal pure;
Parameters
| Name | Type | Description |
|---|---|---|
errordata | bytes | Data returned by failed low-level call |
LibEtherDeposit
Functions
buildRefund
function buildRefund(EtherDeposit memory deposit)
internal
pure
returns (Voucher memory voucher);
LibKeccak256
Functions
hashBytes
Hash a variable-length byte array.
function hashBytes(bytes memory b) internal pure returns (bytes32 result);
Parameters
| Name | Type | Description |
|---|---|---|
b | bytes | The byte array |
hashBlock
Hash a data block at a given index and of a given size.
If the data block is too large, an out-of-memory error might be raised.
If the data block index is too big, an arithmetic error might be raised.
function hashBlock(bytes memory data, uint256 dataBlockIndex, uint256 dataBlockSize)
internal
pure
returns (bytes32 result);
Parameters
| Name | Type | Description |
|---|---|---|
data | bytes | The data |
dataBlockIndex | uint256 | The data block index |
dataBlockSize | uint256 | The data block size |
hashPair
Hash a pair of 32-byte values.
Equivalent to keccak256(abi.encode(a, b)).
Uses assembly to avoid memory allocation or expansion.
function hashPair(bytes32 a, bytes32 b) internal pure returns (bytes32 result);
LibLeafProof
Functions
proveIflagsY
Prove the value of the iflags_Y register of a machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveIflagsY(LeafProof calldata v, bytes32 machineMerkleRoot)
internal
pure
returns (uint64 iflagsY);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof for the iflags_Y register |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
iflagsY | uint64 | The iflags_Y register |
proveHtifTohost
Prove the value of the HTIF tohost register of a machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveHtifTohost(LeafProof calldata v, bytes32 machineMerkleRoot)
internal
pure
returns (uint64 htifTohost);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof for the HTIF tohost register |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
htifTohost | uint64 | The HTIF tohost register |
proveTxBuffer
Prove the first data block of the CMIO tx buffer of a machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveTxBuffer(LeafProof calldata v, bytes32 machineMerkleRoot)
internal
pure
returns (bytes32 txBuffer);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof for the first data block of the CMIO tx buffer |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
txBuffer | bytes32 | The first data block of the CMIO tx buffer |
proveWord
Prove a word at a given address in the machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveWord(
LeafProof calldata v,
bytes32 machineMerkleRoot,
uint64 wordAddress
) internal pure returns (uint64 word);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof |
machineMerkleRoot | bytes32 | The machine Merkle root |
wordAddress | uint64 | The word address |
Returns
| Name | Type | Description |
|---|---|---|
word | uint64 | The proven word |
proveDataBlock
Prove the value of a data block at a given address in the machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveDataBlock(
LeafProof calldata v,
bytes32 machineMerkleRoot,
uint64 dataBlockAddress
) internal pure returns (bytes32 dataBlock);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof |
machineMerkleRoot | bytes32 | The machine Merkle root |
dataBlockAddress | uint64 | The data block address |
Returns
| Name | Type | Description |
|---|---|---|
dataBlock | bytes32 | The proven data block |
proveDataBlock
Prove the value of a data block at a given leaf index in the machine.
May raise InvalidSiblingsArrayLength or InvalidMachineMerkleProof.
function proveDataBlock(
LeafProof calldata v,
bytes32 machineMerkleRoot,
LeafIndex leafIndex
) internal pure returns (bytes32 dataBlock);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof |
machineMerkleRoot | bytes32 | The machine Merkle root |
leafIndex | LeafIndex | The leaf index |
Returns
| Name | Type | Description |
|---|---|---|
dataBlock | bytes32 | The proven data block |
computeMachineMerkleRoot
Compute the machine Merkle root from a leaf proof.
May raise InvalidSiblingsArrayLength.
function computeMachineMerkleRoot(LeafProof calldata v, LeafIndex leafIndex)
internal
pure
returns (bytes32 machineMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
v | LeafProof | The leaf proof |
leafIndex | LeafIndex | The leaf index |
Returns
| Name | Type | Description |
|---|---|---|
machineMerkleRoot | bytes32 | The computed machine Merkle root |
truncateToLeaf
Truncate a word address into leaf index and word offset.
function truncateToLeaf(uint64 wordAddress)
internal
pure
returns (LeafIndex leafIndex, WordOffset wordOffset);
Parameters
| Name | Type | Description |
|---|---|---|
wordAddress | uint64 | The word address |
Returns
| Name | Type | Description |
|---|---|---|
leafIndex | LeafIndex | The leaf index |
wordOffset | WordOffset | The word offset within the data block |
getUint64WordFromDataBlock
Get uint64 word at offset from data block.
Converts word from little-endian to big-endian order.
function getUint64WordFromDataBlock(bytes32 dataBlock, WordOffset wordOffset)
internal
pure
returns (uint64 word);
Parameters
| Name | Type | Description |
|---|---|---|
dataBlock | bytes32 | The data block |
wordOffset | WordOffset | The word offset within the data block |
Returns
| Name | Type | Description |
|---|---|---|
word | uint64 | The uint64 word |
LibMachineValidityProof
Functions
validate
Validate a machine and prove its outputs Merkle root.
May raise InvalidSiblingsArrayLength, InvalidMachineMerkleProof,
InvalidPostEpochMachineIflagsYRegister, or
InvalidPostEpochMachineHtifTohostRegister.
function validate(MachineValidityProof calldata v, bytes32 machineMerkleRoot)
internal
pure
returns (bytes32 outputsMerkleRoot);
Parameters
| Name | Type | Description |
|---|---|---|
v | MachineValidityProof | The machine validity proof |
machineMerkleRoot | bytes32 | The machine Merkle root |
Returns
| Name | Type | Description |
|---|---|---|
outputsMerkleRoot | bytes32 | The proven outputs Merkle root |
LibMath
Author: Felipe Argento
Functions
ctz
Count trailing zeros.
This is a binary search implementation.
function ctz(uint256 x) internal pure returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
x | uint256 | The number you want the ctz of |
clz
Count leading zeros.
This a binary search implementation.
function clz(uint256 x) internal pure returns (uint256 n);
Parameters
| Name | Type | Description |
|---|---|---|
x | uint256 | The number you want the clz of |
Returns
| Name | Type | Description |
|---|---|---|
n | uint256 | The number of leading zeros in x |
ceilLog2
The smallest y for which x <= 2^y.
This is a binary search implementation.
function ceilLog2(uint256 x) internal pure returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
x | uint256 | The number you want the ceilLog2 of |
floorLog2
The biggest y for which x >= 2^y.
This is a binary search implementation.
This function reverts if x = 0 is provided.
function floorLog2(uint256 x) internal pure returns (uint256);
Parameters
| Name | Type | Description |
|---|---|---|
x | uint256 | The number you want the floorLog2 of |
max
The largest of two numbers.
function max(uint256 x, uint256 y) internal pure returns (uint256);
min
The smallest of two numbers.
function min(uint256 x, uint256 y) internal pure returns (uint256);
Errors
FloorLog2OfZeroIsUndefined
Tried to compute floorLog2(0), which is undefined.
error FloorLog2OfZeroIsUndefined();
LibOutputValidityProof
Functions
isSiblingsArrayLengthValid
function isSiblingsArrayLengthValid(OutputValidityProof calldata v)
internal
pure
returns (bool);
computeOutputsMerkleRoot
function computeOutputsMerkleRoot(OutputValidityProof calldata v, bytes32 outputHash)
internal
pure
returns (bytes32);
LibUsdAccount
State Variables
ACCOUNT_SIZE
uint64 constant ACCOUNT_SIZE = 32
Functions
decode
Decode an account.
Reverts if account is not 32 bytes long.
function decode(bytes calldata account)
internal
pure
returns (address user, uint96 balance);
Parameters
| Name | Type | Description |
|---|---|---|
account | bytes | The account |
Returns
| Name | Type | Description |
|---|---|---|
user | address | The user address |
balance | uint96 | The user balance |
encode
Encode an account.
function encode(address user, uint96 balance)
internal
pure
returns (bytes memory account);
Parameters
| Name | Type | Description |
|---|---|---|
user | address | The user address |
balance | uint96 | The user balance |
Returns
| Name | Type | Description |
|---|---|---|
account | bytes | The account |
_checkAccountSize
function _checkAccountSize(uint256 accountSize) internal pure;
LibVoucher
Functions
encode
Encode a voucher as an output.
function encode(Voucher memory v) internal pure returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
v | Voucher | The voucher |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The encoded voucher |
LibWithdrawalConfig
Functions
isValid
function isValid(WithdrawalConfig memory withdrawalConfig)
internal
pure
returns (bool);
Contents
- Erc1155BatchPortal
- Erc1155SinglePortal
- Erc20Portal
- Erc721Portal
- EtherPortal
- IErc1155BatchPortal
- IErc1155SinglePortal
- IErc20Portal
- IErc721Portal
- IEtherPortal
- IPortal
- Portal
Erc1155BatchPortal
Inherits: IErc1155BatchPortal, Portal
Title: ERC-1155 Batch Transfer Portal
This contract allows anyone to perform batch transfers of ERC-1155 tokens to an application contract while informing the off-chain machine.
Functions
depositBatchErc1155Token
function depositBatchErc1155Token(
IERC1155 token,
address appContract,
uint256[] calldata tokenIds,
uint256[] calldata values,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external override;
Erc1155SinglePortal
Inherits: IErc1155SinglePortal, Portal
Title: ERC-1155 Single Transfer Portal
This contract allows anyone to perform single transfers of ERC-1155 tokens to an application contract while informing the off-chain machine.
Functions
depositSingleErc1155Token
function depositSingleErc1155Token(
IERC1155 token,
address appContract,
uint256 tokenId,
uint256 value,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external override;
Erc20Portal
Inherits: IErc20Portal, Portal
Title: ERC-20 Portal
This contract allows anyone to perform transfers of ERC-20 tokens to an application contract while informing the off-chain machine.
Functions
depositErc20Tokens
function depositErc20Tokens(
IERC20 token,
address appContract,
uint256 value,
bytes calldata execLayerData
) external override;
Erc721Portal
Inherits: IErc721Portal, Portal
Title: ERC-721 Portal
This contract allows anyone to perform transfers of ERC-721 tokens to an application contract while informing the off-chain machine.
Functions
depositErc721Token
function depositErc721Token(
IERC721 token,
address appContract,
uint256 tokenId,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external override;
EtherPortal
Inherits: IEtherPortal, Portal
Title: Ether Portal
This contract allows anyone to perform transfers of Ether to an application contract while informing the off-chain machine.
Functions
depositEther
function depositEther(address appContract, bytes calldata execLayerData)
external
payable
override;
IErc1155BatchPortal
Inherits: IPortal
Title: ERC-1155 Batch Transfer Portal interface
Functions
depositBatchErc1155Token
Transfer a batch of ERC-1155 tokens of multiple types to an application contract
and add an input to the application's input box to signal such operation.
The caller must enable approval for the portal to manage all of their tokens
beforehand, by calling the setApprovalForAll function in the token contract.
Please make sure the arrays tokenIds and values have the same length.
If the application is foreclosed, and the deposit input is not processed,
the user can issue a refund. If the user deposits ERC-1155 tokens through a smart contract,
a refund will only succeed if the smart contract accepts it through the onERC1155Received/onERC1155BatchReceived callback.
If the smart contract wallet does not accept the tokens through the callback, they may not be recoverable.
function depositBatchErc1155Token(
IERC1155 token,
address appContract,
uint256[] calldata tokenIds,
uint256[] calldata values,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external;
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The ERC-1155 token contract |
appContract | address | The application contract address |
tokenIds | uint256[] | The identifiers of the tokens being transferred |
values | uint256[] | Transfer amounts per token type |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
IErc1155SinglePortal
Inherits: IPortal
Title: ERC-1155 Single Transfer Portal interface
Functions
depositSingleErc1155Token
Transfer ERC-1155 tokens of a single type to an application contract
and add an input to the application's input box to signal such operation.
The caller must enable approval for the portal to manage all of their tokens
beforehand, by calling the setApprovalForAll function in the token contract.
If the application is foreclosed, and the deposit input is not processed,
the user can issue a refund. If the user deposits ERC-1155 tokens through a smart contract,
a refund will only succeed if the smart contract accepts it through the onERC1155Received/onERC1155BatchReceived callback.
If the smart contract wallet does not accept the tokens through the callback, they may not be recoverable.
function depositSingleErc1155Token(
IERC1155 token,
address appContract,
uint256 tokenId,
uint256 value,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external;
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC1155 | The ERC-1155 token contract |
appContract | address | The application contract address |
tokenId | uint256 | The identifier of the token being transferred |
value | uint256 | Transfer amount |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
IErc20Portal
Inherits: IPortal
Title: ERC-20 Portal interface
Functions
depositErc20Tokens
Transfer ERC-20 tokens to an application contract
and add an input to the application's input box to signal such operation.
The caller must allow the portal to withdraw at least value tokens
from their account beforehand, by calling the approve function in the
token contract.
Only ERC-20 compliant tokens are supported. The portal rejects deposits
of fee-on-transfer ERC-20 tokens: It computes the difference between
balances before and after the transfer. If the difference is not equal
to the transfer amount, it reverts with an appropriate custom error.
The portal also ensures the return value of transferFrom is true,
as specified in the ERC-20 standard. Empty or ill-formed return values
are not accepted and a low-level generic error is raised in those cases.
May raise Erc20TransferFailed, Erc20TransferDecreasedApplicationBalance, or Erc20TransferValueIsNotBalanceDelta.
function depositErc20Tokens(
IERC20 token,
address appContract,
uint256 value,
bytes calldata execLayerData
) external;
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC20 | The ERC-20 token contract |
appContract | address | The application contract address |
value | uint256 | The amount of tokens to be transferred |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Errors
Erc20TransferFailed
Failed to transfer ERC-20 tokens to application
error Erc20TransferFailed();
Erc20TransferDecreasedApplicationBalance
ERC-20 transfer decreased application balance
error Erc20TransferDecreasedApplicationBalance(
uint256 balanceBefore, uint256 balanceAfter
);
Parameters
| Name | Type | Description |
|---|---|---|
balanceBefore | uint256 | The application balance before the transfer |
balanceAfter | uint256 | The application balance after the transfer |
Erc20TransferValueIsNotBalanceDelta
ERC-20 transfer value is different from application balance delta
error Erc20TransferValueIsNotBalanceDelta(uint256 value, uint256 balanceDelta);
Parameters
| Name | Type | Description |
|---|---|---|
value | uint256 | The transfer value |
balanceDelta | uint256 | The application balance delta (after - before) |
IErc721Portal
Inherits: IPortal
Title: ERC-721 Portal interface
Functions
depositErc721Token
Transfer an ERC-721 token to an application contract
and add an input to the application's input box to signal such operation.
The caller must change the approved address for the ERC-721 token
to the portal address beforehand, by calling the approve function in the
token contract.
If the application is foreclosed, and the deposit input is not processed,
the user can issue a refund. If the user deposits an NFT through a smart contract,
a refund will only succeed if the smart contract accepts it through the onERC721Received callback.
If the smart contract wallet does not accept the NFT through the callback, it may not be recoverable.
function depositErc721Token(
IERC721 token,
address appContract,
uint256 tokenId,
bytes calldata baseLayerData,
bytes calldata execLayerData
) external;
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC721 | The ERC-721 token contract |
appContract | address | The application contract address |
tokenId | uint256 | The identifier of the token being transferred |
baseLayerData | bytes | Additional data to be interpreted by the base layer |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
IEtherPortal
Inherits: IPortal
Title: Ether Portal interface
Functions
depositEther
Transfer Ether to an application contract and add an input to the application's input box to signal such operation.
Any Ether sent through this function will be forwarded to the application contract.
If the transfer fails, an EtherTransferFailed error will be raised.
If the application is foreclosed, and the deposit input is not processed,
the user can issue a refund. If the user deposits Ether through a smart contract,
a refund will only succeed if the smart contract accepts it through a message call.
If the smart contract wallet does not accept Ether transfers, funds may not be recoverable.
function depositEther(address appContract, bytes calldata execLayerData)
external
payable;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
execLayerData | bytes | Additional data to be interpreted by the execution layer |
Errors
EtherTransferFailed
Failed to transfer Ether to application
error EtherTransferFailed();
IPortal
Inherits: IVersionGetter, IApplicationChecker
Title: Portal interface
Portal
Inherits: IPortal, RollupsContract
Title: Portal
This contract serves as a base for all the other portals.
Functions
_addInput
Add an input to an application's input box.
function _addInput(address appContract, bytes memory payload) internal;
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
payload | bytes | The input payload |
_getInputBox
Get an application's input box.
function _getInputBox(address appContract) internal view returns (IInputBox);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | IInputBox | The input box |
_getInputBoxAddress
Get an application's input box address.
function _getInputBoxAddress(address appContract) internal view returns (address);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
Returns
| Name | Type | Description |
|---|---|---|
<none> | address | The input box address |
Contents
IRefundOutputBuilder
Inherits: IRefundOutputBuilderErrors, IVersionGetter
Functions
buildRefundOutput
Build an output that, when executed by the application contract, reverts
an unprocessed deposit by transferring the asset(s) back to the original sender
account. This function will be called via the STATICCALL opcode, so any state
changes such as contract creations, log emissions, storage writes, Ether transfers
and self-destructions will revert the call and abort the execution of the refund
output. These state-changing constraints are already checked by the Solidity
compiler when implementing this function as either view or pure.
If the input sender is a contract, the refund output may revert depending on the
asset type (such as Ether, ERC-721, ERC-1155) and whether the depositor contract
implements the necessary receiver entrypoint appropriately.
This function assumes the input box of the application indeed contains an
input with such a sender and payload. May raise UnknownInputSender.
function buildRefundOutput(
address appContract,
address inputSender,
bytes calldata inputPayload
) external view returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
inputSender | address | The input sender |
inputPayload | bytes | The input payload |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The refund output |
IRefundOutputBuilderErrors
Errors
UnknownInputSender
This error is raised whenever a user provides an input whose sender is unknown to the refund output builder contract. Usually, this happens when the user provides a non-deposit input or an input sent by a non-canonical portal contract.
error UnknownInputSender(address inputSender);
Parameters
| Name | Type | Description |
|---|---|---|
inputSender | address | The input sender |
RefundOutputBuilder
Inherits: IRefundOutputBuilder, RollupsContract
State Variables
ETHER_PORTAL
IEtherPortal immutable ETHER_PORTAL
ERC20_PORTAL
IErc20Portal immutable ERC20_PORTAL
ERC721_PORTAL
IErc721Portal immutable ERC721_PORTAL
ERC1155_SINGLE_PORTAL
IErc1155SinglePortal immutable ERC1155_SINGLE_PORTAL
ERC1155_BATCH_PORTAL
IErc1155BatchPortal immutable ERC1155_BATCH_PORTAL
SAFE_TRANSFER
ISafeErc20Transfer immutable SAFE_TRANSFER
Functions
constructor
constructor(
IEtherPortal etherPortal,
IErc20Portal erc20Portal,
IErc721Portal erc721Portal,
IErc1155SinglePortal erc1155SinglePortal,
IErc1155BatchPortal erc1155BatchPortal,
ISafeErc20Transfer safeTransfer
) ;
buildRefundOutput
function buildRefundOutput(
address appContract,
address inputSender,
bytes calldata payload
) external view override returns (bytes memory output);
Contents
- IUsdWithdrawalOutputBuilder
- IUsdWithdrawalOutputBuilderFactory
- IWithdrawalOutputBuilder
- IWithdrawalOutputBuilderErrors
- UsdWithdrawalOutputBuilder
- UsdWithdrawalOutputBuilderFactory
IUsdWithdrawalOutputBuilder
Inherits: IWithdrawalOutputBuilder, IVersionGetter
Functions
token
Get the ERC-20 token used to generate withdrawal outputs.
function token() external view returns (IERC20);
IUsdWithdrawalOutputBuilderFactory
Inherits: IVersionGetter
Title: USD Withdrawal Output Builder Factory interface
For greater simplicity, this factory only supports deterministic deployments. Given that USD withdrawal output builders are stateless contracts, it should not matter whether you deploy one yourself or use an already deployed one with the same token.
Functions
newUsdWithdrawalOutputBuilder
Deploy a new USD withdrawal output builder deterministically.
function newUsdWithdrawalOutputBuilder(IERC20 token, bytes32 salt)
external
returns (IUsdWithdrawalOutputBuilder usdWithdrawalOutputBuilder);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC20 | The USD-like ERC-20 token |
salt | bytes32 | The salt used to deterministically generate the contract address |
Returns
| Name | Type | Description |
|---|---|---|
usdWithdrawalOutputBuilder | IUsdWithdrawalOutputBuilder | The USD withdrawal output builder |
calculateUsdWithdrawalOutputBuilderAddress
Calculate the address of a USD withdrawal output builder to be deployed deterministically.
function calculateUsdWithdrawalOutputBuilderAddress(IERC20 token, bytes32 salt)
external
view
returns (address usdWithdrawalOutputBuilderAddress);
Parameters
| Name | Type | Description |
|---|---|---|
token | IERC20 | The USD-like ERC-20 token |
salt | bytes32 | The salt used to deterministically generate the contract address |
Returns
| Name | Type | Description |
|---|---|---|
usdWithdrawalOutputBuilderAddress | address | The deterministic USD withdrawal output builder address |
getSafeErc20Transfer
Get the safe ERC-20 transfer contract passed down to the USD withdrawal output builders. This contract is used as delegate-call voucher destination.
function getSafeErc20Transfer()
external
view
returns (ISafeErc20Transfer safeErc20Transfer);
Returns
| Name | Type | Description |
|---|---|---|
safeErc20Transfer | ISafeErc20Transfer | The safe ERC-20 transfer contract |
Events
UsdWithdrawalOutputBuilderCreated
A new USD withdrawal output builder was deployed.
MUST be triggered on a successful call to newUsdWithdrawalOutputBuilder.
event UsdWithdrawalOutputBuilderCreated(IUsdWithdrawalOutputBuilder usdWithdrawalOutputBuilder);
Parameters
| Name | Type | Description |
|---|---|---|
usdWithdrawalOutputBuilder | IUsdWithdrawalOutputBuilder | The USD withdrawal output builder |
IWithdrawalOutputBuilder
Inherits: IWithdrawalOutputBuilderErrors
Functions
buildWithdrawalOutput
Build an output that, when executed by the application
contract, transfers the funds of an account to its owner.
The encoding of the account is application-specific but must comply
with one convention: The account byte array must end with the account owner
encoded as a 20-byte big-endian string. This convention allows the node to
query an account by its owner from the accounts drive. The contract must not
assume the account is well-formed. Instead, it should validate its length
(possibly raising an InvalidAccountSize error) and its contents.
This function will be called via the STATICCALL opcode,
so any state changes such as contract creations,
log emissions, storage writes, self-destructions
and Ether transfers will revert the call and abort the execution
of the withdrawal output. These state-changing constraints
are already checked by the Solidity compiler when implementing
this function as either view or pure.
If the input sender is a contract, the withdrawal output may revert depending on
the asset type (such as Ether, ERC-721, ERC-1155) and whether the depositor
contract implements the necessary receiver entrypoint appropriately.
The application contract address might be necessary for vouchers that transfer assets from the application contract's account to the account owner's account (e.g. in the case of ERC-721 and ERC-1155 transfers).
function buildWithdrawalOutput(address appContract, bytes calldata account)
external
view
returns (bytes memory output);
Parameters
| Name | Type | Description |
|---|---|---|
appContract | address | The application contract address |
account | bytes | The input account |
Returns
| Name | Type | Description |
|---|---|---|
output | bytes | The withdrawal output |
IWithdrawalOutputBuilderErrors
Errors
InvalidAccountSize
This error is raised whenever a user provides an ill-sized account for the builder to decode. The error is accompanied by the size of the account whose funds were attempted to be withdrawn and the expected account size suitable for on-chain decoding.
error InvalidAccountSize(uint256 attemptedAccountSize, uint64 accountSize);
Parameters
| Name | Type | Description |
|---|---|---|
attemptedAccountSize | uint256 | The attempted account size, in bytes. |
accountSize | uint64 | The expected account size, in bytes. |
UsdWithdrawalOutputBuilder
Inherits: IUsdWithdrawalOutputBuilder, RollupsContract
State Variables
SAFE_ERC20_TRANSFER
ISafeErc20Transfer immutable SAFE_ERC20_TRANSFER
USD
IERC20 immutable USD
Functions
constructor
constructor(ISafeErc20Transfer safeErc20Transfer, IERC20 usd) ;
token
function token() external view override returns (IERC20);
buildWithdrawalOutput
function buildWithdrawalOutput(address, bytes calldata account)
external
view
override
returns (bytes memory output);
_encodeSafeTransferPayload
function _encodeSafeTransferPayload(address user, uint256 value)
internal
view
returns (bytes memory payload);
_encodeDelegateCallVoucher
function _encodeDelegateCallVoucher(address destination, bytes memory payload)
internal
pure
returns (bytes memory output);
UsdWithdrawalOutputBuilderFactory
Inherits: IUsdWithdrawalOutputBuilderFactory, RollupsContract
Title: USD Withdrawal Output Builder Factory
Allows anyone to reliably deploy a new IUsdWithdrawalOutputBuilder contract.
State Variables
SAFE_ERC20_TRANSFER
ISafeErc20Transfer immutable SAFE_ERC20_TRANSFER
Functions
constructor
constructor(ISafeErc20Transfer safeErc20Transfer) ;
newUsdWithdrawalOutputBuilder
function newUsdWithdrawalOutputBuilder(IERC20 token, bytes32 salt)
external
override
returns (IUsdWithdrawalOutputBuilder usdWithdrawalOutputBuilder);
calculateUsdWithdrawalOutputBuilderAddress
function calculateUsdWithdrawalOutputBuilderAddress(IERC20 token, bytes32 salt)
external
view
override
returns (address usdWithdrawalOutputBuilderAddress);
getSafeErc20Transfer
function getSafeErc20Transfer()
external
view
override
returns (ISafeErc20Transfer safeErc20Transfer);