Platform: Code4rena
Start Date: 12/09/2022
Pot Size: $75,000 USDC
Total HM: 19
Participants: 110
Period: 7 days
Judge: HardlyDifficult
Total Solo HM: 9
Id: 160
League: ETH
Rank: 7/110
Findings: 2
Award: $2,015.33
🌟 Selected for report: 1
🚀 Solo Findings: 1
🌟 Selected for report: bin2chen
1932.8529 USDC - $1,932.85
BuyCrowdfundBase.sol _buy() When callValue = 0 is settledPrice to totalContributions ignoring whether totalContributions > maximumPrice resulting in the minimum proportion of participants expected to become smaller
function _buy( IERC721 token, uint256 tokenId, address payable callTarget, uint96 callValue, bytes calldata callData, FixedGovernanceOpts memory governanceOpts ) ... settledPrice_ = callValue == 0 ? totalContributions : callValue; //**** not check totalContributions>maximumPrice****// if (settledPrice_ == 0) { // Still zero, which means no contributions. revert NoContributionsError(); } settledPrice = settledPrice_;
(AuctionCrowdfund.sol finalize() similar)
add check
function _buy( IERC721 token, uint256 tokenId, address payable callTarget, uint96 callValue, bytes calldata callData, FixedGovernanceOpts memory governanceOpts ) ... settledPrice_ = callValue == 0 ? totalContributions : callValue; if (settledPrice_ == 0) { // Still zero, which means no contributions. revert NoContributionsError(); } +++ if (maximumPrice_ != 0 && settledPrice_ > maximumPrice_) { +++ settledPrice_ = maximumPrice_; +++ } settledPrice = settledPrice_;
#0 - merklejerk
2022-09-22T15:21:23Z
We will cap the callValue to maximumPrice.
#1 - 0xble
2022-10-02T16:13:25Z
#2 - HardlyDifficult
2022-10-04T10:02:22Z
This is a potential violation of user expectations - agree with Medium risk.
🌟 Selected for report: Lambda
Also found by: 0x1f8b, 0x4non, 0x52, 0x5rings, 0xDanielC, 0xNazgul, 0xSmartContract, 0xbepresent, Anth3m, Aymen0909, B2, CRYP70, CertoraInc, Ch_301, Chom, ChristianKuri, CodingNameKiki, Deivitto, Funen, JC, JansenC, Jeiwan, KIntern_NA, MasterCookie, MiloTruck, Olivierdem, PaludoX0, R2, RaymondFam, ReyAdmirado, StevenL, The_GUILD, Tomo, Trust, V_B, __141345__, asutorufos, ayeslick, bin2chen, brgltd, bulej93, c3phas, cccz, ch0bu, cryptphi, csanuragjain, d3e4, delfin454000, djxploit, erictee, fatherOfBlocks, gogo, hansfriese, indijanc, ladboy233, leosathya, lukris02, malinariy, martin, pedr02b2, pfapostol, rvierdiiev, slowmoses, smiling_heretic, tnevler, wagmi
82.4839 USDC - $82.48
1: PartyGovernance.sol accept()
If the user participates in the crowdfunding but has not burn(), at this time votingPower==0, if go to vote, can succeed, but votingPower==0, lost the original should have votingPower Suggest adding votingPower==0 can not vote
function accept(uint256 proposalId, uint256 snapIndex) public onlyDelegateCall returns (uint256 totalVotes) { .. // Increase the total votes that have been cast on this proposal. uint96 votingPower = getVotingPowerAt(msg.sender, values.proposedTime, snapIndex); +++ require(votingPower!=0);
2: Crowdfund.sol _initialize() Suggest adding the judgment that opts.initialContributor is not address(0), to avoid losing the amount
function _initialize(CrowdfundOptions memory opts) internal { .. uint96 initialBalance = address(this).balance.safeCastUint256ToUint96(); if (initialBalance > 0) { +++ require(opts.initialContributor!=address(0)); // If this contract has ETH, either passed in during deployment or // pre-existing, credit it to the `initialContributor`. _contribute(opts.initialContributor, initialBalance, opts.initialDelegate, 0, ""); }