bomblab
bomblab
开始愉快的拆除炸弹吧,(bushi)
通过这次实验可以基本掌握gdb的使用,这次使用了pwndgb插件
可以使用objdump查看反汇编程序,也可以在gdb里使用disassemble反汇编
超详细的wpCSAPP | Lab2-Bomb Lab 深入解析 - 知乎 (zhihu.com)
pwndgb的基本指令
| 指令 | 效果 |
|---|---|
| s | 单步步入 |
| n | 单步步过 |
| r | 重新运行 |
| c | 继续运行 |
| i b, i r | 查看断点、寄存器 |
| return | 退出当前函数 |
| search 114514 | 查找114514 |
| b *0x114514 , b fun_name | 在0x114514处下断点、在函数fun_name处下断点 |
| delete ,delete 114514 | 删除所有断点,删除114514号断点 |
| disassemble main | 反汇编main函数 |
| vmmap | 显示进程的内存映射 |
| cyclic 50 | 生成50个用来溢出的字符 |
| cyclic -l 字符串 | 定位字符串再溢出字符的位置 |
| p 0xffffceec-0xffffcf58 | 计算0xffffceec-0xffffcf58的值 |
phase_1
在phase_1处下断点b phase_1,然后使用s单步
发现传入四个参数,其中rdi寄存器存储我们输入的值,rsi寄存器存储着字符串。然后通过函数strings_not_equal可以判断出函数是将这两个字符串进行比较,然后通过test eax, eax对返回值进行判断
如果
eax的值为零,则零标志位 (ZF) 将被设置为 1。如果
eax的值非零,则零标志位 (ZF) 将被设置为 0.
当ZF标志位为1时,跳转到phase_1+23,否则调用explode——bomb
可以通过x/s查看内存
显然,phase_1的答案为Border relations with Canada have never been better.
phase_2
删除所有断点,进入phase2,下断点,s单步
进入read_six_numbers函数
cmp eax, 5应该是每成功处理一个输入,eax++。scanf函数返回已成功赋值的数据项数,返回值存储在eax寄存器。
eax==5即全部参数处理完毕,由此我们可以确定我们要输入六个参数。
然后继续分析phase_2,直接disassemble phase_2
1 | cmp DWORD PTR [rsp],0x1 |
判断第一个字符是否为1,否则bomb!!
1 | add eax,eax |
每次输入的数就是前面数的两倍
从bomb.c 文件中可以看到,当输入两个命令行参数时,我们可以以一个文件作为输入,因此可以创建ans.txt文件作为输入
第一个参数为 /home/randolfluo/Desktop/csapp/bomb/bomb
第二个参数为 ans.txt
因此执行 argc为2的代码
phase_3
调用scanf函数,若已成功赋值的数据项数eax>1成立,则jg有符号大于则跳转,避开爆炸,因此必须要有三个输入
而我们从scanf函数的format中可以看到,输入了两个整型。但!回车就是第三个输入。
1 | 0x400f6a <phase_3+39> cmp dword ptr [rsp + 8], 7 |
判断第一个输入小于7,然后进行后续跳转
1 | 0x400f75 <phase_3+50> jmp qword ptr [rax*8 + 0x402470] <phase_3+118> |
通过你输入的第一个值来跳转不同验证代码,rax*8 + 0x402470,查看0x402470处的内存,因为linux在x86-64是小端序。小端序意味着较低地址的字节排放在内存中的较低地址,而较高地址的字节排放在内存中的较高地址。
如果输入 1,则跳转到0x0000000000400fb9
则第二个数则0x137,化为十进制即311
phase_4
依然是输入两个整型,将phase_4反汇编一下
1 | Dump of assembler code for function phase_4: |
调用了fun函数,,同时将第一个输入存放进%rdi寄存器。
发现fun函数是个递归函数。我们需要找到最快方式跳出循环
jle 0x400ff2
可以使用word进行分析,其中不同颜色表示不同的跳转地址。
我们可以得出两个条件输入<=7和输入>=7,那么我们输入的第一个数为7,所以我们的输入为7 0
phase5
再次使用word大法
通过输入的字符串每个元素的低四位来索引字符串maduiersnfotvbylSo you think you can stop the bomb with ctrl-c, do you?的值,最后与flyers进行比较,相同则通关。
写个脚本
1 | array='maduiersnfotvbylSo you think you can stop the bomb with ctrl-c, do you?' |
phase_6
下次一定~








