Sashimi Swap攻击分析

博客深入探讨了UniswapV2Router02合约在sashimi和uniswap两个版本中的差异,揭示了一个潜在的安全问题。攻击者可以利用sashimi合约中的逻辑错误,在多步交换过程中提取额外的ETH。该问题源于合约未正确处理多跳路径交换,导致资金可能流入攻击者控制的池子。通过创建特定的代币和路径,攻击者能够榨取其他代币价值并获取ETH。
摘要由CSDN通过智能技术生成

合约地址:
UniswapV2Router02(sashimi):https://etherscan.io/address/0xe4fe6a45f354e845f954cddee6084603cedb9410#code
UniswapV2Router02(uniswap):https://etherscan.io/address/0x7a250d5630b4cf539739df2c5dacb4c659f2488d#code
SashimiInvestment:https://etherscan.io/address/0x3f966fa1c0606e19047ed72068d2857677e07ef4#code
攻击交易:
https://etherscan.io/tx/0xd6a816cc291b24267c03c23c730a84a2699f32a7cf714c8cbe3e47321c76b08f
UniswapV2Router02(sashimi)合约中函数swapExactTokensForETHSupportingFeeOnTransferTokens

function swapExactTokensForETHSupportingFeeOnTransferTokens(
        uint amountIn,
        uint amountOutMin,
        address[] calldata path,
        address to,
        uint deadline
    )
        external
        virtual
        override
        ensure(deadline)
    {
        require(path[path.length - 1] == WETH, 'UniswapV2Router: INVALID_PATH');
        address pair = UniswapV2Library.pairFor(factory, path[0], path[1]);
        _transferIn(msg.sender,pair,path[0],amountIn);
        uint balanceBefore = getTokenInPair(pair,WETH);
        _swapSupportingFeeOnTransferTokens(path, address(this));
        uint balanceAfter = getTokenInPair(pair,WETH);
        uint amountOut = balanceBefore.sub(balanceAfter);   ///获得pai的balance差
        require(amountOut >= amountOutMin, 'UniswapV2Router: INSUFFICIENT_OUTPUT_AMOUNT');
        _transferETH(to, amountOut);
    }

再看UniswapV2Router02(uniswap)合约中函数swapExactTokensForETHSupportingFeeOnTransferTokens的源码

  function swapExactTokensForETHSupportingFeeOnTransferTokens(
        uint amountIn,
        uint amountOutMin,
        address[] calldata path,
        address to,
        uint deadline
    )
        external
        virtual
        override
        ensure(deadline)
    {
        require(path[path.length - 1] == WETH, 'UniswapV2Router: INVALID_PATH');
        TransferHelper.safeTransferFrom(
            path[0], msg.sender, UniswapV2Library.pairFor(factory, path[0], path[1]), amountIn
        );
        _swapSupportingFeeOnTransferTokens(path, address(this));
        uint amountOut = IERC20(WETH).balanceOf(address(this));
        require(amountOut >= amountOutMin, 'UniswapV2Router: INSUFFICIENT_OUTPUT_AMOUNT');
        IWETH(WETH).withdraw(amountOut);
        TransferHelper.safeTransferETH(to, amountOut);
    }

两者差异在sashimi合约中将所有pair计算后放入合约自身内计算,同时swapExactTokensForETHSupportingFeeOnTransferTokens只考虑了token:eth的单池转换,如果path为
token1:token2:eth时就会导致发送代币后无法接收到eth,同样如果路径为(代币以A,B,C代替,E代表Eth),A:E:B:C:E,就会导致代币A兑换的E流入E:B的池子;同时将A:E内池子的Eth差值传给攻击者,这时如果E:B为攻击者创建的池子,就可以撤掉池子再拿一份eth,
所以攻击者创建3个代币。
A:E中放入大量eth。其余池子仅放入少量eth。
后调用swapExactTokensForETHSupportingFeeOnTransferTokens 通过卖出大量A,将大量Eth传入E:B池中,B在传入B:C池…
同时因为sashimi合约中将所有pair计算后放入合约自身内计算,所以通过eth购买其他代币入usdt,dai等继续冲入eth到合约内,再提取eth,来榨取其他代币。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值