diff --git a/contracts/blade/BridgeStorage.sol b/contracts/blade/BridgeStorage.sol index 79ea8afd..2fecf76d 100644 --- a/contracts/blade/BridgeStorage.sol +++ b/contracts/blade/BridgeStorage.sol @@ -4,14 +4,44 @@ pragma solidity ^0.8.19; import "./ValidatorSetStorage.sol"; contract BridgeStorage is ValidatorSetStorage { - mapping(uint256 => BridgeMessageBatch) public batches; + mapping(uint256 => SignedBridgeMessageBatch) public batches; + mapping(uint256 => SignedValidatorSet) public commitedValidatorSets; mapping(uint256 => uint256) public lastCommitted; mapping(uint256 => uint256) public lastCommittedInternal; /// @custom:security write-protection="onlySystemCall()" uint256 public batchCounter; + /// @custom:security write-protection="onlySystemCall()" + uint256 public validatorSetCounter; event NewBatch(uint256 id); + /** + * @notice commits new validator set + * @param newValidatorSet new validator set + * @param signature aggregated signature of validators that signed the new validator set + * @param bitmap bitmap of which validators signed the message + */ + function commitValidatorSet( + Validator[] calldata newValidatorSet, + uint256[2] calldata signature, + bytes calldata bitmap + ) external override onlySystemCall { + _commitValidatorSet(newValidatorSet, signature, bitmap); + + SignedValidatorSet storage signedValidatorSet = commitedValidatorSets[validatorSetCounter]; + signedValidatorSet.signature = signature; + signedValidatorSet.bitmap = bitmap; + + for (uint256 i = 0; i < newValidatorSet.length; ) { + signedValidatorSet.newValidatorSet[i] = newValidatorSet[i]; + unchecked { + ++i; + } + } + + validatorSetCounter++; + } + /** * @notice commits new batch * @param batch new batch @@ -26,9 +56,14 @@ contract BridgeStorage is ValidatorSetStorage { bytes memory hash = abi.encode(keccak256(abi.encode(batch))); verifySignature(bls.hashToPoint(DOMAIN_BRIDGE, hash), signature, bitmap); - batches[batchCounter++] = batch; + SignedBridgeMessageBatch storage signedBatch = batches[batchCounter]; + signedBatch.batch = batch; + signedBatch.signature = signature; + signedBatch.bitmap = bitmap; + + emit NewBatch(batchCounter); - emit NewBatch(batchCounter - 1); + batchCounter++; } /** diff --git a/contracts/blade/ValidatorSetStorage.sol b/contracts/blade/ValidatorSetStorage.sol index 8017cee1..df0b4731 100644 --- a/contracts/blade/ValidatorSetStorage.sol +++ b/contracts/blade/ValidatorSetStorage.sol @@ -38,16 +38,8 @@ contract ValidatorSetStorage is IValidatorSetStorage, Initializable, System { Validator[] calldata newValidatorSet, uint256[2] calldata signature, bytes calldata bitmap - ) external onlySystemCall { - require(newValidatorSet.length > 0, "EMPTY_VALIDATOR_SET"); - - bytes memory hash = abi.encode(keccak256(abi.encode(newValidatorSet))); - - verifySignature(bls.hashToPoint(DOMAIN_VALIDATOR_SET, hash), signature, bitmap); - - _setNewValidatorSet(newValidatorSet); - - emit NewValidatorSet(newValidatorSet); + ) external virtual onlySystemCall { + _commitValidatorSet(newValidatorSet, signature, bitmap); } /** @@ -136,4 +128,20 @@ contract ValidatorSetStorage is IValidatorSetStorage, Initializable, System { // Get the value of the bit at the given 'index' in a byte. return uint8(bitmap[byteNumber]) & (1 << bitNumber) > 0; } + + function _commitValidatorSet( + Validator[] calldata newValidatorSet, + uint256[2] calldata signature, + bytes calldata bitmap + ) internal { + require(newValidatorSet.length > 0, "EMPTY_VALIDATOR_SET"); + + bytes memory hash = abi.encode(keccak256(abi.encode(newValidatorSet))); + + verifySignature(bls.hashToPoint(DOMAIN_VALIDATOR_SET, hash), signature, bitmap); + + _setNewValidatorSet(newValidatorSet); + + emit NewValidatorSet(newValidatorSet); + } } diff --git a/contracts/interfaces/blade/IValidatorSetStorage.sol b/contracts/interfaces/blade/IValidatorSetStorage.sol index be949818..3dee27e5 100644 --- a/contracts/interfaces/blade/IValidatorSetStorage.sol +++ b/contracts/interfaces/blade/IValidatorSetStorage.sol @@ -44,6 +44,28 @@ struct BridgeMessageBatch { uint256 destinationChainId; } +/** + * @param batch batch that is signed + * @param signature aggregated signature of validators that signed the batch + * @param bitmap bitmap of which validators signed the message + */ +struct SignedBridgeMessageBatch { + BridgeMessageBatch batch; + uint256[2] signature; + bytes bitmap; +} + +/** + * @param newValidatorSet new validator set + * @param signature aggregated signature of validators that signed the new validator set + * @param bitmap bitmap of which validators signed the message + */ +struct SignedValidatorSet { + Validator[] newValidatorSet; + uint256[2] signature; + bytes bitmap; +} + interface IValidatorSetStorage { event NewValidatorSet(Validator[] newValidatorSet); diff --git a/docs/blade/BridgeStorage.md b/docs/blade/BridgeStorage.md index 904de0c8..32985fb3 100644 --- a/docs/blade/BridgeStorage.md +++ b/docs/blade/BridgeStorage.md @@ -149,7 +149,7 @@ function batchCounter() external view returns (uint256) ### batches ```solidity -function batches(uint256) external view returns (uint256 sourceChainId, uint256 destinationChainId) +function batches(uint256) external view returns (struct BridgeMessageBatch batch, bytes bitmap) ``` @@ -166,8 +166,8 @@ function batches(uint256) external view returns (uint256 sourceChainId, uint256 | Name | Type | Description | |---|---|---| -| sourceChainId | uint256 | undefined | -| destinationChainId | uint256 | undefined | +| batch | BridgeMessageBatch | undefined | +| bitmap | bytes | undefined | ### bls @@ -239,6 +239,28 @@ function commitValidatorSet(Validator[] newValidatorSet, uint256[2] signature, b | signature | uint256[2] | undefined | | bitmap | bytes | undefined | +### commitedValidatorSets + +```solidity +function commitedValidatorSets(uint256) external view returns (bytes bitmap) +``` + + + + + +#### Parameters + +| Name | Type | Description | +|---|---|---| +| _0 | uint256 | undefined | + +#### Returns + +| Name | Type | Description | +|---|---|---| +| bitmap | bytes | undefined | + ### currentValidatorSet ```solidity @@ -369,6 +391,23 @@ function totalVotingPower() external view returns (uint256) +#### Returns + +| Name | Type | Description | +|---|---|---| +| _0 | uint256 | undefined | + +### validatorSetCounter + +```solidity +function validatorSetCounter() external view returns (uint256) +``` + + + + + + #### Returns | Name | Type | Description |