sqlmap原始碼通讀(一)

凌天labs發表於2019-07-18

一、前情提要

最近實驗室大佬在寫一個滲透測試框架,目的是在出去做滲透測試專案的時候能夠快速發現漏洞,以及實施快速打擊。

 

但無論大小型的掃描器、掃描框架等,結果的真實性、內容豐富性和效率、效用都會形成一個矛盾,因此,能夠價效比最高的發現問題都是掃描框架首要的任務。

 

對於檢測注入這個位置,我們希望能夠快速發現,不需要實際注入得出資料,然後想著正好學習一下sqlmap的原始碼,能夠使用的部分直接拿過來,再根據實際作用改一改。於是就有了這篇文章。對於我的水平應該是99%都看不懂的,但是好在網上相關文章不少。

 

SQLMAP不用過多介紹,是一款檢測和利用SQL隱碼攻擊的工具,基於python編寫。

 

SQL隱碼攻擊 5 種型別:布林注入,時間注入,報錯注入,聯合查詢注入,堆查詢注入。還有一種SQLMAP支援的,內聯注入。

二、SQLMAP使用方法

先來看一下SQLMAP的常見使用方法和引數。

 

幫助資訊:-h/--hh/--version

 

-h 能夠顯示幫助資訊,--hh 能夠顯示更多的資訊
--version 能夠顯示程式版本

 

日誌顯示等級:-v

 

0:只顯示Python的回溯、錯誤和關鍵訊息;
1:同時顯示基本資訊和警告資訊;
2:同時顯示除錯資訊;
3:同時顯示注入的payload;
4:同時顯示HTTP請求;
5:同時顯示HTTP響應頭;
6:同時顯示HTTP響應頁面頁面。

 

指定目標(GET方法):-d/-u/--url/-g

 

-d 表示sqlmap將自己作為客戶端去連線資料庫
-u/--url 指定目標系統的 URL
-g 對Google的搜尋結果進行SQL隱碼攻擊探測,例如:sqlmap.py -g "inurl:".php?id=1."

 

指定引數(GET方法):-p/--batch/--force-ssl

 

-p 對指定的引數進行SQL隱碼攻擊檢測
--batch 不與使用者進行資訊互動,直接執行
--force-ssl 強制使用 SSL/HTTPS 協議

 

指定目標(POST方法):-r/-l/-c

 

-r 將HTTP請求檔案儲存到文字文件中,使用-r引數讀取文字檔案的引數進行SQL隱碼攻擊
-l 將burpsuite log檔案儲存到文字文件中,使用引數-l讀取文字文件的引數進行SQL隱碼攻擊
-c 對配置ini檔案進行SQL隱碼攻擊探測

 

指紋資訊:-f/--fingerprint/-b/--banner

 

-b/--banner 獲取資料庫版本資訊和資料庫型別
-f/--fingerprint 查詢目標系統的資料庫管理系統的指紋資訊

 

列舉:-a/--all/--dbs/--current-user/--privileges-U/--roles/--current-db/--users/--passwords/--tables/--columns/--schema/--dump/--dump-all/-D/-T/-C/--exclude-sysdbs/--count/--schema/--batch/--sql-query/--sql-shell

 

-a/--all 獲取所有資訊
--dbs 列舉DBMS中所有的資料庫
--current-user 獲取當前使用者
--privileges-U username(當前賬號/CU) 檢視當前賬號的許可權
--roles 列出資料庫管理員角色,僅適用於當前資料庫是Oracle
--current-db 獲取當前資料庫
--users 列舉DBMS使用者
--passwords 列舉DBMS使用者密碼hash值
--tables 列舉DBMS資料庫管理系統中的表
--columns 列舉DBMS資料庫管理系統中的列
--schema 列舉DBMS資料庫管理系統的模式
--dump 轉儲DBMS資料庫表項,後面加-C表示轉儲某列,-T轉儲某表,-D轉儲某資料庫,--start,--stop,--first,--last指定開始結束,開頭結尾。
--dump-all 轉儲所有的DBMS資料庫表項
-D 指定列舉的DBMS中的資料庫
-T 指定要列舉的表
-C 指定要列舉的列
-D 資料庫名 --tables 查詢指定資料庫中的表
-D 資料庫名 -T 表名 --columns 查詢指定資料庫的某個表中的列
--exclude-sysdbs 忽略掉系統資料庫
--count 查詢表中的記錄數
--schema 查詢資料庫的架構,包含所有的資料庫,表和欄位,以及各自的型別,一般與--exclude-sysdbs共用
--batch 預設每次自動執行

