淺談文件包含漏洞
文件包含漏洞的出現及危害
文件包含漏洞是一種最常見的漏洞類型,它會影響依賴於腳本運行時的web應用程序。當應用程序使用攻擊者控制的變數構建可執行代碼的路徑時,文件包含漏洞會導致攻擊者任意控制運行時執行的文件。如果一個文件包含這個漏洞,為了方便起見,經常在開發階段就實施。由於它經常用於程序開發階段,所以這就為後來的攻擊埋下了伏筆並導致了各種基於文件的攻擊。
文件包含漏洞主要是程序員把一些公用的代碼寫在一個單獨的文件中,然後使用其他文件進行包含調用,如果需要包含的文件使用硬編碼,一般是不會出現安全問題,但是有時可能不確定需要包含哪些具體文件,所以就會採用變數的形式來傳遞需要包含的文件,但是在使用包含文件的過程中,未對包含的變數進行檢查及過濾,導致外部提交的惡意數據作為變數進入到了文件包含的過程中,從而導致提交的惡意數據被執行。
文件包含漏洞分為本地文件包含(Loacl File Inclusion,LFI)和遠程文件包含(Remote File Inclusion,RFI)。這種漏洞貌不驚人,卻危害很大。通過文件包含漏洞,可以讀取系統中的敏感文件,源代碼文件等,如密碼文件,通過對密碼文件進行暴力破解。若破解成功則可獲取操作系統的用戶賬戶,甚至可通過開放的遠程連接服務進行連接控制。另外不管是本地文件包含還是遠程文件包含,文件包含漏洞還可能導致執行任意代碼。
本地文件包含
本地文件包含就是通過瀏覽器包含web伺服器上的文件,這種漏洞是因為瀏覽器包含文件時沒有進行嚴格的過濾允許遍歷目錄的字元注入瀏覽器並執行。
首先,當值可以直接被控制時,你就會有一個非常類似的如下的代碼片段。
$ file = $ _GET ["file"];
include ($ file);
如果你可以找到上面的代碼,那麼就有一個直接包含的$文件,你可以控制它。
請注意:該文件可以是任何類型,無論它是被刪除的文件類型、圖片還是任意的內容,都包括在內。
首先,在當前文件夾中創建任意後綴的任意文件,如:file.txt(即使是像file.jpg這樣的圖片格式,則會產生以下效果)。
將文件的內容設置為:
phpinfo ();
此時,文件包含漏洞還包含當前伺服器中的其他文件,同時支持包含Web應用程序的目錄,如下所示:
嘗試包括你的硬碟的一些內容,例如:C:WINDOWSsystem.ini。
如果你這樣做,就可以在瀏覽器上看到任何文件的輸出內容。
這隻有當你有完全控制和文件類型沒有進一步指定時才有效。
那麼,如果代碼片段變成如下這樣,你該怎麼做?
$file = $_GET["file"] . ".php";
echo $file;
include($file);
在這種情況下,你可以嘗試按照上面的方法:
這將導致以下的輸出:
你可以看到,如果後綴是固定的,就像上圖一樣,你不會找到前面包含的文件。
所以這裡有另一種方法:%00到達時截斷一個字元串。這個技巧也被廣泛應用於不同的領域,我不會在這裡再詳述,如果想詳細了解,請點此。
在PHP中使用%00:
1.PHP版本
2. PHP `magic_quotes_gpc = off`;
3.PHP不會在收到的參數中使用addslashes函數,例如上面代碼中的$ _GET ["file"],不過在PHP版本5.3或更高版本中,此問題已得到解決。
如果打開gpc或者使用了加法器函數,序列將被正確地轉義。
首先,你可以嘗試如果gpc打開會發生什麼(效果與使用該函數相同)。
如果你啟用了gpc標誌,你可以直接看到這個過程是如何發生的。
接下來可以看看5.3版本中的情況:
這裡也沒有明顯的效果。
所以你可以看到,只要滿足上述三個條件,就可以使用%00。
首先,你要將PHP版本更改為5.2,並在php.ini更改為 magic_quotes_gpc = on tomagic_quotes_gpc = off.後重新啟動Apache。
這使你就能夠在嘗試時使用截斷。
這時可以看到,你已經成功地使用了其中的截斷。
那麼文件只包含了包含的功能嗎?當然不是,之所以會這樣,是因為你可以控制可以包含的內容。
你可以創建一個文件:shell.txt來進一步利用這個漏洞。
你可以看到,其中也包括了shell。
那麼兩者有什麼區別呢?其實沒有什麼區別,原理是一樣的,但是第一個是用後綴來介紹的,第二個是固定在程序後綴後面的。但是可以使用%00,因為當程序流(program stream )遇到%00終止符(terminator)時它會直接終止。
遠程文件包含
遠程文件包含就是允許攻擊者包含一個遠程的文件,一般是在遠程伺服器上預先設置好的腳本。 此漏洞是因為瀏覽器對用戶的輸入沒有進行檢查,導致不同程度的信息泄露、拒絕服務攻擊 甚至在目標伺服器上執行代碼。
本地文件包含與遠程文件有著相同的原理,但前者只能包含伺服器上存在的文件,而後者可以包含遠程伺服器上的文件。
對於遠程文件,你需要考慮以下2點:
1.在php.ini中需要allow_url_include = on和allow_url_fopen= on
2.所需的遠程文件後綴不能與目標伺服器的語言相同,如目標伺服器解析PHP代碼,則遠程文件後綴不能為.php。
讓我解釋一下第二點,如果你的遠程文件具有.php後綴,並且你的遠程文件內容如下所示:
phpinfo ();
那麼在遠程伺服器執行phpinfo()之後,你就可以獲得目標伺服器的內容。由於它不會運行代碼,所以包含的信息不是目標伺服器,而是遠程伺服器。
如下所示:
這是我的PHP5.6版本的遠程設備信息,目標設備是5.2版本。
接下來是包含文件:
你可以看到,包含文件後,你的遠程設備發生了變化,這是為什麼呢?
由於目標伺服器不包含此代碼:
此時,遠程伺服器會執行此代碼的源代碼,如下所示:
所以為了使這個攻擊開始運行,你需要做一些修改:
1.修改配置
2.修改文件後綴
此時,你可以再來嘗試一下包含的攻擊向量:
那麼你可以看到所需的信息在此包含之後返回,並且你的目標設備信息不再改變。
接下來,你要再次為遠程文件包含做一個shell示例。
遠程文件包含使用的前提是,符合本地文件包含的前提並符合遠程文件包含其可用性的前提。
文件包含許多偽協議
文件中可以包含不同的偽協議,我將在下面演示其中的一些:
1.data:text/plain or data: text/plain; base64
2.php://input
3.php://filter
4.file://
5.zip://
其他協議可以在官方文檔中找到。
data:text/plain
輸出直接顯示在相應的URL中,顯示參數:data:text / plain。
然後你需要執行如下所示的php代碼:
data:text/plain; BASE64
有另一種方法來使用data: text/plain; base64,不過此時你需要使用base64編碼來執行PHP代碼,base64php代碼如下所示:
## php://input
php://input訪問請求的原始數據的只讀流(read-only stream),會將post請求中的數據作為php代碼執行。
你可以看到程序自動添加了一個.php後綴,因此使用包括php://input,將自動添加.php,所以它肯定不能正常工作。
此時,你可以參考以上的%00技巧來截斷文件路徑。
你可以看到終止符(terminator)是非常強大的。
php://filter
php://filter可以讀取php文件的代碼base64編碼的輸出並將其返回給你。
例如,你想讀取一個PHP文件,但不希望它是正常的PHP。你可以通過php://filter/read=convert.base64-encode/resource=
../ 讀取文件代碼的內容。
解碼base64後,你可以像正常情況一樣獲取內容:
file://
file://用於訪問本地文件系統,不受allow_url_fopen orallow_url_include的影響,你可以使用file:// absolute / path / to / file來獲取。
zip://
zip://可以訪問zip文件中的文件,但它需要一個絕對路徑。你可以使用zip://[archive absolute path] # [compressed file name]在本地創建一個文件並將其壓縮到一個zip壓縮文件中。
此時,你就可以填入絕對路徑和文件的名稱了。那麼,你可能會有兩個疑問?
為什麼你不能成功顯示包括zip://的錯誤?
這其中就包含zip://C:/phpStudy/WWW/include/phpinfo.zip.php,這是因為你不想包含這個文件,而是想把這個文件包含在zip里。
為什麼是#以後的值?
因為#會忽略它後面的參數,所以你需要在表單中使用%23。還有一點就是,包含的文件以.php結尾,但你壓縮了php後綴的文件。
所以如下所示,你不需要這個後綴。
※淺談Metasploit框架中的Payload
※AtomBombing利用分析
TAG:嘶吼RoarTalk |