二进制漏洞
二进制漏洞
缓冲区溢出
缓冲区:程序在运行前会预留的内存空间,用于临时存储I/O数据
缓冲区溢出:通过向程序的缓冲区写入超出其长度的内容,造成缓冲区的溢出,从而破坏程序的堆栈,造成程序崩溃、系统关机或使程序执行其它指令,以达到攻击的目的
栈溢出
待填充….
堆溢出
堆是程序运行时动态分配的内存,使用完毕后需要把堆指针传给堆释放函数来回收这片内存,否则会造成内存泄露
堆结构
堆块
- 堆区内存按不同大小组织成块,以块为基本单位进行标识
- 块首
- 头部几个字节,可以标识堆块信息
- 块身
- 最终分配给用户使用的数据区
堆表
- 位于堆区的起始位置,用于索引堆区中所有堆块的重要信息
Windows中,占用态的堆块被使用它的程序索引,堆表只索引所有空闲态堆块
空表
空闲双向链表 Freelist
空表索引:堆区一开始的堆表区中有128项的指针数组,每一项包含两个指针
- 第1-127项空闲堆块的大小 = 索引项(ID)x 8字节
- 第0项标识的空表为大于等于1024字节的堆块(小于512KB)
快表
快速单向链表 Lookaside
整型溢出
整数类型都有一个取值范围,当运算结果大于最大值或小于最小值时,就会发生溢出
- 大多数整形溢出不能直接利用,但如果该整形变量决定内存分配等操作,则可作为漏洞被间接利用
存储溢出
1
2
int len1 = 0x10000;
short len2 = len1;
导致len1
为0
运算溢出
对整型数变量进行运算的过程中没有考虑其边界范围,造成运算后的数值超出了其存储空间
符号问题
Apache HTTP Server分块编码漏洞
UAF
User-After-Free,释放后被重用
防范
DEP
Data Execution Prevention,数据执行保护
将非代码段的页表属性设置成“不可执行“,一旦系统从这些地址空间进行取指令操作,CPU就会报告”内存违规”异常,进而”杀死“进程。栈空间也被操作系统设置成”不可执行“属性,因此,注入栈中的Shellcode就无法执行了
- DEP需要硬件页表机制的支持
- x86结构的页表没有NX(不可执行)位
- 只能使用软件模拟的方式
- x64系统支持NX位
- x86结构的页表没有NX(不可执行)位
绕过DEP:ROP
栈金丝雀
canary
在栈中buffer之后的位置放置特殊的值–金丝雀,退出函数之前,检查是否被破坏
1
-fstack-protector (gcc默认开启)
ASLR
Address Space Layout Randomization,地址空间随机化
通过对堆、栈、共享库映射等线性布局的随机化处理,增加攻击者预测目标地址的难度,从而防止攻击者直接定位相关代码
破解:nop sled
- 攻击者难以知道注入代码(shellcode)的地址,所以需要在一定的范围内枚举攻击代码的位置
- 而通过在shellcode之前添加注入很长的nop指令,就可以增加shellcode成功执行的概率
- 因为nop指令无任何操作,会增加eip,使其滑向shellcode
This post is licensed under CC BY 4.0 by the author.