From 773e7f26d89c513a81f7d61ac8db36e7b11ee592 Mon Sep 17 00:00:00 2001 From: echo Date: Wed, 19 Jun 2024 10:45:53 +0800 Subject: [PATCH 01/11] audit fix --- src/collator/CollatorSet.sol | 6 ++-- src/collator/CollatorStakingHub.sol | 15 ++++++---- src/collator/CollatorStakingHubStorage.sol | 6 ++-- test/collator/CollatorStakingHub.t.sol | 32 ++++++++++++++++++---- test/deposit/Deposit.t.sol | 4 ++- 5 files changed, 47 insertions(+), 16 deletions(-) diff --git a/src/collator/CollatorSet.sol b/src/collator/CollatorSet.sol index 7b0b057..5034383 100644 --- a/src/collator/CollatorSet.sol +++ b/src/collator/CollatorSet.sol @@ -45,7 +45,7 @@ abstract contract CollatorSet is Initializable, CollatorStakingHubStorage { address next = collators[prev]; // No duplicate collator allowed. require(collators[cur] == address(0), "!cur"); - // Next collaotr must in the list. + // Next collator must in the list. require(next != address(0), "!prev"); require(_verifyIndex(prev, votes, next), "!votes"); collators[cur] = next; @@ -77,10 +77,10 @@ abstract contract CollatorSet is Initializable, CollatorStakingHubStorage { function _updateVotes(address cur, uint256 newVotes, address oldPrev, address newPrev) internal { require(_isValid(cur), "!valid"); require(collators[cur] != address(0), "!cur"); - require(collators[oldPrev] != address(0), "!oldPrev"); + require(collators[oldPrev] != address(0), "!oldPrev1"); require(collators[newPrev] != address(0), "!newPrev"); if (oldPrev == newPrev) { - require(_isPrevCollator(cur, oldPrev), "!oldPrev"); + require(_isPrevCollator(cur, oldPrev), "!oldPrev2"); require(_verifyIndex(newPrev, newVotes, collators[cur]), "!votes"); votesOf[cur] = newVotes; } else { diff --git a/src/collator/CollatorStakingHub.sol b/src/collator/CollatorStakingHub.sol index 516feb7..e2a5d71 100644 --- a/src/collator/CollatorStakingHub.sol +++ b/src/collator/CollatorStakingHub.sol @@ -18,7 +18,9 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { using EnumerableSet for EnumerableSet.UintSet; // The lock-up period starts with the stake or inscrease stake. - uint256 public constant LOCK_PERIOD = 1 days; + uint256 public constant STAKING_LOCK_PERIOD = 1 days; + // The lock-up period starts with the collator commsission update; + uint256 public constant COMMISSION_LOCK_PERIOD = 7 days; // Staking Pallet Account. address public constant STAKING_PALLET = 0x6D6F646C64612f7374616B690000000000000000; // 0 ~ 100 @@ -65,7 +67,7 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { } function _stake(address collator, address account, uint256 assets) internal { - stakingLocks[collator][account] = LOCK_PERIOD + block.timestamp; + stakingLocks[collator][account] = STAKING_LOCK_PERIOD + block.timestamp; address pool = poolOf[collator]; require(pool != address(0), "!collator"); INominationPool(pool).stake(account, assets); @@ -91,14 +93,14 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { function stakeRING(address collator, address oldPrev, address newPrev) public payable nonReentrant { _stake(collator, msg.sender, msg.value); _increaseVotes(collator, _assetsToVotes(commissionOf[collator], msg.value), oldPrev, newPrev); - stakedRINGOf[msg.sender] += msg.value; + stakedRINGOf[collator][msg.sender] += msg.value; } function unstakeRING(address collator, uint256 assets, address oldPrev, address newPrev) public nonReentrant { _unstake(collator, msg.sender, assets); payable(msg.sender).sendValue(assets); _reduceVotes(collator, _assetsToVotes(commissionOf[collator], assets), oldPrev, newPrev); - stakedRINGOf[msg.sender] -= assets; + stakedRINGOf[collator][msg.sender] -= assets; } function stakeDeposit(address collator, uint256 depositId, address oldPrev, address newPrev) public nonReentrant { @@ -127,9 +129,12 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { function collect(uint256 commission, address oldPrev, address newPrev) public nonReentrant { address collator = msg.sender; require(poolOf[collator] != address(0), "!collator"); + require(commissionLocks[collator] < block.timestamp, "!locked"); + require(commissionOf[collator] != commission, "same"); _removeCollator(collator, oldPrev); _collect(collator, commission); _addCollator(collator, _assetsToVotes(commission, stakedOf(collator)), newPrev); + commissionLocks[collator] = COMMISSION_LOCK_PERIOD + block.timestamp; } /// @dev Distribute collator reward from Staking Pallet Account. @@ -152,7 +157,7 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { } function _collect(address collator, uint256 commission) internal { - require(commission <= COMMISSION_BASE); + require(commission <= COMMISSION_BASE, "!commission"); commissionOf[collator] = commission; emit CommissionUpdated(collator, commission); } diff --git a/src/collator/CollatorStakingHubStorage.sol b/src/collator/CollatorStakingHubStorage.sol index 1df39cd..2e98e6f 100644 --- a/src/collator/CollatorStakingHubStorage.sol +++ b/src/collator/CollatorStakingHubStorage.sol @@ -23,8 +23,10 @@ contract CollatorStakingHubStorage { mapping(address => uint256) public commissionOf; // collator => user => lockTime mapping(address => mapping(address => uint256)) public stakingLocks; - // user => staked ring - mapping(address => uint256) public stakedRINGOf; + // collator => lockTime + mapping(address => uint256) public commissionLocks; + // user => collaotr => staked ring + mapping(address => mapping(address => uint256)) public stakedRINGOf; // user => staked depositIds mapping(address => EnumerableSet.UintSet) internal _stakedDeposits; diff --git a/test/collator/CollatorStakingHub.t.sol b/test/collator/CollatorStakingHub.t.sol index bc48664..6a4bb25 100644 --- a/test/collator/CollatorStakingHub.t.sol +++ b/test/collator/CollatorStakingHub.t.sol @@ -70,6 +70,28 @@ contract CollatorStakingHubTest is Test { assertEq(hub.stakedOf(charleth), 0); } + function test_collect() public { + vm.prank(alith); + address a = hub.createNominationPool(HEAD, 1); + + vm.prank(alith); + vm.expectRevert(bytes("same")); + hub.collect(1, HEAD, HEAD); + + vm.prank(alith); + hub.collect(2, HEAD, HEAD); + assertEq(hub.commissionOf(alith), 2); + + vm.prank(alith); + vm.expectRevert("!locked"); + hub.collect(3, HEAD, HEAD); + + vm.warp(block.timestamp + hub.COMMISSION_LOCK_PERIOD() + 1); + vm.prank(alith); + hub.collect(3, HEAD, HEAD); + assertEq(hub.commissionOf(alith), 3); + } + function test_stakeRING() public { uint256 stake = 1 ether; vm.prank(alith); @@ -78,7 +100,7 @@ contract CollatorStakingHubTest is Test { vm.deal(alice, stake); vm.prank(alice); hub.stakeRING{value: stake}(alith, HEAD, HEAD); - assertEq(hub.stakedRINGOf(alice), stake); + assertEq(hub.stakedRINGOf(alith, alice), stake); assertEq(NominationPool(a).balanceOf(alice), stake); assertEq(hub.votesOf(alith), stake * (100 - commissoin) / 100); assertEq(hub.stakedOf(alith), stake); @@ -117,9 +139,9 @@ contract CollatorStakingHubTest is Test { vm.deal(alice, stake); vm.prank(alice); hub.stakeRING{value: stake}(alith, HEAD, HEAD); - assertEq(hub.stakingLocks(alith, alice), hub.LOCK_PERIOD() + block.timestamp); + assertEq(hub.stakingLocks(alith, alice), hub.STAKING_LOCK_PERIOD() + block.timestamp); - vm.warp(block.timestamp + hub.LOCK_PERIOD() + 1); + vm.warp(block.timestamp + hub.STAKING_LOCK_PERIOD() + 1); vm.prank(alice); hub.unstakeRING(alith, stake, HEAD, HEAD); @@ -142,7 +164,7 @@ contract CollatorStakingHubTest is Test { Deposit(deposit).approve(address(hub), id); vm.prank(alice); hub.stakeDeposit(alith, id, HEAD, HEAD); - assertEq(hub.stakingLocks(alith, alice), hub.LOCK_PERIOD() + block.timestamp); + assertEq(hub.stakingLocks(alith, alice), hub.STAKING_LOCK_PERIOD() + block.timestamp); (address account, uint256 assets, address collator) = hub.depositInfos(id); assertEq(account, alice); assertEq(assets, stake); @@ -174,7 +196,7 @@ contract CollatorStakingHubTest is Test { vm.prank(alice); hub.stakeDeposit(alith, id, HEAD, HEAD); - vm.warp(block.timestamp + hub.LOCK_PERIOD() + 1); + vm.warp(block.timestamp + hub.STAKING_LOCK_PERIOD() + 1); vm.prank(alice); hub.unstakeDeposit(id, HEAD, HEAD); diff --git a/test/deposit/Deposit.t.sol b/test/deposit/Deposit.t.sol index 1f3aff5..65ce5e5 100644 --- a/test/deposit/Deposit.t.sol +++ b/test/deposit/Deposit.t.sol @@ -38,7 +38,9 @@ contract DepositTest is Test, ERC721Holder { uint256 id = Deposit(deposit).deposit{value: 1 ether}(1); assertEq(IERC721(deposit).balanceOf(self), 1); assertEq(IERC721(deposit).ownerOf(id), self); - assertEq(IERC721Metadata(deposit).tokenURI(id), ""); + assertEq( + IERC721Metadata(deposit).tokenURI(id), "ipfs://bafybeih57kauz6npkbafh2x3cv3hyljcakdccuckb4huwnwxxxrtqr5pqe" + ); assertEq(IERC721Enumerable(deposit).tokenOfOwnerByIndex(self, 0), id); assertEq(IERC721Enumerable(deposit).tokenByIndex(0), id); assertEq(IERC721Enumerable(deposit).totalSupply(), 1); From 94b4971a6abf4913e1d22daa450ccfc8905425a5 Mon Sep 17 00:00:00 2001 From: echo Date: Wed, 19 Jun 2024 10:47:51 +0800 Subject: [PATCH 02/11] change voting period --- src/governance/RingDAO.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/governance/RingDAO.sol b/src/governance/RingDAO.sol index 28117cd..652c15a 100644 --- a/src/governance/RingDAO.sol +++ b/src/governance/RingDAO.sol @@ -26,7 +26,7 @@ contract RingDAO is initializer { __Governor_init(name); - __GovernorSettings_init(1 days, 2 weeks, 1_000_000 * 1e18); + __GovernorSettings_init(1 days, 30 days, 1_000_000 * 1e18); __GovernorCountingSimple_init(); __GovernorVotes_init(_token); __GovernorTimelockControl_init(_timelock); From 7009e7d663fdef0d0dd0170cd13c6565c5c4b160 Mon Sep 17 00:00:00 2001 From: echo Date: Wed, 19 Jun 2024 11:06:11 +0800 Subject: [PATCH 03/11] fix kton interest --- src/deposit/Deposit.sol | 2 +- test/deposit/Deposit.t.sol | 5 +++-- 2 files changed, 4 insertions(+), 3 deletions(-) diff --git a/src/deposit/Deposit.sol b/src/deposit/Deposit.sol index f31b3f8..31fd8bc 100644 --- a/src/deposit/Deposit.sol +++ b/src/deposit/Deposit.sol @@ -169,7 +169,7 @@ contract Deposit is function computeInterest(uint256 value, uint256 months) public view returns (uint256) { uint256 interest = INTERESTS[months]; - return value * interest / 10_000; + return value * interest / 10_000 / 10_000; } function isClaimRequirePenalty(uint256 id) public view returns (bool) { diff --git a/test/deposit/Deposit.t.sol b/test/deposit/Deposit.t.sol index 65ce5e5..74bbfc9 100644 --- a/test/deposit/Deposit.t.sol +++ b/test/deposit/Deposit.t.sol @@ -79,8 +79,9 @@ contract DepositTest is Test, ERC721Holder { for (uint256 m = 1; m < 37; m++) { uint256 interest = Deposit(deposit).INTERESTS(m); - safeconsole.log(_computeInterest(UNIT, m)); - // assertEq(Deposit(deposit).computeInterest(UNIT, m), _computeInterest(UNIT, m)); + // safeconsole.log(_computeInterest(UNIT, m)); + // safeconsole.log(Deposit(deposit).computeInterest(UNIT, m)); + assertEq(Deposit(deposit).computeInterest(UNIT, m) / 10000000000, _computeInterest(UNIT, m) / 10000000000); } } From d6d42d5192a12fe2044d8c85aaa3f75a90513adf Mon Sep 17 00:00:00 2001 From: echo Date: Wed, 19 Jun 2024 13:59:57 +0800 Subject: [PATCH 04/11] fix test --- test/deposit/Deposit.t.sol | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/deposit/Deposit.t.sol b/test/deposit/Deposit.t.sol index 74bbfc9..928db01 100644 --- a/test/deposit/Deposit.t.sol +++ b/test/deposit/Deposit.t.sol @@ -44,7 +44,7 @@ contract DepositTest is Test, ERC721Holder { assertEq(IERC721Enumerable(deposit).tokenOfOwnerByIndex(self, 0), id); assertEq(IERC721Enumerable(deposit).tokenByIndex(0), id); assertEq(IERC721Enumerable(deposit).totalSupply(), 1); - assertEq(IERC20(KTON).balanceOf(self), 7.61e16); + assertEq(IERC20(KTON).balanceOf(self), 7.61e12); assertEq(Deposit(deposit).assetsOf(id), 1 ether); assertEq(Deposit(deposit).isClaimRequirePenalty(id), true); } From aa20764e4cfc3e92dcdd3a14e2b293e574ab6280 Mon Sep 17 00:00:00 2001 From: echo Date: Thu, 20 Jun 2024 15:06:24 +0800 Subject: [PATCH 05/11] little change --- src/collator/NominationPool.sol | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/collator/NominationPool.sol b/src/collator/NominationPool.sol index d00fe8d..1b92258 100644 --- a/src/collator/NominationPool.sol +++ b/src/collator/NominationPool.sol @@ -76,14 +76,14 @@ contract NominationPool { function stake(address account, uint256 amount) external onlyHub updateReward(account) { require(amount > 0, "Cannot stake 0"); - _totalSupply = _totalSupply + amount; + _totalSupply += amount; _balances[account] += amount; emit Staked(account, amount); } function withdraw(address account, uint256 amount) public onlyHub updateReward(account) { require(amount > 0, "Cannot withdraw 0"); - _totalSupply = _totalSupply - amount; + _totalSupply -= amount; _balances[account] -= amount; emit Withdrawn(account, amount); } From 972063ca28d53247c58b8816db25b7544c9ba3a0 Mon Sep 17 00:00:00 2001 From: echo Date: Fri, 21 Jun 2024 09:45:40 +0800 Subject: [PATCH 06/11] fix --- .github/workflows/ci.yml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index fa55166..cd81a50 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -32,6 +32,9 @@ jobs: with: version: nightly + - name: Install Dependencies + run: yarn --frozen-lockfile + - name: Run Forge build run: | forge --version From 5298ca9a012edd15b9653bc6c49cefd6b36add29 Mon Sep 17 00:00:00 2001 From: echo Date: Mon, 24 Jun 2024 14:33:47 +0800 Subject: [PATCH 07/11] RingDAO init params --- script/Deploy.s.sol | 10 +++++++++- src/governance/RingDAO.sol | 14 +++++++++----- 2 files changed, 18 insertions(+), 6 deletions(-) diff --git a/script/Deploy.s.sol b/script/Deploy.s.sol index 3d32337..968e343 100644 --- a/script/Deploy.s.sol +++ b/script/Deploy.s.sol @@ -49,7 +49,15 @@ contract DeployScript is Script { "RingDAO.sol:RingDAO", timelock, abi.encodeCall( - RingDAO.initialize, (IVotes(gRING), TimelockControllerUpgradeable(payable(timelock)), "RingDAO") + RingDAO.initialize, + ( + IVotes(gRING), + TimelockControllerUpgradeable(payable(timelock)), + 1 days, + 30 days, + 1_000_000 * 1e18, + "RingDAO" + ) ) ); safeconsole.log("RingDAO: ", ringDAO); diff --git a/src/governance/RingDAO.sol b/src/governance/RingDAO.sol index 652c15a..dcd4263 100644 --- a/src/governance/RingDAO.sol +++ b/src/governance/RingDAO.sol @@ -21,12 +21,16 @@ contract RingDAO is _disableInitializers(); } - function initialize(IVotes _token, TimelockControllerUpgradeable _timelock, string memory name) - public - initializer - { + function initialize( + IVotes _token, + TimelockControllerUpgradeable _timelock, + uint48 initialVotingDelay, + uint32 initialVotingPeriod, + uint256 initialProposalThreshold, + string memory name + ) public initializer { __Governor_init(name); - __GovernorSettings_init(1 days, 30 days, 1_000_000 * 1e18); + __GovernorSettings_init(initialVotingDelay, initialVotingPeriod, initialProposalThreshold); __GovernorCountingSimple_init(); __GovernorVotes_init(_token); __GovernorTimelockControl_init(_timelock); From 4502f8485813cf931404afca7944c67067edf8ad Mon Sep 17 00:00:00 2001 From: echo Date: Mon, 24 Jun 2024 14:34:29 +0800 Subject: [PATCH 08/11] fmt --- src/governance/RingDAO.sol | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/governance/RingDAO.sol b/src/governance/RingDAO.sol index dcd4263..f998bc1 100644 --- a/src/governance/RingDAO.sol +++ b/src/governance/RingDAO.sol @@ -22,8 +22,8 @@ contract RingDAO is } function initialize( - IVotes _token, - TimelockControllerUpgradeable _timelock, + IVotes token, + TimelockControllerUpgradeable timelock, uint48 initialVotingDelay, uint32 initialVotingPeriod, uint256 initialProposalThreshold, @@ -32,8 +32,8 @@ contract RingDAO is __Governor_init(name); __GovernorSettings_init(initialVotingDelay, initialVotingPeriod, initialProposalThreshold); __GovernorCountingSimple_init(); - __GovernorVotes_init(_token); - __GovernorTimelockControl_init(_timelock); + __GovernorVotes_init(token); + __GovernorTimelockControl_init(timelock); } // The following functions are overrides required by Solidity. From 5a0b2ae4b83f049a62f38c9596c9b6f2e065e6ba Mon Sep 17 00:00:00 2001 From: echo Date: Mon, 24 Jun 2024 16:12:15 +0800 Subject: [PATCH 09/11] access control enumerable upgradeable --- src/governance/RingTimelockController.sol | 30 ++++++++++++++++++++++- 1 file changed, 29 insertions(+), 1 deletion(-) diff --git a/src/governance/RingTimelockController.sol b/src/governance/RingTimelockController.sol index e610ea5..ea786b3 100644 --- a/src/governance/RingTimelockController.sol +++ b/src/governance/RingTimelockController.sol @@ -3,12 +3,40 @@ pragma solidity 0.8.20; import "@openzeppelin/contracts-upgradeable/proxy/utils/Initializable.sol"; import "@openzeppelin/contracts-upgradeable/governance/TimelockControllerUpgradeable.sol"; +import "@openzeppelin/contracts-upgradeable/access/extensions/AccessControlEnumerableUpgradeable.sol"; -contract RingTimelockController is Initializable, TimelockControllerUpgradeable { +contract RingTimelockController is Initializable, TimelockControllerUpgradeable, AccessControlEnumerableUpgradeable { function initialize(uint256 minDelay, address[] memory proposers, address[] memory executors, address admin) public initializer { __TimelockController_init(minDelay, proposers, executors, admin); + __AccessControlEnumerable_init(); + } + + function _grantRole(bytes32 role, address account) + internal + override(AccessControlUpgradeable, AccessControlEnumerableUpgradeable) + returns (bool) + { + return super._grantRole(role, account); + } + + function _revokeRole(bytes32 role, address account) + internal + override(AccessControlUpgradeable, AccessControlEnumerableUpgradeable) + returns (bool) + { + return super._revokeRole(role, account); + } + + function supportsInterface(bytes4 interfaceId) + public + view + virtual + override(TimelockControllerUpgradeable, AccessControlEnumerableUpgradeable) + returns (bool) + { + return super.supportsInterface(interfaceId); } } From 1201064110e2e20f0e75dbf0ece2d56de843ebc4 Mon Sep 17 00:00:00 2001 From: echo Date: Mon, 24 Jun 2024 16:30:28 +0800 Subject: [PATCH 10/11] update deploy script --- foundry.toml | 2 +- script/Deploy.s.sol | 47 +++++++++++++++------------- src/governance/GovernanceRing.sol | 8 ++++- test/governance/GovernanceRing.t.sol | 4 +-- 4 files changed, 35 insertions(+), 26 deletions(-) diff --git a/foundry.toml b/foundry.toml index 37701ca..c84ce9e 100644 --- a/foundry.toml +++ b/foundry.toml @@ -2,7 +2,7 @@ src = "src" out = "out" libs = ["lib"] -sender = "0x94655E3Af9AbCe0806254574903f174b91305Aa1" +sender = "0xb34Fcb159951e6EBBeF063eCB21C1c6aa65729E7" force = true ffi = true ast = true diff --git a/script/Deploy.s.sol b/script/Deploy.s.sol index 968e343..c6d12a4 100644 --- a/script/Deploy.s.sol +++ b/script/Deploy.s.sol @@ -13,6 +13,12 @@ import {GovernanceRing} from "../src/governance/GovernanceRing.sol"; import {RingDAO, IVotes, TimelockControllerUpgradeable} from "../src/governance/RingDAO.sol"; contract DeployScript is Script { + address deposit = 0x0634cf1c19Ce993A468Fa7c362208141C854736c; + address timelock = 0xDAE15e7DA1C998a650796541DF6fFEB437cC20E4; + address gRING = 0x4Ef76E24851f694BEe6a64F6345b873081d4F308; + address ringDAO = 0x3aaF69F34AA8527b4CEe546DD691aD24c1fB7AEa; + address hub = 0xD497EF1C7A8732e0761d57429Df5edc17fEaD6e6; + function setUp() public {} function run() public { @@ -22,30 +28,33 @@ contract DeployScript is Script { address multisig = 0x040f331774Ed6BB161412B4cEDb1358B382aF3A5; safeconsole.log("Multisig: ", multisig); - address deposit = Upgrades.deployTransparentProxy( + address deposit_PROXY = Upgrades.deployTransparentProxy( "Deposit.sol:Deposit", multisig, abi.encodeCall(Deposit.initialize, ("RING Deposit NFT", "RDPS")) ); - safeconsole.log("Depoist: ", deposit); - safeconsole.log("Depoist_Logic: ", Upgrades.getImplementationAddress(deposit)); + safeconsole.log("Depoist: ", deposit_PROXY); + safeconsole.log("Depoist_Logic: ", Upgrades.getImplementationAddress(deposit_PROXY)); uint256 minDelay = 3 days; - address timelock = Upgrades.deployTransparentProxy( + + address[] memory proposers = new address[](1); + proposers[0] = ringDAO; + address timelock_PROXY = Upgrades.deployTransparentProxy( "RingTimelockController.sol:RingTimelockController", multisig, - abi.encodeCall(RingTimelockController.initialize, (minDelay, new address[](0), new address[](0), multisig)) + abi.encodeCall(RingTimelockController.initialize, (minDelay, proposers, new address[](0), multisig)) ); - safeconsole.log("Timelock: ", timelock); - safeconsole.log("Timelock_Logic: ", Upgrades.getImplementationAddress(timelock)); + safeconsole.log("Timelock: ", timelock_PROXY); + safeconsole.log("Timelock_Logic: ", Upgrades.getImplementationAddress(timelock_PROXY)); - address gRING = Upgrades.deployTransparentProxy( + address gRING_PROXY = Upgrades.deployTransparentProxy( "GovernanceRing.sol:GovernanceRing", timelock, - abi.encodeCall(GovernanceRing.initialize, (multisig, deposit, "Governance RING", "gRING")) + abi.encodeCall(GovernanceRing.initialize, (multisig, hub, deposit, "Governance RING", "gRING")) ); - safeconsole.log("gRING: ", gRING); - safeconsole.log("gRING_Logic: ", Upgrades.getImplementationAddress(gRING)); + safeconsole.log("gRING: ", gRING_PROXY); + safeconsole.log("gRING_Logic: ", Upgrades.getImplementationAddress(gRING_PROXY)); - address ringDAO = Upgrades.deployTransparentProxy( + address ringDAO_PROXY = Upgrades.deployTransparentProxy( "RingDAO.sol:RingDAO", timelock, abi.encodeCall( @@ -60,20 +69,16 @@ contract DeployScript is Script { ) ) ); - safeconsole.log("RingDAO: ", ringDAO); - safeconsole.log("RingDAO_Logic: ", Upgrades.getImplementationAddress(ringDAO)); + safeconsole.log("RingDAO: ", ringDAO_PROXY); + safeconsole.log("RingDAO_Logic: ", Upgrades.getImplementationAddress(ringDAO_PROXY)); - address hub = Upgrades.deployTransparentProxy( + address hub_PROXY = Upgrades.deployTransparentProxy( "CollatorStakingHub.sol:CollatorStakingHub", timelock, abi.encodeCall(CollatorStakingHub.initialize, (gRING, deposit)) ); - safeconsole.log("Hub: ", hub); - safeconsole.log("Hub_Logic: ", Upgrades.getImplementationAddress(hub)); - - // RingTimelockController(timelock).grantRole(RingTimelockController(timelock).PROPOSER_ROLE(), ringDAO); - // RingTimelockController(gRING).grantRole(GovernanceRing(gRING).MINTER_ROLE(), hub); - // RingTimelockController(gRING).grantRole(GovernanceRing(gRING).BURNER_ROLE(), hub); + safeconsole.log("Hub: ", hub_PROXY); + safeconsole.log("Hub_Logic: ", Upgrades.getImplementationAddress(hub_PROXY)); vm.stopBroadcast(); } diff --git a/src/governance/GovernanceRing.sol b/src/governance/GovernanceRing.sol index ab4786a..ccc5483 100644 --- a/src/governance/GovernanceRing.sol +++ b/src/governance/GovernanceRing.sol @@ -40,7 +40,10 @@ contract GovernanceRing is event WrapDeposit(address indexed account, address indexed token, uint256 depositId); event UnwrapDeposit(address indexed account, address indexed token, uint256 depositId); - function initialize(address admin, address dps, string memory name, string memory symbol) public initializer { + function initialize(address admin, address hub, address dps, string memory name, string memory symbol) + public + initializer + { DEPOSIT = IDeposit(dps); __ERC20_init(name, symbol); __AccessControlEnumerable_init(); @@ -49,6 +52,9 @@ contract GovernanceRing is __ReentrancyGuard_init(); _grantRole(DEFAULT_ADMIN_ROLE, admin); + + _grantRole(MINTER_ROLE, hub); + _grantRole(BURNER_ROLE, hub); } /// @custom:oz-upgrades-unsafe-allow constructor diff --git a/test/governance/GovernanceRing.t.sol b/test/governance/GovernanceRing.t.sol index ea70265..82b1e3e 100644 --- a/test/governance/GovernanceRing.t.sol +++ b/test/governance/GovernanceRing.t.sol @@ -25,11 +25,9 @@ contract GovernanceRingTest is Test { Upgrades.deployTransparentProxy( "GovernanceRing.sol:GovernanceRing", msg.sender, - abi.encodeCall(GovernanceRing.initialize, (self, deposit, name, symbol)) + abi.encodeCall(GovernanceRing.initialize, (self, self, deposit, name, symbol)) ) ); - gRING.grantRole(gRING.MINTER_ROLE(), self); - gRING.grantRole(gRING.BURNER_ROLE(), self); } function test_initialize() public view { From db3ced4a2d188ef315320ab544c2b1c8a16050b8 Mon Sep 17 00:00:00 2001 From: echo Date: Tue, 25 Jun 2024 18:00:17 +0800 Subject: [PATCH 11/11] typo --- src/collator/CollatorStakingHub.sol | 8 ++++---- src/collator/CollatorStakingHubStorage.sol | 6 +++--- test/collator/CollatorStakingHub.t.sol | 8 ++++---- 3 files changed, 11 insertions(+), 11 deletions(-) diff --git a/src/collator/CollatorStakingHub.sol b/src/collator/CollatorStakingHub.sol index e2a5d71..27f407a 100644 --- a/src/collator/CollatorStakingHub.sol +++ b/src/collator/CollatorStakingHub.sol @@ -62,7 +62,7 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { poolOf[collator] = pool; _addCollator(collator, 0, prev); - _collect(collator, commission); + _collate(collator, commission); emit NominationPoolCreated(pool, collator, prev); } @@ -126,13 +126,13 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { require(_stakedDeposits[account].remove(depositId), "!remove"); } - function collect(uint256 commission, address oldPrev, address newPrev) public nonReentrant { + function collate(uint256 commission, address oldPrev, address newPrev) public nonReentrant { address collator = msg.sender; require(poolOf[collator] != address(0), "!collator"); require(commissionLocks[collator] < block.timestamp, "!locked"); require(commissionOf[collator] != commission, "same"); _removeCollator(collator, oldPrev); - _collect(collator, commission); + _collate(collator, commission); _addCollator(collator, _assetsToVotes(commission, stakedOf(collator)), newPrev); commissionLocks[collator] = COMMISSION_LOCK_PERIOD + block.timestamp; } @@ -156,7 +156,7 @@ contract CollatorStakingHub is ReentrancyGuardUpgradeable, CollatorSet { return INominationPool(pool).totalSupply(); } - function _collect(address collator, uint256 commission) internal { + function _collate(address collator, uint256 commission) internal { require(commission <= COMMISSION_BASE, "!commission"); commissionOf[collator] = commission; emit CommissionUpdated(collator, commission); diff --git a/src/collator/CollatorStakingHubStorage.sol b/src/collator/CollatorStakingHubStorage.sol index 2e98e6f..a4c850e 100644 --- a/src/collator/CollatorStakingHubStorage.sol +++ b/src/collator/CollatorStakingHubStorage.sol @@ -21,11 +21,11 @@ contract CollatorStakingHubStorage { mapping(address => address) public poolOf; // collator => commission mapping(address => uint256) public commissionOf; - // collator => user => lockTime + // collator => user => stakingLockTime mapping(address => mapping(address => uint256)) public stakingLocks; - // collator => lockTime + // collator => commissonLockTime mapping(address => uint256) public commissionLocks; - // user => collaotr => staked ring + // user => collator => staked ring mapping(address => mapping(address => uint256)) public stakedRINGOf; // user => staked depositIds mapping(address => EnumerableSet.UintSet) internal _stakedDeposits; diff --git a/test/collator/CollatorStakingHub.t.sol b/test/collator/CollatorStakingHub.t.sol index 6a4bb25..1d5cc99 100644 --- a/test/collator/CollatorStakingHub.t.sol +++ b/test/collator/CollatorStakingHub.t.sol @@ -76,19 +76,19 @@ contract CollatorStakingHubTest is Test { vm.prank(alith); vm.expectRevert(bytes("same")); - hub.collect(1, HEAD, HEAD); + hub.collate(1, HEAD, HEAD); vm.prank(alith); - hub.collect(2, HEAD, HEAD); + hub.collate(2, HEAD, HEAD); assertEq(hub.commissionOf(alith), 2); vm.prank(alith); vm.expectRevert("!locked"); - hub.collect(3, HEAD, HEAD); + hub.collate(3, HEAD, HEAD); vm.warp(block.timestamp + hub.COMMISSION_LOCK_PERIOD() + 1); vm.prank(alith); - hub.collect(3, HEAD, HEAD); + hub.collate(3, HEAD, HEAD); assertEq(hub.commissionOf(alith), 3); }