偷天换日合约易主,地址变脸移花接木 |成都链安漏洞分析连载第四期 —— 底层函数误用漏洞
针对区块链安全问题,成都链安科技团队每一周都将出智能合约安全漏洞解析连载,希望能帮助程序员写出更加安全牢固的合约,防患于未然。
引子:阵有纵横,天衡为梁,地轴为柱。梁柱以精兵为之,故观其阵,则知精兵之所有。共战他敌时,频更其阵,暗中抽换其精兵,或竟代其为梁柱,势成阵塌,遂兼其兵。并此敌以击他敌之首策
——《三十六计第二十五计之偷梁换柱》
却说“重入”“竞态”里应外合币穷财尽,“交互”“限制”强强联手链泰民安,锁定关键变量,应用内置函数,不留可乘之机。
此回,底层函数调用险象环生 外部功能慎用防患未然
时至今日,加密货币市场价值富可敌国,已达3000亿美元,是加拿大最大银行RBC两倍有余。行情较好的加密货币蕴含大量的资本,在数字交易所中这座“金库”中大放光彩,犹如璀璨夺目的宝石。但同时也吸引了众多行走江湖的黑客神偷。为此,合约的安全成为重中之重,迭代扩展后的新协议带来的不一定是严丝合缝的守护,也可能有意想不到的疏漏,无孔不入的黑客便试图寻找衔接处的缝隙。
今天我们来说说关于底层函数调用时产生的隐患:可注入call漏洞和delegatecall误用漏洞
事件回顾
2018年5月11日, 人工智能项目方ATN发现其代币ATN Token供应量发生异常,市场上流通的代币无故增加了1100万个。并且黑客在完事之后还不忘隐藏踪迹,归还了权限地址,并且将偷来的Token分发到14个账户地址当中,试图掩人耳目[1]。
好在项目方及时采取了措施,定位了所有可疑账户并采用了冻结销毁等措施,才维持住代币市场的稳定运行。
ATN项目方为了实现代币互换,权限扩展以及控制,合约升级三个新型的功能,采用的是更新的ERC223协议来开发智能合约,并且使用了DS-auth库[1]。按理说双剑合璧能使安全等级的提升颇有成效,却被始料未及的攻击泼了一盆冷水。
追根溯源,主要问题出在代币互换的实现——call函数,即合约外部调用函数的实现过程中。
合约外部调用在最近的游戏智能合约中使用广泛,因为这样能够提高代码复用率,简化代码。最新的MyCryptoChamp游戏漏洞就源于合约内部算法生成的随机数可被预测,没有调用外部可靠的随机数生成模块。所以合约外部调用还是很实用的一项功能,但是利是弊就要看合约编写者的功力了。
何为合约外部调用
专业的来说,call与delegatecall函数让 Ethereum开发者将他们的代码模块化(Modularise)。用 call函数来处理对合约的外部标准信息调用(Standard MessageCall)时,代码在外部函数的环境中运行。 delegate函数也是标准消息调用,但在目标地址中的代码会在调用合约的环境下运行,也就是说,保持msg.sender 和 msg.value不变。该功能支持实现库,开发人员可以为未来的合约创建可重用的代码。
通俗的来说,它是一个合约调用另一个合约某些功能的方式[2]。
拿西游记打个比方:
话说唐僧去西天取经途中遇到了法力高强的妖怪,要过这一难,必须孙大圣出马,于是八戒和沙僧去花果山搬救兵请猴子。
但是如果请来的那位并不是悟空,而是假猴王六耳猕猴,可能不光妖怪降服不了,师傅都会被拐跑。
这就是黑客用来投机倒把的伎俩,利用跨合约调用这个过程偷梁换柱,打入合约内部。我们来看具体案例的分析。
漏洞分析以及详细修复建议
1. 可注入call漏洞
漏洞分析
call是以太坊智能合约编写语言Solidity提供的底层函数,用来与外部合约或者库进行交互。此类函数使用时需要对调用参数的安全性进行判定,建议谨慎使用。
案例代码:
receiver,_custom_fallback,_from, _amount,_data是由用户控制的,也就是说用户可以控制整个call调用,包括调用的合约地址(receiver),调用哪个函数(_custom_fallback),以及传递的参数(_from,_amount,_data),这实际上是很危险的。在ATN事件中攻击者通过指定receiver为案例合约地址,利用DS-Auth授权,调用合约自身的函数,从而获得了合约的控制权[3]。
此外,下面是ERC223标准的另一个call错误实现[4]:
这种合约本身允许用户自定义 call()
任意地址上任意函数的设计,十分危险。攻击者可以很容易地借用当前合约的身份来进行任何操作。可能导致如下后果:
1)允许攻击者以缺陷合约身份来盗走其它 Token 合约中的 Token
2)与 ds-auth 之类的鉴权机制结合,绕过合约自身的权限检查
3)允许攻击者以缺陷合约身份来盗走其它 Token 账户所授权(Approve)的Token
4)攻击者可传入虚假数据(_data)欺骗 Receiver 合约
漏洞修复
1)推荐使用如下方式调用tokenFallback函数
2 ) DS-Auth在设置权限的时候,不要把合约本身地址加入白名单
2. delegatecall误用漏洞
漏洞分析
DELEGATECALL
会保持调用环境不变的属性表明,构建无漏洞的定制库并不像人们想象的那么容易。库中的代码本身可以是安全的,无漏洞的,但是当在另一个应用的环境中运行时,可能会出现新的漏洞。
案例
案例代码来源于Ethernaut第6关[5]
在主合约Delegation的fallback函数中,可通过delegatecall调用Delegate合约的函数,并在主合约环境下执行,如果msg.data是0xdd365b8b
(pwn()的函数签名),即调用Delegate的pwn函数,那么消息发起者就可以变成主合约的owner[6]。
漏洞修复
Solidity 为实现库合约提供了关键字 library
(参见 SolidityDocs 了解更多详情)。这确保了library
是无状态(Stateless)且不可自毁的。强制让library
成为无状态的,可以缓解本节所述的存储环境的复杂性。无状态library
还可以防止攻击者直接修改library
状态以实现对依赖于library
代码的合约的攻击。在使用时 DELEGATECALL
时要特别注意库合约和调用合约可能对状态变量进行修改,并且尽可能构建无状态library
。
真假难辨,如何防范
黑客千方百计试图欺骗合约,或无所不用其极地打开合约的后门,对合约的安全开发过程是一个严峻的考验,从内部和外部我们可以做到以下两点进行防范:
1, 跨合约调用时,要慎用外部函数,周全考虑可能的调用风险,及时添补相应函数和规则,杜绝外患。
2, 内部权限设置必须考虑可能的权限被夺取的情况,从代码逻辑性和功能准确性全方面进行考量。
智能合约的安全规则终将会在安全团队与黑客的较量中不断完善,我们要做好打持久战的准备。
欲知后事,且看下回: 地址恢复功亏一篑,身份判断轻虑浅谋,逻辑补全自圆其说,原理辨析帷幄运筹
引用:
[1]
ATN抵御合约攻击的报告:
https://atn.io/resource/aareport.pdf
[2]
以太坊智能合约call注入攻击:
https://blog.csdn.net/u011721501/article/details/80757811
[3]
ATN披露特殊场景下的以太坊合约重大漏洞并与慢雾科技达成战略合作:
https://www.bitansuo.com/articles/512680.html
[4]
ERC223-token-standardhttps:/github.com/Dexaran/ERC223-token-standard/tree/Recommended
[5]
Ethernauthttps://ethernaut.zeppelin.solutions
[6]
delegatecallhttps://blog.sigmaprime.io/solidity-security.html
相关阅读:
关于链安科技
成都链安科技有限公司,专注区块链安全领域,总部位于成都。由电子科技大学杨霞教授和郭文生教授共同创建,团队核心成员由30多名分别来自海外知名高校和实验室(CSDS、耶鲁、UCLA)留学经历的副教授、博士后、博士、硕士及阿里、华为等知名企业精英组成。其核心技术为形式化验证,该团队使用此技术为航天、军事等领域的安全关键系统提供多年的形式化验证服务,是国内唯一一家将此技术应用到区块链安全领域的公司。
成都链安科技作为分布式战略投资的唯一区块链安全公司,已与Huobi、OKEX、KuCoin、LBank、CoinMex、Becent、JBEX、ONT、Scry、CareerOn、IoTeX、DALICHAIN、比原链、布比区块链、云象区块链、币小白等多家单位签订战略合作协议,并与全球顶级的形式化验证团队法国Inria达成合作。在国家工信部发布的《2018中国区块链产业白皮书》中公司榜上有名,且荣获“OKEx 最佳安全审计合作伙伴奖”。公司已经入选Etherscan智能合约安全审计推荐名单。
「成都链安科技」
作为火币、OKex、KuCoin、LBank等
著名交易所指定的合约审计公司。
入选Etherscan智能合约安全审计名单。
欢迎联系链安,进行智能合约安全审计。
·
电话:028-83262585
网站:www.lianantech.com
邮箱:vaas@lianantech.com
官网:
https://www.lianantech.com
GitHub网址:
https://github.com/Lianantech/VCA
Facebook网址:
https://www.facebook.com/LianAnTechChengdu/
twitter网址:
https://twitter.com/LianAnTech_com
Telegram中文群:
https://t.me/LiananTech_cn
Telegram英文群:
https://t.me/LiananTech_en
微博:
https://weibo.com/u/6566884467
CSDN博客:
https://blog.csdn.net/CDLianan
知识星球:
点击了解更多