關于被動式掃描的碎碎念

來源:http://bbs.ichunqiu.com/thread-9619-1-1.html?from=ch

0x00 簡介

分布式掃描好多人都寫過,例如:

burp的sqli插件

Matt前輩的http://zone.wooyun.org/content/24172

豬豬俠前輩的http://zone.wooyun.org/content/21289

Ver007前輩的http://zone.wooyun.org/content/24333

0x_Jin前輩的http://zone.wooyun.org/content/24341

填上個坑填的心煩,想著也造個輪子绍坝,忙活了幾天,寫了一個簡單的雛形

Github:https://github.com/liuxigu/ScanSqlTestchromeExtensions

在此感謝bstaint宵荒、sunshadow的幫助

Sqlmapapi本來就是為了實現分布式注入寫的,在被動掃描的基礎上 加節(jié)點就實現分布式了

最初想的是用chrome插件來實現代碼注入

用js來獲取標簽的同域url,用js是防止一些站的反爬蟲措施,還有對于a href指向相對鏈接的的情況,用js會自動補全域名.

Chrome webRequest API OnBeforeRequest獲取即將請求的url

設想獲取url后 喂給sqlmapapi, 將能注入的url寫入到文本里,js 的 FileSystemObject gg.. 本來是準備用php實現文件io的…

talk is cheap show me the code.

0x01 Chrome manifest.json

[AppleScript]純文本查看復制代碼

?

01

02

03

04

05

06

07

08

09

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24#!js

{

"name":"sqlInjectionTest",

"version":"0.1",

"description":"you know...",

"manifest_version":2,

"content_scripts":[{

"matches":["*://*/*"],

"js":["inject.js"]

}],

"permissions":[

"*://*/*",

"webRequest",

"webRequestBlocking"

],

"browser_action":{

"default_icon":"icon.png",

"default_title":"scan url inject"

}

}

0x02 Sqlmapapi.py code

一:固定Admin Id

Sqlmapapi啟動后 是這樣子:

[AppleScript]純文本查看復制代碼

?

1

2

3

4

5

6#!bash

root@kali:~/桌面/sqlmap# python sqlmapapi.py -s

[22:02:17] [INFO] Running REST-JSON API serverat'127.0.0.1:8775'..

[22:02:17] [INFO] Admin ID:7c4be58c7aab5f38cb09eb534a41d86b

[22:02:17] [DEBUG] IPC database:/tmp/sqlmapipc-5JVeNo

[22:02:17] [DEBUG] REST-JSON API server connectedtoIPC database

AdminID每次都會變,這樣導致任務管理不方便,我們更改一下sqlmap的源碼

定位到/sqlmap/lib/utils/api.py 的server函數

看到644行的os.urandom,直接改成一個固定字符串就行了

例如 我改成了DataStore.admin_id = hexencode('wooyun')

以后就固定是Admin ID: 776f6f79756e

還有個更簡單的辦法

return True

二:sqlmap掃描任務結束自動寫入文本

判斷當前任務是否掃描完成 訪問http://127.0.0.1:8775/admin/ss/list

[AppleScript]純文本查看復制代碼

?

1

2

3

4

5

6

7

8#!python

{

"tasks":{

"4db4e3bd4410efa9":"terminated"

},

"tasks_num":1,

"success":true

}

Terminated代表任務已終止,

http://127.0.0.1:8775/scan/4db4e3bd4410efa9/data

[AppleScript]純文本查看復制代碼

?

1

2

3

4

5

6#!python

{

"data":[],

"success":true,

"error":[]

}

“data”存放了sqlmapapi檢測時用的payload, “data”非空就代表當前任務是可注入的,sqlmapapi并沒有自帶回調方式…輪詢浪費開銷,這里我選擇修改源碼

定位到scan_data函數 ,可以看到,假如可注入,就會從data表檢索數據并寫入到json_data_message,表名為data, 代碼向上翻,定位到將數據入庫的代碼

在StdDbOut類里,第230行汁雷,在insert前 插入

[AppleScript]純文本查看復制代碼

?

01

02

03

04

05

06

07

08

09

10#!python

withopen('/tmp/'+str(self.taskid)+'.txt','a+')asfileHandleTemp,\

closing(requests.get('http://127.0.0.1:8775/option/'+str(self.taskid)+'/list',stream=True))asreqTemp:

fileHandleTemp.write(

json.loads(reqTemp.text)['options']['url']+'\n'+

json.loads(reqTemp.text)['options']['data']+'\n'+

json.loads(reqTemp.text)['options']['Cookie']+'\n'+

json.loads(reqTemp.text)['options']['Referer']+'\n'

)

記得加載三個模塊

[AppleScript]純文本查看復制代碼

?

1

2

3

4#!python

import json

import requests

fromcontextlib importclosing

本意是獲取能注入的url寫入到文本里,在源碼里沒找到繼承這個類的地方…懶得去找了

訪問http://127.0.0.1:8775/option/id/list

