A critical vulnerability has been discovered in the MembershipFactory contract that allows users to join the same tier multiple times, bypassing intended membership restrictions and potentially manipulating voting power.
The MembershipFactory contract fails to prevent users from joining the same tier multiple times. Through the callExternalContract function, users can repeatedly call joinDAO for the same tier, resulting in:
Multiple NFT mints of the same tier to the same address
Multiple token payments being processed
Potential manipulation of voting power
Bypassing of tier membership limits
function testCallExternalContractReentrancy() public {
// Initial setup
testCreateNewDAOMembership();
membershipFactory.grantRole(membershipFactory.EXTERNAL_CALLER(), addr1);
testERC20.mint(addr1, 2000);
// Prepare joinDAO call data
bytes4 selector = bytes4(keccak256("joinDAO(address,uint256)"));
bytes memory encodedParams = abi.encode(daoAddress, uint256(0));
bytes memory data = abi.encodePacked(
selector,
encodedParams,
uint256(uint160(addr1))
);
// Execute multiple joins
membershipFactory.callExternalContract(
address(membershipFactory),
data
);
membershipFactory.callExternalContract(
address(membershipFactory),
data
);
// Verify the bug
IERC1155 membership = IERC1155(daoAddress);
uint256 nftBalance = membership.balanceOf(addr1, 0);
assertEq(nftBalance, 2, "User can join the same tier multiple times!");
// Verify token spending
uint256 finalBalance = testERC20.balanceOf(addr1);
assertEq(finalBalance, 1400); // 2000 - (300 * 2)
}
Economic Impact
Users can acquire multiple NFTs of the same tier
Multiple token payments are processed for the same tier
Governance Impact
Potential manipulation of voting power
Disruption of DAO governance mechanisms
System Integrity
Bypass of tier membership limits
Violation of intended membership restrictions
foundry
Implement a mapping to track user tier membership:
mapping(address => mapping(address => mapping(uint256 => bool))) public userTierMembership;
// dao => user => tier => hasJoined
The contest is live. Earn rewards by submitting a finding.
This is your time to appeal against judgements on your submissions.
Appeals are being carefully reviewed by our judges.