Cyfrin / 2023-08-sparkn

Other
10 stars 15 forks source link

Proxy address can be blocklisted by Token like USDC #498

Open codehawks-bot opened 1 year ago

codehawks-bot commented 1 year ago

Proxy address can be blocklisted by Token like USDC

Severity

High Risk

Relevant GitHub Links

https://github.com/Cyfrin/2023-08-sparkn/blob/0f139b2dc53905700dd29a01451b330f829653e9/src/ProxyFactory.sol#L76C1-L90C6

Summary

Proxy address can be blocklisted by Token like USDC

Vulnerability Details

Proxy address can be predicted before cause of salt is emitted across chain.Using this parameter to know the address ahead and can be forced to blocklist by malicious actors sending dangerous tokens

Impact

Proxy contract wont be able to transfer its tokens to winners.

    //USDC blacklisted test...
/*      function testRevertIfTheProxyIsBlackListed() public setUpContestForJasonAndSentUSDCToken(organizer) {
        // before
        assertEq(mockUsdc.balanceOf(user1), 0 ether);
        assertEq(mockUsdc.balanceOf(stadiumAddress), 0 ether);

        bytes32 randomId_ = keccak256(abi.encode("Jason", "001"));
        bytes memory data = createData();
        //somehow malicious user force proxy address to get blacklisted...
        vm.startPrank(tokenMinter);
        mockUsdc.setBlackList(proxyAddress_1);
        vm.stopPrank();

        vm.warp(9 days); // 9 days later
        vm.startPrank(organizer);
        vm.expectRevert();
        proxyFactory.deployProxyAndDistribute(randomId_, address(distributor), data);
        vm.stopPrank();

    } */

Here's simple mockUSDC contract i made

//! USDC with Blacklisting ability...
/* pragma solidity 0.8.18;

import {ERC20} from "openzeppelin/token/ERC20/ERC20.sol";
import {Ownable} from "openzeppelin/access/Ownable.sol";

/*
 * @title MockUSDC
 * @author CodeFox
 * @dev this is a random ERC20 token for testing purposes
 * This can be supposed to be an stable coin in the current system 
 */
/*
contract MockUSDC is ERC20, Ownable {
    error MockUSDC__AmountMustBeMoreThanZero();
    error MockUSDC__AddressBlackListed();
    mapping(address=>bool) public blackListed;
    constructor(string memory name, string memory symbol) ERC20(name, symbol) {
        _mint(msg.sender, 100000 * 10 ** decimals());
    }

    function mint(address _to, uint256 _amount) external onlyOwner returns (bool) {
        if (_amount == 0) {
            revert MockUSDC__AmountMustBeMoreThanZero();
        }
        _mint(_to, _amount);
        return true;
    }

    function setBlackList(address _blackListedAddress) public onlyOwner {
        blackListed[_blackListedAddress]=true;

    }

    function transfer(address to, uint256 amount) public virtual override returns (bool){
        if(blackListed[msg.sender]) revert MockUSDC__AddressBlackListed();
        super.transfer(to,amount);
        return true;
    }

    function transferFrom(address from, address to, uint256 amount) public virtual override returns (bool){
        if(blackListed[from]) revert MockUSDC__AddressBlackListed();
        super.transferFrom(from,to,amount);
        return true;
    }
} */

Tools Used

Foundry Test suite

Recommendations

Before sending usdc token check the proxy address if its address blocklisted .

ASaidOguz commented 1 year ago

According to time elapsed after deployment of the proxy some malicious user can send bad tokens to proxy address after it received the usdc might lead the proxy locked down .This way all the funds the proxy has will be blocked by USDC main contract .I wasnt meant of winners addresses.

PatrickAlphaC commented 1 year ago

If the protocol itself is blocklisted, you can't do anything. Also, you can't send tokens to a blocklisted address. So this recommendation wouldn't help either.

Technically, this submission is invalid, but we lumped your blocklisted finding in because blocklisted addresses are an issue, just not the proxy. The root cause is there, but the attack vector is wrong.

Leaving as such.