簡體   English   中英

如何使用 ESAPI 修復 HTTP 響應拆分漏洞

[英]How to fix the HTTP Response splitting vulnerability with ESAPI

在最近的 findbugs (FB) 運行后,它抱怨一個:安全 - HTTP 響應拆分漏洞以下代碼觸發它:

String referrer = req.getParameter("referrer");
 if (referrer != null) {
  launchURL += "&referrer="+(referrer);
 }
resp.sendRedirect(launchURL);

基本上,'referrer' http 參數包含一個 url,當單擊我們應用程序中的后退按鈕時,瀏覽器將返回到該 url。 它作為參數附加到 url。 經過一番研究,我知道我需要清理引薦來源網址。 經過更多研究,我發現esapi項目似乎提供了這種功能:

//1st canonicalize
import org.owasp.esapi.Encoder;
import org.owasp.esapi.Validator;
import org.owasp.esapi.reference.DefaultEncoder;
import org.owasp.esapi.reference.DefaultValidator;
[...]
Encoder encoder = new DefaultEncoder(new ArrayList<String>());
String cReferrer = encoder.canonicalize(referrer);

但是我不知道如何檢測例如 jscript 代碼或其他不屬於引薦來源網址的內容。 那么我怎樣才能用 esapi 實現呢?

我試過了:

Validator validator = new DefaultValidator(encoder);
validator.isValidInput("Redirect URL",referrer,"HTTPParameterValue",512,false);

但是這不起作用。 我需要的是一個函數,它導致:

http://www.google.com (好的)

http://www.google.com/login?dest=http://google.com/%0D%0ALocation : javascript:%0D%0A%0D%0Aalert(document.cookie) (不行)

或者調用以下語句就足夠了?

encoder.encodeForHTMLAttribute(referrer);

任何幫助表示贊賞。

如果有人感興趣,這是我的最終解決方案。 首先我規范化然后 URL 解碼字符串。 如果 CR 或 LF 存在 (\\n \\r),我只是剪切了以 \\n 或 \\r 開頭的潛在“攻擊”字符串的其余部分。

String sanitize(String url) throws EncodingException{
    
    Encoder encoder = new DefaultEncoder(new ArrayList<String>());
    //first canonicalize
    String clean = encoder.canonicalize(url).trim();
    //then url decode 
    clean = encoder.decodeFromURL(clean);
    
    //detect and remove any existent \r\n == %0D%0A == CRLF to prevent HTTP Response Splitting
    int idxR = clean.indexOf('\r');
    int idxN = clean.indexOf('\n');
    
    if(idxN >= 0 || idxR>=0){
        if(idxN<idxR){
            //just cut off the part after the LF
            clean = clean.substring(0,idxN);
        }
        else{
            //just cut off the part after the CR
            clean = clean.substring(0,idxR);
        }
    }
    
    //re-encode again
    return encoder.encodeForURL(clean);
}

從理論上講,我可以稍后針對 ESAPI.properties 中定義的“HTTPParameterValue”正則表達式驗證該值,但是它不喜歡 http:// 中的冒號,我沒有進一步調查。

測試后還有一句話:現在大多數現代瀏覽器(Firefox> 3.6,Chrome,IE10等)都檢測到這種漏洞並且不執行代碼......

我建議使用白名單方法,其中您只檢查referrer字符串中允許的字符。 正則表達式將是一個不錯的選擇。

編輯:

您使用的類org.owasp.esapi.reference.DefaultEncoder並沒有真正編碼任何東西。 看看方法的源代碼encodeForHTMLAttribute(referrer) 在這里grepcode 典型的 URL 編碼(編碼回車和換行) 也無濟於事

因此,前進的道路將是設備一些驗證邏輯,用於檢查有效的字符集。 這是另一篇有見地的文章

我認為您的想法是正確的,但使用的是不合適的編碼器。 Referer [sic] 標頭值實際上是一個 URL,而不是 HTML 屬性,因此您確實要使用:

encoder.encodeForURL(referrer);

-凱文

如果字符串中有“\\n\\r”,則接受的答案將不起作用。 示例:如果我有字符串: "This is str\\n\\rstr" ,它返回"This is str\\nstr"

上述接受答案的修正版本是:

 String sanitizeCarriageReturns(String value) {
        int idxR = value.indexOf('\r');
        int idxN = value.indexOf('\n');

        if (idxN >= 0 || idxR >= 0) {
            if ((idxN > idxR && idxR<0) || (idxR > idxN && idxR>=0)) {
                    value = value.substring(0, idxN);
                } else if (idxN < idxR){
                    value = value.substring(0, idxR);
                } 

        }
        return value;
    }

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM