Memory Layout
x86-64 Linux Memory Layout
在当时的硬件最大只支持47位,这就是00007FFFFFFFFFFF(11个F,7用2进制表示是3个1)出现在这里的原因。
2^47近似等于128*10^12,也就是128TB。10^15是PB 10^18是EXB,谷歌当时每天能产生好几PB的数据。10^21是ZB。
据估算(当时)如果把全世界一年所有人拍摄的视频的内存加起来就是几个ZB。
在上图中,stack指针的范围是8MB,访问如果超出这个界限,那么就会segmentation fault。
往下更下方的地址是你的程序存放的代码的位置。
x86-64 Example Addresses
如上图 小的数组恰巧被被分配在了粉色区域的稍微高出一点的地方,类似的,那些巨大的数组被分配在了接近栈的限制的地方。
如果是这去引用中间的这篇空白区域会产生一定的错误。
然后将会发生的事情是,如果你持续的调用malloc,两边的地址会朝向中间靠近。原则上来说,如果你有太多的内存请求,上下的两块会香芋并且malloc将会放回0。
Buffer Overflow
Buffer Overflow Stack
Code Injection Attacks
How Does The Attack Code Execute?
在程序中注入新的函数。
What To Do About Buffer Overflow Attacks
那么我们要怎么做才能阻止overflow attack呢?
大致是有三种方法
1. Avoid Overflow Vulnerabilities in Code (!)
- 使用fgets()代替gets() 比如使用库函数限制输入的数据长度。
- strncpy代替strcpy
- 不使用带有%s的scanf,使用fgets(),或者使用滴啊有%ns的scanf
2. System-Level Protection can help
随机的地址偏移,让黑客不知道从哪里插入代码
3. Stack Canaries can help
基本做的就是从stack中获得canaries的信息,看看和本应该过来的canaries是否相等,相等很fine。不相等,说明程序可能已经被corrupt了。
carnaries的中文就是金丝雀,这是以前在矿井工作的工人拿来检测矿井毒性的一个方法:提前把金丝雀放到矿井下,如果金丝雀没死,说明矿井是安全的,如果金丝雀死了,则说明矿金非常不安全。
Protected Buffer Disassembly
老师说其他两种方法其实黑客都可以破解,但是canary这种方法还没有人能破解。
Unions
类似C中的struct,将所有的类型集合,赋予一个最大数量的byte.
Union Allocation