本文从源代码层面详解介绍了?Solidity(?0.8.13<=solidity<0.8.17)编译器在编译过程中,因为?Yul?优化机制的缺陷导致的状态变量赋值操作被错误删除的中/高漏洞原理及相应的预防措施。
帮助合约开发人员提高合约开发时的安全意识,有效规避或缓解?SOL-2022-7?漏洞对合约代码安全性的影响。
官方文档。
在编译过程的?UnusedStoreEliminator?优化步骤中,编译器会将“冗余”的?Storage?写入操作移除,但由于对“冗余”的识别缺陷,当某个?Yul?函数块调用特定的用户定义函数(函数内部存在某个分支不影响调用块的执行流),且在该?Yul?函数块中被调用函数前后存在对同一状态变量的写入操作,会导致在?Yul?优化机制将块中该用户定义函数被调用前的所有的?Storage?写入操作从编译层面被永久删除。
考虑如下代码:
contractEocene{
????????uintpublicx;
????????functionattack()public{
????????????????x=1;
Soluna 2022年全年加密货币收入为2440万美元,增长123%:金色财经报道,加密采矿数据中心开发商Soluna Holdings发布截至 2022 年 12 月 31 日的全年财务业绩。到 2022 年,专有挖矿生产了 883 个等值的比特币。与 2021 年的 1,430 万美元相比,2022 年的总收入增长了 99%,达到 2,850 万美元。增长的原因是 Project Sophie 设施在 2022 年 3 月全面通电后采矿业务显着增加。2022 年调整后的 EBITDA 为 - 460 万美元,而 2021 年为 150 万美元。不包括折旧的总收入成本占收入的百分比从 2021 年的 41% 增加到 2022 年的 62%,这主要是由于比特币价格下降和能源成本增加所致。[2023/4/4 13:43:01]
????????????????x=2;
????????}
}
在?UnusedStoreEliminator?优化时,x=?1?显然对于函数?attack()的整个执行是冗余的。自然的,优化后的?Yul?代码会将?x=?1;删除来降低合约的?gas?消耗。
接下来考虑在中间插入对自定义函数调用:
Solana基础设施公司Helius完成310万美元融资:10月20日消息,Solana基础设施初创公司Helius宣布完成310万美元种子轮融资,Reciprocal Ventures和Chapter One领投,Solana Ventures、Alchemy Ventures、Big Brain Ventures 、Propel VC等机构以及Magic Eden联合创始人Zhuoxun Yin、Squads联合创始人Stepan Simkin等天使投资人参投。
据悉,Helius由前Coinbase和Amazon Web Services工程师共同创立,旨在提供工具帮助开发人员以更少的时间和更低的成本构建Web3应用程序。Helius在两个月前推出邀请制Alpha测试,目前已向公众开放其平台。(Decrypt)[2022/10/20 16:30:33]
contractEocene{
uintpublicx;
functionattack(uinti)public{
????????x=1;
????????y(i);
????????x=2;
Solana联创:以太坊在可扩展性方面还有很长的路要走:金色财经报道,Solana Labs联合创始人Anatoly Yakovenko在接受采访时表示,根据交易和用户的数量,合并对改善以太坊的可扩展性影响很小。他说:“\"以太坊的合并并没有真正改善网络的可扩展性。当你看看Solana每天从应用程序和用户那里处理的交易数量时,它不仅仅是以太坊,而是所有基于以太坊的区块链的总和。所以我认为以太坊在可扩展性方面还有很长的路要走。”
然而,Yakovenko表示,合并对加密货币来说是一个积极的方面,它将带来一些清晰度,特别是关于PoS的安全性方面,同时吸引资本流入。(Finbold)[2022/9/21 7:11:35]
}
functiony(uinti)internal{
????????if(i>0){
????????????????return;
????????}
????????assembly{return(?0,?0。
}
}
显然,由于?y()函数的调用,我们需要判断?y()函数是否会影响函数?attack()的执行,如果?y()函数可以导致整个函数执行流终止(注意,不是回滚,Yul?代码中的?return()函数可以实现),那么?x=?1?显然是不能删除的,所以对于上面的合约来说由于?y()函数中存在?assembly{return(?0,?0。可以导致整个消息调用终止,x=?1?自然不能被删除。
Solana上的NFT项目SolBlocks被指侵权:9月16日消息,基于Solana的NFT项目SolBlocks被指在未授权的情况下使用Art Blocks上的生成艺术系列作品Fidenza的代码。Fidenza的创作者Tyler Hobbs称此举令人不快。
据悉,近几周,包括Solana在内的公链上有越来越多的创作者推出NFT,随之而来的是越来越多的山寨项目。除了SolBlocks,Solana上的SolPunks,SolSquiggle分别抄袭了CryptoPunks和Chromie Squiggle。(Crypto Briefing)[2021/9/16 23:28:57]
但在?Solidity?编译器中,由于代码逻辑的问题,使得?x=?1?在编译时被错误的删除,永久改变了代码逻辑。
实际编译测试结果如下:
震惊!不应该被优化的?x=?1?的?Yul?代码丢了!欲知后事如何,请往下看。
在?solidiry?编译器代码的?UnusedStoreEliminator?中,通过?SSA?变量追踪和控制流追踪来判断一个?Storage?写入操作是否是冗余的。当进入一个自定义函数中时,UnusedStoreEliminator?如果遇到:
USDT已在Solana链上发行:金色财经报道,在Solana被选为USDT发行人数月后,USDT已首次在Solana区块链上铸造。[2021/2/4 18:50:08]
memory?或?storage?写入操作:将?memory?和?storage?写入操作存储到?m_store?变量中,并将该操作的初始状态设置为?Undecided;
函数调用:获取函数的?memory?或?storage?读写操作位置,并和?m_store?变量中存储的所有?Undecided?状态下的操作进行对比:
1.如果是对?m_store?中存储操作的写入覆盖,则将?m_store?中对应的操作状态改为?Unused
2.如果是对?m_store?中存储操作的读取,则将对应?m_store?中的对应操作状态改为?Used
3.如果该函数没有任何可以继续执行消息调用的分支,将?m_store?中所有的内存写操作改为?Unused
???1.在上诉条件下,如果函数可以终止执行流,将?m_store?中,状态为?Undecided?状态的?storage?写操作改为?Used;反之,标识为?Unused
函数结束:将所有标记为?Unused?的写入操作删除
对?memory?或?storage?写入操作的初始化代码如下:
可以看到,将遇到的?memory?和?storage?写入操作存储到?m_store?中
遇到函数调用时的处理逻辑代码如下:
其中,operationFromFunctionCall()和?applyOperation()实现上诉的?2.1?,?2.2?处理逻辑。位于下方的基于函数的?canContinue?和?canTerminate?进行判断的?If?语句实现?2.3?逻辑。
需要注意,正是下方的?If?判断的缺陷,导致了漏洞的存在!!!
operationFromFunctionCall()来获取该函数的所有?memory?或?storage?读写操作,这里需要注意,Yul?中存在很多的内置函数,例如?sstore(),?return()。这里可以看到对于内置函数和用户定义函数有不同的处理逻辑。
而?applyOperation()函数则是将从?operationFromFuncitonCall()获取的所有读写操作进行对比,来判断存储到?m_store?中的是否在该次函数调用中被读写,并修改?m_store?中的对应的操作状态。
考虑上述的?UnusedStoreEliminator?优化逻辑对?Eocene?合约的?attack()函数的处理:
将?x=?1?存储操作到?m_store?变量中,状态设置为?Undecided
????1.遇到?y()函数调用,获取?y()函数调用的所有读写操作
????2.遍历?m_store?变量,发现?y()调用引起的所有读写操作和?x=?1?无关,x=?1?状态仍然是?Undecided
????????1.获取?y()函数的控制流逻辑,因为?y()函数存在可以正常返回的分支,所以?canContinue?为?True,不进入?If?判断。x=?1?状态仍然为?Undecided!!!
????3.遇到?x=?2?存储操作:
????????1.?遍历?m_store?变量,发现处于?Undecided?状态的?x=?1?,x=?2?操作覆盖?x=?1?,设置?x=?1?状态为?Unused。
????????2.?将?x=?2?操作存入?m_store,初始状态为?undecided。
????4.函数结束:
????????1.将所有?m_store?中?undecided?状态的操作状态改为?Used
????????2.将所有?m_store?中?Unused?状态的操作删除
显然,在调用函数时,如果被调用函数可以终止消息执行,应该将被调用函数前所有的?Undecided?状态的写入操作改为?Used,而不是依旧保留为?Undecided,导致位于被调用函数前的写入操作被错误的删除。
此外,需要注意的是,每个用户自定义函数控制流标识是会传递的,所以在多个函数递归调用的场景下,即便最底层函数满足上诉逻辑,x=?1?也有可能被删除。
在Solidity中,举例了基本相同的逻辑下,不会受到影响的合约代码。但,该代码不受该漏洞的影响并不是因为?UnusedStoreEliminator?的处理逻辑存在其他可能,而是在?UnusedStoreEliminator?之前的?Yul?优化步骤中,存在?FullInliner?优化过程会将微小或只有一次调用的被调用函数,嵌入到调用函数中,避免了漏洞触发条件中的用户定义函数。
contractNormal{
????uintpublicx;
????functionf(boola)public{
????????x=1;
????????g(a);
????????x=2;
????}
????functiong(boola)internal{
????????if(!a)
????????assembly{return(?0,?0。
????}
}
编译结果如下:
函数?g(boola)被嵌入到函数?f()中,避免了用户定义函数的漏洞条件,避免了漏洞的产生。
2.解决方案
最根本的解决方案是不使用在受影响范围的?solidity?编译器进行编译,如果需要使用漏洞版本的编译器,可以考虑在编译时去除?UnusedStoreEliminator?优化步骤。
如果想要从合约代码层面进行漏洞缓解,考虑到多个优化步骤的复杂性,以及实际函数调用流的复杂性,请寻找专业的安全人员进行代码审计来帮助发现合约中的因为该漏洞导致的安全问题。
标签:TORSTOSTORSOLSunny AggregatorStonk MarketHistoryDAOsol币价格走势图
原文作者:ThorHartvigsen,加密KOL原文编译:Felix,PANews四月份,部分VC和聪明钱有一些大的投资组合变化.
1900/1/1 0:00:00本文来自Coingecko,原文作者:LimYuQian,由Odaily星球日报译者Katie辜编译.
1900/1/1 0:00:00尊敬的用户:火必和波场Tron、BitTorrent已于2022年已达成战略合作伙伴关系。波场Tron和BitTorrent一直是行业中用户基数以及TVL领先的公链,为繁荣波场生态,火必支持响应.
1900/1/1 0:00:00最近的20亿柴犬销毁交易引起了怀疑。怀疑是由于进行销毁的钱包地址的活动性质所致。SHIB燃烧率在过去24小时内上升了108.17%。ShibaInu销毁计划是memecoin团队的突出发展之一.
1900/1/1 0:00:00為回饋廣大用戶對XT.COM的支持,XT.COM將舉辦一系列紅包活動,以表達對您真誠的感謝!時間:2023年05月05日00:00-2023年05月15日23:59活動1:獨家福利.
1900/1/1 0:00:00ForesightNews消息,据欧科云链OKLink安全团队监测,2023年4月安全事件共造约6000万美金的损失,与上个月相比,损失金额有所回落,但安全事件数量依旧不减.
1900/1/1 0:00:00