From 2e9dfab97e198119a0f8357957c75035c5cb65d1 Mon Sep 17 00:00:00 2001 From: RiccardoBiosas Date: Wed, 16 Mar 2022 18:54:27 +0100 Subject: [PATCH 1/2] BondingManager-fuzzing: added fuzzing campaign against BondingManager 'transferBond' --- src/test/BondingManagerFuzzer.sol | 95 +++++++++++++++++++++++++++++++ 1 file changed, 95 insertions(+) create mode 100644 src/test/BondingManagerFuzzer.sol diff --git a/src/test/BondingManagerFuzzer.sol b/src/test/BondingManagerFuzzer.sol new file mode 100644 index 00000000..e8264c2f --- /dev/null +++ b/src/test/BondingManagerFuzzer.sol @@ -0,0 +1,95 @@ +pragma solidity ^0.8.9; + +import "ds-test/test.sol"; +import "contracts/governance/Governor.sol"; +import "contracts/bonding/BondingManager.sol"; +import "contracts/snapshots/MerkleSnapshot.sol"; +import "contracts/token/LivepeerToken.sol"; +import "contracts/rounds/RoundsManager.sol"; +import "contracts/Controller.sol"; + +interface CheatCodes { + function roll(uint256) external; + + function startPrank(address) external; + + function prank(address) external; + + function stopPrank() external; + + function assume(bool) external; +} + +// forge test -vvv --fork-url --fork-block-number 6768456 --match-contract BondingManagerFuzzer +contract BondingManagerFuzzer is DSTest { + CheatCodes public constant CHEATS = CheatCodes(HEVM_ADDRESS); + + BondingManager public constant BONDING_MANAGER = BondingManager(0x35Bcf3c30594191d53231E4FF333E8A770453e40); + address public constant MINTER_ADDRESS = 0xc20DE37170B45774e6CD3d2304017fc962f27252; + LivepeerToken public constant LIVEPEER_TOKEN = LivepeerToken(0x289ba1701C2F088cf0faf8B3705246331cB8A839); + RoundsManager public constant ROUNDS_MANAGER = RoundsManager(0xdd6f56DcC28D3F5f27084381fE8Df634985cc39f); + Controller public constant CONTROLLER = Controller(0xD8E8328501E9645d16Cf49539efC04f734606ee4); + + address public constant delegator = 0xF8E893C7D84E366f7Bc6bc1cdB568Ff8c91bCF57; + address public constant delegatorB = 0x5bE44e23041E93CDF9bCd5A0968524e104e38ae1; + address public constant delegate = 0xDcd2CD1a27118E65A3d8aF6518F62b78D056Ac5a; + uint256 public constant STARTING_BLOCK = 14265594; + + function testTransferBond(uint256 _amount) public { + CHEATS.assume(_amount > 0.01 ether && _amount < 100000 ether); + CHEATS.roll(STARTING_BLOCK); + CHEATS.prank(delegatorB); + BONDING_MANAGER.claimEarnings(0); + CHEATS.prank(delegator); + BONDING_MANAGER.claimEarnings(0); + + CHEATS.prank(MINTER_ADDRESS); + LIVEPEER_TOKEN.mint(delegator, _amount); + + CHEATS.startPrank(delegator); + (uint256 initialBondedAmount, , address initialDelegateAddress, , , , ) = BONDING_MANAGER.getDelegator( + delegator + ); + LIVEPEER_TOKEN.approve(address(BONDING_MANAGER), _amount); + BONDING_MANAGER.bond(_amount, delegate); + + // time-travels to new new round and initializes it + CHEATS.roll(STARTING_BLOCK + ROUNDS_MANAGER.roundLength()); + ROUNDS_MANAGER.initializeRound(); + (uint256 updatedBondedAmount, , address updatedDelegateAddress, , , , ) = BONDING_MANAGER.getDelegator( + delegator + ); + assertEq(updatedBondedAmount, initialBondedAmount + _amount); + assertEq(updatedDelegateAddress, delegate); + + (uint256 initialRecipientBondedAmount, , address initialRecipientDelegateAddress, , , , ) = BONDING_MANAGER + .getDelegator(delegatorB); + + BondingManager(BONDING_MANAGER).transferBond( + delegatorB, + _amount, + address(0), + address(0), + address(0), + address(0) + ); + + // // time-travels to new new round and initializes it + CHEATS.roll(block.timestamp + ROUNDS_MANAGER.roundLength() * 2); + ROUNDS_MANAGER.initializeRound(); + + BONDING_MANAGER.claimEarnings(0); + (uint256 bondedAmountAfter, , address delegateAddressAfter, , , , ) = BONDING_MANAGER.getDelegator(delegator); + assertEq(delegateAddressAfter, bondedAmountAfter == 0 ? address(0) : delegate); + assertEq(bondedAmountAfter, updatedBondedAmount - _amount); + + (uint256 recipientBondedAmountAfter, , address recipientDelegateAddressAfter, , , , ) = BONDING_MANAGER + .getDelegator(delegatorB); + + assertEq(recipientDelegateAddressAfter, initialRecipientDelegateAddress); + assertTrue(recipientDelegateAddressAfter != address(0)); + assertEq(recipientBondedAmountAfter, initialRecipientBondedAmount + _amount); + + CHEATS.stopPrank(); + } +} From 4072168a41af5c428db4a98bccca04e57ae4147e Mon Sep 17 00:00:00 2001 From: RiccardoBiosas Date: Mon, 23 May 2022 09:43:01 +0200 Subject: [PATCH 2/2] foundry tests: enforced a more consistent coding style in BondingManagerFuzzer --- src/test/BondingManagerFuzzer.sol | 42 +++++++++++++------------------ 1 file changed, 18 insertions(+), 24 deletions(-) diff --git a/src/test/BondingManagerFuzzer.sol b/src/test/BondingManagerFuzzer.sol index e8264c2f..8004f5f6 100644 --- a/src/test/BondingManagerFuzzer.sol +++ b/src/test/BondingManagerFuzzer.sol @@ -25,48 +25,47 @@ contract BondingManagerFuzzer is DSTest { CheatCodes public constant CHEATS = CheatCodes(HEVM_ADDRESS); BondingManager public constant BONDING_MANAGER = BondingManager(0x35Bcf3c30594191d53231E4FF333E8A770453e40); - address public constant MINTER_ADDRESS = 0xc20DE37170B45774e6CD3d2304017fc962f27252; LivepeerToken public constant LIVEPEER_TOKEN = LivepeerToken(0x289ba1701C2F088cf0faf8B3705246331cB8A839); RoundsManager public constant ROUNDS_MANAGER = RoundsManager(0xdd6f56DcC28D3F5f27084381fE8Df634985cc39f); Controller public constant CONTROLLER = Controller(0xD8E8328501E9645d16Cf49539efC04f734606ee4); - address public constant delegator = 0xF8E893C7D84E366f7Bc6bc1cdB568Ff8c91bCF57; - address public constant delegatorB = 0x5bE44e23041E93CDF9bCd5A0968524e104e38ae1; - address public constant delegate = 0xDcd2CD1a27118E65A3d8aF6518F62b78D056Ac5a; + address public constant MINTER_ADDRESS = 0xc20DE37170B45774e6CD3d2304017fc962f27252; + address public constant DELEGATOR = 0xF8E893C7D84E366f7Bc6bc1cdB568Ff8c91bCF57; + address public constant DELEGATOR_B = 0x5bE44e23041E93CDF9bCd5A0968524e104e38ae1; + address public constant DELEGATE = 0xDcd2CD1a27118E65A3d8aF6518F62b78D056Ac5a; uint256 public constant STARTING_BLOCK = 14265594; function testTransferBond(uint256 _amount) public { CHEATS.assume(_amount > 0.01 ether && _amount < 100000 ether); CHEATS.roll(STARTING_BLOCK); - CHEATS.prank(delegatorB); + CHEATS.prank(DELEGATOR_B); BONDING_MANAGER.claimEarnings(0); - CHEATS.prank(delegator); + CHEATS.prank(DELEGATOR); BONDING_MANAGER.claimEarnings(0); CHEATS.prank(MINTER_ADDRESS); - LIVEPEER_TOKEN.mint(delegator, _amount); + LIVEPEER_TOKEN.mint(DELEGATOR, _amount); + + CHEATS.startPrank(DELEGATOR); + (uint256 initialBondedAmount, , , , , , ) = BONDING_MANAGER.getDelegator(DELEGATOR); - CHEATS.startPrank(delegator); - (uint256 initialBondedAmount, , address initialDelegateAddress, , , , ) = BONDING_MANAGER.getDelegator( - delegator - ); LIVEPEER_TOKEN.approve(address(BONDING_MANAGER), _amount); - BONDING_MANAGER.bond(_amount, delegate); + BONDING_MANAGER.bond(_amount, DELEGATE); // time-travels to new new round and initializes it CHEATS.roll(STARTING_BLOCK + ROUNDS_MANAGER.roundLength()); ROUNDS_MANAGER.initializeRound(); (uint256 updatedBondedAmount, , address updatedDelegateAddress, , , , ) = BONDING_MANAGER.getDelegator( - delegator + DELEGATOR ); assertEq(updatedBondedAmount, initialBondedAmount + _amount); - assertEq(updatedDelegateAddress, delegate); + assertEq(updatedDelegateAddress, DELEGATE); (uint256 initialRecipientBondedAmount, , address initialRecipientDelegateAddress, , , , ) = BONDING_MANAGER - .getDelegator(delegatorB); + .getDelegator(DELEGATOR_B); BondingManager(BONDING_MANAGER).transferBond( - delegatorB, + DELEGATOR_B, _amount, address(0), address(0), @@ -74,17 +73,12 @@ contract BondingManagerFuzzer is DSTest { address(0) ); - // // time-travels to new new round and initializes it - CHEATS.roll(block.timestamp + ROUNDS_MANAGER.roundLength() * 2); - ROUNDS_MANAGER.initializeRound(); - - BONDING_MANAGER.claimEarnings(0); - (uint256 bondedAmountAfter, , address delegateAddressAfter, , , , ) = BONDING_MANAGER.getDelegator(delegator); - assertEq(delegateAddressAfter, bondedAmountAfter == 0 ? address(0) : delegate); + (uint256 bondedAmountAfter, , address delegateAddressAfter, , , , ) = BONDING_MANAGER.getDelegator(DELEGATOR); + assertEq(delegateAddressAfter, bondedAmountAfter == 0 ? address(0) : DELEGATE); assertEq(bondedAmountAfter, updatedBondedAmount - _amount); (uint256 recipientBondedAmountAfter, , address recipientDelegateAddressAfter, , , , ) = BONDING_MANAGER - .getDelegator(delegatorB); + .getDelegator(DELEGATOR_B); assertEq(recipientDelegateAddressAfter, initialRecipientDelegateAddress); assertTrue(recipientDelegateAddressAfter != address(0));