**The nonReentrant modifier is not implemented properly, the **locked **variable is not updated to **true inside the modifier. Allowing recursive calls to the function.
The nonReentrant modifier isn't implemented properly and doesn't prevent reentrant calls, the function is vulnerable to reentrancy attacks, which allows an attacker to repeatedly call the refund() function before the state updates to prevent further withdrawals.
Here’s how an attacker might exploit the reentrancy vulnerability for ETH:
First Call to refund:
The attacker calls refund and enters _refundETH.
ETH is sent to the attacker’s contract via _to.transfer(refundValue).
The attacker’s fallback/receive function is triggered.
Reentrant Call:
In the fallback function, the attacker calls refund again.
Since locked hasn't been updated the modifier doesn't prevent reentrancy.
Because etherBalance[_to] has not yet been set to 0, the attacker can withdraw ETH again.
Repeat:
The attacker repeats this process until all ETH in the contract is drained
ERC20 tokens are safe because they are immediately updated to 0 once they are transferred in_refundERC20
The enitre ether of the contract can be drained by a bad actor, by repeatedly calling the refund() function using a fallback()/receive() function call before the etherBalance mapping is updated.
Manual Review
Update the nonReentrant modifier to ensure it works as intended.
    
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.