1. 一段具有缓冲区溢出的C代码[Asm] 纯文本查看 复制代码 #include "stdio.h"
#include "string.h"
#include <windows.h>
char payload[] = "aaaaaaaabbbbbbbbbbbbxxxx";
void exp()
{
system("whoami");
}
void func()
{
char buffer[8];
strcpy(buffer,payload);
printf("%s",buffer);
}
int main(){
func();
getchar();
return 0;
} 2. 原因是strcpy()函数没有检查copy的长度而导致的溢出简单的说缓冲区溢出漏洞的原理就是因为输入了过长的字符,而缓冲区本身又没有有效的验证机制,导致过长的字符将返回地址覆盖掉,当函数需要返回的时候,由于此时的返回地址是一个无效地址,因此导致程序出错。利用: 假设所覆盖的返回地址是一个有效地址,而在该地址处又包含着有效的指令,那么系统就会毫不犹豫地跳到该地址去执行指令。3. 调用func函数的压栈
4. 编译代码,用OllyDbg进行加载分析一开始的地址并不是main 函数,所以需要定位到 main 函数的地址
这个时候把IDA打开,找到main函数,按X键交叉引用一下
找到调用main函数的地址0x00401804
5. 在OD中按ctrl+G,然后输入地址0x00401804就来到调用main函数的地方
此处按下F2下断点,然后按F9让程序跳到此处,再F7单步进入main函数里
结合IDA分析发现地址0x 0040F988是调用func函数的地方,按F8单步步过到
6. 程序在执行进入CALL的时候,都会将CALL下面那条语句的地址入栈,这样当CALL执行完后,程序再将该地址出栈,这样就能知道下一步应该执行哪条指令。一般将这个地址称为“返回地址”
当call func函数的时候地址0x 0040F98D将被压入栈中,按F7步入
堆栈区 0x0012FF2C 处保存要返回的地址0x 0040F98D 7.结合IDA发现地址0x00401091就是strcpy 函数的地方
观察 strcpy 函数执行前后栈空间的变化,当函数执行完后发现堆栈区 0x0012FF2C 处保存要返回的地址0x 0040F98D已经被覆盖为0x62626262(bbbb)
8.原来它所保存的值为0x 0040F98D,在执行完func函数后,需要执行该地址处的指令。现在栈中的内容变成了比如上图中的 0x62626262,那么当func函数执行完毕后,程序会跳到地址 0x62626262 处继续执行。
9.根据这个原理,假设覆盖的返回地址是一个有效地址,而该地址又包含有效的指令,那么系统就会跳到该地址去执行指令。在IDA中发现exp()函数的地址为0x 00401020,把这个地址覆盖原来的返回地址可以这样修改payload字符串的值,注意大小端的问题
重新编译程序后载入OD中分析
当执行完func函数之后,程序成功跳到exp()函数去执行
|