作者:Gilberto Najera-Gutierrez
譯者:飛龍
協(xié)議:CC BY-NC-SA 4.0
簡介
每個滲透測試的目標(biāo)都是識別應(yīng)用、服務(wù)器或網(wǎng)絡(luò)中的可能缺陷,它們能夠讓攻擊者有機(jī)會獲得敏感系統(tǒng)的信息或訪問權(quán)限。檢測這類漏洞的原因不僅僅是了解它們的存在以及推斷出其中的漏洞,也是為了努力預(yù)防它們或者將它們降至最小。
這一章我們,我們會觀察一些如何預(yù)防多數(shù) Web 應(yīng)用漏洞的例子和推薦,根據(jù) OWASP:
https://www.owasp.org/index.php/Category:OWASP_Top_Ten_Project
10.1 預(yù)防注入攻擊
根據(jù) OWASP,Web 應(yīng)用中發(fā)現(xiàn)的最關(guān)鍵的漏洞類型就是一些代碼的注入攻擊,例如 SQL 注入、OS 命令注入、HTML 注入(XSS)。
這些漏洞通常由應(yīng)用的弱輸入校驗導(dǎo)致。這個秘籍中,我們會設(shè)計一些處理用戶輸入和構(gòu)造所使用的請求的最佳實踐。
操作步驟
- 為了防止注入攻擊,首先需要合理校驗輸入。在服務(wù)端,這可以由編寫我們自己的校驗流程來實現(xiàn),但是最佳選擇是使用語言自己的校驗流程,因為它們更加廣泛使用并測試過。一個極好的激勵就是 PHP 中的
filter_var,或者 ASP.NET 中的 校驗助手。例如,PHP 中的郵箱校驗類似于:
1 function isValidEmail($email){
2 return filter_var($email, FILTER_VALIDATE_EMAIL);
3 }
- 在客戶端,檢驗可以由創(chuàng)建 JavaScript 校驗函數(shù)來完成,使用正則表達(dá)式。例如,郵箱檢驗流程是:
1 function isValidEmail (input) {
2 var result=false;
3 var email_regex = /^[a-zA-Z0-9._-]+@([a-zA-Z0-9.-]+\.)+[azA-Z0-9.-]{2,4}$/;
4 if ( email_regex.test(input) ) {
5 result = true;
6 }
7 return result;
8 }
- 對于 SQL 注入,避免拼接輸入值為查詢十分關(guān)鍵。反之,使用參數(shù)化查詢。每個編程語言都有其自己的版本:
PHP MySQLLi:
1 $query = $dbConnection->prepare('SELECT * FROM table WHERE name = ?');
2 $query->bind_param('s', $name);
3 $query->execute();
C#:
1 string sql = "SELECT * FROM Customers WHERE CustomerId = @ CustomerId";
2 SqlCommand command = new SqlCommand(sql); command.Parameters.Add(new SqlParameter("@CustomerId", System. Data.SqlDbType.Int));
3 command.Parameters["@CustomerId"].Value = 1;
Java:
1 String custname = request.getParameter("customerName");
2 String query = "SELECT account_balance FROM user_data WHERE user_ name =? ";
3 PreparedStatement pstmt = connection.prepareStatement( query );
4 pstmt.setString( 1, custname);
5 ResultSet results = pstmt.executeQuery( );
考慮注入出現(xiàn)的時機(jī),對減少可能的損失總量也有幫助。所以,使用低權(quán)限的系統(tǒng)用戶來運行數(shù)據(jù)庫和 Web 服務(wù)器。
確保輸入用于連接數(shù)據(jù)庫服務(wù)器的用戶不是數(shù)據(jù)庫管理員。
禁用甚至刪除允許攻擊者執(zhí)行系統(tǒng)命令或提權(quán)的儲存過程,例如 MSSQL 服務(wù)器中的
xp_cmdshell。
工作原理
預(yù)防任何類型代碼注入攻擊的主要部分永遠(yuǎn)是合理的輸入校驗,位于服務(wù)端也位于客戶端。
對于 SQL 注入,始終使用參數(shù)化或者預(yù)編譯查詢。而不是拼接 SQL 語句和輸入。參數(shù)化查詢將函數(shù)參數(shù)插入到 SQL 語句特定的位置,消除了程序員通過拼接構(gòu)造查詢的需求。
這個秘籍中,我們使用了語言內(nèi)建的校驗函數(shù),但是如果你需要校驗一些特殊類型的參數(shù),你可以通過使用正則表達(dá)式創(chuàng)建自己的版本。
除了執(zhí)行正確校驗,我們也需要在一些人蓄意注入一些代碼的情況下,降低淪陷的影響。這可以通過在操作系統(tǒng)的上下文中為 Web 服務(wù)器合理配置用戶權(quán)限,以及在數(shù)據(jù)庫服務(wù)器上下文中配置數(shù)據(jù)庫和 OS 來實現(xiàn)。
另見
對于數(shù)據(jù)校驗來講,最有用的工具就是正則表達(dá)式。在處理和過濾大量信息的時候,它們也能夠讓滲透測試變得更容易。所以好好了解它們很有必要。我推薦你查看一些站點:
http://www.regexr.com/ 一個很好的站點,其中我們可以獲得示例和參數(shù)并測試我們自己的表達(dá)式來查看是否有字符串匹配。
http://www.regular-expressions.info 它包含教程和實例來了解如何使用正則表達(dá)式。它也有一份實用的參考,關(guān)于主流語言和工具的特定實現(xiàn)。
http://www.princeton.edu/~mlovett/reference/Regular-Expressions.pdf (Jan Goyvaerts 編寫的《Regular Expressions, The Complete Tutorial》)就像它的標(biāo)題所說,它是個正則表達(dá)式的非常完備的腳本,包含許多語言的示例。
10.2 構(gòu)建合理的身份驗證和會話管理
帶有缺陷的身份驗證和會話管理是當(dāng)今 Web 應(yīng)用中的第二大關(guān)鍵的漏洞。
身份驗證是用戶證明它們是它們所說的人的過程。這通常通過用戶名和密碼來完成。一些該領(lǐng)域的常見缺陷是寬松的密碼策略,以及隱藏式的安全(隱藏資源缺乏身份驗證)。
會話管理是登錄用戶的會話標(biāo)識符的處理。在 Web 服務(wù)器中,這可以通過實現(xiàn)會話 Cookie 和標(biāo)識來完成。這些標(biāo)識符可以植入、盜取,或者由攻擊者使用社會工程、XSS 或 CSRF 來“劫持”。所以,開發(fā)者必須特別注意如何管理這些信息。
這個秘籍中,我們會設(shè)計到一些實現(xiàn)用戶名/密碼身份驗證,以及管理登錄用戶的會話標(biāo)識符的最佳實踐。
操作步驟
如果應(yīng)用中存在只能由授權(quán)用戶查看的頁面、表單或者任何信息片段,確保在展示它們之前存在合理的身份驗證。
確保用戶名、ID、密碼和所有其它身份驗證數(shù)據(jù)是大小寫敏感的,并且對每個用戶唯一。
建立強(qiáng)密碼策略,強(qiáng)迫用戶創(chuàng)建至少滿足下列條件的密碼:
- 對于 8 個字符,推薦 10 個。
- 使用大寫和小寫字母。
- 至少使用一個數(shù)字。
- 至少使用一個特殊字符(空格、
!、&、#、%,以及其它)。 - 禁止用戶名、站點名稱、公司名稱或者它們的變體(大小寫轉(zhuǎn)換、l33t、它們的片段)用于密碼。
- 禁止使用“常見密碼”列表中的密碼:https://www.teamsid.com/worst-passwords-2015/ 。
- 永遠(yuǎn)不要顯示用戶是否存在或者信息格式是否正確的錯誤信息。對不正確的登錄請求、不存在的用戶、名稱或密碼不匹配模式、以及所有可能的登錄錯誤使用相同的泛化信息。這種信息類似于:
- 登錄數(shù)據(jù)不正確。
- 用戶名或密碼無效。
- 訪問禁止。
密碼不能以純文本格式儲存在數(shù)據(jù)庫中。使用強(qiáng)哈希算法,例如 SHA-2、scrypt、或者 bcrypt,它們特別為難以使用 GPU 破解而設(shè)計。
在對比用戶輸入和密碼時,計算輸入的哈希之后比較哈希之后的字符串。永遠(yuǎn)不要解密密碼來使用純文本用戶輸入來比較。
避免基本的 HTML 身份驗證。
-
可能的話,使用多因素驗證(MFA),這意味著使用不止一個身份驗證因素來登錄:
- 一些你知道的(賬戶信息或密碼)
- 一些你擁有的(標(biāo)識或手機(jī)號)
- 一些你的特征(生物計量)
如果可能的話,實現(xiàn)證書、預(yù)共享密鑰、或其它無需密碼的身份校驗協(xié)議(OAuth2、OpenID、SAML、或者 FIDO)。
對于會話管理,推薦使用語言內(nèi)建的會話管理系統(tǒng),Java、ASP.NET和 PHP。它們并不完美,但是能夠確保提供設(shè)計良好和廣泛測試的機(jī)制,而且比起開發(fā)團(tuán)隊在時間緊迫情況下的自制版本,它們更易于實現(xiàn)。
始終為登錄和登錄后的頁面使用 HTTPS – 顯然,要防止只接受 SSL 和 TLS v1.1 連接。
為了確保 HTTPS 能夠生效,可以使用 HSTS。它是由 Web 應(yīng)用指定的雙向選擇的特性。通過 Strict-Transport-Security 協(xié)議頭,它在 http://
存在于 URL 的情況下會重定向到安全的選項,并防止“無效證書”信息的覆寫。例如使用 Burp Suite 的時候會出現(xiàn)的情況。更多信息請見:https://www.owasp.org/index.php/HTTP_Strict_Transport_Security 。始終設(shè)置 HTTPOnly 和安全的 Cookie 屬性。
設(shè)置最少但實際的會話過期時間。確保正常用戶離開之后,攻擊者不能復(fù)用會話,并且用戶能夠執(zhí)行應(yīng)用打算執(zhí)行的操作。
工作原理
身份校驗機(jī)制通常在 Web 應(yīng)用中簡化為用戶名/密碼登錄頁面。雖然并不是最安全的選擇,但它對于用戶和開發(fā)者最簡單,以及當(dāng)密碼被盜取時,最重要的層面就是它們的強(qiáng)度。
我們可以從這本書看到,密碼強(qiáng)度由破解難度決定,通過爆破、字典或猜測。這個秘籍的第一個提示是為了使密碼更難以通過建立最小長度的混合字符集來破解,難以通過排除更直覺的方案(用戶名、常見密碼、公司名稱)來猜測,并且通過使用強(qiáng)哈?;蚣用軆Υ?,難以在泄露之后破解。
對于會話管理來說,過期時間、唯一性和會話 ID 的強(qiáng)度(已經(jīng)在語言內(nèi)建機(jī)制中實現(xiàn)),以及 Cookie 設(shè)置中的安全都是關(guān)鍵的考慮因素。
談?wù)撋矸菪r灠踩淖钪匾膶用媸?,如果消息可以通過中間人攻擊攔截或者服務(wù),沒有任何安全配置、控制或強(qiáng)密碼是足夠安全的。所以,合理配置的加密通信頻道的使用,例如 TLS,對保護(hù)我們的用戶身份數(shù)據(jù)來說極其重要。
另見
OWASP 擁有一些非常好的頁面,關(guān)于身份校驗和會話管理。我們推薦你在構(gòu)建和配置 Web 應(yīng)用時閱讀并仔細(xì)考慮它們。
- https://www.owasp.org/index.php/Authentication_Cheat_Sheet
- https://www.owasp.org/index.php/Session_Management_Cheat_Sheet
10.3 預(yù)防跨站腳本
我們之前看到,跨站腳本,在展示給用戶的數(shù)據(jù)沒有正確編碼,并且瀏覽器將其解釋并執(zhí)行為腳本代碼時發(fā)生。這也存在輸入校驗因素,因為惡意代碼通常由輸入變量插入。
這個秘籍中,我們會涉及開發(fā)者所需的輸入校驗和輸出編碼,來防止應(yīng)用中的 XSS 漏洞。
工作原理
應(yīng)用存在 XSS 漏洞的第一個標(biāo)志是,頁面準(zhǔn)確反映了用戶提供的輸入。所以,嘗試不要使用用戶提供的信息來構(gòu)建輸出文本。
當(dāng)你需要將用戶提供的信息放在輸出頁面上時,校驗這些數(shù)據(jù)來防止任何類型代碼的插入。我們已經(jīng)在 A1 中看到如何實現(xiàn)它。
出于一些原因,如果用戶被允許輸入特殊字符或者代碼段,在它插入到輸出之前,過濾或合理編碼文本。
對于過濾,在 PHP 中,可以使用
filter_var。例如,如果你想讓字符串為郵件地址:
1 $email = "john(.doe)@exa//mple.com";
2 $email = filter_var($email, FILTER_SANITIZE_EMAIL);
3 echo $email;
對于編碼,你可以在 PHP 中使用htmlspecialchars:
1 $str = "The JavaScript HTML tags are <script> for opening, and </ script> for closing.";
2 echo htmlspecialchars($str);
在 .NET 中,對于 4.5 及更高版本,System.Web.Security.AntiXss
命名空間提供了必要的工具。對于 .NET 框架 4 及之前的版本,你可以使用 Web 保護(hù)庫:http://wpl.codeplex.com/。同樣,為了防止儲存型 XSS,在儲存進(jìn)數(shù)據(jù)庫或從數(shù)據(jù)庫獲取之前,編碼或過濾每個信息片段。
不要忽略頭部、標(biāo)題、CSS和頁面的腳本區(qū)域,因為它們也可以被利用。
工作原理
除了合理的輸入校驗,以及不要將用戶輸入用作輸出信息,過濾和編碼也是防止 XSS 的關(guān)鍵層面。
過濾意味著從字符串移除不允許的字符。這在輸入字符串中存在特殊字符時很實用。
編碼將特殊字符轉(zhuǎn)換為 HTML 代碼表示。例如,&變?yōu)?code>&、<變?yōu)?code><。一些應(yīng)用允許在輸入字符串中使用特殊字符,對它們來說過濾不是個選擇。所以應(yīng)該在將輸入插入頁面,或者儲存進(jìn)數(shù)據(jù)庫之前編碼輸入。
另見
OWASP 擁有值得閱讀的 XSS 預(yù)防速查表:
10.4 避免直接引用不安全對象
當(dāng)應(yīng)用允許攻擊者(也是校驗過的用戶)僅僅修改請求中的,直接指向系統(tǒng)對象的參數(shù)值,來訪問另一個未授權(quán)的對象時,就存在不安全對象的直接引用(IDOR)。我們已經(jīng)在本地文件包含和目錄遍歷漏洞中看到了一些例子。
根據(jù) OWASP,IDOR 是 Web 應(yīng)用中第四大關(guān)鍵漏洞。這些漏洞通常由不良的訪問控制實現(xiàn),或者“隱藏式安全”策略(如果用戶不能看到它,他們就不能知道它的存在)導(dǎo)致。這些在沒有經(jīng)驗的開發(fā)者之中是個常見的做法。
這個秘籍中,我們會涉及在設(shè)計訪問控制機(jī)制時應(yīng)該考慮的關(guān)鍵層面,以便預(yù)防 IDOR 漏洞。
操作步驟
使用非直接引用優(yōu)于直接引用。例如,不要通過參數(shù)中的名稱來引用頁面(
URL?page="restricted_page"),而是要創(chuàng)建索引,并在內(nèi)部處理它(URL?page=2)。將非直接引用映射到用戶(會話)層面,于是用戶僅僅能夠訪問授權(quán)的對象,即使它們修改了下標(biāo)。
在傳遞相應(yīng)對象之前校驗引用,如果請求的用戶沒有權(quán)限來訪問,展示通用錯誤頁面。
輸入校驗也是很重要的,尤其是目錄遍歷和文件包含的情況下。
永遠(yuǎn)不要采取“隱藏式安全”的策略。如果有些文件包含受限的信息,即使它沒有引用,有些人也會把它翻出來。
工作原理
不安全對象的直接引用在 Web 應(yīng)用中的表現(xiàn)形式有所不同,從目錄遍歷到敏感的 PDF 文檔的引用。但是它們的大多數(shù)都依賴于一個假設(shè),即用戶永遠(yuǎn)不會找到方法來訪問不能顯式訪問的東西。
為了防止這種漏洞,需要在設(shè)計和開發(fā)期間執(zhí)行一些積極操作。設(shè)計可靠授權(quán)機(jī)制,來驗證嘗試訪問一些信息的用戶的關(guān)鍵是,是否用戶真正允許訪問它。
將引用對象映射為下標(biāo)來避免對象名稱直接用于參數(shù)值(就像 LFI 中的那樣)是第一步。攻擊者也可以修改下標(biāo),這很正常,就像對對象名稱所做的那樣。但是數(shù)據(jù)庫中存在下標(biāo)-對象的表的話,添加字段來規(guī)定訪問所需的權(quán)限級別,比起沒有任何表并且直接通過名稱來訪問資源,要容易得多。
之前說過,下標(biāo)的表可能包含訪問對象所需的權(quán)限級別,更加嚴(yán)格的話還有擁有者的 ID。所以,它只能夠在請求用戶是擁有者的情況下訪問。
最后,輸入校驗必須存在于 Web 應(yīng)用安全的每個層面。
10.5 基本的安全配置指南
系統(tǒng)的默認(rèn)配置,包括操作系統(tǒng)和Web 服務(wù)器,多數(shù)用于演示和強(qiáng)調(diào)他們的基本或多數(shù)有關(guān)特性,并不能保護(hù)它們不被攻擊。
一些常見的可能使系統(tǒng)淪陷的默認(rèn)配置,是數(shù)據(jù)庫、Web 服務(wù)器或CMS 安裝時創(chuàng)建的默認(rèn)管理員賬戶,以及默認(rèn)管理員頁面、默認(rèn)?;厮蒎e誤信息,以及其它。
這個秘籍中,我們會涉及 OWASP Top 10 中第五大關(guān)鍵漏洞,錯誤的安全配置。
操作步驟
- 可能的話,刪除所有管理員應(yīng)用,例如 Joomla 的 admin,WordPress 的 admin,PhpMyAdmin,或者 Tomcat Manager。如果不能這樣,使它們只能從本地網(wǎng)絡(luò)訪問,例如,在 Apache 服務(wù)器中禁止來自外部網(wǎng)絡(luò)的 PhpMyAdmin 訪問,修改
httd.conf文件(或者相應(yīng)的站點配置文件)。
1 <Directory /var/www/phpmyadmin>
2
3 Order Deny,Allow
4 Deny from all
5 Allow from 127.0.0.1 ::1
6 Allow from localhost
7 Allow from 192.168
8 Satisfy Any
9
10 </Directory>
這會首先禁止所有地址到phpmyadmin目錄的訪問,之后它允許任何來自 locaohost 和以192.168開頭的地址的請求,這是本地網(wǎng)絡(luò)的地址。
- 修改所有 CMS、應(yīng)用、數(shù)據(jù)庫、服務(wù)器和框架的所有管理員密碼,使其強(qiáng)度足夠。一些應(yīng)用的例子是:
- Cpanel
- Joomla
- WordPress
- PhpMyAdmin
- Tomcat manager
禁用所有不必要或未使用的服務(wù)器和應(yīng)用特性。從日?;蛎恐軄砜?,新的漏洞都出現(xiàn)在 CMS 的可選模塊和插件中。如果你的應(yīng)用不需要它們,就不要激活它們。
始終執(zhí)行最新的安全補(bǔ)丁和更新。在生成環(huán)境,建立測試環(huán)境來預(yù)防使站點不工作的缺陷十分重要,因為新版本存在一些兼容性及其它問題。
建立不會泄露跟蹤信息、軟件版本、程序組件名稱,或任何其它調(diào)試信息的自定義的錯誤頁面。如果開發(fā)者需要跟蹤錯誤記錄或者一些一些標(biāo)識符對于技術(shù)支持非常必要,創(chuàng)建帶有簡單 ID 和錯誤描述的索引,并只展示 ID 給用戶。所以當(dāng)錯誤報告給相關(guān)人士的時候,它們會檢查下標(biāo)并且知道發(fā)生了什么錯誤。
采取“最小權(quán)限原則”。每個用戶在每個層面(操作系統(tǒng)、數(shù)據(jù)庫、或應(yīng)用)上都應(yīng)該只能夠嚴(yán)格訪問正確操作所需的信息。
使用上一個要點來考慮賬戶,構(gòu)建安全配置的原則,并且將其應(yīng)用到每個新的實現(xiàn)、更新或發(fā)布以及當(dāng)前系統(tǒng)中。
強(qiáng)制定期的安全測試或?qū)徲?,來幫助檢測錯誤配置或遺漏的補(bǔ)丁。
工作原理
談?wù)摪踩团渲脝栴}時,“細(xì)節(jié)決定成敗”十分恰當(dāng)。web 服務(wù)器、數(shù)據(jù)庫服務(wù)器、CMS、或者應(yīng)用配置應(yīng)該在完全可用和實用、以及保護(hù)用戶和擁有者之間取得平衡。
Web 應(yīng)用的一個常見錯誤配置就是一些 Web 管理站點對整個互聯(lián)網(wǎng)都可見。這看起來并不是個大問題,但是我們應(yīng)該知道,管理員登錄頁面更容易吸引攻擊者,因為它可以用于獲得高級權(quán)限等級,并且任何 CMS、數(shù)據(jù)或者站點管理工具都存在已知的常用默認(rèn)密碼列表。所以,我們強(qiáng)烈推薦不要把這些管理站點暴露給外部,并且盡可能移除它們。
此外,強(qiáng)密碼的使用,以及修改默認(rèn)密碼(即使它們是強(qiáng)密碼),在發(fā)布應(yīng)用到公司內(nèi)部網(wǎng)絡(luò),以及互聯(lián)網(wǎng)的時候需要強(qiáng)制執(zhí)行。當(dāng)今,當(dāng)我們將服務(wù)器開放給外部的時候,它收到的第一個流量就是端口掃描,登錄頁面請求,以及登錄嘗試,甚至在第一個用戶知道該應(yīng)用之前。
自定義錯誤頁面的使用有助于安全準(zhǔn)備,因為 Web 服務(wù)器和應(yīng)用中的默認(rèn)的錯誤信息展示太多的信息(從攻擊者角度),它們關(guān)于錯誤、所使用的編程語言、?;厮荨⑺褂玫臄?shù)據(jù)庫、操作系統(tǒng)以及其它。這些信息不應(yīng)該暴露,因為它會幫助我們理解應(yīng)用如何構(gòu)建,并且提供所使用軟件的版本和名稱。攻擊者通過這些信息就可以搜索已知漏洞,并構(gòu)造更加有效的攻擊過程。
一旦我們的服務(wù)器上的部署應(yīng)用和所有服務(wù)都正確配置,我們就可以制訂安全原則并且將其應(yīng)用于所有要配置的新服務(wù)器或者已更新的服務(wù)器,或者當(dāng)前帶有合理規(guī)劃的生產(chǎn)服務(wù)器。
這個配置原則需要持續(xù)測試,以便改進(jìn)它以及持續(xù)保護(hù)新發(fā)現(xiàn)的漏洞。
10.6 保護(hù)敏感數(shù)據(jù)
當(dāng)應(yīng)用儲存或使用敏感信息(信用卡號碼、社會安全號碼、健康記錄,以及其它)時,必須采取特殊的手段來保護(hù)它們,因為它可能為負(fù)責(zé)保護(hù)它們的組織帶來嚴(yán)重的信用、經(jīng)濟(jì)或者法律損失,以及被攻破。
OWASP Top 10 的第六名是敏感數(shù)據(jù)泄露,它發(fā)生在應(yīng)該保護(hù)的數(shù)據(jù)以純文本泄露,或者帶有弱安全措施的時候。
這個秘籍中,我們會涉及一些處理、傳遞和儲存這種數(shù)據(jù)類型的最佳實踐。
操作步驟
如果你使用的敏感數(shù)據(jù)可以在使用之后刪除,那么刪除它。最好每次使用信用卡的時候詢問用戶,避免被盜取。
在處理支付的時候,始終使用支付網(wǎng)關(guān),而不是在你的服務(wù)器中儲存數(shù)據(jù)。查看:
http://ecommerce-platforms.com/ ecommerce-selling-advice/choose-payment-gateway-ecommerce-store。如果我們需要儲存敏感數(shù)據(jù),我們要采取的第一個保護(hù)就是使用強(qiáng)密碼算法和相應(yīng)的強(qiáng)密鑰來加密。推薦 Twofish、AES、RSA 和三重 DES。
密碼儲存在數(shù)據(jù)庫的時候,應(yīng)該以單項哈希函數(shù)的哈希形式存儲,例如,bcypt、scrypt 或 SHA-2。
確保所有敏感文檔只能被授權(quán)用戶訪問。不要在 Web 服務(wù)器的文檔根目錄儲存它們,而是在外部目錄儲存,并通過程序來訪問。如果出于某種原因必須在服務(wù)器的文檔根目錄儲存敏感文件,使用
.htaccess文件來防止直接訪問:
1 Order deny,allow
2 Deny from all
- 禁用包含敏感數(shù)據(jù)的頁面緩存。例如,在 Apache 中我們可以禁用 PDF 和 PNG 的緩存,通過
httpd.conf中的下列設(shè)置:
1 <FilesMatch "\.(pdf|png)>
2 FileETag None
2 Header unset ETag
4 Header set Cache-Control "max-age=0, no-cache, no-store, mustrevalidate"
5 Header set Pragma "no-cache"
6 Header set Expires "Wed, 11 Jan 1984 05:00:00 GMT"
7 </FilesMatch>
- 如果你允許文件上傳,始終使用安全的通信頻道來傳輸敏感數(shù)據(jù),也就是帶有 TLS 的 HTTPS,或者 FTPS(SSH 上的 FTP)。
工作原理
對于保護(hù)敏感數(shù)據(jù),我們需要最小化數(shù)據(jù)泄露或交易的風(fēng)險。這就是正確加密儲存敏感數(shù)據(jù),以及保護(hù)加密密鑰是所做的第一件事情的原因。如果可能不需要儲存這類數(shù)據(jù),這只是個理想選擇。
密碼應(yīng)該使用單向哈希算法,在將它們儲存到數(shù)據(jù)之前計算哈希。所以,即使它們被盜取,攻擊者也不能立即使用它們,并且如果密碼強(qiáng)度足夠,哈希也是足夠強(qiáng)的算法,它就不會在短時間內(nèi)被破解。
如果我們在 Apache 服務(wù)器的文檔根目錄(/var/ www/html/)儲存敏感文檔或數(shù)據(jù),我們就通過 URL 將這些信息暴露用于下載。所以,最好將它儲存到別的地方,并編寫特殊的服務(wù)端代碼來在必要時獲取它們,并帶有預(yù)先的授權(quán)檢查。
此外,例如 Archive.org、WayBackMachine 或者 Google 緩存頁面,可能在緩存含有敏感信息的文件時,以及我們沒能在應(yīng)用的上一個版本有效保護(hù)它們時產(chǎn)生安全問題。所以,不允許緩存此類文檔非常重要。
10.7 確保功能級別的訪問控制
功能級別的訪問控制是訪問控制的一種,用于防止匿名者或未授權(quán)用戶的功能調(diào)用。根據(jù) OWASP,缺乏這種控制是 Web 應(yīng)用中第七大嚴(yán)重的安全問題。
這個秘籍中,我們會看到一些推薦來提升我們的應(yīng)用在功能級別上的訪問控制。
操作步驟
確保每一步都正確檢查了工作流的權(quán)限。
禁止所有默認(rèn)訪問,之后在顯示的授權(quán)校驗之后允許訪問。
用戶、角色和授權(quán)應(yīng)該在靈活的媒介中儲存,例如數(shù)據(jù)庫或者配置文件,不要硬編碼它們。
同樣,“隱藏式安全”不是很好的策略。
工作原理
開發(fā)者只在工作流的開始檢查授權(quán),并假設(shè)下面的步驟都已經(jīng)對用戶授權(quán),這是常見的現(xiàn)象。攻擊者可能會嘗試調(diào)用某個功能,它是工作流的中間步驟,并由于控制缺失而能夠訪問它。
對于權(quán)限,默認(rèn)禁止所有用戶是個最佳實踐。如果我們不知道一些用戶是否有權(quán)訪問一些功能,那么它們就不應(yīng)該執(zhí)行。將你的權(quán)限表轉(zhuǎn)化為授權(quán)表。如果某些用戶在某些功能上沒有顯式的授權(quán),則禁止它們的訪問。
在為你的應(yīng)用功能構(gòu)建或?qū)崿F(xiàn)訪問控制機(jī)制的時候,將所有授權(quán)儲存在數(shù)據(jù)庫中,或者在配置文件中(數(shù)據(jù)庫是最好的選項)。如果用戶角色和權(quán)限被硬編碼,它們就會難以維護(hù)、修改或更新。
10.8 防止 CSRF
當(dāng) Web 應(yīng)用沒有使用會話層面或者操作層面的標(biāo)識,或者標(biāo)識沒有正確實現(xiàn)的時候,它們就可能存在跨站請求偽造漏洞,并且攻擊者可以強(qiáng)迫授權(quán)用戶執(zhí)行非預(yù)期的操作。
CSRF 是當(dāng)今 Web 應(yīng)用的第八大嚴(yán)重漏洞,根據(jù) OWASP, 并且我們在這個秘籍中會看到如何在應(yīng)用中防止它。
操作步驟
第一步也是最實際的 CSRF 解決方案就是實現(xiàn)唯一、操作層面的標(biāo)識。所以每次用戶嘗試執(zhí)行某個操作的時候,會生成新的標(biāo)識并在服務(wù)端校驗。
唯一標(biāo)識應(yīng)該不能被輕易由攻擊者猜測,所以它們不能將其包含在 CSRF 頁面中。隨機(jī)生成是個好的選擇。
在每個可能為 CSRF 目標(biāo)的表單中包含要發(fā)送的標(biāo)識。“添加到購物車”請求、密碼修改表單、郵件、聯(lián)系方式或收貨信息管理,以及銀行的轉(zhuǎn)賬頁面都是很好的例子。
標(biāo)識應(yīng)該在每次請求中發(fā)送給服務(wù)器。這可以在 URL 中實現(xiàn),或者任何其它變量或者隱藏字段,都是推薦的。
驗證碼的使用也可以防止 CSRF。
同樣,在一些關(guān)鍵操作中詢問重新授權(quán)也是個最佳實踐,例如,銀行應(yīng)用中的轉(zhuǎn)賬操作。
工作原理
防止 CSRF 完全是確保驗證過的用戶是請求操作的人。由于瀏覽器和 Web 應(yīng)用的工作方式,最佳實踐是使用標(biāo)識來驗證操作,或者可能的情況下使用驗證碼來控制。
由于攻擊者打算嘗試破解標(biāo)識的生成,或者驗證系統(tǒng),以一種攻擊者不能猜測的方式,安全地生成它們非常重要。而且要使它們對每個用戶和每個操作都唯一,因為復(fù)用它們會偏離它們的目的。
驗證碼控制和重新授權(quán)有時候會非常麻煩,使用戶反感。但是如果操作的重要性值得這么做,用戶可能愿意接受它們來換取額外的安全級別。
另見
有一些編程庫有助于實現(xiàn) CSRF 防護(hù),節(jié)省開發(fā)者的大量工作。例子之一就是 OWASP 的 CSRF Guard:https://www.owasp.org/index.php/CSRFGuard。
10.9 在哪里尋找三方組件的已知漏洞
現(xiàn)在的 Wbe 應(yīng)用不再是單個開發(fā)者,也不是單個開發(fā)團(tuán)隊的作品。開發(fā)功能性、用戶友好、外觀吸引人的 Web 應(yīng)用涉及到三方組件的使用,例如編程庫,外部服務(wù)的 API(Fackbook、Google、Twitter),開發(fā)框架,以及許多其它的組件,其中編程、測試和打補(bǔ)丁的工作量很少,甚至沒有。
有時候這些三方組件被發(fā)現(xiàn)存在漏洞,并且它們將這些漏洞轉(zhuǎn)移到了我們的應(yīng)用中。許多帶有漏洞組件的應(yīng)用很長時間都沒有打補(bǔ)丁,使整個組織的安全體系中出現(xiàn)缺陷。這就是 OWASP 將使用帶有已知漏洞的三方組件劃分為 Web 應(yīng)用安全的第九大威脅的原因。
這個秘籍中,我們會了解,如果一些我們所使用的組件擁有已知漏洞,應(yīng)該到哪里尋找,以及我們會查看一些這種漏洞組件的例子。
操作步驟
第一個建議是,優(yōu)先選擇受支持和廣泛使用的知名軟件。
為你的應(yīng)用所使用的三方組件保持安全更新和補(bǔ)丁的更新。
用于搜索一些特定組件的漏洞的好地方就是廠商的網(wǎng)站:它們通常擁有“發(fā)布說明”部分,其中它們會公布它們糾正了哪個 bug 或漏洞。這里我們可以寸照我們所使用的(或更新的)版本,并且插件是否有有已知的問題沒有打補(bǔ)丁。
同樣,廠商通常擁有安全建議站點,例如 Microsoft:
https://technet.microsoft.com/library/security/,Joomla:https:// developer.joomla.org/security-centre.html,和Oracle:http://www. oracle.com/technetwork/topics/security/alerts-086861.html。我們可以使用它們來保持我們用于應(yīng)用的軟件的更新。也有一些廠商無關(guān)的站點,它們致力于通知我們漏洞和安全問題。有個非常好的網(wǎng)站,集中了多個來源的信息,是 CVE Details(
http://www.cvedetails.com/)。這里我們可以搜索多數(shù)廠商或產(chǎn)品,或者列出所有已知漏洞(至少是擁有 CVE 號碼的漏洞),并且按照年份、版本和 CVSS 分?jǐn)?shù)排列。同時,黑客發(fā)布利用和發(fā)現(xiàn)的站點也是個獲得漏洞和我們所使用的軟件的信息的好地方。最流行的是 Exploit DB(
https://www.exploit-db.com/)。 Full disclosure 郵件列表(http://seclists.org/fulldisclosure/),以及 Packet Storm 的文件部分(https://packetstormsecurity.com/files/)。一旦我們發(fā)現(xiàn)了我們軟件組件中的漏洞,我們必須評估它是否對我們的應(yīng)用必要,或者需要移除。如果不能這樣,我們需要盡快打補(bǔ)丁。如果沒有可用的補(bǔ)丁或變通方案,并且漏洞是高危的,我們必須開始尋找組件的替代。
工作原理
考慮在我們的應(yīng)用中使用三方軟件組件之前,我們需要查看它的安全信息,并了解,我們所使用的組件是否有更穩(wěn)定更安全的版本或替代。
一旦我們選擇了某個,并且將其包含到我們的應(yīng)用中,我們需要使其保持更新。有時它可能涉及到版本改動以及沒有后向兼容,但是這是我們想要維持安全的代價。如果我們不能更新或為高危漏洞打補(bǔ)丁,我們還可以使用 WAF(Web 應(yīng)用防火墻)和IPS(入侵檢測系統(tǒng))來防止攻擊。
除了在執(zhí)行滲透測試的時候比較實用,下載和漏洞發(fā)布站點可以被系統(tǒng)管理員利用,用于了解可能出現(xiàn)什么攻擊,它們的原理,以及如何保護(hù)應(yīng)用避免它們。
10.10 重定向驗證
根據(jù) OWASP,未驗證的重定向和轉(zhuǎn)發(fā)是 Web 應(yīng)用的第十大嚴(yán)重安全問題。它發(fā)生在應(yīng)用接受 URL 或內(nèi)部頁面作為參數(shù)來執(zhí)行重定向或轉(zhuǎn)發(fā)操作的時候。如果參數(shù)沒有正確驗證,攻擊者就能夠濫用它來使其重定向到惡意網(wǎng)站。
這個秘籍中,我們會了解如何驗證我們接受的用于重定向或轉(zhuǎn)發(fā)的參數(shù),我們需要在開發(fā)應(yīng)用的時候?qū)崿F(xiàn)它。
操作步驟
不希望存在漏洞嗎?那就不要使用它。無論怎樣,都不要使用重定向和轉(zhuǎn)發(fā)。
如果需要使用重定向,嘗試不要使用用戶提供的參數(shù)(請求變量)來計算出目標(biāo)。
如果需要使用參數(shù),實現(xiàn)一個表,將其作為重定向的目錄,使用 ID 代替 URL 作為用戶應(yīng)該提供的參數(shù)。
始終驗證重定向和轉(zhuǎn)發(fā)操作涉及到的輸入。使用正則表達(dá)式或者白名單來檢查提供的值是否有效。
工作原理
重定向和轉(zhuǎn)發(fā)是釣魚者和其它社會工程師最喜歡用的工具,并且有時候我們對目標(biāo)沒有任何安全控制。所以,即使它不是我們的應(yīng)用,它的安全問題也會影響我們的信譽(yù)。這就是最好不要使用它們的原因。
如果這種重定向的目標(biāo)是已知站點,例如 Fackbook 或 Google,我們就可以在配置文件或數(shù)據(jù)表中建立目標(biāo)目錄,并且不需要使用客戶端提供的參數(shù)來實現(xiàn)。
如果我們構(gòu)建包含所有允許的重定向和轉(zhuǎn)發(fā) URL 的數(shù)據(jù)表,每個都帶有 ID,我們可以將 ID 用于參數(shù),而不是目標(biāo)本身。這是一種白名單的形式,可以防止無效目標(biāo)的插入。
最后同樣是校驗。我們始終要校驗每個來自客戶端的輸入,這非常重要,因為我們不知道用戶要輸入什么。如果我們校驗了重定向目標(biāo)的正確性,除了惡意轉(zhuǎn)發(fā)或重定向之外,我們還可以防止可能的 SQL 注入、XSS或者目錄遍歷。所以,它們都是相關(guān)的。
版權(quán)聲明:本文轉(zhuǎn)載自wizardforcel的專欄,如有侵權(quán),請與本人聯(lián)系。
專欄鏈接:http://blog.csdn.net/wizardforcel
原文鏈接:http://blog.csdn.net/wizardforcel/article/details/52829673