if (usdUpdateProposal.approvals[msg.sender] == _usdProposalId)
revert ProposalAlreadyApprovedError();
This is to ensure that when a proposal is approved by a Pricefeed role, the same address cannot disapprove the same proposal. This is an invariant where the same msg.sender cannot approve and disapprove the same proposal.
However, when approving, there is no check to see if the Pricefeed role has already disapproved the proposal.
Lines of code
https://github.com/code-423n4/2024-05-munchables/blob/main/src/managers/LockManager.sol#L225-L226 https://github.com/code-423n4/2024-05-munchables/blob/main/src/managers/LockManager.sol#L191-L197
Vulnerability details
Impact
LockManager
allows users to lock tokens in return forrewards
. They can unlock their tokens once their respectiveunlockTime
has passed.When users unlock their tokens,
AccountManager::forceHarvest()
is called, which gives users reward based off theUSD
value of their locked tokens.This
USD
value can be changed at anytime by aproposer
withPricefeed
role via a call toproposeUSDPrice()
.If enough
Pricefeed
roles approve the newUSD
value, that value will then be updated.Pricefeed
roles can also disapprove the proposedUSD
value. If enough disapprove, then the proposal will be rejected.There is a check in place to ensure that if a
Pricefeed
role has already approved a proposal, then they cannot disapprove it.However, this invariant can be broken by disapproving first and then proceeding to approve the same proposal.
Proof of Concept
When an address with
Pricefeed
role disapproves a proposedUSD
value, there is a check to see if they already approvedLockManager.sol#L225-L226
This is to ensure that when a proposal is approved by a
Pricefeed
role, the same address cannot disapprove the same proposal. This is an invariant where the same msg.sender cannot approve and disapprove the same proposal.However, when approving, there is no check to see if the
Pricefeed
role has already disapproved the proposal.#L191-L197
The same
Pricefeed
role can approve a proposal they already disapproved, breaking a protocol invariant.Tools Used
Manual Review.
Recommended Mitigation Steps
Upon approval, revert if the caller had already disapproved the proposal:
Assessed type
Invalid Validation