以太坊parity客户端全版本远程DoS漏洞分析

DVPNET 2019-02-16 11:18 2.45万
分享

本文由五个章节组成,分别是 Parity 相关介绍、UTF-8 编码是什么、Rust 危险的字符串切片、漏洞分析、修复方案和总结。今天我们将由浅入深地为各位读者展示以太坊的 parity 客户端全版本远程 DoS 漏洞分析。

以太坊parity客户端全版本远程DoS漏洞分析

一、Parity相关介绍

以太坊 Parity 客户端是除 Geth 之外使用量最高的一款以太坊客户端,使用的是 Rust 语言。

根据 ethernodes 最新数据显示:以太坊 Parity 客户端在整个以太坊网络中占 30%,Geth 客户端占 40%。

以太坊parity客户端全版本远程DoS漏洞分析

在今年 2 月 3 日时,这款客户端官方发表公告称修复了一个远程拒绝服务的严重漏洞,这个漏洞影响2.2.9之前的版本和2.3.2-beta之前的版本,而2.2.9和2.3.2-beta已经是最新版。从官方的通告来看,可理解为:目前这个漏洞通杀漏洞修复前的所有版本。

虽然该漏洞影响版本很多,但影响范围有限。原因便是该漏洞需要攻击者能够访问目标 Parity 客户端的 JSONRPC,而 Parity 默认是不对外开放 JSONRPC 端口。 

该漏洞具体影响范围可以通过 FOFA 统计出结果:

以太坊parity客户端全版本远程DoS漏洞分析从上图,我们可以看到目前公网上有1195个parity节点开放了JSONRPC端口,故该漏洞影响版本多,但影响范围有限。

二、UTF-8编码是什么?

我们在研究这个漏洞之前需要了解一下UTF-8编码,来帮助我们更好为漏洞研究做准备。

Unicode是一种字符编码,是目前计算机行业内比较通用的一个编码,因为Unicode把所有语言都统一到一套编码里,解决了行业内由于语言不一致而导致的乱码问题。

而UTF-8(8-bit Unicode Transformation Format)是一种针对Unicode的可变长度字符编码,又称万国码。

在这篇漏洞分析中,你只需要知道以下知识点就够了:

UTF-8编码中,一个英文字符占一个字节,一个中文(含繁体)占三个字节。

三、Rust危险的字符串切片

在上个章节中介绍了UTF-8编码的原因是:Rust就是使用的UTF-8编码,以太坊Parity客户端使用的编程语言是Rust。

字符串切片很好理解,就是截取出字符串中的某一段字符串,不过Rust的字符串切片有一个毛病:

切的是字节,不是字符

笔者简单来测试一下,如下图:

以太坊parity客户端全版本远程DoS漏洞分析

通过图片内容显示,我们可以看到当切片str1字符串的0-3个元素的时候,切出来了”DVP”3个字符,但是当切片3-6个元素的时候,如果按字符切的话应该切出来“是最棒”,但是并没有。

为什么会出现这种情况?

原因是Rust按字节切片。在文章此部分之前提到过:在UTF-8中英文占1个字节,中文占3个字节,所以我们切3-6就只切出来了“是”这一个字。

这是正好3个字节切片切到了一个完整中文字符的情况。设想一下:假如切片切的是2个字节呢?

—  会显示半个中文吗?

—  答案是:当然不会了。

当切片切出来不是一个完整字符的时候,Rust不会给你切出来任何字符,而是报错。 

简单测试一下

以太坊parity客户端全版本远程DoS漏洞分析通过图片我们可以看到,当切片3-5的时候程序报错了,因为切到的不是一个完整的中文字符。

以太坊 Parity 客户端正是犯了这个错误,这也是我们今天本文中漏洞分析的关键所在。

四、漏洞分析

DVP安全团队在编写本文时,官网没有披露任何漏洞详情,可能是因为一些节点还未更新到新版修复漏洞的缘故,而且检索一番之后发现网络上也没见到有人在讨论这个漏洞,于是只能去Parity的github中翻查commit记录,试图找到关于这个漏洞的修复补丁,通过补丁来分析漏洞,最终我们看到了这个commit:

