29015 - [SC - Low] Boolean return value of addresscall function no...
Submitted on Mar 4th 2024 at 19:36:27 UTC by @kaysoft for Boost | Puffer Finance
Report ID: #29015
Report type: Smart Contract
Report severity: Low
Target: https://etherscan.io/address/0x3C28B7c7Ba1A1f55c9Ce66b263B33B204f2126eA#code
Impacts:
Contract fails to deliver promised returns, but doesn't lose value
Description
Brief/Intro
The Timelock.sol contract's executeTransfaction(...)
function implements a target.call()
function without checking the return value for the success of the transaction.
When an address.call
is made to a function of a contract and it reverts, the error is not bubbled up but instead returns a false
return value. Not checking the boolean return value causes the sender of the transaction to assume the call is successful until the user checks manually because the whole transaction will be successful.
Vulnerability Details
When exceptions happen in an address.call()
, they do not "bubble up" but instead return a false boolean value.
That should be checked with a require()
statement.
The executeTransaction()
external function of Timelock.sol calls the internal _executeTransaction
. The issue lies in the fact that _executeTransaction
makes a target.call()
call without checking the returned boolean value. The internal _executeTransaction
just returns the values returned from the target.call()
. Also the executeTransaction()
external function did not check the returned boolean value either making the whole transaction successful.
This will make the user assume that target.call()
was also successfully executed unless manually checked.
Impact Details
Failure of target.call()
not validated which will make the user assume success of the target.call()
unless the transaction and the contract is manually checked.
##Recommendation Consider adding a check for target.call()
and also add a contract existence check for target
contract.
References
https://github.com/PufferFinance/pufETH/blob/2768d69196717e9f77a6837153b426e06e15c51f/src/Timelock.sol#L265
https://docs.soliditylang.org/en/latest/control-structures.html#error-handling-assert-require-revert-and-exceptions
Proof of Concept
This POC can be added to the Timelock.t.sol file
This transaction sets the newPauser
as zero address which should normally revert due to the require statement in the setPauser
function but it does not revert because the boolean return value is not checked. This creates a successful transaction which can make the user think the new pauser is set.
Last updated