Protocol allows a voter to vote both `for` & `against` the same proposal which not only goes against natural voting logic and would cause for wrong approvals/disapprovals since the `>= DISAPPROVE_THRESHOLD`& `>= APPROVE_THRESHOLD` checks would use inflated data
Audit: 2024-05-munchables-findings
Severity: MEDIUM

# Lines of code

https://github.com/code-423n4/2024-05-munchables/blob/57dff486c3cd905f21b330c2157fe23da2a4807d/src/managers/LockManager.sol#L191-L198


# Vulnerability details


## Proof of Concept

Take a look at https://github.com/code-423n4/2024-05-munchables/blob/57dff486c3cd905f21b330c2157fe23da2a4807d/src/managers/LockManager.sol#L506-L527

```solidity
    function _execUSDPriceUpdate() internal {
        if (
            usdUpdateProposal.approvalsCount >= APPROVE_THRESHOLD &&
            usdUpdateProposal.disapprovalsCount < DISAPPROVE_THRESHOLD
        ) {
            uint256 updateTokensLength = usdUpdateProposal.contracts.length;
            for (uint256 i; i < updateTokensLength; i++) {
                address tokenContract = usdUpdateProposal.contracts[i];
                if (configuredTokens[tokenContract].nftCost != 0) {
                    configuredTokens[tokenContract].usdPrice = usdUpdateProposal
                        .proposedPrice;

                    emit USDPriceUpdated(
                        tokenContract,
                        usdUpdateProposal.proposedPrice
                    );
                }
            }

            delete usdUpdateProposal;
        }
    }
```

This is the function that's inherently called upon when the price is to be updated and when more than/ or equal to `APPROVE_THRESHOLD` have been, have voted `for the proposal`, issue however is from how protocol currently counts the `for & against` votes for a specific update.
Going through both `approveUSDPrice()` & `disapproveUSDPrice()` we can see that there whereas there is a check when disapproving that a pricefeeder has not approved of the same update, a similar check does not exist during approving and a price feeder who has previously disapproved can still approve. These are the checks applied for the functions:

- In `approveUSDPrice()` https://github.com/code-423n4/2024-05-munchables/blob/57dff486c3cd905f21b330c2157fe23da2a4807d/src/managers/LockManager.sol#L191-L198

```solidity
        if (usdUpdateProposal.proposer == address(0)) revert NoProposalError();
        if (usdUpdateProposal.proposer == msg.sender)
            revert ProposerCannotApproveError();
        if (usdUpdateProposal.approvals[msg.sender] == _usdProposalId)
            revert ProposalAlreadyApprovedError();
        if (usdUpdateProposal.proposedPrice != _price)
            revert ProposalPriceNotMatchedError();

```

- In `disapproveUSDPrice()` https://github.com/code-423n4/2024-05-munchables/blob/57dff486c3cd905f21b330c2157fe23da2a4807d/src/managers/LockManager.sol#L224-L231

```solidity
        if (usdUpdateProposal.proposer == address(0)) revert NoProposalError();
        if (usdUpdateProposal.approvals[msg.sender] == _usdProposalId)
            revert ProposalAlreadyApprovedError();
        if (usdUpdateProposal.disapprovals[msg.sender] == _usdProposalId)
            revert ProposalAlreadyDisapprovedError();
        if (usdUpdateProposal.proposedPrice != _price)