内容简介:偶然在Reddit上看到,一位以太坊发烧友Zac Mitton发布了一个智能合约,如果你能在其中找到bug,智能合约就会自动把奖金转到你的账户!代码地址:该合约有效期为30天,初始奖金是10个ETH,并且他承诺每天会增加1ETH的悬赏,到今天为止奖金账户里已经有24个ETH了,价值3万多RMB!刺不刺激?心不心动?我们先来看看到底是怎么一回事吧~Zac在Github上提到,做这件事情的初衷是为了验证一种更好的抵御Block-Gas-Limit攻击的方案。
偶然在Reddit上看到,一位以太坊发烧友Zac Mitton发布了一个智能合约,如果你能在其中找到bug,智能合约就会自动把奖金转到你的账户!代码地址: https://github.com//zmitton/eth-heap
该合约有效期为30天,初始奖金是10个ETH,并且他承诺每天会增加1ETH的悬赏,到今天为止奖金账户里已经有24个ETH了,价值3万多RMB!刺不刺激?心不心动?我们先来看看到底是怎么一回事吧~
1.Block-Gas-Limit攻击
Zac在Github上提到,做这件事情的初衷是为了验证一种更好的抵御Block-Gas-Limit攻击的方案。
那么什么是Block-Gas-Limit攻击呢?我们知道,以太坊虚拟机执行每条指令都需要消耗一定的油量(gas)的,并且某些指令消耗的油量还比较高,以目前的EIP158为例,参见下表:
当然,攻击者在攻击过程中也需要支付比较高的油费,但是如果攻击能带来非常可观的经济效益,那这点点成本可以忽略不计。有些读者可能反应过来了:前段时间很火的 Fomo3D游戏 ,第一轮结束时黑客不就是用的这种手段嘛!最终黑客收获了 10000+ETH 的奖池,价值 2200多万 !
那么如何抵御这种攻击呢?以太坊并没有提出比较好的方案,有一种提案是限制每次合约调用可以从存储中读取的字节数,但是听起来不是什么好主意。Zac兄弟就思考良久,一拍大腿,用二叉堆啊!
2.二叉堆
我们先来回忆一下数据结构相关的内容:首先,啥叫个堆?
堆是一棵完全树,但是是用数组形式表示的。可以分为2种类型:
-
大顶堆:堆中任意节点总是大于它的子节点的值
-
小顶堆:堆中任意节点总是大于它的子节点的值
比如下图就是一个大顶堆:
可以看到,其实就是把数据按层顺序存储到数组里。如果节点的索引为 i ,那么它的左孩子的索引就是 2i ,右孩子的索引就是 2i+1 。(这里跟Zac的代码实现保持一致,抛弃数组的第一个元素)
二叉堆的核心是在“插入节点”和“删除节点”后如何保证堆的“大顶”或者“小顶”特性。以大顶堆为例,我们依次分析一下。
2.1插入节点
假设我们要把22插入堆中,首先我们把22添加到末尾:
然后通过“索引/2”找到父节点,如果值大于父节点的值,跟父节点交换:
继续通过“索引/2”找到父节点,值仍大于父节点的值,跟父节点交换:
2.2删除节点
假设我们要上图的基础上,删除最上面的100这个节点。首先把100从堆中删除,然后把最后一个元素填充到原先100所在的位置:
然后通过“索引2i和2i+1”找到它的左右孩子,挑比较大的那个进行交换:
继续通过“索引2i和2i+1”找到它的左右孩子,挑比较大的那个进行交换:
当然,如果你要删除中间某个节点,有可能需要向上冒泡,也有可能需要向下冒泡,需要具体情况具体处理。
聊完了基础知识,让我们再回到智能合约上来吧。
3.怎么找bug?
Zac希望通过二叉堆,将查找的时间复杂度从O(N)降低到到O(logN),这样就可以大大降低交易消耗的油量,从而抵御Block-Gas-Limit攻击。更进一步,他认为这种算法还可以被用于实现去中心化交易协议!在交易撮合过程中,我们需要根据买单的价格,寻找相匹配的价格最高的卖单。我们并不需要对堆进行完全排序,因为如果价格最高的卖单不满足要求的话,交易撮合就失败了,我们并不需要查找价格第二高的卖单。
因此,他亲自实现了这份极具价值的代码,并发起了这个悬赏计划。可以通过下面的命令下载代码:
npm install eth-heap --save
实际上他写了两个合约:核心算法Heap.sol仅有110行代码,而BountyHeap.sol则封装了一些堆操作API方便挑战者们调用,同时提供了一些校验API,如果校验API发现某些属性出现异常,就会直接把奖金从合约账户中转给交易发起者!具体来说,分为以下三类属性的校验:
- 堆属性:如果发现某个节点的值小于它的子节点的值,则打破了该属性,挑战成功
- 完全属性:堆是一棵完全树,如果树的中间出现了空洞,则打破了该属性,挑战成功
- ID维护属性:如果出现了重复的节点ID,或者某个ID指向空节点,则打破了该属性,挑战成功
也就是说,你可以通过堆操作API进行插入、删除、查询等操作,如果成功造成了堆状态异常,则可以调用校验API直接提取奖金,无需任何人的授权~
4.成本评估
发起交易调用智能合约是需要消耗油费的,因此大家肯定很关心成本评估问题。Zac在GitHub上晒出了500个节点情况下执行操作需要消耗的油量的均值:
extractById() insert() extractMax()
另外,根据Zac的测试,数据两每增大一倍,消耗的油量就要增加20000:
好了,就说到这里吧,我要赶着去撸合约代码了,祝各位好运~ :smiley:
更多文章欢迎关注“鑫鑫点灯”专栏: https://blog.csdn.net/turkeycock
或关注飞久微信公众号:以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网
猜你喜欢:- 用堆找出最小的 N 个数
- MySQL如何找出未提交事务信息
- 找出软件通用功能点的方法
- git – 如何找出合并提交父母的编号?
- 找出数组中出现次数超过一半的数
- 「Oracle」善用日志挖掘,找出罪魁祸首
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Rails Cookbook
奥西尼 / 江苏东南大学 / 2007-6 / 68.00元
Rails是业界领先的新一代Web 2.0应用程序开发框架,而这本《Rails Cookbook》里充满了为了让你成为Rails开发专家而准备的各种解决方案。讨论范围覆盖了从基本概念,如安装Rails及设置开发环境,到最新的各种技巧,如开发符合REST协议规范的Web服务等。 Rails可提供更轻量级的代码、更丰富的功能和更快捷的量身定制过程,由此带来了一场Web开发革命。《Rails Co......一起来看看 《Rails Cookbook》 这本书的介绍吧!