[AppleScript]純文本查看復制代碼

?

01

02

03

04

05

06

07

08

09

10

11#!python

Response:

{

"options":{

......

"url":[url]http://58.59.39.43:9080/wscgs/xwl.do?smid=02&bgid=01&bj=8[/url]

……

}

"success":{

...

}

0x03 inject.js code

1.

那么要過濾掉javascript::偽協議和無sql操作的href

看到有這樣寫的:

[AppleScript]純文本查看復制代碼

?

1

2#!js

ifre.match('^(javascript|:;|#)',_url) or _url is None or re.match('.(jpg|png|bmp|mp3|wma|wmv|gz|zip|rar|iso|pdf|txt|db)$',_url):

甚至這樣的:

[AppleScript]純文本查看復制代碼

?

01

02

03

04

05

06

07

08

09

10#!js

filename=urlpath[i+1:len(urlpath)]

?0?2?0?2?0?2?0?2print?0?2"Filename:?0?2",filename

?0?2?0?2?0?2?0?2res=filename.split('.')

?0?2?0?2?0?2?0?2if(len(res)>1):

?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2extname=res[-1]

?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2ext=["css","js","jpg","jpeg","gif","png","bmp","html","htm","swf","ico","ttf","woff","svg","cur","woff2"]

?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2for?0?2blacklist?0?2in?0?2ext:

?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2if(extname==blacklist):

?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2?0?2return?0?2False

這兩種方式假如遇到這樣的url: http://xxx/aaa/ ,就會造成無意義的開銷.

判斷是否可以進行get注入測試,其實只需要

str.match(/[\?]/); 無get參數的頁面會返回null

我們這樣寫: /http(s)?:\/\/ ([\w\W-]+\/)+ ([\w\W]+\?)+/;

再加上同域過濾净嘀,js中沒有php那樣可以在字符串中用{}引用變量的值,要在正則中拼接變量需要用RegExp對象:

[AppleScript]純文本查看復制代碼

?

1

2

3#!js

var urlLegalExpr="http(s)?:\/\/"+document.domain+"([\\/\\w\\W]+\\?)+";

var objExpr=newRegExp(urlLegalExpr,"gi");

2.

Js是在http response后執(zhí)行的,要進行post注入侠讯,必須在OnBeforeRequest之前獲取,chrome提供了相關的api,這個沒什么可說的 ,看代碼吧

inject.js code:

[AppleScript]純文本查看復制代碼

?

001

002

003

004

005

006

007

008

009

010

011

012

013

014

015

016

017

018

019

020

021

022

023

024

025

026

027

028

029

030

031

032

033

034

035

036

037

038

039

040

041

042

043

044

045

046

047

048

049

050

051

052

053

054

055

056

057

058

059

060

061

062

063

064

065

066

067

068

069

070

071

072

073

074

075

076

077

078

079

080

081

082

083

084

085

086

087

088

089

090

091

092

093

094

095

096

097

098

099

100

101

102

103

104

105

106

107

108

109

110

111

112

113

114

115

116

117

118

119

120

121#!js

main();

functionmain(){

var urlLegalExpr="http(s)?:\/\/"+document.domain+"([\\/\\w\\W]+\\?)+";

var objExpr=newRegExp(urlLegalExpr,"gi");

urlArray=document.getElementsByTagName('a');

for(i=0;i

if(objExpr.test(urlArray[i].href)){

sqlScanTest(urlArray[i].href);

}

}

}

function sqlScanTest(url,payload){

sqlmapIpPort="http://127.0.0.1:8775";

var payload=arguments[1] ||'{"url":"'+url+'","User-Agent":"wooyun"}';

Connection('GET',sqlmapIpPort+'/task/new','',function(callback){

var response=JSON.parse(callback);

if(response.success){

Connection('POST',sqlmapIpPort+'/scan/'+response.taskid+'/start',payload,function(callback){

var responseTemp=JSON.parse(callback);

if(!responseTemp.success){

alert('urlsendtosqlmapapierror');

}

}

)

}

else{

alert('sqlmapapi create taskerror');

}

}

)

}

function Connection(Sendtype,url,content,callback){

if(window.XMLHttpRequest){

var xmlhttp=newXMLHttpRequest();

}

else{

var xmlhttp=newActiveXObject("Microsoft.XMLHTTP");

}

xmlhttp.onreadystatechange=function(){

if(xmlhttp.readyState==4&&xmlhttp.status==200)

{

callback(xmlhttp.responseText);

}

}

xmlhttp.open(Sendtype,url,true);

xmlhttp.setRequestHeader("Content-Type","application/json");

xmlhttp.send(content);

}

function judgeUrl(url){

var objExpr=newRegExp(/^http(s)?:\/\/127\.0\.0\.1/);

returnobjExpr.test(url);

}

var payload={};

chrome.webRequest.onBeforeRequest.addListener(

function(details){

if(details.method=="POST"&&!judgeUrl(details.url)){

var saveParamTemp="";

for(var iindetails.requestBody.formData){

saveParamTemp+="&"+i+"="+details.requestBody.formData[i][0];

}

saveParamTemp=saveParamTemp.replace(/^&/,'');

//console.log(saveParamTemp);

payload["url"]=details.url;

payload["data"]=saveParamTemp;

}

//console.log(details);

},

{urls:[""]},

["requestBody"]);

chrome.webRequest.onBeforeSendHeaders.addListener(

function(details){

if(details.method=="POST"&&!judgeUrl(details.url)){

//var cookieTemp="",uaTemp="",refererTemp="";

for(var ecx=0;ecx

switch(details.requestHeaders[ecx].name){

case"Cookie":

payload["Cookie"]=details.requestHeaders[ecx].value;

break;

case"User-Agent":

payload["User-Agent"]=details.requestHeaders[ecx].value;

break;

case"Referer":

payload["Referer"]=details.requestHeaders[ecx].value;

break;

default:

break;

}

}

sqlScanTest("test",JSON.stringify(payload));

return{requestHeaders:details.requestHeaders};

}

},

{urls:[""]},

["requestHeaders"]);

Sqlmap能用的選項都可以在http://ip:port/option/taskid/list里查看,用到哪項寫到payload里就行了,最好是做成實時刷新代理,之前寫過爬蟲的時候寫過一個python版的挖藏,有空的話會改成js加入到inject.js里.

201602040648396999862.jpg(163.2 KB, 下載次數: 0)

下載附件保存到相冊

6?小時前上傳

0x04 參考文獻

《使用sqlmapapi.py批量化掃描實踐》http://drops.wooyun.org/tips/6653

《chrome webRequest API》https://developer.chrome.com/extensions/webRequest

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市厢漩,隨后出現的幾起案子膜眠,更是在濱河造成了極大的恐慌,老刑警劉巖溜嗜,帶你破解...
    沈念sama閱讀 218,607評論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件宵膨,死亡現場離奇詭異,居然都是意外死亡炸宵,警方通過查閱死者的電腦和手機辟躏,發(fā)現死者居然都...
    沈念sama閱讀 93,239評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來土全,“玉大人捎琐,你說我怎么就攤上這事」祝” “怎么了瑞凑?”我有些...
    開封第一講書人閱讀 164,960評論 0 355
  • 文/不壞的土叔 我叫張陵,是天一觀的道長概页。 經常有香客問我拨黔,道長,這世上最難降的妖魔是什么绰沥? 我笑而不...
    開封第一講書人閱讀 58,750評論 1 294
  • 正文 為了忘掉前任,我火速辦了婚禮贺待,結果婚禮上徽曲,老公的妹妹穿的比我還像新娘。我一直安慰自己麸塞,他們只是感情好秃臣,可當我...
    茶點故事閱讀 67,764評論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著哪工,像睡著了一般奥此。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上雁比,一...
    開封第一講書人閱讀 51,604評論 1 305
  • 那天稚虎,我揣著相機與錄音,去河邊找鬼偎捎。 笑死蠢终,一個胖子當著我的面吹牛序攘,可吹牛的內容都是我干的。 我是一名探鬼主播寻拂,決...
    沈念sama閱讀 40,347評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼程奠,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了祭钉?” 一聲冷哼從身側響起瞄沙,我...
    開封第一講書人閱讀 39,253評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎慌核,沒想到半個月后距境,有當地人在樹林里發(fā)現了一具尸體,經...
    沈念sama閱讀 45,702評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡遂铡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 37,893評論 3 336
  • 正文 我和宋清朗相戀三年肮疗,在試婚紗的時候發(fā)現自己被綠了。 大學時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片扒接。...
    茶點故事閱讀 40,015評論 1 348
  • 序言:一個原本活蹦亂跳的男人離奇死亡伪货,死狀恐怖,靈堂內的尸體忽然破棺而出钾怔,到底是詐尸還是另有隱情碱呼,我是刑警寧澤,帶...
    沈念sama閱讀 35,734評論 5 346
  • 正文 年R本政府宣布宗侦,位于F島的核電站愚臀,受9級特大地震影響,放射性物質發(fā)生泄漏矾利。R本人自食惡果不足惜姑裂,卻給世界環(huán)境...
    茶點故事閱讀 41,352評論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望男旗。 院中可真熱鬧舶斧,春花似錦、人聲如沸察皇。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,934評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽什荣。三九已至矾缓,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間稻爬,已是汗流浹背嗜闻。 一陣腳步聲響...
    開封第一講書人閱讀 33,052評論 1 270
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留因篇,地道東北人泞辐。 一個月前我還...
    沈念sama閱讀 48,216評論 3 371
  • 正文 我出身青樓笔横,卻偏偏與公主長得像,于是被迫代替她去往敵國和親咐吼。 傳聞我的和親對象是個殘疾皇子吹缔,可洞房花燭夜當晚...
    茶點故事閱讀 44,969評論 2 355

推薦閱讀更多精彩內容