AttackLab-phase5
提供的指令字节序列
题目描述
阶段五要求你对RTARGET程序进行ROP攻击,用指向你的cookie字符串的指针,使程序调用touch3函数。
这一关,允许你使用函数start_farm和end_farm之间的所有gadget。除了第四阶段允许的那些指令,还允许使用movl指令(如图2C所示),以及图2D中的2字节指令,它们可以作为有功能的nop,不改变任何寄存器或内存的值,例如,andb %al, %al,这些指令对寄存器的低位字节做操作,但是不改变它们的值。
提示:
· 官方答案需要8个gadgets。
解题过程
第三关的时候我们已知
touch3:0x401931
cookie:34 61 66 36 39 32 61 33 00
所需完成的任务
- 把cookie放入栈中
- 获取cookie所处位置的地址
- 将改地址移入%rdi
- 调用touch3
1 | mov addr, %rdi |
初步想法
尝试
既然说了官方答案是8个gadgets,那就证明我们的当然不会一风顺,也就是说我们需要不断把简单的问题变得复杂,但是这也需要从简单开始
1 获取地址的方法
想要或许地址就必须要利用%rsp的值,所以我先试试找到所有有关的mov %rsp到别的寄存器的指令
查表可知,字节序列应该是48 89 eX (X表示0到7——对应不同reg)
该序列能找到6个,两个较为合适,不知道有没有区别,暂且使用第一个
1 | mov %rap, %rax |
此时已经用到了0个gadget
2 获取的地址应该是什么
48 89 e0 c3表示
1 | movq %rsp, %rax |
但是如果当前%rsp的值已经是cookie了,如果没有办法执行pop,那我们就没有办法去ret到下一个gadget了,程序也会到此崩溃(so will I)
但是我并没有在89 eX序列后找到字节将pop插入到ret前,QAQ
不过这一点也提醒了我,不可直接通过mov %rsp获取到cookie的地址,所以应该想办法用能够获取到的地址,根据cookie的偏移量计算出cookie的地址(毕竟farm里有好多lea)
此时已经用到了1个gadget
3 利用获取的地址找到cookie
找到唯一可以让我们自己控制偏移量的lea指令
- 看起来需要两个参数,其中%rdi作为base,应该用我们在第二步中所得到的地址作为base
- 计算后找到cookie,并把值放到%rax中,所以在此步之后我们需要再把%rax mov 到 %rdi中,调用touch3即可
- 难点在于%rsi的值如何确定:不过因为 %rsp * 1为偏移量,所以我们只需要把偏移量算好移入%rsi即可
此时已经用到了1个gadget
4 将base传入%rdi
所以不妨让我们尝试先把base(基础地址传入到上面的add_xy函数中)
1 | mov %rax, %rdi |
此时已经用到了2个gadgets
5 将偏移量传入%rsi
其实偏移量的大小是我们自己决定的,因为在那个7个gadget和cookie阴暗聚集的空间中,所存放的所有东西都是我们自己放进去的。
所以我们当然也可以把偏移量栈中,再想办法把偏移量pop出来,传递到%rsi中,用于add_xy的调用
pop出来之后,我们需要把%rax的值mov到%rsi中
mov的Dest为%rsi的,我只找到89 d6是有结果的,最合适的是这个
但是它的source为%rdx所以我们需要先把%rax的值传到%rdx中
但是又发现没有直接以%rax作为source,把%rdx作为dest的,可以找到%rcx到%rdx
所以先把%rax移动到%rcx(祈祷会有),还好找到了(其中的08是不会影响到我们的值的,可以查表去看08具体干什么,这里不再赘述)
总结一下我们为了将偏移量移入%rsi,路径为%rax->%rcx->%rdx->%rsi,所以上面三个图倒着看即为顺序
偏移量应为:计算如下图
此时已经用到了6个gadgets
6 通过偏移量计算cookie地址
到此处我们算是完成了传参的过程,最后调用
再将%rax mov 到%rdi中,即可完成gadget的位置安排
7 栈的情况及最终输入
偏移量应该为 $8 * 9 = 72_{(10)} = 48_{(16)}$
gadget1到8的地址为
1 | 401a29 |
加上要填写的cookie和touch3的地址
touch3:0x401931
cookie:34 61 66 36 39 32 61 33 00
最终输入
1 | 00 00 00 00 00 00 00 00 |