我正在上一门计算机安全课程,还有一个额外的学分,可以将可执行代码插入到缓冲区溢出中。我有我正在尝试操作的目标程序的c源代码,并且我已经达到了能够成功覆盖当前函数堆栈帧的eip的程度。但是,我总是遇到Segmentation故障,因为我提供的地址总是错误的。问题是当前函数在pthread内部,因此,堆栈的地址似乎总是在程序的不同运行之间发生变化。是否有任何方法可以在pthread中查找堆栈地址(或者用于估计pthread中的堆栈地址)? (注意:pthread_create的第二个参数为null,所以我们不是手动分配堆栈地址)
答案 0 :(得分:7)
我建议阅读关于利用缓冲区溢出漏洞 Smashing The Stack For Fun And Profit 的优秀(如果有点过时)文章/教程。
以下是摘录摘录:
问题是我们不知道在内存空间的哪个位置 程序我们正在尝试利用代码(以及后面的字符串 它将被放置。解决它的一种方法是使用JMP和CALL 指令。 JMP和CALL指令可以使用IP相对寻址, 这意味着我们可以在不需要的情况下跳转到当前IP的偏移量 知道我们想要跳转到的内存的确切地址。
您可以使用一些内联汇编来检索堆栈指针的当前值。 Smashing The Stack For Fun And Profit 中的所有示例都溢出main
中的缓冲区,但您可以轻松地使用相同的技术来溢出从pthread调用的函数中的缓冲区。下面的代码是基于文章( overflow1.c )中的一个示例构建的,以表明使用pthreads可以使用相同的技术。您将使用的实际技术取决于您尝试利用的目标程序。
/* get value of sp off the stack - not essential to example */
unsigned long get_sp()
{
__asm__("movl %esp,%eax"); /* equiv. of 'return esp;' in C */
}
int foo()
{
char buffer[96];
/* overflow buffer to overwrite return address */
/* and place code to be executed into buffer. */
...
return 0;
}
void *thread(void *arg)
{
printf("thread stack 0x%x\n", get_sp());
foo();
return NULL;
}
int main(int argc, char **argv)
{
printf("main stack 0x%x\n", get_sp());
pthread_t t;
pthread_create(&t, NULL, thread, NULL);
pthread_join(t, NULL);
return 0;
}
答案 1 :(得分:0)
在不了解应用程序的情况下,我们有点难以理解,但首先想到的是heap spraying。
答案 2 :(得分:0)
除了我之前的回答,您可能还想阅读以下内容:
以下文章重点介绍堆溢出: