WAF(Web應用防火牆)淺析
微信公眾號:計算機與網絡安全
ID:Computer-network
1、關於WAF
WAF(Web Application Firewall,Web應用防火牆)是通過執行一系列針對HTTP/HTTPS的安全策略來專門為Web應用提供保護的一款產品。
WAF基本上可以分為以下幾類。
(1)軟件型WAF
以軟件形式裝在所保護的服務器上的WAF,由於安裝在服務器上,所以可以接觸到服務器上的文件,直接檢測服務器上是否存在WebShell、是否有文件被創建等。
(2)硬件型WAF
以硬件形式部署在鏈路中,支持多種部署方式,當串聯到鏈路中時可以攔截惡意流量,在旁路監聽模式時只記錄攻擊不進行攔截。
(3)雲WAF
一般以反向代理的形式工作,通過配置NS記錄或CNAME記錄,使對網站的請求報文優先經過WAF主機,經過WAF主機過濾后,將認為無害的請求報文再發送給實際網站服務器進行請求,可以說是帶防護功能的CDN。
(4)網站系統內置的WAF
網站系統內置的WAF也可以說是網站系統中內置的過濾,直接鑲嵌在代碼中,相對來說自由度高,一般有以下這幾種情況。
● 輸入參數強制類型轉換(intval等)。
● 輸入參數合法性檢測。
● 關鍵函數執行(SQL執行、頁面顯示、命令執行等)前,對經過代碼流程的輸入進行檢測。
● 對輸入的數據進行替換過濾后再繼續執行代碼流程(轉義/替換掉特殊字符等)。
網站系統內置的WAF與業務更加契合,在對安全與業務都比較了解的情況下,可以更少地收到誤報與漏報。
2、WAF判斷
下面介紹判斷網站是否存在WAF的幾種方法。
(1)SQLMap
使用SQLMap中自帶的WAF識別模塊可以識別出WAF的種類,但是如果按下面裝的WAF並沒有什么特征,SQLMap就只能識別出類型是Generic。
下面以某衛士官網為例,在SQLMap中輸入以下命令,結果如圖1所示。
sqlmap.py –u "http://xxx.com"--identify-waf--batch
圖1 使用SQLMap識別WAF
可以看到識別出WAF的類型為XXX Web Application Firewall。
要想了解詳細的識別規則可以查看SQLMap的WAF目錄下的相關腳本,也可以按照其格式自主添加新的WAF識別規則,寫好規則文件后直接放到WAF目錄下即可。
(2)手工判斷
這個也比較簡單,直接在相應網站的URL后面加上最基礎的測試語句,比如union select 1,2,3%23,並且放在一個不存在的參數名中,本例里使用的是參數aaa,如圖2所示,觸發了WAF的防護,所以網站存在WAF。
圖2 WAF攔截了非法請求
因為這里選取了一個不存在的參數,所以實際並不會對網站系統的執行流程造成任何影響,此時被攔截則說明存在WAF。
被攔截的表現為(增加了無影響的測試語句后):頁面無法訪問、響應碼不同、返回與正常請求網頁時不同的結果等。
3、一些WAF的繞過方法
(1)大小寫混合
在規則匹配時只針對了特定大寫或特定小寫的情況,在實戰中可以通過混合大小寫的方式進行繞過(現在幾乎沒有這樣的情況),如下所示。
uNion sElEct 1,2,3,4,5
(2)URL編碼
極少部分的WAF不會對普通字符進行URL解碼,如下所示。
union select 1,2,3,4,5
上述命令將被編碼為如下所示的命令。
%75%6E%69%6F%6E%20%73%65%6C%65%63%74%20%31%2C%32%2C%33%2C%34%2C%35
還有一種情況就是URL二次編碼,WAF一般只進行一次解碼,而如果目標Web系統的代碼中進行了額外的URL解碼,即可進行繞過。
union select 1,2,3,4,5
上述命令將被編碼為如下所示的命令。
%2575%256E%2569%256F%256E%2520%2573%2565%256C%2565%2563%2574%2520%2531%252C%2532% 252C%2533%252C%2534%252C%2535
(3)替換關鍵字
WAF采用替換或者刪除select/union這類敏感關鍵詞的時候,如果只匹配一次則很容易進行繞過。
union select 1,2,3,4,5
上述命令將轉換為如下所示的命令。
unuionion selselectect 1,2,3,4,5
(4)使用注釋
注釋在截斷SQL語句中用得比較多,在繞過WAF時主要使用其替代空格(/*任意內容*/),適用於檢測過程中沒有識別注釋或替換掉了注釋的WAF。
Union select 1,2,3,4,5
上述命令將轉換為如下所示的命令。
union/*2333*/select/*aaaa*/1,2,3,4,5
還可以使用內聯注釋嘗試繞過WAF的檢測。
(5)多參數請求拆分
對於多個參數拼接到同一條SQL語句中的情況,可以將注入語句分割插入。
例如請求URL時,GET參數為如下格式。
a=[input1]&b=[input2]
將GET的參數a和參數b拼接到SQL語句中,SQL語句如下所示。
and a=[input1]and b=[input2]
這時就可以將注入語句進行拆分,如下所示。
a=union/*&b=*/select 1,2,3,4
最終將參數a和參數b拼接,得到的SQL語句如下所示。
and a=union /*and b=*/select 1,2,3,4
(6)HTTP參數污染
HTTP參數污染是指當同一參數出現多次,不同的中間件會解析為不同的結果,具體如表1所示(例子以參數color=red&color=blue為例)。
表1 HTTP參數污染
在上述提到的中間線中,IIS比較容易利用,可以直接分割帶逗號的SQL語句。在其余的中間線中,如果WAF只檢測了同參數名中的第一個或最后一個,並且中間件特性正好取與WAF相反的參數,則可成功繞過。下面以IIS為例,一般的SQL注入語句如下所示。
Inject=union select 1,2,3,4
將SQL注入語句轉換為以下格式。
Inject=union/*&inject=*/select/*&inject=*/1&inject=2&inject=3&inject=4
最終在IIS中讀入的參數值將如下所示。
Inject=union/*,*/select/*,*/1,2,3,4
(7)生僻函數
使用生僻函數替代常見的函數,例如在報錯注入中使用polygon()函數替換常用的updatexml()函數,如下所示。
SELECT polygon((select*from(select*from(select@@version)f)x));
(8)尋找網站源站IP
對於具有雲WAF防護的網站而言,只要找到網站的IP地址,然后通過IP訪問網站,就可以繞過雲WAF的檢測。
常見的尋找網站IP的方法有下面這幾種。
● 尋找網站的歷史解析記錄。
● 多個不同區域ping網站,查看IP解析的結果。
● 找網站的二級域名、NS、MX記錄等對應的IP。
● 訂閱網站郵件,查看郵件發送方的IP。
(9)注入參數到cookies中
某些程序員在代碼中使用$_REQUEST獲取參數,而$_REQUEST會依次從GET/POST/cookie中獲取參數,如果WAF只檢測了GET/POST而沒有檢測cookie,可以將注入語句放入cookie中進行繞過。




