From 1282aeb2c31c6430e6497044a177e3c5a82a8941 Mon Sep 17 00:00:00 2001 From: Kresh Date: Tue, 2 Jul 2024 12:08:29 +0400 Subject: [PATCH] complete vault tests --- src/contracts/delegator/BaseDelegator.sol | 4 +- .../delegator/FullRestakeDelegator.sol | 17 +- .../delegator/NetworkRestakeDelegator.sol | 18 +- src/contracts/vault/Vault.sol | 14 +- .../delegator/IFullRestakeDelegator.sol | 1 + .../delegator/INetworkRestakeDelegator.sol | 1 + test/vault/Vault.t.sol | 381 +++++++++++++++--- 7 files changed, 381 insertions(+), 55 deletions(-) diff --git a/src/contracts/delegator/BaseDelegator.sol b/src/contracts/delegator/BaseDelegator.sol index 278aecb5..b262c391 100644 --- a/src/contracts/delegator/BaseDelegator.sol +++ b/src/contracts/delegator/BaseDelegator.sol @@ -176,6 +176,8 @@ contract BaseDelegator is Entity, AccessControlUpgradeable, IBaseDelegator { IBaseDelegator.BaseParams memory baseParams = _initializeInternal(vault_, data_); - _grantRole(DEFAULT_ADMIN_ROLE, baseParams.defaultAdminRoleHolder); + if (baseParams.defaultAdminRoleHolder != address(0)) { + _grantRole(DEFAULT_ADMIN_ROLE, baseParams.defaultAdminRoleHolder); + } } } diff --git a/src/contracts/delegator/FullRestakeDelegator.sol b/src/contracts/delegator/FullRestakeDelegator.sol index 076706f5..a1281184 100644 --- a/src/contracts/delegator/FullRestakeDelegator.sol +++ b/src/contracts/delegator/FullRestakeDelegator.sol @@ -214,8 +214,21 @@ contract FullRestakeDelegator is BaseDelegator, IFullRestakeDelegator { ) internal override returns (IBaseDelegator.BaseParams memory) { InitParams memory params = abi.decode(data, (InitParams)); - _grantRole(NETWORK_LIMIT_SET_ROLE, params.networkLimitSetRoleHolder); - _grantRole(OPERATOR_NETWORK_LIMIT_SET_ROLE, params.operatorNetworkLimitSetRoleHolder); + if ( + params.baseParams.defaultAdminRoleHolder == address(0) + && ( + params.networkLimitSetRoleHolder == address(0) || params.operatorNetworkLimitSetRoleHolder == address(0) + ) + ) { + revert MissingRoleHolders(); + } + + if (params.networkLimitSetRoleHolder != address(0)) { + _grantRole(NETWORK_LIMIT_SET_ROLE, params.networkLimitSetRoleHolder); + } + if (params.operatorNetworkLimitSetRoleHolder != address(0)) { + _grantRole(OPERATOR_NETWORK_LIMIT_SET_ROLE, params.operatorNetworkLimitSetRoleHolder); + } return params.baseParams; } diff --git a/src/contracts/delegator/NetworkRestakeDelegator.sol b/src/contracts/delegator/NetworkRestakeDelegator.sol index 7fcb28aa..e85774e9 100644 --- a/src/contracts/delegator/NetworkRestakeDelegator.sol +++ b/src/contracts/delegator/NetworkRestakeDelegator.sol @@ -214,8 +214,22 @@ contract NetworkRestakeDelegator is BaseDelegator, INetworkRestakeDelegator { ) internal override returns (IBaseDelegator.BaseParams memory) { InitParams memory params = abi.decode(data, (InitParams)); - _grantRole(NETWORK_LIMIT_SET_ROLE, params.networkLimitSetRoleHolder); - _grantRole(OPERATOR_NETWORK_SHARES_SET_ROLE, params.operatorNetworkSharesSetRoleHolder); + if ( + params.baseParams.defaultAdminRoleHolder == address(0) + && ( + params.networkLimitSetRoleHolder == address(0) + || params.operatorNetworkSharesSetRoleHolder == address(0) + ) + ) { + revert MissingRoleHolders(); + } + + if (params.networkLimitSetRoleHolder != address(0)) { + _grantRole(NETWORK_LIMIT_SET_ROLE, params.networkLimitSetRoleHolder); + } + if (params.operatorNetworkSharesSetRoleHolder != address(0)) { + _grantRole(OPERATOR_NETWORK_SHARES_SET_ROLE, params.operatorNetworkSharesSetRoleHolder); + } return params.baseParams; } diff --git a/src/contracts/vault/Vault.sol b/src/contracts/vault/Vault.sol index 0f2f99fc..e217aafd 100644 --- a/src/contracts/vault/Vault.sol +++ b/src/contracts/vault/Vault.sol @@ -246,7 +246,7 @@ contract Vault is VaultStorage, MigratableEntity, AccessControlUpgradeable, IVau * @inheritdoc IVault */ function setSlasher(address slasher_) external onlyRole(SLASHER_SET_ROLE) { - if (!IRegistry(SLASHER_FACTORY).isEntity(slasher_)) { + if (slasher_ != address(0) && !IRegistry(SLASHER_FACTORY).isEntity(slasher_)) { revert NotSlasher(); } @@ -330,10 +330,14 @@ contract Vault is VaultStorage, MigratableEntity, AccessControlUpgradeable, IVau slasherSetEpochsDelay = params.slasherSetEpochsDelay; - _grantRole(DEFAULT_ADMIN_ROLE, params.defaultAdminRoleHolder); + if (params.defaultAdminRoleHolder != address(0)) { + _grantRole(DEFAULT_ADMIN_ROLE, params.defaultAdminRoleHolder); + } if (params.slasher == address(0)) { - _grantRole(SLASHER_SET_ROLE, params.slasherSetRoleHolder); + if (params.slasherSetRoleHolder != address(0)) { + _grantRole(SLASHER_SET_ROLE, params.slasherSetRoleHolder); + } } else { _slasher.address_ = params.slasher; } @@ -341,7 +345,9 @@ contract Vault is VaultStorage, MigratableEntity, AccessControlUpgradeable, IVau if (params.depositWhitelist) { depositWhitelist = true; - _grantRole(DEPOSITOR_WHITELIST_ROLE, params.depositorWhitelistRoleHolder); + if (params.depositorWhitelistRoleHolder != address(0)) { + _grantRole(DEPOSITOR_WHITELIST_ROLE, params.depositorWhitelistRoleHolder); + } } } diff --git a/src/interfaces/delegator/IFullRestakeDelegator.sol b/src/interfaces/delegator/IFullRestakeDelegator.sol index e2f48ffd..532f3202 100644 --- a/src/interfaces/delegator/IFullRestakeDelegator.sol +++ b/src/interfaces/delegator/IFullRestakeDelegator.sol @@ -4,6 +4,7 @@ import {IBaseDelegator} from "./IBaseDelegator.sol"; interface IFullRestakeDelegator is IBaseDelegator { error ExceedsMaxNetworkLimit(); + error MissingRoleHolders(); /** * @notice Initial parameters needed for a full restaking delegator deployment. diff --git a/src/interfaces/delegator/INetworkRestakeDelegator.sol b/src/interfaces/delegator/INetworkRestakeDelegator.sol index bcac11e9..56f34a1f 100644 --- a/src/interfaces/delegator/INetworkRestakeDelegator.sol +++ b/src/interfaces/delegator/INetworkRestakeDelegator.sol @@ -4,6 +4,7 @@ import {IBaseDelegator} from "./IBaseDelegator.sol"; interface INetworkRestakeDelegator is IBaseDelegator { error ExceedsMaxNetworkLimit(); + error MissingRoleHolders(); /** * @notice Initial parameters needed for a full restaking delegator deployment. diff --git a/test/vault/Vault.t.sol b/test/vault/Vault.t.sol index a200525e..87a26fe6 100644 --- a/test/vault/Vault.t.sol +++ b/test/vault/Vault.t.sol @@ -182,6 +182,7 @@ contract VaultTest is Test { assertEq(vault.collateral(), address(collateral)); assertEq(vault.delegator(), delegator_); assertEq(vault.slasher(), address(0)); + assertEq(vault.slasherIn(0), address(0)); assertEq(vault.burner(), burner); assertEq(vault.epochDuration(), epochDuration); assertEq(vault.slasherSetEpochsDelay(), slasherSetEpochsDelay); @@ -248,6 +249,190 @@ contract VaultTest is Test { assertEq(vault.previousEpochStart(), blockTimestamp - (vault.epochDuration() - 1) - vault.epochDuration()); } + function test_CreateRevertInvalidEpochDuration(uint256 slasherSetEpochsDelay) public { + slasherSetEpochsDelay = bound(slasherSetEpochsDelay, 3, 50); + uint48 epochDuration = 0; + + uint64 lastVersion = vaultFactory.lastVersion(); + vm.expectRevert(IVault.InvalidEpochDuration.selector); + vaultConfigurator.create( + IVaultConfigurator.InitParams({ + version: lastVersion, + owner: alice, + vaultParams: IVault.InitParams({ + collateral: address(collateral), + delegator: address(0), + slasher: address(0), + burner: address(0xdEaD), + epochDuration: epochDuration, + slasherSetEpochsDelay: slasherSetEpochsDelay, + depositWhitelist: false, + defaultAdminRoleHolder: alice, + slasherSetRoleHolder: alice, + depositorWhitelistRoleHolder: alice + }), + delegatorIndex: 0, + delegatorParams: abi.encode( + INetworkRestakeDelegator.InitParams({ + baseParams: IBaseDelegator.BaseParams({defaultAdminRoleHolder: alice}), + networkLimitSetRoleHolder: alice, + operatorNetworkSharesSetRoleHolder: alice + }) + ), + withSlasher: false, + slasherIndex: 0, + slasherParams: "" + }) + ); + } + + function test_CreateRevertInvalidCollateral(uint48 epochDuration, uint256 slasherSetEpochsDelay) public { + epochDuration = uint48(bound(epochDuration, 1, 50 weeks)); + slasherSetEpochsDelay = bound(slasherSetEpochsDelay, 3, 50); + + uint64 lastVersion = vaultFactory.lastVersion(); + vm.expectRevert(IVault.InvalidCollateral.selector); + vaultConfigurator.create( + IVaultConfigurator.InitParams({ + version: lastVersion, + owner: alice, + vaultParams: IVault.InitParams({ + collateral: address(0), + delegator: address(0), + slasher: address(0), + burner: address(0xdEaD), + epochDuration: epochDuration, + slasherSetEpochsDelay: slasherSetEpochsDelay, + depositWhitelist: false, + defaultAdminRoleHolder: alice, + slasherSetRoleHolder: alice, + depositorWhitelistRoleHolder: alice + }), + delegatorIndex: 0, + delegatorParams: abi.encode( + INetworkRestakeDelegator.InitParams({ + baseParams: IBaseDelegator.BaseParams({defaultAdminRoleHolder: alice}), + networkLimitSetRoleHolder: alice, + operatorNetworkSharesSetRoleHolder: alice + }) + ), + withSlasher: false, + slasherIndex: 0, + slasherParams: "" + }) + ); + } + + function test_CreateRevertInvalidSlasherSetEpochsDelay( + uint48 epochDuration, + uint256 slasherSetEpochsDelay + ) public { + epochDuration = uint48(bound(epochDuration, 1, 50 weeks)); + slasherSetEpochsDelay = bound(slasherSetEpochsDelay, 0, 2); + + uint64 lastVersion = vaultFactory.lastVersion(); + vm.expectRevert(IVault.InvalidSlasherSetEpochsDelay.selector); + vaultConfigurator.create( + IVaultConfigurator.InitParams({ + version: lastVersion, + owner: alice, + vaultParams: IVault.InitParams({ + collateral: address(collateral), + delegator: address(0), + slasher: address(0), + burner: address(0xdEaD), + epochDuration: epochDuration, + slasherSetEpochsDelay: slasherSetEpochsDelay, + depositWhitelist: false, + defaultAdminRoleHolder: alice, + slasherSetRoleHolder: alice, + depositorWhitelistRoleHolder: alice + }), + delegatorIndex: 0, + delegatorParams: abi.encode( + INetworkRestakeDelegator.InitParams({ + baseParams: IBaseDelegator.BaseParams({defaultAdminRoleHolder: alice}), + networkLimitSetRoleHolder: alice, + operatorNetworkSharesSetRoleHolder: alice + }) + ), + withSlasher: false, + slasherIndex: 0, + slasherParams: "" + }) + ); + } + + function test_CreateRevertNotDelegator(uint48 epochDuration, uint256 slasherSetEpochsDelay) public { + epochDuration = uint48(bound(epochDuration, 1, 50 weeks)); + slasherSetEpochsDelay = bound(slasherSetEpochsDelay, 3, 50); + + uint64 lastVersion = vaultFactory.lastVersion(); + vm.expectRevert(IVault.NotDelegator.selector); + vaultFactory.create( + lastVersion, + alice, + true, + abi.encode( + IVault.InitParams({ + collateral: address(collateral), + delegator: address(0), + slasher: address(0), + burner: address(0xdEaD), + epochDuration: epochDuration, + slasherSetEpochsDelay: slasherSetEpochsDelay, + depositWhitelist: false, + defaultAdminRoleHolder: alice, + slasherSetRoleHolder: alice, + depositorWhitelistRoleHolder: alice + }) + ) + ); + } + + function test_CreateRevertNotSlasher(uint48 epochDuration, uint256 slasherSetEpochsDelay) public { + epochDuration = uint48(bound(epochDuration, 1, 50 weeks)); + slasherSetEpochsDelay = bound(slasherSetEpochsDelay, 3, 50); + + uint64 lastVersion = vaultFactory.lastVersion(); + vault = Vault(vaultFactory.create(lastVersion, alice, false, "")); + + address delegator = delegatorFactory.create( + 0, + true, + abi.encode( + address(vault), + abi.encode( + INetworkRestakeDelegator.InitParams({ + baseParams: IBaseDelegator.BaseParams({defaultAdminRoleHolder: alice}), + networkLimitSetRoleHolder: alice, + operatorNetworkSharesSetRoleHolder: alice + }) + ) + ) + ); + + vm.expectRevert(IVault.NotSlasher.selector); + vault.initialize( + lastVersion, + alice, + abi.encode( + IVault.InitParams({ + collateral: address(collateral), + delegator: delegator, + slasher: address(1), + burner: address(0xdEaD), + epochDuration: epochDuration, + slasherSetEpochsDelay: slasherSetEpochsDelay, + depositWhitelist: false, + defaultAdminRoleHolder: alice, + slasherSetRoleHolder: alice, + depositorWhitelistRoleHolder: alice + }) + ) + ); + } + function test_DepositTwice(uint256 amount1, uint256 amount2) public { amount1 = bound(amount1, 1, 100 * 10 ** 18); amount2 = bound(amount2, 1, 100 * 10 ** 18); @@ -358,9 +543,8 @@ contract VaultTest is Test { assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp - 1)), shares1); assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp)), shares1); assertEq(vault.activeSharesOf(alice), shares1); - (bool checkpointExists, uint48 checkpointKey, uint256 checkpointValue) = + (, uint48 checkpointKey, uint256 checkpointValue) = vault.activeSharesOfCheckpointAt(alice, uint48(blockTimestamp)); - assertEq(checkpointExists, true); assertEq(checkpointKey, blockTimestamp - 1); assertEq(checkpointValue, shares1); assertEq(vault.activeBalanceOfAt(alice, uint48(blockTimestamp - 1)), amount1); @@ -369,9 +553,7 @@ contract VaultTest is Test { assertEq(vault.activeSharesOfAt(bob, uint48(blockTimestamp - 1)), 0); assertEq(vault.activeSharesOfAt(bob, uint48(blockTimestamp)), shares2); assertEq(vault.activeSharesOf(bob), shares2); - (checkpointExists, checkpointKey, checkpointValue) = - vault.activeSharesOfCheckpointAt(bob, uint48(blockTimestamp)); - assertEq(checkpointExists, true); + (, checkpointKey, checkpointValue) = vault.activeSharesOfCheckpointAt(bob, uint48(blockTimestamp)); assertEq(checkpointKey, blockTimestamp); assertEq(checkpointValue, shares2); assertEq(vault.activeBalanceOfAt(bob, uint48(blockTimestamp - 1)), 0); @@ -379,6 +561,18 @@ contract VaultTest is Test { assertEq(vault.activeBalanceOf(bob), amount2); } + function test_DepositRevertInvalidOnBehalfOf(uint256 amount1) public { + amount1 = bound(amount1, 1, 100 * 10 ** 18); + + uint48 epochDuration = 1; + vault = _getVault(epochDuration); + + vm.startPrank(alice); + vm.expectRevert(IVault.InvalidOnBehalfOf.selector); + vault.deposit(address(0), amount1); + vm.stopPrank(); + } + function test_DepositRevertInsufficientDeposit() public { uint48 epochDuration = 1; vault = _getVault(epochDuration); @@ -426,9 +620,8 @@ contract VaultTest is Test { assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp - 1)), shares); assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp)), shares - burnedShares); assertEq(vault.activeSharesOf(alice), shares - burnedShares); - (bool checkpointExists, uint48 checkpointKey, uint256 checkpointValue) = + (, uint48 checkpointKey, uint256 checkpointValue) = vault.activeSharesOfCheckpointAt(alice, uint48(blockTimestamp)); - assertEq(checkpointExists, true); assertEq(checkpointKey, blockTimestamp); assertEq(checkpointValue, shares - burnedShares); assertEq(vault.activeBalanceOfAt(alice, uint48(blockTimestamp - 1)), amount1); @@ -468,9 +661,7 @@ contract VaultTest is Test { assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp - 1)), shares); assertEq(vault.activeSharesOfAt(alice, uint48(blockTimestamp)), shares - burnedShares); assertEq(vault.activeSharesOf(alice), shares - burnedShares); - (checkpointExists, checkpointKey, checkpointValue) = - vault.activeSharesOfCheckpointAt(alice, uint48(blockTimestamp)); - assertEq(checkpointExists, true); + (, checkpointKey, checkpointValue) = vault.activeSharesOfCheckpointAt(alice, uint48(blockTimestamp)); assertEq(checkpointKey, blockTimestamp); assertEq(checkpointValue, shares - burnedShares); assertEq(vault.activeBalanceOfAt(alice, uint48(blockTimestamp - 1)), amount1 - amount2); @@ -508,6 +699,20 @@ contract VaultTest is Test { assertEq(vault.totalSupply(), amount1 - amount2 - amount3); } + function test_WithdrawRevertInvalidClaimer(uint256 amount1) public { + amount1 = bound(amount1, 1, 100 * 10 ** 18); + + uint48 epochDuration = 1; + vault = _getVault(epochDuration); + + _deposit(alice, amount1); + + vm.expectRevert(IVault.InvalidClaimer.selector); + vm.startPrank(alice); + vault.withdraw(address(0), amount1); + vm.stopPrank(); + } + function test_WithdrawRevertInsufficientWithdrawal(uint256 amount1) public { amount1 = bound(amount1, 1, 100 * 10 ** 18); @@ -561,6 +766,33 @@ contract VaultTest is Test { assertEq(vault.isWithdrawalsClaimed(vault.currentEpoch() - 1, alice), true); } + function test_ClaimRevertInvalidRecipient(uint256 amount1, uint256 amount2) public { + amount1 = bound(amount1, 1, 100 * 10 ** 18); + amount2 = bound(amount2, 1, 100 * 10 ** 18); + vm.assume(amount1 >= amount2); + + uint48 epochDuration = 1; + vault = _getVault(epochDuration); + + uint256 blockTimestamp = block.timestamp * block.timestamp / block.timestamp * block.timestamp / block.timestamp; + + _deposit(alice, amount1); + + blockTimestamp = blockTimestamp + 1; + vm.warp(blockTimestamp); + + _withdraw(alice, amount2); + + blockTimestamp = blockTimestamp + 2; + vm.warp(blockTimestamp); + + vm.startPrank(alice); + uint256 currentEpoch = vault.currentEpoch(); + vm.expectRevert(IVault.InvalidRecipient.selector); + vault.claim(address(0), currentEpoch - 1); + vm.stopPrank(); + } + function test_ClaimRevertInvalidEpoch(uint256 amount1, uint256 amount2) public { amount1 = bound(amount1, 1, 100 * 10 ** 18); amount2 = bound(amount2, 1, 100 * 10 ** 18); @@ -638,42 +870,6 @@ contract VaultTest is Test { _claim(alice, currentEpoch - 2); } - function test_CreateRevertInvalidEpochDuration() public { - uint48 epochDuration = 0; - - uint64 lastVersion = vaultFactory.lastVersion(); - vm.expectRevert(IVault.InvalidEpochDuration.selector); - vaultConfigurator.create( - IVaultConfigurator.InitParams({ - version: lastVersion, - owner: alice, - vaultParams: IVault.InitParams({ - collateral: address(collateral), - delegator: address(0), - slasher: address(0), - burner: address(0xdEaD), - epochDuration: epochDuration, - slasherSetEpochsDelay: 3, - depositWhitelist: false, - defaultAdminRoleHolder: alice, - slasherSetRoleHolder: alice, - depositorWhitelistRoleHolder: alice - }), - delegatorIndex: 0, - delegatorParams: abi.encode( - INetworkRestakeDelegator.InitParams({ - baseParams: IBaseDelegator.BaseParams({defaultAdminRoleHolder: alice}), - networkLimitSetRoleHolder: alice, - operatorNetworkSharesSetRoleHolder: alice - }) - ), - withSlasher: false, - slasherIndex: 0, - slasherParams: "" - }) - ); - } - function test_SetDepositWhitelist() public { uint48 epochDuration = 1; @@ -735,6 +931,20 @@ contract VaultTest is Test { _deposit(bob, 1); } + function test_SetDepositorWhitelistStatusRevertInvalidAccount() public { + uint48 epochDuration = 1; + + vault = _getVault(epochDuration); + + _grantDepositWhitelistSetRole(alice, alice); + _setDepositWhitelist(alice, true); + + _grantDepositorWhitelistRole(alice, alice); + + vm.expectRevert(IVault.InvalidAccount.selector); + _setDepositorWhitelistStatus(alice, address(0), true); + } + function test_SetDepositorWhitelistStatusRevertNoDepositWhitelist() public { uint48 epochDuration = 1; @@ -762,6 +972,79 @@ contract VaultTest is Test { _setDepositorWhitelistStatus(alice, bob, true); } + function test_SetSlasher() public { + uint48 epochDuration = 1; + + vault = _getVault(epochDuration); + + address slasher = slasherFactory.create(0, true, abi.encode(address(vault), "")); + + uint256 blockTimestamp = block.timestamp * block.timestamp / block.timestamp * block.timestamp / block.timestamp; + + _setSlasher(alice, slasher); + assertEq(vault.slasher(), address(0)); + assertEq(vault.slasherIn(0), address(0)); + assertEq(vault.slasherIn(1), address(0)); + assertEq(vault.slasherIn(2), address(0)); + assertEq(vault.slasherIn(3), slasher); + assertEq(vault.slasherIn(4), slasher); + + blockTimestamp = blockTimestamp + 1; + vm.warp(blockTimestamp); + + assertEq(vault.slasher(), address(0)); + assertEq(vault.slasherIn(0), address(0)); + assertEq(vault.slasherIn(1), address(0)); + assertEq(vault.slasherIn(2), slasher); + assertEq(vault.slasherIn(3), slasher); + assertEq(vault.slasherIn(4), slasher); + + blockTimestamp = blockTimestamp + 2; + vm.warp(blockTimestamp); + + assertEq(vault.slasher(), slasher); + assertEq(vault.slasherIn(0), slasher); + assertEq(vault.slasherIn(1), slasher); + assertEq(vault.slasherIn(2), slasher); + assertEq(vault.slasherIn(3), slasher); + assertEq(vault.slasherIn(4), slasher); + + _setSlasher(alice, address(0)); + assertEq(vault.slasher(), slasher); + assertEq(vault.slasherIn(0), slasher); + assertEq(vault.slasherIn(1), slasher); + assertEq(vault.slasherIn(2), slasher); + assertEq(vault.slasherIn(3), address(0)); + assertEq(vault.slasherIn(4), address(0)); + + blockTimestamp = blockTimestamp + 2; + vm.warp(blockTimestamp); + + assertEq(vault.slasher(), slasher); + assertEq(vault.slasherIn(0), slasher); + assertEq(vault.slasherIn(1), address(0)); + assertEq(vault.slasherIn(2), address(0)); + assertEq(vault.slasherIn(3), address(0)); + assertEq(vault.slasherIn(4), address(0)); + + _setSlasher(alice, slasher); + assertEq(vault.slasher(), slasher); + assertEq(vault.slasherIn(0), slasher); + assertEq(vault.slasherIn(1), slasher); + assertEq(vault.slasherIn(2), slasher); + assertEq(vault.slasherIn(3), slasher); + assertEq(vault.slasherIn(4), slasher); + } + + function test_SetSlasherRevertNotSlasher() public { + uint48 epochDuration = 1; + + vault = _getVault(epochDuration); + + vm.expectRevert(IVault.NotSlasher.selector); + _setSlasher(alice, address(1)); + } + function _getVault(uint48 epochDuration) internal returns (Vault) { (address vault_,,) = vaultConfigurator.create( IVaultConfigurator.InitParams({ @@ -888,4 +1171,10 @@ contract VaultTest is Test { vault.setDepositorWhitelistStatus(depositor, status); vm.stopPrank(); } + + function _setSlasher(address user, address slasher) internal { + vm.startPrank(user); + vault.setSlasher(slasher); + vm.stopPrank(); + } }