Apache HTTP Server 版本2.2
suEXEC特性使得Apache可以使用與調(diào)用web服務(wù)器的用戶不同的用戶身份來運行CGI和SSI程序。而通常情況下,CGI或者SSI程序執(zhí)行時使用和web服務(wù)器相同的用戶身份。
正確運用該特性,可以減少很多因為提供用戶執(zhí)行私有CGI或者SSI程序所帶來的安全風(fēng)險。但如果配置不當(dāng)?shù)脑挘瑒t可能引起很多問題,使你的計算機產(chǎn)生更多的安全漏洞。如果你對管理 setuid root 程序以及可能導(dǎo)致的安全問題不熟悉的話,我們強烈建議你不要使用suEXEC。
在我們開始切入正題之前,你必須明白Apache開發(fā)組以及本文檔所做的假設(shè)。
首先,我們假設(shè)你正在使用類UNIX操作系統(tǒng),只有這類操作系統(tǒng)才具有setuid和setgid命令。所有的其他命令行的例子也是如此。其他的操作系統(tǒng)平臺,即使也支持suEXEC,但是它的配置可能和我們所講的并不相同。
第二,我們假設(shè)你熟悉計算機的安全和管理計算機的一些基本概念。這關(guān)系到如何正確理解setuid/setgid操作以及對你的系統(tǒng)可能帶來的各種影響和不同的安全等級。
第三,我們假設(shè)你正在使用源代碼未經(jīng)修改的suEXEC版本。所有suEXEC的代碼都經(jīng)過開發(fā)者的仔細查驗并做過大量測試。在這些代碼中,人們采取了各種預(yù)防措施,使之簡單、健壯、安全。修改這些代碼可能會導(dǎo)致預(yù)料之外的問題和安全隱患。所以我們強烈地建議你不要修改代碼,除非你精通安全編程,并愿意和Apache開發(fā)組共享成果。
第四,也是最后一點,Apache開發(fā)組已經(jīng)決定默認不安裝suEXEC。suEXEC的配置需要管理員細致關(guān)注各個細節(jié)。在仔細考察過關(guān)于suEXEC的各種設(shè)置方法后,管理員應(yīng)該使用標準的安裝方法來安裝suEXEC。設(shè)置的參數(shù)應(yīng)該經(jīng)過仔細推敲,以保證系統(tǒng)的安全運行。Apache開發(fā)組希望通過限制suEXEC的安裝,僅使那些經(jīng)過細致理解,并有能力運用它的管理員來使用。
你還想使用suEXEC嗎?還想?很好!那我們開始吧!
在我們開始配置和安裝suEXEC之前,我們需要先討論一下它的安全模型。這樣,你才能更好的理解suEXEC內(nèi)部究竟做了些什么事情,以及哪些確保系統(tǒng)安全的預(yù)防措施。
suEXEC是基于一個setuid的"封裝"程序,該程序由"主"Apache web服務(wù)器調(diào)用。當(dāng)一個HTTP請求的是管理員指定的、以不同于"主"服務(wù)器用戶身份運行的CGI或SSI程序時,該封裝程序?qū)⒈徽{(diào)用。處理這樣的請求時,Apache將被請求的程序名及其UID和GID提供給suEXEC封裝器。
封裝器(wrapper)通過處理下面所描述的步驟,來決定封裝的成功或失敗:如果有任意一個條件為假,程序?qū)彦e誤情況記錄到日志中,退出并返回錯誤信息。否則繼續(xù)執(zhí)行。(以下所說的"程序"均指"CGI/SSI程序")
確保運行封裝器的是一個系統(tǒng)中確實存在的用戶。
封裝器僅在使用了正確數(shù)量的參數(shù)調(diào)用時才會執(zhí)行。Apache web服務(wù)器知道正確的參數(shù)格式是什么。如果封裝器沒有收到正確數(shù)量的參數(shù),則說明要么被黑客攻擊,要么Apache二進制代碼中suEXEC的部分出了問題。
這個用戶是可以運行封裝器的用戶嗎?僅有一個用戶(Apache用戶)被允許運行封裝器。
目標CGI/SSI程序包含了"/"開頭或者有".."后向路徑索引嗎?這些都是不允許的;并且目標程序必須位于suEXEC的文檔根目錄下。(參見下面的:--with-suexec-docroot=DIR
)
目標程序的所屬用戶名存在嗎?
目標程序的所屬用戶組存在嗎?
目前,suEXEC不允許root執(zhí)行CGI/SSI程序。
最小UID值是在配置中指定的。你可以指定允許執(zhí)行CGI/SSI程序的最小UID值,這樣可以保證不會和系統(tǒng)賬號沖突。
目前,suEXEC不允許root組用戶執(zhí)行CGI/SSI程序。
最小GID值是在配置中指定的。你可以指定允許執(zhí)行CGI/SSI程序的最小GID值,這樣可以保證不會和系統(tǒng)賬號沖突。
這里就是程序變?yōu)槟繕擞脩艉徒M的關(guān)鍵步驟了。我們是通過調(diào)用setuid和setgid來實現(xiàn)的。在組訪問列表中,和該用戶相關(guān)的所有組信息都將被初始化。
如果不存在,將無法包含程序文件。如果不能切換一般也表示目錄不存在。
如果是對于服務(wù)器的一般請求,那么請求的目錄是在suEXEC的根文檔目錄下嗎?如果請求的是一個用戶目錄,那么該目錄是在suEXEC配置的該用戶的根目錄下嗎?(參見:suEXEC配置選項)
我們不想把目錄開放給其他人;只有屬主才可以改變該目錄中的內(nèi)容。
如果不存在,當(dāng)然無法繼續(xù)運行。
我們不想給其他人有修改程序的權(quán)限。
我們不想要執(zhí)行的程序被再次改變UID/GID。
用戶是這個文件的屬主嗎?
suEXEC通過建立一個安全的可執(zhí)行路徑(在配置中定義)來清除該進程的環(huán)境變量,同時只傳送在安全環(huán)境變量列表(配置中定義)中所列出的環(huán)境變量。
這里就是suEXEC結(jié)束,并開始運行目標程序的地方了。
這是suEXEC封裝器標準操作方式的安全模型。它有些嚴格,并強加了CGI/SSI設(shè)計上的限制。但它是仔細考慮過安全之后一步步發(fā)展起來的模型。
更多關(guān)于該安全模型如何根據(jù)服務(wù)器的配置來限制使用者的權(quán)限,以及恰當(dāng)?shù)膕uEXEC安裝步驟能夠避免的安全隱患,請參見警告和舉例部分。
繼續(xù)我們的探險 ...
suEXEC配置選項
--enable-suexec
--with-suexec-xxxxx
選項,以使APACI使用suEXEC功能來處理請求。--with-suexec-bin=PATH
suexec
二進制程序的路徑必須用這個選項指定并硬編碼在服務(wù)器里。比如:--with-suexec-bin=/usr/sbin/suexec
--with-suexec-caller=UID
--with-suexec-userdir=DIR
UserDir
指令(即不帶"*"),則此處應(yīng)該被設(shè)置為相同的值。當(dāng)UserDir
指令所指向的目錄與"passwd"文件所指定的用戶宿主目錄不同時,suEXEC將不會正常工作,其默認值是"public_html"。如果所支持的虛擬主機對每個用戶有不同的UserDir
,則應(yīng)該把他們集中在同一個父目錄下,而用這個參數(shù)指向這個父目錄。如果配置不當(dāng),"~userdir"下的cgi請求將無效!--with-suexec-docroot=DIR
DocumentRoot
。它是除UserDir
外suEXEC唯一可以使用的目錄。其默認目錄是 --datadir
值所指定的帶有"/htdocs"的后綴的目錄,比如:如果配置了"--datadir=/home/apache
",那么"/home/apache/htdocs"目錄將作為suEXEC處理器的文檔根目錄。--with-suexec-uidmin=UID
--with-suexec-gidmin=GID
--with-suexec-logfile=FILE
--logfiledir
)。--with-suexec-safepath=PATH
編譯和安裝suEXEC處理器
若用 --enable-suexec
打開了suEXEC功能,那么執(zhí)行make
命令時(Apache自帶的)suexec
二進制文件就會被自動建立。所有組件編譯完畢后執(zhí)行 make install
命令進行安裝時,suexec
文件將被安裝在 --sbindir
選項指定的目錄中,默認為"/usr/local/apache2/sbin/suexec"。
注意,安裝過程需要root權(quán)限。為了使suEXEC處理器可以設(shè)置UID,其所有者必須為root
,并且文件模式中的執(zhí)行位必須設(shè)置為1(允許執(zhí)行)。
設(shè)置許可權(quán)限
雖然suEXEC包裝會檢查以確保它的調(diào)用者就是配置選項
--with-suexec-caller
所指定的用戶。但是總是存在這樣的可能性:一個系統(tǒng)或者庫在suEXEC執(zhí)行用戶身份檢查之前調(diào)用它,這樣就存在一個可利用的漏洞。通常,避免這種問題的最佳辦法是,使用文件系的統(tǒng)權(quán)限來確保只有Apache組用戶運行的程序才能執(zhí)行suEXEC。
如果你的web-server是按照如下所示進行配置的:
User www
Group webgroup
并且suexec
被安裝在"/usr/local/apache2/sbin/suexec"目錄,你應(yīng)當(dāng)運行以下命令:
chgrp webgroup /usr/local/apache2/bin/suexec
chmod 4750 /usr/local/apache2/bin/suexec
這將確保只有Apache組用戶運行的程序才能執(zhí)行suEXEC。
Apache在啟動過程中,會在 --sbindir
選項指定的目錄(默認為:"/usr/local/apache/sbin/suexec")中尋找suexec
。如果Apache找到了一個正確配置的suEXEC處理器,會在錯誤日志中記錄以下信息:
[notice] suEXEC mechanism enabled (wrapper: /path/to/suexec)
如果服務(wù)器啟動后沒有這個信息,那么很可能是服務(wù)器沒找到適當(dāng)?shù)奶幚砥鳎蛘呤沁@個執(zhí)行程序沒有安裝setuid root。
如果要在Apache服務(wù)器運行過程中打開suEXEC功能,則必須停止并重新啟動Apache。用一個簡單的HUP或USR1信號來重新啟動是不夠的。
如果要關(guān)閉suEXEC功能,應(yīng)該刪除suexec
文件,并停止和重新啟動Apache。
對CGI程序的請求僅在下述兩種情況下才會調(diào)用suEXEC包裝:對一個含SuexecUserGroup
指令的虛擬主機發(fā)起請求,或者該請求由mod_userdir
模塊處理。
虛擬主機:
使用suEXEC處理器的方法之一是在VirtualHost
定義中使用SuexecUserGroup
指令。通過設(shè)置這個指令來確定不同于主服務(wù)器的UID,所有對CGI資源的請求將以<VirtualHost>
所定義的User和Group身份執(zhí)行。如果<VirtualHost>
中沒有這個指令,則將以主服務(wù)器的UID身份執(zhí)行。
用戶目錄:
由mod_userdir
處理的請求會調(diào)用suEXEC處理器以被請求的用戶目錄所屬的UID執(zhí)行CGI程序。此功能的唯一要求是,此用戶必須有CGI執(zhí)行權(quán)限,并且其腳本符合上述安全檢查的要求。參見 --with-suexec-userdir
編譯選項。
如上所述,suEXEC處理器會在 --with-suexec-logfile
選項所指定的日志文件中記錄信息。如果你感覺配置和安裝不正常,可以查看這個日志以及服務(wù)器的錯誤日志。
注意!這部分文檔可能還沒有完成。查看最新的修訂版本,請到Apache開發(fā)組的在線文檔。
以下是有關(guān)限制和服務(wù)器安裝的幾個注意事項,在提交任何關(guān)于suEXEC的"bugs"以前,請仔細閱讀。
出于安全和效率考慮,所有suEXEC請求必須被限制在虛擬主機或者用戶目錄的頂層。舉例來說,如果你配置了4個虛擬主機,你必須把所有虛擬主機的文檔根目錄都安置在同一個主Apache目錄中,這樣才能為虛擬主機啟用suEXEC。(例子以后會有的)
改變這個變量的值是危險的,必須確保其中每個路徑都是可以信任的目錄。你不會希望誰都可以在你的服務(wù)器上安裝特洛伊木馬。
重申,如果你不清楚你在干什么就盡量避免,否則會帶來大麻煩的。