不知道有没有听说过缓冲区溢出,那什么是缓冲区溢出呢?缓冲区溢出就是在大缓冲区中的数据向小缓冲区复制的过程中,由于没有进行边界检查,从而导致数据从小缓冲区溢出而冲掉了相邻内存区域的其它数据。缓冲区溢出是很常见的内存错误,攻击者入侵系统利用缓冲区溢出几乎可以做任何事情,因为成功利用缓冲区溢出漏洞不仅可以修改内存中变量的数据,还可以劫持进程,执行恶意代码,获取主机控制权。
我们要理解这一类攻击手法,那就有必要了解一下计算机体系架构,CPU,寄存器,内存等知识。Windows系统程序运行时内存可以分为四个部分:
1.代码区,.text区段,这个区域存储着被装入的二进制机器代码。
2.数据区,.data区段,存储全局变量。
3.堆区,一个进程可以在堆区动态地申请一定大小的内存,用完之后再还给堆区。
4.栈区,用于动态地存储函数之间的调用关系,传递参数,保存函数返回地址。
我们这里介绍的是栈溢出,所以先介绍一下栈的结构(堆溢出攻击与栈溢出攻击完全不同,注意一下)。
栈是一种数据结构,是一种先进后出的数据表,有两种操作:出栈pop和入栈push,栈的标识也有两个:栈顶top和栈低base。系统中也有一个系统栈,与普通栈一样,系统栈由系统维护,主要用于实现高级语言中函数的调用。程序中各个函数的跳转都是与系统栈结合完成的,当一个函数被调用的时候,系统栈会给这个函数开辟一个新的栈帧,把它压入栈中。栈帧中的内存空间被所属的函数独占,一般情况下不会和其它函数共享,当函数返回时,系统栈会弹出该函数的栈帧。
每一个函数独占自己的栈帧空间,当前正在运行的函数栈帧总是在栈顶,汇编中有两个寄存器与栈相关:
1.esp,栈指针寄存器,extended stack pointer,存放一个指针,指向系统栈最上面一个栈帧的栈顶。
2.ebp,基址指针寄存器,extended base pointer,存放一个指针,指向系统栈最上面一个栈帧的栈底。
注意一下栈帧底部和栈底是两个不同的概念:
栈低:系统栈的底部。
栈帧底部:系统栈最上面那个栈帧的底部。
在函数栈帧中一般包含了几类信息