The withdrawInheritedFunds()
function in InheritanceManager.sol
fails if any beneficiary rejects ETH transfers. This means that a malicious or faulty beneficiary can permanently block all withdrawals, effectively locking all inherited funds in the contract.
Location:
InheritanceManager.sol
, function withdrawInheritedFunds()
Root cause:
The contract distributes ETH in a loop.
If one beneficiary rejects the transfer (e.g., via revert()
in a fallback function), the entire function reverts.
Other beneficiaries are blocked from withdrawing their funds.
Proof of Concept (PoC) test case:
A malicious beneficiary contract that rejects ETH:
Test result:
When withdrawInheritedFunds()
is called, the contract fails to process any withdrawals because of one bad beneficiary.
As a result, the contract remains locked unless it is upgraded or externally modified.
Severity: Critical
An attacker or a misconfigured wallet can permanently freeze all inherited funds.
No withdrawals are possible unless the contract is upgraded or modified.
Even a legitimate beneficiary with a broken wallet (e.g., a smart contract without a receive()
function) could accidentally lock all funds.
Manual code review
Slither
Foundry
Solution: Skip failing transfers instead of reverting everything
Modify withdrawInheritedFunds()
to skip failed transactions instead of reverting the entire function:
Alternative fix: Allow manual withdrawal retries
Add a function to retry failed withdrawals.
Allow beneficiaries to manually claim funds instead of the contract distributing them.
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.