PeckShield 安全人员跟进分析发现,0x Exchange 合约在校验订单签名时存在缺陷,导致攻击者可以进行恶意挂单,进而将用户的数字资产低价卖出,扰乱正常的交易秩序。
0x 协议受到不少去中心化交易所和钱包的青睐,从 Etherscan 的 DEX 过去七天交易份额的饼图中能看到,排名靠前的 Radar Relay 和 Tokenlon 都是基于 0x 协议:
另外,从 DAppTotal 的 DEX 24小时交易额排名中也能看到它们的排名:
由于 Ethereum 平台上大量的 DEX 都使用了 0x 协议,而作为最根本的 Token Tranfer 主合约出问题,这对于整个 DEX 领域来说,都是比较重大的事件。
isValidWalletSignature(bytes32, address, bytes) 函数用于验证给定的 Wallet 合约所定义的签名信息与给定的签名是否一致,用于确保 Order 是由正确的 Maker/Taker 执行的交易。但是 0x Exchange 合约在验证的过程中,存在着比较严重的问题:
上图是这一函数的全部逻辑,分为两部分:
- 组装签名具体字段为 ABI 编码格式;
- 根据组装的 ABI 编码内容计算签名值正确性。
- 引入 cdStart 指针,指向 calldata 中对应的位置;
-
对 WalletAddress 调用 staticcall() OpCode 计算签名正确性,
注意观察代码,其中的 input 和 output 都为 cdStart 这一指针,即复用 input/output 的内存;
- 检验步骤 2.2 中的结果是否正确。
当被调用的合约(即这里的 WalletAddress )没有 code, 也就是 EOA 账号的情况下,什么都没有的执行,直接返回。因此,对应到 isValidWalletSignature(bytes32, address, bytes) 函数来说,其中的 cdStart 所对应的内存内容在调用 staticcall() 前后并没有变化,而后面在判断签名是否正确的 isValid 取值的时候,也就取到了错误的值。
用户通过 fillOrder(Order, uint256, bytes) 函数完成 Token 买卖,PeckShield 安全人员发现,这一函数的三个参数可以由用户自由配置:
分别为:
- 代表订单信息的 Order 类型;
- 用户为此订单付出的 Token 数量;
- Order 对应的签名信息 signature
攻击者可伪造用户挂单,低价获得用户代币。
鉴于此安全漏洞的危害性,PeckShield 安全人员发现 0x 项目方在漏洞被发现的时候先紧急关闭了 0x Exchange v2.0 合约的 Token transfer 功能,将所有的 ERC20、ERC721、以及 MultiAsset 的 Transfer 功能全部下线;随后部署了修复后的合约,同时告知用户及使用了 0x Exchange 的所有 DEX 及 Relayer,相关的迁移升级工作正在进行中。受此影响,基于 0x 协议的交易所及钱包,包括 Radar Relay, Tokenlon, Star Bit 等紧急暂停了交易服务。
PeckShield 安全人员通过漏洞特性分析链上数据发现,从 0x Exchange 2018-09 上线至今,并没有因此安全漏洞造成的用户直接资产损失。
对于使用了 0x 的 DEX 及钱包来说,当前的阶段需要暂停交易服务,如无法暂停交易服务的话,可将对应的 0x Exchange 合约地址变更为当前已经修复的合约地址。
PeckShield 安全人员在此提醒广大开发者及时排查合约的相关代码,避免类似问题可能造成的安全风险,对于 DEX 等 DeFi 类项目,项目方在上线前需要找有资质的安全公司审计安全风险。
本文地址: https://www.xiguacaijing.com/news/guandian/2019/10039.html
赞助商