Skip to content

Commit

Permalink
feat(contracts-communication): remove batching (#2599)
Browse files Browse the repository at this point in the history
* feat: scaffold InterchainDB interface changes

* feat: scaffold Module interface changes

* feat: update InterchainEntry

* test: update DB tests

* test: update Client tests

* refactor: ModuleBatch -> ModuleEntry

* feat: remove `entryIndex` from InterchainTx

* feat: scaffold Client interface changes

* feat: start updating the Module

* test: update integration tests

* cleanup: remove BatchingV1

* feat: update InterchainDB

* cleanup: remove entryIndex from apps

* cleanup: remove entryIndex from Client events

* feat: update ClientV1

* cleanup: remove entryIndex from DB

* test: update SynapseModule tests

* cleanup: ClientV1

* cleanup: DB

* cleanup: Module

* cleanup: remove batch lib

* docs: smol fixes
  • Loading branch information
ChiTimesChi authored May 9, 2024
1 parent bc97878 commit e6588f7
Show file tree
Hide file tree
Showing 56 changed files with 1,507 additions and 2,407 deletions.
160 changes: 67 additions & 93 deletions packages/contracts-communication/contracts/InterchainClientV1.sol

Large diffs are not rendered by default.

351 changes: 117 additions & 234 deletions packages/contracts-communication/contracts/InterchainDB.sol

Large diffs are not rendered by default.

17 changes: 3 additions & 14 deletions packages/contracts-communication/contracts/apps/AbstractICApp.sol
Original file line number Diff line number Diff line change
Expand Up @@ -25,19 +25,9 @@ abstract contract AbstractICApp is AbstractICAppEvents, IInterchainApp {
/// @dev App is responsible for keeping track of interchain clients, and must verify the message sender.
/// @param srcChainId Chain ID of the source chain, where the message was sent from.
/// @param sender Sender address on the source chain, as a bytes32 value.
/// @param dbNonce The Interchain DB nonce of the batch containing the message entry.
/// @param entryIndex The index of the message entry within the batch.
/// @param dbNonce The Interchain DB nonce of the message entry.
/// @param message The message being sent.
function appReceive(
uint64 srcChainId,
bytes32 sender,
uint64 dbNonce,
uint64 entryIndex,
bytes calldata message
)
external
payable
{
function appReceive(uint64 srcChainId, bytes32 sender, uint64 dbNonce, bytes calldata message) external payable {
if (!_isInterchainClient(msg.sender)) {
revert InterchainApp__CallerNotInterchainClient(msg.sender);
}
Expand All @@ -47,7 +37,7 @@ abstract contract AbstractICApp is AbstractICAppEvents, IInterchainApp {
if (!_isAllowedSender(srcChainId, sender)) {
revert InterchainApp__SrcSenderNotAllowed(srcChainId, sender);
}
_receiveMessage(srcChainId, sender, dbNonce, entryIndex, message);
_receiveMessage(srcChainId, sender, dbNonce, message);
}

/// @notice Returns the verification configuration of the Interchain App.
Expand Down Expand Up @@ -173,7 +163,6 @@ abstract contract AbstractICApp is AbstractICAppEvents, IInterchainApp {
uint64 srcChainId,
bytes32 sender,
uint64 dbNonce,
uint64 entryIndex,
bytes calldata message
)
internal
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@ import {OptionsV1} from "../../libs/Options.sol";
import {Address} from "@openzeppelin/contracts/utils/Address.sol";

contract ExampleAppV1 is ICAppV1 {
event MessageReceived(uint64 srcChainId, bytes32 sender, uint64 dbNonce, uint64 entryIndex, bytes message);
event MessageSent(uint64 dstChainId, uint64 dbNonce, uint64 entryIndex, bytes32 transactionId);
event MessageReceived(uint64 srcChainId, bytes32 sender, uint64 dbNonce, bytes message);
event MessageSent(uint64 dstChainId, uint64 dbNonce, bytes32 transactionId);

constructor(address admin) ICAppV1(admin) {
_grantRole(IC_GOVERNOR_ROLE, admin);
Expand All @@ -37,7 +37,7 @@ contract ExampleAppV1 is ICAppV1 {
options: OptionsV1({gasLimit: gasLimit, gasAirdrop: gasAirdrop}),
message: message
});
emit MessageSent(dstChainId, desc.dbNonce, desc.entryIndex, desc.transactionId);
emit MessageSent(dstChainId, desc.dbNonce, desc.transactionId);
}

/// @notice Returns the fee required to send a message using `sendMessage`.
Expand All @@ -59,12 +59,11 @@ contract ExampleAppV1 is ICAppV1 {
uint64 srcChainId,
bytes32 sender,
uint64 dbNonce,
uint64 entryIndex,
bytes calldata message
)
internal
override
{
emit MessageReceived(srcChainId, sender, dbNonce, entryIndex, message);
emit MessageReceived(srcChainId, sender, dbNonce, message);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,8 @@ contract PingPongApp is ICAppV1 {

event GasLimitSet(uint256 gasLimit);
event PingDisrupted(uint256 counter);
event PingReceived(uint256 counter, uint64 dbNonce, uint64 entryIndex);
event PingSent(uint256 counter, uint64 dbNonce, uint64 entryIndex);
event PingReceived(uint256 counter, uint64 dbNonce);
event PingSent(uint256 counter, uint64 dbNonce);

constructor(address admin) ICAppV1(admin) {
_grantRole(IC_GOVERNOR_ROLE, admin);
Expand Down Expand Up @@ -55,14 +55,13 @@ contract PingPongApp is ICAppV1 {
uint64 srcChainId,
bytes32, // sender
uint64 dbNonce,
uint64 entryIndex,
bytes calldata message
)
internal
override
{
uint256 counter = abi.decode(message, (uint256));
emit PingReceived(counter, dbNonce, entryIndex);
emit PingReceived(counter, dbNonce);
if (counter > 0) {
// Don't revert if the balance is low, just stop sending messages.
_sendPingPongMessage({dstChainId: srcChainId, counter: counter - 1, lowBalanceRevert: false});
Expand All @@ -81,7 +80,7 @@ contract PingPongApp is ICAppV1 {
return;
}
InterchainTxDescriptor memory desc = _sendToLinkedApp(dstChainId, messageFee, options, message);
emit PingSent(counter, desc.dbNonce, desc.entryIndex);
emit PingSent(counter, desc.dbNonce);
}

/// @dev Sets the gas limit for the interchain messages.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,19 +14,17 @@ abstract contract InterchainClientV1Events {
/// @notice Emitted when a new interchain transaction is sent through the InterchainClientV1.
/// The Receiver on the destination chain will receive the specified message once the transaction is executed.
/// @param transactionId The unique identifier of the interchain transaction.
/// @param dbNonce The nonce of batch containing the transaction's DB entry.
/// @param entryIndex The index of the transaction's DB entry in the batch.
/// @param dbNonce The nonce of entry containing the transaction.
/// @param dstChainId The chain ID of the destination chain.
/// @param srcSender The sender of the transaction on the source chain.
/// @param dstReceiver The receiver of the transaction on the destination chain.
/// @param verificationFee The fee paid to verify the batch on the destination chain.
/// @param verificationFee The fee paid to verify the entry on the destination chain.
/// @param executionFee The fee paid to execute the transaction on the destination chain.
/// @param options The execution options for the transaction.
/// @param message The payload of the message being sent.
event InterchainTransactionSent(
bytes32 indexed transactionId,
uint64 dbNonce,
uint64 entryIndex,
uint64 dstChainId,
bytes32 indexed srcSender,
bytes32 indexed dstReceiver,
Expand All @@ -39,15 +37,13 @@ abstract contract InterchainClientV1Events {
/// @notice Emitted when an interchain transaction is received by the InterchainClientV1.
/// The Receiver on the destination chain has just received the message sent from the source chain.
/// @param transactionId The unique identifier of the interchain transaction.
/// @param dbNonce The nonce of batch containing the transaction's DB entry.
/// @param entryIndex The index of the transaction's DB entry in the batch.
/// @param dbNonce The nonce of entry containing the transaction.
/// @param srcChainId The chain ID of the source chain.
/// @param srcSender The sender of the transaction on the source chain.
/// @param dstReceiver The receiver of the transaction on the destination chain.
event InterchainTransactionReceived(
bytes32 indexed transactionId,
uint64 dbNonce,
uint64 entryIndex,
uint64 srcChainId,
bytes32 indexed srcSender,
bytes32 indexed dstReceiver
Expand All @@ -56,10 +52,7 @@ abstract contract InterchainClientV1Events {
/// @notice Emitted when the proof of execution is written to InterchainDB. This allows the source chain
/// to verify that the transaction was executed by a specific executor, if necessary.
/// @param transactionId The unique identifier of the interchain transaction.
/// @param dbNonce The nonce of batch containing the written proof's DB entry.
/// @param entryIndex The index of the written proof's DB entry in the batch.
/// @param dbNonce The nonce of entry containing the transaction.
/// @param executor The address of the executor that completed the transaction.
event ExecutionProofWritten(
bytes32 indexed transactionId, uint64 dbNonce, uint64 entryIndex, address indexed executor
);
event ExecutionProofWritten(bytes32 indexed transactionId, uint64 dbNonce, address indexed executor);
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,35 +3,25 @@ pragma solidity ^0.8.0;

abstract contract InterchainDBEvents {
/// @notice Emitted when a local entry is written to the database.
/// @param dbNonce The nonce of the batch containing the entry.
/// @param entryIndex The index of the entry within the batch.
/// @param srcWriter The address of the writer.
/// @param dataHash The written data hash.
event InterchainEntryWritten(
uint64 indexed dbNonce, uint64 entryIndex, bytes32 indexed srcWriter, bytes32 dataHash
);

/// @notice Emitted when a local batch is finalized.
/// @param dbNonce The nonce of the finalized batch.
/// @param batchRoot The Merkle root hash of the finalized batch.
event InterchainBatchFinalized(uint64 indexed dbNonce, bytes32 batchRoot);
/// @param dbNonce The nonce of the written entry.
/// @param srcWriter The address of the entry writer.
/// @param digest The written data digest.
/// @param entryValue The value of the written entry: keccak256(abi.encode(srcWriter, digest)).
event InterchainEntryWritten(uint64 indexed dbNonce, bytes32 indexed srcWriter, bytes32 digest, bytes32 entryValue);

/// @notice Emitted when a remote batch is verified by the Interchain Module.
/// @param module The address of the Interchain Module that verified the batch.
/// @notice Emitted when a remote entry is verified by the Interchain Module.
/// @param module The address of the Interchain Module that verified the entry.
/// @param srcChainId The ID of the source chain.
/// @param dbNonce The nonce of the verified batch.
/// @param batchRoot The Merkle root hash of the verified batch.
event InterchainBatchVerified(
address indexed module, uint64 indexed srcChainId, uint64 indexed dbNonce, bytes32 batchRoot
/// @param dbNonce The nonce of the verified entry.
/// @param entryValue The value of the verified entry: keccak256(abi.encode(srcWriter, digest)).
event InterchainEntryVerified(
address indexed module, uint64 indexed srcChainId, uint64 indexed dbNonce, bytes32 entryValue
);

/// @notice Emitted when a local batch is requested to be verified on a remote chain
/// @notice Emitted when a local entry is requested to be verified on a remote chain
/// using the set of Interchain Modules.
/// @param dstChainId The ID of the destination chain.
/// @param dbNonce The nonce of the batch to be verified.
/// @param batchRoot The Merkle root hash of the batch to be verified.
/// @param srcModules The addresses of the Interchain Modules that will verify the batch.
event InterchainBatchVerificationRequested(
uint64 indexed dstChainId, uint64 indexed dbNonce, bytes32 batchRoot, address[] srcModules
);
/// @param dbNonce The nonce of the entry to be verified.
/// @param srcModules The addresses of the Interchain Modules that will verify the entry.
event InterchainEntryVerificationRequested(uint64 indexed dstChainId, uint64 indexed dbNonce, address[] srcModules);
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,15 @@
pragma solidity ^0.8.0;

abstract contract InterchainModuleEvents {
/// @notice Emitted when a batch verification on a remote chain is requested.
/// @notice Emitted when an entry verification on a remote chain is requested.
/// @param dstChainId The chain ID of the destination chain.
/// @param batch The encoded batch to be verified.
/// @param ethSignedBatchHash The digest of the batch (EIP-191 personal signed).
event BatchVerificationRequested(uint64 indexed dstChainId, bytes batch, bytes32 ethSignedBatchHash);
/// @param entry The encoded entry to be verified.
/// @param ethSignedEntryHash The digest of the entry (EIP-191 personal signed).
event EntryVerificationRequested(uint64 indexed dstChainId, bytes entry, bytes32 ethSignedEntryHash);

/// @notice Emitted when a batch from the remote chain is verified.
/// @notice Emitted when an entry from the remote chain is verified.
/// @param srcChainId The chain ID of the source chain.
/// @param batch The encoded batch that was verified.
/// @param ethSignedBatchHash The digest of the batch (EIP-191 personal signed).
event BatchVerified(uint64 indexed srcChainId, bytes batch, bytes32 ethSignedBatchHash);
/// @param entry The encoded entry that was verified.
/// @param ethSignedEntryHash The digest of the entry (EIP-191 personal signed).
event EntryVerified(uint64 indexed srcChainId, bytes entry, bytes32 ethSignedEntryHash);
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
pragma solidity ^0.8.0;

abstract contract SynapseModuleEvents {
/// @notice Emitted when a verifier is added. The verifier signatures are required to verify a batch.
/// @notice Emitted when a verifier is added. The verifier signatures are required to verify an entry.
/// @param verifier The address of the verifier.
event VerifierAdded(address verifier);

Expand All @@ -11,18 +11,18 @@ abstract contract SynapseModuleEvents {
event VerifierRemoved(address verifier);

/// @notice Emitted when a threshold is set.
/// The threshold is the minimum number of verifiers required to verify a batch.
/// The threshold is the minimum number of verifiers required to verify an entry.
/// @param threshold The threshold value.
event ThresholdSet(uint256 threshold);

/// @notice Emitted when a gas oracle is set. The gas oracle will be used to estimate the gas cost of
/// verifying a batch on the remote chain.
/// verifying an entry on the remote chain.
/// @param gasOracle The address of the gas oracle.
event GasOracleSet(address gasOracle);

/// @notice Emitted when the gas limit estimate is set for a chain.
/// @param chainId The chain ID of the chain.
/// @param gasLimit The gas limit estimate for verifying a batch on the chain.
/// @param gasLimit The gas limit estimate for verifying an entry on the chain.
event VerifyGasLimitSet(uint64 chainId, uint256 gasLimit);

/// @notice Emitted when the gas data from the gas oracle is sent to the remote chain.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,7 @@ pragma solidity ^0.8.0;

/// @notice Minimal interface for the Interchain App to work with the Interchain Client.
interface IInterchainApp {
function appReceive(
uint64 srcChainId,
bytes32 sender,
uint64 dbNonce,
uint64 entryIndex,
bytes calldata message
)
external
payable;
function appReceive(uint64 srcChainId, bytes32 sender, uint64 dbNonce, bytes calldata message) external payable;

// ═══════════════════════════════════════════════════ VIEWS ═══════════════════════════════════════════════════════

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,18 @@ interface IInterchainClientV1 {
enum TxReadiness {
Ready,
AlreadyExecuted,
BatchAwaitingResponses,
BatchConflict,
EntryAwaitingResponses,
EntryConflict,
ReceiverNotICApp,
ReceiverZeroRequiredResponses,
TxWrongDstChainId,
UndeterminedRevert
}

error InterchainClientV1__BatchConflict(address module);
error InterchainClientV1__ChainIdNotLinked(uint64 chainId);
error InterchainClientV1__ChainIdNotRemote(uint64 chainId);
error InterchainClientV1__DstChainIdNotLocal(uint64 chainId);
error InterchainClientV1__EntryConflict(address module);
error InterchainClientV1__ExecutionServiceZeroAddress();
error InterchainClientV1__FeeAmountBelowMin(uint256 feeAmount, uint256 minRequired);
error InterchainClientV1__GasLeftBelowMin(uint256 gasLeft, uint256 minRequired);
Expand Down Expand Up @@ -60,26 +60,18 @@ interface IInterchainClientV1 {
payable
returns (InterchainTxDescriptor memory desc);

function interchainExecute(
uint256 gasLimit,
bytes calldata transaction,
bytes32[] calldata proof
)
external
payable;
function interchainExecute(uint256 gasLimit, bytes calldata transaction) external payable;

function writeExecutionProof(bytes32 transactionId) external returns (uint64 dbNonce, uint64 entryIndex);
function writeExecutionProof(bytes32 transactionId) external returns (uint64 dbNonce);

// ═══════════════════════════════════════════════════ VIEWS ═══════════════════════════════════════════════════════

function isExecutable(bytes calldata transaction, bytes32[] calldata proof) external view returns (bool);
function getTxReadinessV1(
InterchainTransaction memory icTx,
bytes32[] calldata proof
)
function isExecutable(bytes calldata transaction) external view returns (bool);
function getTxReadinessV1(InterchainTransaction memory icTx)
external
view
returns (TxReadiness status, bytes32 firstArg, bytes32 secondArg);

function getInterchainFee(
uint64 dstChainId,
address srcExecutionService,
Expand Down
Loading

0 comments on commit e6588f7

Please sign in to comment.