逆向工程日记之缓冲区溢出的基本原理(一)

前言

Hello,各位广大的网友们好。笔者为大二在校大学生,软件学院。为践行费曼学习法,并在前辈的建议下开始写自己的一系列博客,网上对于缓冲区溢出的例子基本在与Linux环境下操作。对未了解Linux内核以及常见操作指令的新手并不友好。鉴于此写下此文。

实验前提

  1. 实验环境 :windows 10;
  2. 使用工具 :IDA pro , OllyDBG,vc6.0;
  3. 目标软件 :test1.exe , test2.exe

所需基础

基础汇编指令

简单C语言基础

数据结构(仅堆栈)

即使上面基础缺失,本文任有大量的注释及解释帮助理解。

概要

通过编写两个C例程序,使用工具OD,IDA pro进行逆向分析。针对汇编语句中CALL机制剖析缓冲区溢出的基本原理。

实验开始

编写实验程序text1.exe , text2.exe

text1.exe中C代码如下:

#include<stdio.h>  //引入头文件
#include<string.h>

char name[] = "zhemu";  //定义全局变量

int main()            //返回值 主函数main()
{
	char buffer[8];   //开辟8个字节的空间用来存储变量name
	strcpy(buffer,name);  //内置函数(作用):将变量name内容赋值给buffer变量
	printf("%s\n",buffer);  //输出在控制台
	getchar();               //方便观察 作用:等待用户输入按键
	return 0;                //返回值
}

text1.c中 ,变量name赋值给buffer后并未引起缓冲区溢出

text2.exe中C代码如下:

#include<stdio.h>  //引入头文件
#include<string.h>

char name[] = "zhemuzhemu";  //定义全局变量 !!多了个zhemu

int main()            //返回值 主函数main()
{
	char buffer[8];   //开辟8个字节的空间用来存储变量name
	strcpy(buffer,name);  //内置函数(作用):将变量name内容赋值给buffer变量
	printf("%s\n",buffer);  //输出在控制台
	getchar();               //方便观察 作用:等待用户输入按键
	return 0;                //返回值
}

text1.c中 ,变量name赋值给buffer后引起缓冲区溢出

对text1.exe进行逆向分析。

将vc6.0生成的debug版本exe拖入OllyDBG进行逆向分析

OllyDBG载入方式:
1.鼠标拖动exe进入到OD控件区域
2.文件-附加-选择运行中的进程
第一次载入
!由于新版本的Visual Studio,微软加入GS机制,防止缓冲区溢出的情况出现

由上图:004015B0地址为软件初始运行地址,并非main函数的起始地址。可通过F7/F8一步步运行至main函数所在地址。过于繁琐,所以采用IDA快速定位main函数所在地址,如下图:

在这里插入图片描述
快速定位main函数所在地址
1.双击进入main
2.右键选择Text View,初始默认为Graph View
可得main函数地址如下图:
在这里插入图片描述
4.IDA 快捷键Ctrl+x 定位上一层交叉引用。(简单理解就是从哪里来 ,谁调用它)
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
由此可知,开始main函数上一个地址00401693,重返OD进行堆栈溢出研究
在这里插入图片描述
通过OD中快捷键Ctrl+G快速定位到call函数上一条指令地址,快捷键F2对00401693下断点,快捷键F9让调试直接运行到此处代码。 同时也可以按F4运行于此!

在这里插入图片描述
F8步过程序,留意右下角栈区调用情况。
调用CALL函数:
1.将CALL下一个地址压入栈(00401694)
2.jmp CALL

在这里插入图片描述
由上图: 压入栈区为地址(00401694)返回地址。重要关键地方
笔者在右下角栈区设置转换为ASCII数据 方便观察

在这里插入图片描述
新手可以忽略之前栈平衡以及栈区开辟空间指令,由地址00401030可知,此时与C语言代码对应开始,将ASCII压入栈区,并进行strcpy赋值操作。

对汇编认识可以初步认识此步骤,重点在于调用完CALL之后返回到初始地址下一条

来到call函数调用返回所在位置:

在这里插入图片描述
可以看出retn返回的地方栈区栈顶指向的地址为:00401699 call函数调用完下一指令

OK,到此为止我们了解了一个CALL函数调用的基本过程,直接进入text2.exe分析,当堆栈溢出栈区会发生什么呢?

对text2.exe进行逆向分析。

步骤不多累赘与text1.exe完全一摸一样,唯一不一样在于栈区返回地址被溢出(占用)
在这里插入图片描述
由上图可知:
1.原本改返回值:00401699地址被占用 且指向错误的地址(或不应该的地址)

缓冲区溢出漏洞原理总结

至此,大家应该已经了解了缓冲区溢出漏洞的原理,它就是因为我们输入了过长的字符,而缓冲区本身又没有有效的验证机制,导致过长的字符将返回地址覆盖掉了,当我们的函数需要返回的时候,由于此时的返回地址是一个无效地址,因此导致程序出错。
那么依据这个原理,假设我们所覆盖的返回地址是一个有效地址,而在该地址处又包含着有效的指令,那么我们的系统就会毫不犹豫地跳到该地址处去执行指令。因此,如果想利用缓冲区溢出的漏洞,我们就可以构造出一个有效地址出来,然后将我们想让计算机执行的代码写入该地址,这样一来,我们就通过程序的漏洞,让计算机执行了我们自己编写的程序。

本文其中例子与实例深受i春秋启发,并进行归纳总结,笔者才学疏浅,若有错误之处欢迎指出

  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值