Skip to content

Commit

Permalink
fix(contracts-communication): interchain module ignore nonces (#2604)
Browse files Browse the repository at this point in the history
* feat: remove dbNonce from Module interface

* cleanup: update Module interface references

* refactor: lint
  • Loading branch information
ChiTimesChi authored May 9, 2024
1 parent ca1690d commit be4351b
Show file tree
Hide file tree
Showing 7 changed files with 31 additions and 76 deletions.
11 changes: 4 additions & 7 deletions packages/contracts-communication/contracts/InterchainDB.sol
Original file line number Diff line number Diff line change
Expand Up @@ -135,7 +135,7 @@ contract InterchainDB is InterchainDBEvents, IInterchainDB {
/// @param dstChainId The chain id of the destination chain
/// @param srcModules The source chain addresses of the Interchain Modules to use for verification
function getInterchainFee(uint64 dstChainId, address[] calldata srcModules) external view returns (uint256 fee) {
(, fee) = _getModuleFees(dstChainId, getDBNonce(), srcModules);
(, fee) = _getModuleFees(dstChainId, srcModules);
}

/// @notice Check if the entry is verified by the Interchain Module on the destination chain.
Expand Down Expand Up @@ -221,7 +221,7 @@ contract InterchainDB is InterchainDBEvents, IInterchainDB {
)
internal
{
(uint256[] memory fees, uint256 totalFee) = _getModuleFees(dstChainId, entry.dbNonce, srcModules);
(uint256[] memory fees, uint256 totalFee) = _getModuleFees(dstChainId, srcModules);
if (msg.value < totalFee) {
revert InterchainDB__FeeAmountBelowMin(msg.value, totalFee);
} else if (msg.value > totalFee) {
Expand All @@ -234,9 +234,7 @@ contract InterchainDB is InterchainDBEvents, IInterchainDB {
payload: InterchainEntryLib.encodeEntry(entry)
});
for (uint256 i = 0; i < len; ++i) {
IInterchainModule(srcModules[i]).requestEntryVerification{value: fees[i]}(
dstChainId, entry.dbNonce, versionedEntry
);
IInterchainModule(srcModules[i]).requestEntryVerification{value: fees[i]}(dstChainId, versionedEntry);
}
emit InterchainEntryVerificationRequested(dstChainId, entry.dbNonce, srcModules);
}
Expand Down Expand Up @@ -265,7 +263,6 @@ contract InterchainDB is InterchainDBEvents, IInterchainDB {
/// @dev Get the verification fees for the modules
function _getModuleFees(
uint64 dstChainId,
uint64 dbNonce,
address[] calldata srcModules
)
internal
Expand All @@ -278,7 +275,7 @@ contract InterchainDB is InterchainDBEvents, IInterchainDB {
}
fees = new uint256[](len);
for (uint256 i = 0; i < len; ++i) {
fees[i] = IInterchainModule(srcModules[i]).getModuleFee(dstChainId, dbNonce);
fees[i] = IInterchainModule(srcModules[i]).getModuleFee(dstChainId);
totalFee += fees[i];
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,15 +8,9 @@ interface IInterchainModule {
error InterchainModule__ChainIdNotRemote(uint64 chainId);
error InterchainModule__FeeAmountBelowMin(uint256 feeAmount, uint256 minRequired);

function requestEntryVerification(
uint64 dstChainId,
uint64 dbNonce,
bytes memory versionedEntry
)
external
payable;
function requestEntryVerification(uint64 dstChainId, bytes memory versionedEntry) external payable;

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

function getModuleFee(uint64 dstChainId, uint64 dbNonce) external view returns (uint256);
function getModuleFee(uint64 dstChainId) external view returns (uint256);
}
Original file line number Diff line number Diff line change
Expand Up @@ -28,27 +28,19 @@ abstract contract InterchainModule is InterchainModuleEvents, IInterchainModule
/// with no guarantee of ordering.
/// @dev Could be only called by the Interchain DataBase contract.
/// @param dstChainId The chain id of the destination chain
/// @param dbNonce The database nonce of the entry on the source chain
/// @param versionedEntry The versioned entry to verify
function requestEntryVerification(
uint64 dstChainId,
uint64 dbNonce,
bytes memory versionedEntry
)
external
payable
{
function requestEntryVerification(uint64 dstChainId, bytes memory versionedEntry) external payable {
if (msg.sender != INTERCHAIN_DB) {
revert InterchainModule__CallerNotInterchainDB(msg.sender);
}
if (dstChainId == block.chainid) {
revert InterchainModule__ChainIdNotRemote(dstChainId);
}
uint256 requiredFee = _getModuleFee(dstChainId, dbNonce);
uint256 requiredFee = _getModuleFee(dstChainId);
if (msg.value < requiredFee) {
revert InterchainModule__FeeAmountBelowMin({feeAmount: msg.value, minRequired: requiredFee});
}
bytes memory moduleData = _fillModuleData(dstChainId, dbNonce);
bytes memory moduleData = _fillModuleData(dstChainId);
bytes memory encodedEntry = ModuleEntryLib.encodeVersionedModuleEntry(versionedEntry, moduleData);
bytes32 ethSignedEntryHash = MessageHashUtils.toEthSignedMessageHash(keccak256(encodedEntry));
_requestVerification(dstChainId, encodedEntry);
Expand All @@ -57,9 +49,8 @@ abstract contract InterchainModule is InterchainModuleEvents, IInterchainModule

/// @notice Get the Module fee for verifying an entry on the specified destination chain.
/// @param dstChainId The chain id of the destination chain
/// @param dbNonce The database nonce of the entry on the source chain
function getModuleFee(uint64 dstChainId, uint64 dbNonce) external view returns (uint256) {
return _getModuleFee(dstChainId, dbNonce);
function getModuleFee(uint64 dstChainId) external view returns (uint256) {
return _getModuleFee(dstChainId);
}

/// @dev Should be called once the Module has verified the entry and needs to signal this
Expand All @@ -83,11 +74,11 @@ abstract contract InterchainModule is InterchainModuleEvents, IInterchainModule
function _requestVerification(uint64 dstChainId, bytes memory encodedEntry) internal virtual {}

/// @dev Internal logic to fill the module data for the specified destination chain.
function _fillModuleData(uint64 dstChainId, uint64 dbNonce) internal virtual returns (bytes memory) {}
function _fillModuleData(uint64 dstChainId) internal virtual returns (bytes memory) {}

/// @dev Internal logic to handle the auxiliary module data relayed from the remote chain.
function _receiveModuleData(uint64 srcChainId, uint64 dbNonce, bytes memory moduleData) internal virtual {}

/// @dev Internal logic to get the module fee for verifying an entry on the specified destination chain.
function _getModuleFee(uint64 dstChainId, uint64 dbNonce) internal view virtual returns (uint256);
function _getModuleFee(uint64 dstChainId) internal view virtual returns (uint256);
}
Original file line number Diff line number Diff line change
Expand Up @@ -195,14 +195,7 @@ contract SynapseModule is InterchainModule, ClaimableFees, Ownable, SynapseModul
}

/// @dev Internal logic to fill the module data for the specified destination chain.
function _fillModuleData(
uint64 dstChainId,
uint64 // dbNonce
)
internal
override
returns (bytes memory moduleData)
{
function _fillModuleData(uint64 dstChainId) internal override returns (bytes memory moduleData) {
moduleData = _getSynapseGasOracle().getLocalGasData();
// Exit early if data is empty
if (moduleData.length == 0) {
Expand Down Expand Up @@ -236,15 +229,7 @@ contract SynapseModule is InterchainModule, ClaimableFees, Ownable, SynapseModul
// ══════════════════════════════════════════════ INTERNAL VIEWS ═══════════════════════════════════════════════════

/// @dev Internal logic to get the module fee for verifying an entry on the specified destination chain.
function _getModuleFee(
uint64 dstChainId,
uint64 // dbNonce
)
internal
view
override
returns (uint256)
{
function _getModuleFee(uint64 dstChainId) internal view override returns (uint256) {
// On the remote chain the verifyRemoteEntry(entry, signatures) function will be called.
// We need to figure out the calldata size for the remote call.
// selector (4 bytes) + entry + signatures
Expand Down
4 changes: 2 additions & 2 deletions packages/contracts-communication/test/InterchainDB.Src.t.sol
Original file line number Diff line number Diff line change
Expand Up @@ -103,8 +103,8 @@ contract InterchainDBSourceTest is Test, InterchainDBEvents {
}

function getModuleCalldata(InterchainEntry memory entry) internal view returns (bytes memory) {
bytes memory vEntry = getVersionedEntry(entry);
return abi.encodeCall(IInterchainModule.requestEntryVerification, (DST_CHAIN_ID, entry.dbNonce, vEntry));
bytes memory versionedEntry = getVersionedEntry(entry);
return abi.encodeCall(IInterchainModule.requestEntryVerification, (DST_CHAIN_ID, versionedEntry));
}

function addressToBytes32(address addr) internal pure returns (bytes32) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,16 +9,9 @@ import {VersionedPayloadLib} from "../../contracts/libs/VersionedPayload.sol";
// solhint-disable ordering
// solhint-disable no-empty-blocks
contract InterchainModuleMock is IInterchainModule {
function requestEntryVerification(
uint64 dstChainId,
uint64 dbNonce,
bytes calldata versionedEntry
)
external
payable
{}
function requestEntryVerification(uint64 dstChainId, bytes calldata versionedEntry) external payable {}

function getModuleFee(uint64 dstChainId, uint64 dbNonce) external view returns (uint256) {}
function getModuleFee(uint64 dstChainId) external view returns (uint256) {}

function mockVerifyRemoteEntry(address interchainDB, bytes calldata versionedEntry) external {
IInterchainDB(interchainDB).verifyRemoteEntry(versionedEntry);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -67,10 +67,10 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
return payloadLibHarness.encodeVersionedPayload(MOCK_DB_VERSION, entryLibHarness.encodeEntry(entry));
}

function requestEntryVerification(uint256 msgValue, uint64 dbNonce, bytes memory versionedEntry) internal {
function requestEntryVerification(uint256 msgValue, bytes memory versionedEntry) internal {
deal(interchainDB, msgValue);
vm.prank(interchainDB);
module.requestEntryVerification{value: msgValue}(DST_CHAIN_ID, dbNonce, versionedEntry);
module.requestEntryVerification{value: msgValue}(DST_CHAIN_ID, versionedEntry);
}

function encodeAndHashEntry(InterchainEntry memory entry)
Expand All @@ -97,13 +97,13 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
bytes memory versionedEntry = getVersionedEntry(mockEntry);
vm.expectEmit(address(module));
emit EntryVerificationRequested(DST_CHAIN_ID, encodedEntry, ethSignedHash);
requestEntryVerification(FEE, mockEntry.dbNonce, versionedEntry);
requestEntryVerification(FEE, versionedEntry);
}

function test_requestVerification_accumulatesFee() public {
deal(address(module), 5 ether);
bytes memory versionedEntry = getVersionedEntry(mockEntry);
requestEntryVerification(FEE, mockEntry.dbNonce, versionedEntry);
requestEntryVerification(FEE, versionedEntry);
assertEq(address(module).balance, 5 ether + FEE);
}

Expand All @@ -112,13 +112,13 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
bytes memory versionedEntry = getVersionedEntry(mockEntry);
vm.expectEmit(address(module));
emit EntryVerificationRequested(DST_CHAIN_ID, encodedEntry, ethSignedHash);
requestEntryVerification(FEE + 1, mockEntry.dbNonce, versionedEntry);
requestEntryVerification(FEE + 1, versionedEntry);
}

function test_requestVerification_feeAboveRequired_accumulatesFee() public {
deal(address(module), 5 ether);
bytes memory versionedEntry = getVersionedEntry(mockEntry);
requestEntryVerification(FEE + 1, mockEntry.dbNonce, versionedEntry);
requestEntryVerification(FEE + 1, versionedEntry);
assertEq(address(module).balance, 5 ether + FEE + 1);
}

Expand All @@ -127,7 +127,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
vm.expectRevert(
abi.encodeWithSelector(IInterchainModule.InterchainModule__FeeAmountBelowMin.selector, FEE - 1, FEE)
);
requestEntryVerification(FEE - 1, mockEntry.dbNonce, versionedEntry);
requestEntryVerification(FEE - 1, versionedEntry);
}

function test_claimFees_zeroClaimFee_emitsEvent() public {
Expand Down Expand Up @@ -233,8 +233,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
}

function test_getModuleFee_thresholdTwo() public view {
// TODO: dbNonce
assertEq(module.getModuleFee(DST_CHAIN_ID, 0), FEE);
assertEq(module.getModuleFee(DST_CHAIN_ID), FEE);
}

function test_getModuleFee_callsGasOracle_gasLimitDefault_twoSigners() public {
Expand All @@ -245,8 +244,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
gasOracle.estimateTxCostInLocalUnits, (DST_CHAIN_ID, DEFAULT_GAS_LIMIT, remoteCalldata.length)
);
vm.expectCall(address(gasOracle), expectedCalldata);
// TODO: dbNonce
module.getModuleFee(DST_CHAIN_ID, 0);
module.getModuleFee(DST_CHAIN_ID);
}

function test_getModuleFee_callsGasOracle_gasLimitDefault_threeSigners() public {
Expand All @@ -259,8 +257,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
gasOracle.estimateTxCostInLocalUnits, (DST_CHAIN_ID, DEFAULT_GAS_LIMIT, remoteCalldata.length)
);
vm.expectCall(address(gasOracle), expectedCalldata);
// TODO: dbNonce
module.getModuleFee(DST_CHAIN_ID, 0);
module.getModuleFee(DST_CHAIN_ID);
}

function test_getModuleFee_callsGasOracle_gasLimitSet_twoSigners() public {
Expand All @@ -272,8 +269,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
bytes memory expectedCalldata =
abi.encodeCall(gasOracle.estimateTxCostInLocalUnits, (DST_CHAIN_ID, 200_000, remoteCalldata.length));
vm.expectCall(address(gasOracle), expectedCalldata);
// TODO: dbNonce
module.getModuleFee(DST_CHAIN_ID, 0);
module.getModuleFee(DST_CHAIN_ID);
}

function test_getModuleFee_callsGasOracle_gasLimitSet_threeSigners() public {
Expand All @@ -287,8 +283,7 @@ contract SynapseModuleSourceTest is Test, ClaimableFeesEvents, InterchainModuleE
bytes memory expectedCalldata =
abi.encodeCall(gasOracle.estimateTxCostInLocalUnits, (DST_CHAIN_ID, 200_000, remoteCalldata.length));
vm.expectCall(address(gasOracle), expectedCalldata);
// TODO: dbNonce
module.getModuleFee(DST_CHAIN_ID, 0);
module.getModuleFee(DST_CHAIN_ID);
}

function test_getVerifyGasLimit_default() public view {
Expand Down

0 comments on commit be4351b

Please sign in to comment.