Project

One World
NFTDeFi
15,000 USDC
View results
Submission Details
Severity: medium
Invalid

`updateDAOMembership` is vulnerable to frontrun and will break the allowed amount limit of tier.

Summary

When the DAO creator creates the DAO, they set the token allowance for each tier. During updates, the creator can modify the allowed token amount per tier. However, this creates an opportunity for frontrunning, which could potentially alter the actual token limit intended for existing tiers.
The token amount allowed for each tier is set inside the createNewDAOMembership function :

function createNewDAOMembership(DAOInputConfig calldata daoConfig, TierConfig[] calldata tierConfigs)
external returns (address) {
require(currencyManager.isCurrencyWhitelisted(daoConfig.currency), "Currency not accepted.");
require(daoConfig.noOfTiers == tierConfigs.length, "Invalid tier input.");
require(daoConfig.noOfTiers > 0 && daoConfig.noOfTiers <= TIER_MAX, "Invalid tier count.");
require(getENSAddress[daoConfig.ensname] == address(0), "DAO already exist.");
if (daoConfig.daoType == DAOType.SPONSORED) {
require(daoConfig.noOfTiers == TIER_MAX, "Invalid tier count for sponsored.");
}
// enforce maxMembers
uint256 totalMembers = 0;
for (uint256 i = 0; i < tierConfigs.length; i++) {
totalMembers += tierConfigs[i].amount;
}
require(totalMembers <= daoConfig.maxMembers, "Sum of tier amounts exceeds maxMembers.");

Inside updateDAOMembership the EXTERNAL_CALLER is allowed to adjust the current amount for each tier. it also include any new tier which will be added.

dao/MembershipFactory.sol:100
100: function updateDAOMembership(string calldata ensName, TierConfig[] memory tierConfigs)
101: external onlyRole(EXTERNAL_CALLER) returns (address) {
102: address daoAddress = getENSAddress[ensName];
103: require(tierConfigs.length <= TIER_MAX, "Invalid tier count.");
104: require(tierConfigs.length > 0, "Invalid tier count.");
105: require(daoAddress != address(0), "DAO does not exist.");
106: DAOConfig storage dao = daos[daoAddress];
107: if(dao.daoType == DAOType.SPONSORED){
108: require(tierConfigs.length == TIER_MAX, "Invalid tier count.");
109: }
110:
111: uint256 maxMembers = 0;
112:
113: // Preserve minted values and adjust the length of dao.tiers
114: for (uint256 i = 0; i < tierConfigs.length; i++) {
115: if (i < dao.tiers.length) {
116: tierConfigs[i].minted = dao.tiers[i].minted; // @audit : reserve the minted values
117: }
118: }
119:
120: // Reset and update the tiers array
121: delete dao.tiers;
122: for (uint256 i = 0; i < tierConfigs.length; i++) {
123: dao.tiers.push(tierConfigs[i]);
124: maxMembers += tierConfigs[i].amount; // @audit : stores the new values for amount it also includes the existing one
125: }
126:
127: // updating the ceiling limit acc to new data
128: if(maxMembers > dao.maxMembers){
129: dao.maxMembers = maxMembers;
130: }
131:
132: dao.noOfTiers = tierConfigs.length;
133: return daoAddress;
134: }

At Line 124 it is evident that after this update the new allowed amount will be used for current and newly added tiers. it will open a oppurtunity for attacker as dicussed below:

POC

The attacker can exploits it via frontrunning updateDAOMembership function when adjusting tier configurations in the DAO.

  1. Create DAO:
    The DAO has two tiers with the following configuration:

    Tier Amount Allowed Max Members Minted
    0 15 30 10
    1 15 30 10
  2. Some token got minted on each tier.

  3. DAO Update:
    The DAO owner decides to add a new tier and adjusts the existing token amounts for each tier:

    Tier Amount Allowed Max Members Minted
    0 10 30 10
    1 10 30 10
    2 10 30 0
  4. The DAO owner submits this updateDAOMembership transaction to adjust the token amounts.

  5. An attacker sees the pending updateDAOMembership transaction and frontruns it by minting additional tokens for tier 0.
    By doing so, they increase the total tokens minted in tier 0 to 11, surpassing the updated limit of 10 before the DAO change is applied.

Impact

  1. The DAO’s updated configuration now shows 10 tokens allowed for tier 0, but 11 tokens have already been minted, bypassing the intended token limit.

  2. This inconsistency in the token amounts undermines the DAO’s tier restrictions, allowing the attacker to bypass the intended limits for each tier.

Tools Used

Manual Review

Recommendations

To mitigate this Issue introduce pause/unpause mechanism . which will help you to keep each token tier in limit.

Updates

Lead Judging Commences

0xbrivan2 Lead Judge
9 months ago
0xbrivan2 Lead Judge 9 months ago
Submission Judgement Published
Invalidated
Reason: Incorrect statement

Appeal created

0xaman Submitter
9 months ago
0xbrivan2 Lead Judge
9 months ago
0xbrivan2 Lead Judge 9 months ago
Submission Judgement Published
Invalidated
Reason: Incorrect statement

Support

FAQs

Can't find an answer? Chat with us on Discord, Twitter or Linkedin.