0x00 原理
思路來自美團杯2021,本來說出題人已經把select通過正則過濾了,就不該總是往用select進行查詢那方面想-》 select id from users where username='admin' and password='admin'
0x01 繞過方法
首先我們測出or沒被過濾,and被過濾,||沒被過濾,異或沒被過濾,但是select被過濾了,如果糾結於用盲注,那麼就必須要用到select。
然後題目還過濾了單引號,可以用到之前那篇隨筆我提到的方法。通過 username=admin\ 去註釋掉查詢語句中的單引號進行繞過,然後再到密碼欄插入payload。
一開始我採用的payload: username=admin&password=|| 1=1 通過這種判斷 得到了 頁面的提示 no flag here,但是感覺提示的不是很明白。
之後構造了 username=admin&password=(ord(left(database(),1))/**/regexp/**/0x67)1 得到了資料庫名的第一個字元是g 最後一個字元是p ,然後 測得資料庫有3個字元。
但其實仔細一想這樣不行, 因為 select 根本沒法用,後面如果要查表 或者 查列都必須用到select。 所以必須換種思路。
0x02 技巧
- 如果是密碼框,而且過濾了if,可通過case when...then...else...end替換
如果沒過濾的話,猜測密碼列就是 password ,所以可在那構造判斷,原payload是or//if(password//regexp//0x67,1,0) ,因為前面的使用者名稱是錯的,所以是0,實際上是0 or if(password regexp 0x67,1,0) ,
語句邏輯為 如果password列中有0x67轉成的字元就返回1,否則返回0
實驗:
通過這樣構造 查詢到了匹配成功時的id, 但是 這樣的話 不管 是否匹配 都有查詢結果,所以頁面可能顯示是一樣的 難以判斷。
所以我們需要改成延時盲注
如果過濾了if 和 逗號 需要改成
or//case//when//password//regexp//binary//0x67//then//sleep(3)//else//112//end;
語句邏輯為 如果 密碼匹配到了某個十六進位制,實際上就是匹配到了某個確切的字元 就 休眠3秒,通過這種方式判斷密碼列中的flag,且區分大小寫。
binary 是為了防止 出現大小寫相同匹配
使用了binary時 是區分大小寫的
反之