逆向与Bof基础

一逆向及Bof基础实践说明

 实践目标

本次实践的对象是一个名为pwn1的linux可执行文件。

该程序正常执行流程是:main调用foo函数,foo函数会简单回显任何用户输入的字符串。

该程序同时包含另一个代码片段,getShell,会返回一个可用Shell。正常情况下这个代码是不会被运行的。我们实践的目标就是想办法运行这个代码片段。我们将学习两种方法运行这个代码片段,然后学习如何注入运行任何Shellcode

实验过程:

第一部分实验:

1、先下载并解压pwn1

 

:可能是由于我上课时没有注意到必须先解压后再来进行反汇编,导致实验与指导书上老是不同,心累。。。。,后经同学提醒,才走上正路

2、反汇编

 

 

(注:我们找的是main下的命令,故要按enter直至到达main处)

  

"call 8048491 <foo>"是汇编指令

是说这条指令将调用位于地址8048491处的foo函数;

其对应机器指令为e8 d7ffffff”,e8即跳转之意。

本来正常流程,此时此刻EIP的值应该是下条指令的地址,即80484ba,但如一解释e8这条指令呢,CPU就会转而执行 “EIP + d7ffffff”这个位置的指令。“d7ffffff”是补码,表示-4141=0x29,80484ba +d7ffffff= 80484ba-0x29正好是8048491这个值,

 

main函数调用foo,对应机器指令为“ e8 d7ffffff”,

那我们想让它调用getShell,只要修改“d7ffffff”为,"getShell-80484ba"对应的补码就行。

Windows计算器,直接 47d-4ba就能得到补码,是c3ffffff

下面我们就修改可执行文件,将其中的call指令的目标地址由d7ffffff变为c3ffffff

此上引用与指导书。

3、复制学号文件:

 

注(cpls等都为Linux指令,我自己参考的是《鸟哥的私房菜》第三版,可以使用man 来查询用法,还有强大的Tab补全键)

4、修改可执行文件

以下操作是在vi

ESC键(目的是为了进入到编辑模式)

输入如下,将显示模式切换为16进制模式                 :%!xxd

查找要修改的内容                                       /e8d7

找到后前后的内容和反汇编的对比下,确认是地方是正确的修改d7c3

转换16进制为原格式                                     :%!xxd -r

存盘退出vi                                              :wq

 

很奇怪(为什么过滤了3行)

 

修改:按ESC后,箭头键移动光标到指定位置,后R+修改的字符进行修改

 

5、再反汇编看一下,call指令是否正确调用getShell

 

6、运行下改后的代码,会得到shell提示符#

实验完成

(注:在这步操作中,不知是不是人品的问题,

输入 .\20151120

结果出现了bash::无法找到那个文件或目录,我很崩,结果我问了问同学,只有一个同学出现了和我一样的问题,然后我们更新了一个包之后,恢复了正常,然而并不知所以然)

 

(另,在更新包时,出现了E:无法获得锁的问题

自行百度: 输入 sudo rm /var/cache/apt/archives/lock

 sudo rm /var/lib/dpkg/lock后解决了问题)

 

 

三、实验体会

    这是我第二次接触网络安全的课程,第一次是信息安全概论,然而在这次,感觉知识有莫大的提升,从未涉及过多网络攻防知识的我深感基础太差,因此,需要大量的自行充电,在这次实验中,了解了kali的一些操作命令,还有汇编语言的知识,甚至还有进制的问题,总之这门课博大精深,希望接下来能有更大收获。

 

第二部分实验:

通过构造输入参数,造成BOF攻击,改变程序执行流

知识要求:堆栈结构,返回地址 学习目标:理解攻击缓冲区的结果,掌握返回地址的获取 进阶:掌握ELF文件格式,掌握动态技术

 1反汇编,了解程序的基本功能

注意这个函数getShell,我们的目标是触发这个函数  ==

 

该可执行文件正常运行是调用如下函数foo,这个函数有Buffer overflow漏洞

2、确认输入字符串哪几个字符会覆盖到返回地址

Gdb 运行程序

如果输入字符串1111111122222222333333334444444412345678,那 1234 那四个数最终会覆盖到堆栈上的返回地址,进而CPU会尝试运行这个位置的代码。那只要把这四个字符替换为 getShell 的内存地址,输给2015112020151120就会运行getShell

 

3确认用什么值来覆盖返回地址

getShell的内存地址,通过反汇编时可以看到,即0804847d。

4构造输入字符串

由为我们没法通过键盘输入\x7d\x84\x04\x08这样的16进制值,所以先生成包括这样字符串的一个文件。\x0a表示回车,如果没有的话,在程序运行时就需要手工按一下回车键

可以使用16进制查看指令xxd查看input文件的内容是否如预期。

第二部分结束。

 

 

第三部分:

 

 

注入Shellcode并执行

 

 

准备一段Shellcode

shellcode就是一段机器指令(code

通常这段机器指令的目的是为获取一个交互式的shell(像linuxshell或类似windows下的cmd.exe),

所以这段机器指令被称为shellcode

在实际的应用中,凡是用来注入的机器指令段都通称为shellcode,像添加一个用户、运行一条指令。

 

最基本的shellcode的编写可参考许同学的文章Shellcode入门,写得非常之清楚详实。以下实践即使用该文章中生成的shellcode。如下:

 

\x31\xc0\x50\x68\x2f\x2f\x73\x68\x68\x2f\x62\x69\x6e\x89\xe3\x50\x53\x89\xe1\x31\xd2\xb0\x0b\xcd\x80\

 

构造要注入的payload

Linux下有两种基本构造攻击buf的方法:

retaddr+nop+shellcode

nop+shellcode+retaddr

因为retaddr在缓冲区的位置是固定的,shellcode要不在它前面,要不在它后面。

简单说缓冲区小就把shellcode放后边,缓冲区大就把shellcode放前边

--

 

我们这个buf够放这个shellcode

结构为:nops+shellcode+retaddr

nop一为是了填充,二是作为“着陆区/滑行区”。

我们猜的返回地址只要落在任何一个nop上,自然会滑到我们的shellcode

 

然后百度了一下,install一下就ok

修改些设置。这部分的解释请看第5小节Bof攻击防御技术.

 

 execstack -s 20151120    //设置堆栈可执行

 execstack -q 20151120    //查询文件的堆栈是否可执行

X pwn1

 more /proc/sys/kernel/randomize_va_space

2

 echo "0" > /proc/sys/kernel/randomize_va_space //关闭地址随机化

 more /proc/sys/kernel/randomize_va_space 验证一下

0

然后构造一个shellcode进行注入

注意:(cat input_shellcode;cat) | ./20151120 完了不能回车,就保持不动,另打开一个终端查找进程号,不然就出错凉凉。

Ps -ef | grep 20151120为查找进程号

Gdb调试程序:

结果如下:不知道对否,出现了非法指令,想吐。。。。

另:可参考https://wenku.baidu.com/view/503d7977f242336c1eb95e1c.html?from=search

我对堆栈等寄存器不熟,所以这个网址可以弥补知识

posted on 2018-03-22 17:50  20151120肖明  阅读(207)  评论(0编辑  收藏