利用gcc自带的功能-fstack-protector检测栈溢出及其实现
最近又遇到了一個(gè)崩潰,棧回溯非常怪異。
/lib/i386-linux-gnu/libc.so.6(gsignal+0x4f) [0xb2b751df] /lib/i386-linux-gnu/libc.so.6(abort+0x175) [0xb2b78825] /lib/i386-linux-gnu/libc.so.6(+0x6b39a) [0xb2bb239a] /lib/i386-linux-gnu/libc.so.6(__fortify_fail+0x45) [0xb2c4b0e5] /lib/i386-linux-gnu/libc.so.6(+0x102eba) [0xb2c49eba] /ramdisk/xxxxxx() [0x8467639] /ramdisk/xxxxxx() [0x849a802] /ramdisk/xxxxxx() [0x84b75da] /ramdisk/xxxxxx(xxxxxxxxxxxx+0x444) [0x84b9224]其中的xxxxx是公司的模塊和函數(shù),故隱藏,對(duì)接下去的分析沒有影響。
一開始,因?yàn)闆]有接觸過__fortify_fail這個(gè)函數(shù),另外加上因?yàn)橛幸徊糠謼;厮輿]有對(duì)應(yīng)的符號(hào),我以為是數(shù)組溢出把棧信息破壞了。但實(shí)際上想想不對(duì),如果是棧信息被破壞了,不出意外的話,應(yīng)該是回溯不到某些很有序的函數(shù)的,這些函數(shù)我沒上。
后來同事無意的一句話,說__fortify_fail是內(nèi)存檢測,我才百度了一下這個(gè)__fortify_fail函數(shù),那么這個(gè)函數(shù)是什么情況下會(huì)被調(diào)用的呢?
一。gcc編譯選項(xiàng)-fstack-protector和-fstack-protector-all
正是我在前面猜測的錯(cuò)誤原因,牛人Stack Guard?就想出了保護(hù)棧信息的方式,在ebp和ip等信息的地址下面放一個(gè)保護(hù)數(shù),如果棧溢出,那么這個(gè)8位數(shù)會(huì)被修改,就會(huì)導(dǎo)致函數(shù)進(jìn)入棧溢出錯(cuò)誤處理函數(shù),也就是導(dǎo)致了上面的棧。
二。比較加選項(xiàng)前后的反匯編代碼
源碼:
#include <stdio.h> int main() {char a;int i;memcpy(&a,"ss",2);printf("1\n");memcpy(&i,"sssss",4);printf("2\n");return 0; }使用gdb調(diào)試該程序,首先查看a和i的地址,
(gdb) p &a $1 = 0xbffff69b "\b\364\037\374\267\220\204\004\b" (gdb) p &i $2 = (int *) 0xbffff694顯然變量a的地址要高,更接近棧頂。可以證明i的溢出并不一定能被檢測到,而a的檢測一定會(huì)被檢測到。
看下匯編代碼的對(duì)比。
movw $0x7373那句話就是往a里面拷貝ss,所以整個(gè)程序前后的差異在于插入兩段代碼,這兩段的代碼就是用來檢測局部變量。
運(yùn)行溢出時(shí)的棧
#0 0xb7fdd424 in __kernel_vsyscall () #1 0xb7e4f1ef in raise () from /lib/i386-linux-gnu/libc.so.6 #2 0xb7e52835 in abort () from /lib/i386-linux-gnu/libc.so.6 #3 0xb7e8a2fa in ?? () from /lib/i386-linux-gnu/libc.so.6 #4 0xb7f20dd5 in __fortify_fail () from /lib/i386-linux-gnu/libc.so.6 #5 0xb7f20d8a in __stack_chk_fail () from /lib/i386-linux-gnu/libc.so.6 #6 0x08048485 in main ()與本文最前面的錯(cuò)誤是一致的
三。走讀代碼修改錯(cuò)誤。
?
四。總結(jié)
當(dāng)然這個(gè)舉措并不能夠完全的抑制棧溢出,如果跳過了保護(hù)數(shù),那么還是檢測不到棧溢出的,并且對(duì)其他的局部變量溢出沒有保護(hù)。當(dāng)然每個(gè)變量都保護(hù)會(huì)大大增加程序復(fù)雜度。
?
轉(zhuǎn)載于:https://www.cnblogs.com/leo0000/p/5719186.html
總結(jié)
以上是生活随笔為你收集整理的利用gcc自带的功能-fstack-protector检测栈溢出及其实现的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 19、Java并发编程:线程间协作的两种
- 下一篇: 海量处理面试题