我正尝试在64位Mac OS X 10.6上使用C编写一个简单的缓冲区溢出。概念是这样的:
void function() {
char buffer[64];
buffer[offset] += 7; // i'm not sure how large offset needs to be, or if
// 7 is correct.
}
int main() {
int x = 0;
function();
x += 1;
printf("%d\n", x); // the idea is to modify the return address so that
// the x += 1 expression is not executed and 0 gets
// printed
return 0;
}
下面是main的汇编转储的一部分:
...
0x0000000100000ebe <main+30>: callq 0x100000e30 <function>
0x0000000100000ec3 <main+35>: movl $0x1,-0x8(%rbp)
0x0000000100000eca <main+42>: mov -0x8(%rbp),%esi
0x0000000100000ecd <main+45>: xor %al,%al
0x0000000100000ecf <main+47>: lea 0x56(%rip),%rdi # 0x100000f2c
0x0000000100000ed6 <main+54>: callq 0x100000ef4 <dyld_stub_printf>
...
我想跳过movl
指令,这意味着我需要将返回地址递增42 - 35 =7(对吗?)。现在我需要知道返回地址存储在哪里,这样我才能计算正确的偏移量。
我尝试手动搜索正确的值,但要么打印出1,要么得到abort trap
--是否存在某种缓冲区溢出保护?
使用偏移量88在我的机器上工作。我使用了Nemo的方法来查找返回地址。
发布于 2011-06-03 05:02:17
Roddy是对的,你需要对指针大小的值进行操作。
我会从读取你的exploit函数中的值(并打印它们)开始,而不是写它们。当您爬行通过数组的末尾时,您应该开始看到堆栈中的值。不久,您应该找到返回地址,并能够将其与反汇编程序转储对齐。
发布于 2011-06-03 04:53:29
您可以尝试在调试器中运行代码,一次单步执行每条装配线,并检查堆栈的内存空间和寄存器。
发布于 2011-06-03 05:03:08
我总是喜欢对好的数据类型进行操作,就像下面这样:
struct stackframe {
char *sf_bp;
char *sf_return_address;
};
void function() {
/* the following code is dirty. */
char *dummy;
dummy = (char *)&dummy;
struct stackframe *stackframe = dummy + 24; /* try multiples of 4 here. */
/* here starts the beautiful code. */
stackframe->sf_return_address += 7;
}
使用此代码,您可以轻松地通过调试器检查stackframe->sf_return_address
中的值是否与您的预期相符。
https://stackoverflow.com/questions/6220212
复制相似问题