標籤:system esx ops 變數 rck nmf sls ups rar
sourcecode核心代碼:
1 <? 2 3 function genRandomString() { 4 $length = 10; 5 $characters = "0123456789abcdefghijklmnopqrstuvwxyz"; 6 $string = ""; 7 8 for ($p = 0; $p < $length; $p++) { 9 $string .= $characters[mt_rand(0, strlen($characters)-1)];10 }11 12 return $string;13 }14 15 function makeRandomPath($dir, $ext) {16 do {17 $path = $dir."/".genRandomString().".".$ext;18 } while(file_exists($path));19 return $path;20 }21 22 function makeRandomPathFromFilename($dir, $fn) {23 $ext = pathinfo($fn, PATHINFO_EXTENSION);24 return makeRandomPath($dir, $ext);25 }26 27 if(array_key_exists("filename", $_POST)) {28 $target_path = makeRandomPathFromFilename("upload", $_POST["filename"]);29 30 31 if(filesize($_FILES[‘uploadedfile‘][‘tmp_name‘]) > 1000) {32 echo "File is too big";33 } else if (! exif_imagetype($_FILES[‘uploadedfile‘][‘tmp_name‘])) {34 echo "File is not an image";35 } else {36 if(move_uploaded_file($_FILES[‘uploadedfile‘][‘tmp_name‘], $target_path)) {37 echo "The file <a href=\"$target_path\">$target_path</a> has been uploaded";38 } else{39 echo "There was an error uploading the file, please try again!";40 }41 }42 } else {43 ?>
關鍵區段已標為紅色,該指令碼的初期分析參見上一篇writeup。
這是exif_imagetype()的介紹(http://php.net/manual/en/function.exif-imagetype.php)
為什麼該函數會通過讀取檔案的第一個位元組簽名來判斷圖片類型呢?
Magic number(https://en.wikipedia.org/wiki/Magic_number_%28programming%29#Magic_numbers_in_other_uses)
List of file signatures(https://en.wikipedia.org/wiki/List_of_file_signatures)
Magic file number(http://www.astro.keele.ac.uk/oldusers/rno/Computing/File_magic.html)
思路一:直接通過篡改file signature將php指令碼偽裝成
這個地方將php指令碼偽裝為BMP格式更方便一些,因為BMP格式對應的file signature為字元BM可以用ascii碼錶示,不需要通過hexeditor等16進位編輯器進行編輯
1 BM<?php $a = system(‘cat /etc/natas_webpass/natas14‘);echo $a;?>
在本地寫一個測試檔案test2.php
1 <?php echo exif_imagetype(‘test.php‘); ?>
輸出結果為6
注意這題依舊是在本地用一個hidden的filename變數”強制“將格式轉為jpg,上傳前要先把它改成php
思路二:篡改圖片的Exif,在其中添加php指令碼。
我們可以建立一個圖片,在圖片的exif中添加php指令碼(如comment),當伺服器上的php解譯器解釋php時,它只會理會<?php ?>中的代碼,而對其他的文本當做html直接輸出。
以下是通過GIM建立圖片:
使用hexeditor開啟建立的圖片:
前4個位元組為file signature,以@開始後的一個句子就是php指令碼。
上傳執行後即可得到flag。
總結:這個題和上個題的根本漏洞就在於管理者將格式控制單元放在了用戶端(即那個hidden的filename變數),以為在服務端是通過pathinfo($fn, PATHINFO_EXTENSION)得到格式一定是filename的jpg。然而用戶端可以通過篡改filename變數使得伺服器將尾碼名填寫為.php,這個題雖然增加了通過file signature/file magic number來判斷檔案是否為圖片,然而這也是可以篡改的。總之,對用戶端的行為完全不能信任,對其上傳的檔案要給與最低許可權,在伺服器端一定要有完整驗證手段,並且這種手段不能依賴於用戶端設定好的非審查變數。
拿到flag:Lg96M10TdfaPyVBkJdjymbllQ5L6qdl1
Natas Wargame Level 13 Writeup(檔案上傳漏洞,篡改file signature,Exif)