--sql-query/--sql-shell 執行自定義的SQL語句,例:--sql-query="select from users;"所得到的內容被儲存到dump目錄中*

 

指定資料:--data/--cookie/--param-del/--user-agent/--random-agent/--host/--referer/--method

 

--data=DATA 指定post資料包中被傳輸的值,例:sqlmap.py -u "http//www.xxx.com" --data="name=123&pass=456" -f
--cookie=COOKIE 指定cookie值登入web程式,並且會嘗試自動注入cookie值,需要在level 2或者大於level 2等級才會進行cookie注入。如果cookie被伺服器端更新,那麼sqlmap也會自動更新cookie值。例:sqlmap -u "http://www.xxx.com/index/?id=1&Submit=Submit#" -p id --cookie="security=low; PHPSESSID=d806c1f76f24a9687640ce497afc8f20" --batch
--param-del 告知sqlmap變數分隔符。web程式一般預設是&符號作為分隔符,如果並非&,則需要指定變數分隔符,例:sqlmap.py -u "http://www.xxx.com" --data="user=123;pass=456" --param-del=";" -f
--user-agent 指定UA頭部資訊。sqlmap預設使用UA為:sqlmap/1.0-dev-版本號 http://sqlmap.org
--random-agent 使用sqlmap/txt/user-agents.txt字典中的UA頭部進行隨機替換
--host=host header 指定host頭部資訊,當level為5的時候才會檢測host值
--referer=REFERER 指定Referer頭部資訊,當level大於等於三 ,才回去檢測referer頭部是否存在注入
--method=GET/POST 指定使用get或者POST方式傳送資料,預設以get方式傳送

 

注入模組配置:-p/--skip/-u/--dbms/--os/--invalid-bignum/--invalid-logical/--no-cast/--tamper

 

-p 指定掃描的引數,也可以指定HTTP頭部欄位,例:sqlmap.py -u "http://www.xxx.com/?id=1" -p "User-Agent,Referer,id"
--skip 跳過對某些引數進行測試。當使用--level的值很大但是有個別引數不想去測試的時候使用--skip去跳過 例:sqlmap.py -u "http://www.xxx.com/?id=1" --skip "User-Agent,Referer,id"
-u 設定URL注入點。當有些網站將引數和值一起加入到URL連結中,sqlmap是預設不對其進行掃描的,所以我們需要去指定對某個引數值進行注入,例:sqlmap.py -u "http://www.xxx.com/param1/value1
/param2/value2" --dbms 設定目標伺服器所使用的DBMS,例:--dbms="mysql"
--os 指定目標的作業系統,例:--os="linux"
--invalid-bignum 給引數值給與最大值讓其失效
--invalid-logical 使用布林判斷使取值失效
--no-cast 榨取資料時,sqlmap將所有的結果轉換成字串,並用空格替換null值(老版本mysql資料庫需要開啟此開關)
--tamper=TAMPER 使用給定的指令碼去混淆繞過應用層的過濾,比如waf/ids等。該檔案存放在/sqlmap/tamper檔案下,例:sqlmap.py -u "www.xxx.com/?id=1" -p "id" --tamper="between.py,overlongutf8more.py,lowercase.py "

 