https://github.com/paritytech/parity-ethereum/commit/3b23c2e86d09a8a8b8cd99dfa02390177498e6b7

大概看了一下,基本可以确认这就是修复补丁了,补丁中多处把字符串切片换成了starts_with函数:

以太坊parity客户端全版本远程DoS漏洞分析通过上图,可以看到,在之前的写法中是先把字符串的0至2个元素切出来,并判断是不是以”0x”开头,如果长度小于2并且前两个元素的字符串不是”0x”的话就返回一个error.本文上面我们了解了Rust的切片是存在一定危险性的,如果被切片的字符串可控的话就会导致程序报错。

那么,这些使用了字符串切片的地方是否能被远程利用呢?

仔细看图可以发现,图中被修改的两个文件都在rpc目录的types目录下,我们猜测应该是为JSONRPC接口传来的数据定义的一些类型,图中就有hash和uint。

再去翻查以下官方的RPC文档:.

以太坊parity客户端全版本远程DoS漏洞分析原来官方文档其实都有说明,由于json里面只有字符串和数值两个类型,所以像integers、byte、hashes这些数据类型都是通过以0x为前缀的字符串形式编码传输的。 

根据官方文档的描述,我们测试漏洞就很方便了。在文档给的请求样例中任意找一个参数中有0x前缀的,省去了看函数调用链的时间。

这里找了一个比较常见的eth_getTransactionByHash接口,请求方式如下:

curl --data '{"method":"eth_getTransactionByHash","params":["交易hash"],"id":1,"jsonrpc":"2.0"}' -H "Content-Type: application/json" -X POST localhost:8545利用的话也很简单,将”交易hash”替换为中文字符串就行了,例如:curl --data '{"method":"eth_getTransactionByHash","params":["你好DVP"],"id":1,"jsonrpc":"2.0"}' -H "Content-Type: application/json" -X POST localhost:8545实际演示一下:

以太坊parity客户端全版本远程DoS漏洞分析

可以看到在请求接口后节点确实发生了异常并崩溃了。

五、修复方案和总结

官方的修复方案前面有提到,就是将字符串[a..b]这种切片写法全部修改掉。

不过这只是一时的修补方案,若想长久的预防此类漏洞,我们认为公链开发者应该要比传统软件开发者更了解语言的特性,因为很多代码用常规编程思维去看问题不大,但是语言本身可能存在一些开发者并不了解的特性,在特性的辅助下漏洞就产生了,之前就有公链使用go语言滥用make函数,而且参数控制不当,然后产生由OOM导致的拒绝服务漏洞。

故 DVP 安全团队通过本期漏洞分析希望能够借此给大家警示,区块链开发者在未来的开发之路上,需要更加了解语言的特性,这样才能让区块链生态更加稳固、安全。


本文来源:核财经 原文作者:DVPNET 责任编辑:越乐
声明:奔跑财经登载此文出于传递更多信息之目的,并不意味着赞同其观点或证实其描述。文章内容仅供参考,不构成投资建议。投资者据此操作,风险自担。

评论

还没有人评论,快来评论吧

相关新闻

贝莱德旗下的比特币ETF IBIT资产管理规模达到138亿美元,即将超越GBTC

2024-03-28 15:12
BlackRock的比特币ETF IBIT有望很快超越GBTC,成为 ETF 历史上增长最快的 ETF。>
Coingape 7066

以太坊联合创始人Vitalik Buterin质疑元宇宙的未来

2024-03-28 14:26
在首尔举行的 BUIDL 亚洲会议上,Buterin 阐明了他的担忧,挑战了人们对元宇宙的普遍理解。>
BeepCrypto 7346

法院驳回SEC关于Coinbase钱包是未注册经纪商的说法

2024-03-28 12:46
美国纽约南区联邦地区法院驳回了美国证券交易委员会(SEC)关于Coinbase钱包是一个未注册经纪商的说法。>
CryptoNews 7851