Submitted by HollaDieWaldfee, also found by Aymen0909, minhtrng, adriro, sces60107, wagmi, sk8erboy, SmartSek, bin2chen, Allarious, cccz, kaliberpoziomka8552, rvierdiiev, and Saintcode_
The MinipoolManager.recordStakingError function (https://github.com/code-423n4/2022-12-gogopool/blob/aec9928d8bdce8a5a4efe45f54c39d4fc7313731/contracts/contract/MinipoolManager.sol#L484-L515) does not decrease the minipoolCount of the staker.
This means that if a staker has a minipool that encounters an error, his minipoolCount can never go to zero again.
This is bad because the minipoolCount is used in ClaimNodeOp.calculateAndDistributeRewards to determine if the rewardsStartTime of the staker should be reset (https://github.com/code-423n4/2022-12-gogopool/blob/aec9928d8bdce8a5a4efe45f54c39d4fc7313731/contracts/contract/ClaimNodeOp.sol#L81-L84).
Since the minipoolCount cannot go to zero, the rewardsStartTime will never be reset.
This means that the staker is immediately eligible for rewards when he creates a minipool again whereas he should have to wait rewardsEligibilityMinSeconds before he is eligible (which is 14 days at the moment) (https://github.com/code-423n4/2022-12-gogopool/blob/aec9928d8bdce8a5a4efe45f54c39d4fc7313731/contracts/contract/ClaimNodeOp.sol#L51).
To conclude, failing to decrease the minipoolCount allows the staker to earn higher rewards because he is eligible for staking right after he creates a new minipool and does not have to wait again.
I have created the following test that you can add to the MinipoolManager.t.sol file that logs the minipoolCount in the Staking, Error and Finished state.
The minipoolCount is always 1 although it should decrease to 0 when recordStakingError is called.
VSCode
You need to simply add the line staking.decreaseMinipoolCount(owner); to the MinipoolManager.recordStakingError function.
0xju1ie (GoGoPool) confirmed
Alex the Entreprenerd (judge) commented:
emersoncloud (GoGoPool) mitigated:
Status: Mitigation confirmed by RaymondFam and hansfriese.
