C语言常见漏洞-缓冲区溢出

缓冲区溢出是指当计算机向缓冲区内填充数据位数时超过了缓冲区本身的容量溢出的数据覆盖在合法数据上。

理想的情况是程序检查数据长度并不允许输入超过缓冲区长度的字符,但是绝大多数程序都会假设数据长度总是与所分配的储存空间相匹配,这就为缓冲区溢出埋下隐患。

缓冲区溢出有堆缓冲区和栈缓冲区溢出,二者有些不同,大部分情况下都是讨论栈溢出。

1.原理

1.1 函数调用栈情况

程序运行时,为了实现函数之间的相互隔离,需要在调用新函数时保存当前函数的状态,这些信息全在栈上,为此引入栈帧。每一个栈帧保存者一个未运行完的函数的信息,包括局部变量等等。栈帧的边界由ebp/rbp(栈底指针)和esp/rsp(栈顶指针)确定。

先看一看函数调用时的栈情况,以func1调用func2为例。假如func2有2个形参。

当func1调用 func2会执行如下汇编码

push arg2
push arg1
call func2
add esp, 8

一般一个函数(func2)的起始和终止汇编代码会有如下操作

push ebp
mov ebp, esp
sub esp, xxx
...
mov esp, ebp
pop ebp
retn

func1调用func2之前,栈中只有func1的局部变量。

  • 执行call指令前,func1func2的2个参数压栈,此时ebp在func1局部变量之下,esp指向func2的第一个参数arg1
  • 之后执行call指令,将程序下一条指令的eip(add esp,8)压栈,跳到func2。ebp不变,esp指向返回地址。
  • 之后跳到func2指向push ebpfunc1的ebp被压栈。ebp依旧不变。
  • 执行mov ebp, esp。此时func2的ebp指向的是func1的ebp。
  • 执行sub esp, xxx,扩充栈空间,给局部变量清出空间。
  • 执行mov esp, ebp,销毁func2栈帧,再执行pop ebp。恢复func1的ebp。此时retn弹出func1的 eip(func2的返回地址)并回到func1继续执行。
  • 回到add esp, 8指令。清除func2的2个参数,此时栈中只剩func1局部变量。

func2执行完sub esp, xxx后整个栈空间布局如下,此时ebp指向的是func1的ebp。从func2返回地址到func1的局部变量都属于func1的栈帧。

func2局部变量
func1的ebp
func2返回地址(func1某条指令)
func2 2个参数
func1局部变量

1.2 缓冲区溢出

void function(
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值