摘要: 本文主要介紹在Linux操作系統下PHP網站服務器配置的方法與技巧,從Web服務器安全、PHP本身的安全配置分別介紹配置方法,很好地解決了PHP網站在Linux系統下的應用。
關鍵詞: Linux操作系統PHP服務器安全配置
一、Web服務器安全
PHP是Web服務器的一個模塊功能,所以要想使PHP擁有較安全的配置,首先要保證Web服務器的安全,當然Web服務器要安全就必須先保證系統安全。PHP可以和各種Web服務器結合,這里只討論Apache。筆者建議以chroot方式安裝啟動Apache,這樣即使Apache和PHP及其腳本出現漏洞,受影響的也只有這個禁錮的系統,不會危害實際系統。但是我們使用chroot的Apache后,會給應用帶來一定的麻煩,比如連接mysql時必須用“127.0.0.1”地址,使用tcp連接而不能用localhost實現socket連接,這在效率上會稍微差一點。mail函數發送郵件也存在一定的問題,因為php.ini里的:
[mail function];
For Win32 only.
SMTP=localhost,
For Win32 only.
sendmail_from=me@localhost.com
這都是針對Win32平臺的,所以我們需要在chroot環境下調整好sendmail。
二、PHP本身問題
1.遠程溢出
PHP-4.1.2以下的所有版本都存在文件上傳遠程緩沖區溢出漏洞,而且攻擊程序已經廣泛流傳,成功率非常高:
http://packetstormsecurity.org/0204-exploits/7350fun
http://hsj.shadowpenguin.org/misc/php3018_exp.txt
2.遠程拒絕服務
PHP-4.2.0和PHP-4.2.1存在PHP multipart/form-data POST請求處理遠程漏洞,雖然不能獲得本地用戶權限,但是也能造成拒絕服務。
3.safe_mode繞過漏洞
PHP-4.2.2以下到PHP-4.0.5版本都存在PHP mail函數繞過safe_mode限制執行命令漏洞。從4.0.5版本開始,mail函數增加了第五個參數,設計者可以突破safe_mode的限制執行命令,其中4.0.5版本突破非常簡單,只需用分號隔開后面加shell命令就可以了。
三、PHP本身的安全配置
PHP的配置非常靈活,我們可以通過php.ini、httpd.conf、.htAccess文件(該目錄必須設置了AllowOverride All或Options)進行設置,還可以在腳本程序里使用ini_set()和其他的特定的函數進行設置,通過phpinfo()和get_cfg_var()函數可以得到配置選項的各個值。
如果配置選項是唯一PHP_INI_SYSTEM屬性的,我們必須通過php.ini和httpd.conf來修改,其修改的是PHP的Master值,但修改之后必須重啟apache才能生效。其中php.ini設置的選項是對Web服務器所有腳本生效,httpd.conf里設置的選項是對該定義的目錄下所有腳本生效。
在討論Linux系統下安全配置PHP服務器之前,我們應該了解PHP的safe_mode模式。
1.safe_mode
safe_mode是唯一PHP_INI_SYSTEM屬性,它必須通過php.ini或httpd.conf來設置。要啟用safe_mode,只需修改php.ini:
safe_mode=On
重啟apache后,safe_mode就生效了,啟動safe_mode,會對許多PHP函數進行限制,特別是和系統相關的文件打開、命令執行等函數。
雖然safe_mode不是萬能的(低版本的PHP可以繞過),但筆者還是強烈建議用戶打開安全模式,這樣在一定程度上能夠避免一些未知的攻擊。不過啟用safe_mode會有很多限制,可能對應用帶來影響,所以用戶還需要調整代碼和配置才能和諧。被安全模式限制或屏蔽的函數我們可以參考PHP手冊。
2.變量濫用
PHP默認register_globals=On,對于Get、Post、Cookie、Environment、Session的變量我們可以直接注冊成全局變量。它們的注冊順序是variables_order=″EGPCS″(可以通過php.ini修改),同名變量variables_order右邊的覆蓋左邊,所以變量的濫用極易造成程序的混亂,而且腳本程序員往往沒有對變量初始化的習慣,像如下的程序片斷就極易受到攻擊:
//test_1.php
if($pass == ″hello″)
$auth = 1,
if($auth == 1)
echo ″some important information″,
else
echo ″nothing″,
?>
攻擊者只需用如下的請求就能繞過檢查:
http://victim/test_1.php?auth=1
PHP-4.1.0發布的時候建議關閉register_globals,并提供了7個特殊的數組變量來使用各種變量。對于從Get、Post、Cookie等來的變量并不會直接注冊成變量,我們必須通過數組變量來存取。PHP-4.2.0發布的時候,php.ini默認配置就是register_globals = Off,這使得程序使用PHP自身初始化的默認值,一般為0,避免了攻擊者控制判斷變量。
解決方法:
配置文件php.ini設置register_globals = Off。
這要求程序員對作為判斷的變量在程序最開始初始化為一個值。
參考文獻:
[1]周星.基于PHP應用的數據共享與傳遞技術.北京:人民郵電出版社,2007.
[2]網勝工作室著.PHP410程序設計.北京:北京希望電子出版社,2006.
[3]仲進平.PHP網絡開發技術程序設計[M].北京:人民郵電出版社,2007.
[4]飛思科技產品研發中心.PHP網站設計與實現.北京:電子工業出版社,2004.