2012-02-05 54 views
2

我看這個例子w.r.t在堆棧中執行代碼:理解在執行堆棧的C代碼(蘋果黑客手冊代碼)

#include <stdio.h> 
    #include <stdlib.h> 
    #include <string.h> 
    char shellcode[] = 「\xeb\xfe」; 
    int main(int argc, char *argv[]){ 
      void (*f)(); 
      char x[4]; 
      memcpy(x, shellcode, sizeof(shellcode)); 
      f = (void (*)()) x; 
      f(); 
} 

這將導致一個分段錯誤。我的理解是因爲shellcode的剩餘字節內存不足,因爲x只有4個字節的大小。這導致創建複製到堆棧內存的寫入操作,並導致seg。由於堆棧內存是隻讀的故障。 我的理解是否正確?

+1

堆棧不是隻讀的,但很可能不可執行。 – 2012-02-05 00:21:48

+0

只有3個字節可以複製。 '\ x'表示接下來的兩個字符表示實際放入程序的字節的十六進制值。 – ughoavgfhw 2012-02-05 00:23:10

回答

2

準確地說你正在使用哪種操作系統?

爲了從Mac黑客手冊引用:

豹不設置XD位上的任何內存部分除了 堆棧。 目前還不清楚這是一個錯誤,疏忽還是故意, 但即使軟件的內存權限設置爲 不可執行,您仍然可以在堆棧之外的任何地方執行。以下簡單的程序說明了這一點。

[您的代碼段如下]

(重點煤礦。)

如果權限被設置爲不可執行的(或者如果權限被省略共)的代碼應該段錯誤。它並不在Leopard上,即使作者也提出質疑。你觀察到的是現代操作系統的完美正常行爲。

我會補充:嘗試通過調試器運行它。 \xeb\xfe是一個無限循環,但你在技術上不應該循環一次。操作系統應該把你放在手腕上(這顯然是在這裏發生的)。

+1

明白了。沒有意識到\ xeb \ xfe是一個無限循環。我正在獅子測試這個。所以基本上,因爲函數永遠不會返回的堆棧將永遠不會返回,這將有點凍結系統......這是重點嗎? – ZionKing 2012-02-05 00:33:50

+0

@ZionKing進程獨立運行,因此它不會凍結系統。 – 2012-02-05 00:45:35

+0

這也有助於:http://stackoverflow.com/questions/5609745/jmp-short-0x0-causing-loop-forever – ZionKing 2012-02-05 00:46:25