[英]Why does eip doesn't change in this buffer overflow attempt?
我正在尝试处理缓冲区溢出。 我不知道eip的价值在这里发生了什么。
这是C代码:
void copy(char *arg) {
char msg[256];
strcpy(msg,arg);
}
它的组装:
0x804847d <copy+25>: call 0x8048368 <strcpy@plt>
0x8048482 <copy+30>: leave
0x8048483 <copy+31>: ret
我输入一个像“ _ \\ xAA \\ xBB \\ xCC \\ xDD”这样的字符串作为参数,其大小经过计算,以便最后4个字节将是$ ebp之后的4个字节(以覆盖实际的返回地址)。 而且似乎可行。
在gdb中:
(break before strcpy)
x/2wx $ebp
0xbffffb38: 0xbffffb58 0x080484d2
n
(just after strcpy execution)
x/2wx $ebp
0xbffffb38: 0x80cdd189 0x080484b6
...
n
...
x/2wx $ebp
0xbffffb38: 0x80cdd189 0x080484b6
所以返回地址是0x080484d2
,在我溢出后返回的地址是0x080484b6
,这就是我想要的。 但是程序退出:“无法访问地址0x80cdd18d的内存”。
我不知道为什么未将$ eip设置为我的地址,并且由于代码的地址为0x08048 ...我非常有信心$ ebp + 4是包含返回地址的地方
我再次尝试使用较小的4个字节的字符串,这一次它覆盖了$ ebp而不是$ ebp + 4,并且在返回之后,将$ eip设置为$ ebp + 4中包含的值
有什么解释吗?
好的,谢谢@Wumpus Q. Wumbley,这有助于我理解事情。
做next
跳跃leave
和ret
干脆。 ret
是更改eip
的指令,它必须等效于pop eip
。 但是leave
之前先修改堆栈指针esp
和ebp
(尤其是因为当我覆盖ebp + 4时,我更改了ebp包含的值)
TLDR:不覆盖ebp的值会使它成功工作。
如果这是针对x86(而不是x86-64)的,则通常的函数序言包括推入ebp
,然后为其分配esp
的值,这会将返回地址留在堆栈上的地址为ebp+4
。
看一下函数的反汇编,看看第一条指令是否看起来像这样:
pushl %ebp
movl %esp, %ebp
如果是这样,这就是偏移的原因。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.