身份認證:--auth-type/--auth-cred/--auth-file

 

--auth-type=AUTH 指定HTTP認證型別(Basic, Digest, NTLM or PKI)
--auth-cred=AUTH 指定HTTP認證證照(格式為:name:password),例:sqlmap.py -u "http://www.xxx.com/?id=1" --auth-type=Basic --auth-cred "user:pass"
--auth-file=AUTH 指定HTTP認證PEM格式的證照/私鑰檔案

 

代理類:--proxy/--proxy-cred/--ignore-proxy/--tor/--tor-type

 

--proxy="http://127.0.0.1:8081" 設定代理伺服器
--proxy-cred="name:pass" 例:sqlmap -u "http://www.xxx.com/?id=1" --proxy="http://127.0.0.1:8081" --proxy-cred="user:pass" -f
--ignore-proxy 忽略系統級代理設定,通常用於掃描本地網路目標
--tor 使用匿名網路進行注入
--tor-type 指定tor網路連線型別

 

延時類:--delay/--timeout/--retries/--randomize/--scope

 

--delay=DELAY 每次HTTP(S)請求之間延遲時間,值為浮點數,單位為秒,預設無延遲
--timeout=TIMEOUT 設定超時時間,預設30秒
--retries=RETRIES 設定重連次數,預設3次
--randomize 設定隨機改變的引數值
--scope 利用正規表示式過濾日誌內容

 

技術型別:--technique/--time-sec/--union-cols/--union-char/--union-from/--dns-domain/--second-order

 

SQLMAP對於以下引數具有預設值:

 

--technique=TECH 指定sqlmap使用的檢測技術,預設情況下會測試所有的方式。
--time-sec=TIMESEC 設定延遲時間,基於時間的注入檢測預設延遲時間是5秒
--union-cols=UCOLS 聯合查詢時預設是1-10列,當level=5時會增加到測試50個欄位數,可以使用此引數設定查詢的欄位數。
--union-char=UCHAR 預設情況下sqlmap針對UNION查詢的注入會使用NULL字元;
--union-from=UFROM 在UNION查詢SQL隱碼攻擊的FROM部分中使用的表
--dns-domain=DNS 攻擊者控制了某DNS伺服器,使用此功能可以提高資料查詢的速度
--second-order=URL 使用此引數指定到哪個頁面獲取響應判斷真假,--second-order後面跟一個判斷頁面的URL地址。

 

CSRF TOKEN 繞過:--csrf-url/--csrf-token

 

--csrf-url=URL 獲取token的連結
--csrf-token=param 你提交注入包中,token引數

 

檢測類:--level/--risk/--string/--not-string/--Regexp/--code

 

--level 共有5級,預設等級1
--risk 共有4級,預設等級1,risk升高將使用update等方法測試,將造成資料被篡改等風險
--string 指定頁面返回某個字串則為真
--not-string 指定頁面不返回某個字串則為真
--Regexp 當查詢的值為真時,使用正規表示式去匹配
--code 當查詢的值為真時,執行HTTP code

 

系統檔案操作:--file-read/--file-write

 

--file-read=RFILE 從後端DBMS檔案系統中讀取檔案(讀取系統檔案),例:--file-read="/etc/passwd"
--file-write=SHELL.PHP --file-dest=DFILE 把當前系統的檔案寫入到目標伺服器的某個目錄下去

 

OS系統訪問:--os-cmd/--os-shell/--os-pwn/--os-smbrelay/--os-bof

 

--os-cmd 執行任意作業系統命令(適用於資料庫為mysql,postgresql,或Sql Server,並且當前使用者有許可權使用特定的函式),例:--os-cmd id :執行id命令,後期是與sqlmap進行互動,生成UDF函式在作業系統下執行命令
--os-shell 獲取一個shell(目標系統為管理員許可權,並且得知絕對路徑)
--os-pwn 獲取一個OOB shell,meterpreter或VNC
--os-smbrelay 一鍵獲取一個OOB shell,meterpreter或VNC
--os-bof 儲存過程緩衝區溢位利用
UDF注入:--udf-inject/--shared-lib
UDF:自定義函式,利用UDF函式達到執行作業系統命令
--udf-inject 注入使用者自定義函式
--shared-lib=SHLIB 指定共享庫的本地路徑

 

