Closed code423n4 closed 1 year ago
berndartmueller marked the issue as primary issue
outdoteth marked the issue as sponsor confirmed
I agree with the warden that checking the existence of the base and NFT token contract is lacking (in terms of a QA improvement). However, deploying pairs with non-existent token contracts leads to a non-functioning Pair
contract. Please see the great explanation from @Shungy for further details -> https://github.com/code-423n4/2022-12-caviar-findings/issues/455#issuecomment-1360966128
Additionally, one of the stated security considerations from the sponsors mentions the risk of malicious pairs. Please see https://github.com/code-423n4/2022-12-caviar#malicious-base-token-or-nft-contracts
Due to the fact that deployed pairs with non-existent token contracts will cause the add
, remove
, buy
, sell
functions to revert anyway and the known risk stated by the sponsor, I'm downgrading the finding to QA (low).
berndartmueller changed the severity to QA (Quality Assurance)
berndartmueller marked the issue as grade-c
Lines of code
https://github.com/code-423n4/2022-12-caviar/blob/0212f9dc3b6a418803dbfacda0e340e059b8aae2/src/Caviar.sol#L28-L43
Vulnerability details
The
create()
function inCaviar.sol
is not checking whether the NFT or baseToken actually exists. If the supplied address is not a contract or doesn’t implement the requiredname()
andsymbol()
function, the name/symbol is derived from the first symbols of the hex address. While this doesn’t have any impact upon creation of the pair, a non-existing NFT or baseToken contract might become risky when interacting with thePair.sol
contract.Pair.sol
uses solmate’sSafeTransferLib
for transferring ERC20’s, which doesn’t check whether the ERC20 contract actually exists (https://github.com/Rari-Capital/solmate/blob/main/src/utils/SafeTransferLib.sol#L9). As a result, when the token's address has no code, the transaction will just succeed with no error.One possible, albeit unlikely exploit scenario would be the following:
More likely would be leveraging the fact it's becoming popular for protocols to deploy their token across multiple networks. In this case, a common practice is to deploy the token contract from the same deployer address and with the same nonce so that the token address can be the same for all the networks.
For example: 1INCH is using the same token address for both Ethereum and BSC; Gelato's GEL token is using the same token address for Ethereum, Fantom and Polygon.
A sophisticated attacker can exploit it by taking advantage of this and creating vaults on multiple other networks with base tokens which are not yet deployed on this network. The attacker could follow the same pattern as above and alter the state of the contract such that he/she is able to steal base tokens from future users once they start using the vault.
Impact
As it might be possible to steal funds from the Pair contract and future users of the system, the impact is considered high.
Tool Used
Manual Review
Recommended Mitigation Steps
We recommend to check whether the NFT and base token contract actually exist when creating the new pair in
create()
ofCaviar.sol
: