一:SQL注入分類sql
SQL注入通常分爲兩類:一階SQL注入(普通SQL注入),二階SQL注入數據庫
二:兩者進行比較工具
0x01:一階SQL注入:測試
1;一階SQL注入發生在一個HTTP請求和響應中,對系統的攻擊是當即執行的;網站
2;攻擊者在http請求中提交非法輸入;get
3;應用程序處理非法輸入,使用非法輸入構造SQL語句;原理
4;在攻擊過程當中向攻擊者返回結果。date
0x02:二階SQL注入:select
1;攻擊者在http請求中提交惡意輸入;權限
2;惡意輸入保存在數據庫中;
3;攻擊者提交第二次http請求;
4;爲處理第二次http請求,程序在檢索存儲在數據庫中的惡意輸入,構造SQL語句;
5;若是攻擊成功,在第二次請求響應中返回結果。
三:危害比較
一階SQL注入和二階SQL注入危害一致,攻擊者得到數據庫的訪問權限,竊取相關數據,可是一階SQL注入能夠經過相關工具掃描出來,而二階SQL注入更微妙,一般二階SQL注入漏洞的測試主要依據測試人員對系統功能的理解和對常出錯位置經驗的判斷,可是應用功能的增長,經驗的測試結果並不能保證測試結果。
四:二階SQL注入原理講解
假設一個網站數據庫中存在一個用戶名爲:「admin」,密碼爲:「123456」。攻擊者註冊用戶名爲:「admin'-- 」,密碼爲:「123」;程序中的代碼爲:
String name=StringEscapeUtiles.escapeSql(request.getParameter("Name"));
String pwd=StringEscapeUtiles.escapeSql(request.getParameter("pwd"));
String sql1="insert into user(username,password) values ("name","pwd")";
程序在把輸入數據存入數據庫以前,對輸入的數據中的單引號進行了轉義來防止惡意輸入對對數據庫中數據帶來的影響,避免了一階注入帶來的問題,可是在數據庫中存入的用戶名任然爲:「admin'-- 」。如今攻擊者要更新密碼,程序會首先判斷用戶是否存在,代碼爲:
String name=StringEscapeUtiles.escapeSql(request.getParameter("Name"));
String oldpwd=StringEscapeUtiles.escapeSql(request.getParameter("oldpwd"));
String newpwd=StringEscapeUtiles.escapeSql(request.getParameter("newpwd"));
String sql2 = "select * from user where username="name" and password="oldpwd"";
確認用戶存在且密碼正確時,應用程序執行更新密碼語句:
sql3="update user set password="newpwd" where username="username"";
在數據庫中執行語句爲:
update user set password =「111111」 where username='admin'-- '
在數據庫語句這種「-- 」表示註釋,所以「-- 」後面的語句不會執行;最終攻擊者改變的不是「admin'-- 」的密碼,而是admin的密碼,從而實現攻擊。
以上爲本人閱讀相關材料並結合我的體會所寫,有不當之處敬請指教。