Platform: Code4rena
Start Date: 08/06/2022
Pot Size: $115,000 USDC
Total HM: 26
Participants: 72
Period: 11 days
Judge: leastwood
Total Solo HM: 14
Id: 132
League: ETH
Rank: 22/72
Findings: 2
Award: $484.46
🌟 Selected for report: 0
🚀 Solo Findings: 0
🌟 Selected for report: xiaoming90
https://github.com/code-423n4/2022-06-connext/blob/b4532655071566b33c41eac46e75be29b4a381ed/contracts/contracts/core/connext/facets/BridgeFacet.sol#L389 https://github.com/code-423n4/2022-06-connext/blob/b4532655071566b33c41eac46e75be29b4a381ed/contracts/contracts/core/connext/facets/BridgeFacet.sol#L1025 https://github.com/code-423n4/2022-06-connext/blob/b4532655071566b33c41eac46e75be29b4a381ed/contracts/contracts/core/connext/libraries/AssetLogic.sol#L347 https://github.com/code-423n4/2022-06-connext/blob/b4532655071566b33c41eac46e75be29b4a381ed/contracts/contracts/core/connext/libraries/AssetLogic.sol#L347
L389: BridgeFacet.sol: handle function
L1025: BridgeFacet.sol: Comment About This
L1029: BridgeFacet.sol: SafeIncrease of Allowance
L347: AssetLogic.sol: Usage of SafeApprove
Each call apart from the first one that relies on the swapFromLocalAssetIfNeededForExactOut
function will be reverted and the whole call will suffer a reversal in cascade. This will deny future nomad relayers calls to handle
and as a consequence, jam the relayer logic.
The relayer logic according to the comments and description provided by the Connext team suggests that the handle
function is called once a router message has been optimistically verified. The flow of how the calls are being triggered will be the following:
handle
, L389._reconcile
, L541. This function will handle how the balance of tokens is managed regarding minting and AMM swapping._reconcileProcessPortal
is called in order to repay Aave Portal.swapFromLocalAssetIfNeededForExactOut
L226 logic managed by the AssetLogic
library._swapAssetOut
, trigger made at L226, where the implementation is at L304.SafeERC20.safeApprove(IERC20(_assetIn), address(pool), _amountIn)
.The first time this whole loop is called, every step will pass and the transaction will be mined. But when the second call is triggered, the step 6 will be reverted by following the SafeERC20
function logic:
/** * @dev Deprecated. This function has issues similar to the ones found in * {IERC20-approve}, and its usage is discouraged. * * Whenever possible, use {safeIncreaseAllowance} and * {safeDecreaseAllowance} instead. */ function safeApprove( IERC20 token, address spender, uint256 value ) internal { // safeApprove should only be called when setting an initial allowance, // or when resetting it to zero. To increase and decrease it, use // 'safeIncreaseAllowance' and 'safeDecreaseAllowance' require( (value == 0) || (token.allowance(address(this), spender) == 0), "SafeERC20: approve from non-zero to non-zero allowance" ); _callOptionalReturn(token, abi.encodeWithSelector(token.approve.selector, spender, value)); }
The reversal comes from the require
statement under the execution of the safeApprove
call, more precisely the last argument of the or logic operator
.
As the handle
function is meant to be called several times, this may incur in a severe jamming of the relayer logic preventing them to perform further calls.
OpenZeppelin suggests not using this implementation as is deprecated and it should only be called if the initial allowance wants to be set (initial state of the contract allowances). In order to manage the allowances, following the SafeERC20
standard suggestions, it is advisable to use instead SafeERC20.safeIncreaseAllowance
and SafeERC20.safeDecreaseAllowance
.
#0 - ecmendenhall
2022-06-20T15:36:43Z
Duplicate of #154
#1 - LayneHaber
2022-06-25T20:00:41Z
See #154
#2 - 0xleastwood
2022-08-13T22:35:44Z
Good description of the same issue in #154.
🌟 Selected for report: BowTiedWardens
Also found by: 0x1f8b, 0x29A, 0x52, 0xNazgul, 0xNineDec, 0xf15ers, 0xkatana, 0xmint, Chom, ElKu, Funen, IllIllI, JMukesh, Jujic, Kaiziron, Lambda, MiloTruck, Ruhum, SmartSek, SooYa, TerrierLover, TomJ, WatchPug, Waze, _Adam, asutorufos, auditor0517, bardamu, c3phas, catchup, cccz, ch13fd357r0y3r, cloudjunky, cmichel, cryptphi, csanuragjain, defsec, fatherOfBlocks, hansfriese, hyh, jayjonah8, joestakey, k, kenta, obtarian, oyc_109, robee, sach1r0, shenwilly, simon135, slywaters, sorrynotsorry, tintin, unforgiven, xiaoming90, zzzitron
143.5334 USDC - $143.53
The following lines of code contain unresolved commented TODO's that must be reviewed, deleted or implemented depending each case.
It is important to remark that by developing the implementations pointed by those to do's; their logics, possible impacts and plausible attack vectors associated that could happen will require further audits to determine if they convey or not further risks.