兩條命令需一起使用

 

爆破錶/欄位名:--common-tables/--common-columns

 

使用場景:

 

mysql版本<5.0的時候,沒有information_schema庫 mysql版本>=5.0,但無權讀取information_schema庫
微軟的access資料庫,預設無權讀取MSysObjects庫。

 

--common-tables 爆破錶名,例:sqlmap.py -u "http://www.baidu.com/?id=1" --common-tables
--common-columns 暴力破解列名

 

Windows登錄檔:--reg-read/--reg-add/--reg-del/--reg-key/--reg/value/--reg-data/--reg-type

 

--reg-read 讀取登錄檔的值
--reg-add 寫入登錄檔值
--reg-del 刪除登錄檔值
--reg-key,--reg-value,--reg-data,--reg-type 登錄檔輔助選項

 

一般性引數:-s/-t/--charset/--crawl/--csv-del/--dbms-creb/--flush-session/--fresh-queries/--hex/--save

 

-s 指定sqlite會話檔案儲存位置
-t 記錄流量檔案儲存位置
--charset 強制字元編碼,例:--charset=GBK
--crawl 從開始位置爬站深度,例:--crawl=3
--csv-del dump 下來的資料以CVS格式儲存
--dbms-creb 指定資料庫賬號
--slush-session 清空session
--fresh-queries 忽略session查詢結果
--hex 當dump下非ASCii字元內容時,將其編碼成16進賬形式,收到後解析還原
--save 將命令儲存成配置檔案

 

WAF對抗類:--check-waf/--identify-waf/--hpp

 

--check-waf 檢測WAF/IPS/IDS
--hpp 繞過WAF/IPS/ISD,尤其是對ASP/IIS和ASP.NET/IIS有效
--identify-waf 徹底的WAF/IPS/IDS檢測,支援三十多種產品

 

最佳化效能:-o/--predict-output/--keep-alive/--null-connection/--threads
-o 開啟所有最佳化開關
--predict-output 預測常見的查詢輸出
--keep-alive 使用持久的HTTP(S)連線
--null-connection 從沒有實際的HTTP響應體中檢索頁面長度
--threads=THREADS 設定最大的HTTP(S)請求併發量(預設為1)

 

其他引數:--safe-url/--safe-freq/--skip-urlencode/--eval/--mobile/--purge-output/--smart/--wizard

 

--safe-url=SAFEURL 指定需要去重複掃描的地址
--safe-freq 指定每傳送多少次的注入請求之後接著發正常請求,有些web應用程式會在攻擊者多次訪問錯誤的請求時遮蔽掉以後的所有請求,所以設定這兩個引數防止以後無法進行注入 --skip-urlencode 跳過URL編碼的載荷,預設在get請求中是需要對傳輸資料進行編碼,但是有些web伺服器不遵守RPC標準編碼,使用原始字元提交資料,所以使用這個引數使sqlmap不使用URL編碼的引數進行測試

 

--eval=EBALCODE 在請求之前執行提供的python程式碼,例:sqlmap.py -u "http://www.xxx.com/?id=1&hash=c4ca4238a0b923820dcc509a6f75849b" --evel="import hashlib;hash=hashlib.md5(id).hexdigest()"
--mobile 模擬智慧手機裝置,修改User-Agent為手機端的UA
--purge-output 清空output資料夾
--smart 當有大量檢測目標時,只修改基於錯誤的檢測結果
--wizard 設定使用者嚮導引數,教你一步步針對目標註入

相關文章