Exemple #1
0
def import_report():
    """
    Import a MSF Pro XML Report.

    TODO: FINISH HIM!
    """

    msf_settings = msf_get_config(session)
    if msf_settings['workspace'] is None:
        redirect(URL('api_settings'))

    msf = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
    if not msf.login():
        response.flash = "Error logging into Metasploit, check your settings"
        redirect(URL('api_settings'))

    form = SQLFORM.factory(
        Field('whitelist', 'text', label=T('Whitelist hosts/nets')),
        Field('blacklist', 'text', label=T('Blacklist hosts/nets')),
    )

    if form.accepts(request, sesssion):
        # build the configuration hash
        rpt_data = {}
        rpt_data['DS_REPORT_TYPE'] = 'XML'
        rpt_data['DS_WHITELIST_HOSTS'] = form.vars.whitelist
        rpt_data['DS_BLACKLIST_HOSTS'] = form.vars.blacklist
        rpt_data['Workdspace'] = msf_settings['workspace']

        # send the report request and get the task id
        rpt_taskid = msf.pro_start_report(rpt_data)
Exemple #2
0
def list_lootfiles():
    """
    Lists local loot files for import processing into Kvasir. This does not
    use the Metasploit API and depends upon a directory being local to the
    web2py server instance. The API is used to check if pro is installed
    and sets the loot_dir to Linux or Windows path
    """
    import os
    import re
    response.title = "%s :: Metasploit Loots" % (settings.title)
    msf_settings = msf_get_config(session)

    dbsvcs = db.t_services
    loot_dir = request.args(0)

    if not loot_dir:
        try:
            from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
            msf = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
            if msf.pro_about():
                if platform in ["linux", "linux2"]:
                    loot_dir = "/opt/metasploit_pro/apps/pro/loot"
                else:
                    loot_dir = "C:\\Metasploit\\apps\\pro\\loot"
        except ImportError, error:
            pass
Exemple #3
0
def task_list():
    """Obtains a list of tasks"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task List" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, tasks=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(error=str(error), alert=True, tasks=None)

    tasks = msf.task_list()
    tasklist = []
    if 'status' in request.vars:
        # only return specific tasks as defined in status
        for taskid, task in tasks.items():
            if task['status'] == request.vars.status.lower():
                tasklist.append({taskid: task})
    else:
        tasklist = tasks

    return dict(tasks=tasklist)
Exemple #4
0
def import_pwdump():
    """Downloads a pwdump loot and processes it"""
    msf_settings = msf_get_config(session)
    alert = False
    error = None
    response.title = "%s :: Import Metasploit PWDUMP Loot" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(alert=True, error=str(error), form=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
        data = msf.loot_list(msf_settings['workspace'])
    except MSFProAPIError as error:
        return dict(alert=True, error=str(error), form=None)

    if not alert:
        loot_list = []  # list of loot IDs and IPs
        loot_hosts = {}  # mapping of IP to loot IDs
        for k, v in data.items():
            if v['ltype'] == 'host.windows.pwdump' or v[
                    'ltype'] == 'windows.hashes':
                loot_list.append([k, v['host']])
                loot_hosts.setdefault(v['host'], k)

        form = SQLFORM.factory(
            Field('hosts',
                  'list',
                  requires=IS_IN_SET(loot_list, multiple=True),
                  label=T('Host')),
            Field('host_text', 'text', label=T('Host list (1 per line)')),
            Field('addevidence', 'boolean', label=T('Add to Evidence')),
        )

        if form.accepts(request, session):
            from skaldship.metasploit import process_pwdump_loot
            data = []
            # based on which form data is entered, make a new loot_list
            if len(form.vars.hosts) > 0:
                loot_list = form.vars.hosts
            elif len(form.vars.host_text) > 0:
                for ip in form.vars.host_text.split('\n'):
                    try:
                        loot_list.append(loot_hosts[ip])
                    except:
                        logging.debug("%s not found in MSF loot list" % (ip))
                        continue

            retval = process_pwdump_loot(loot_list, msf)
            response.flash = "PWDUMP files imported\n%s" % (retval)
        elif form.errors:
            response.flash = "Errors in your form"
    else:
        form = None

    return dict(form=form, alert=alert, error=str(error))
Exemple #5
0
def list_lootfiles():
    """
    Lists local loot files for import processing into Kvasir. This does not
    use the Metasploit API and depends upon a directory being local to the
    web2py server instance. The API is used to check if pro is installed
    and sets the loot_dir to Linux or Windows path
    """
    import os
    import re
    response.title = "%s :: Metasploit Loots" % (settings.title)
    msf_settings = msf_get_config(session)

    dbsvcs = db.t_services
    loot_dir = request.args(0)

    if not loot_dir:
        try:
            from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
            msf = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
            if msf.pro_about():
                if platform in ["linux", "linux2"]:
                    loot_dir = "/opt/metasploit_pro/apps/pro/loot"
                else:
                    loot_dir = "C:\\Metasploit\\apps\\pro\\loot"
        except ImportError, error:
            pass
Exemple #6
0
def import_report_xml():
    """
    Upload/import Metasploit XML export file
    """
    import time
    import os
    from skaldship.general import check_datadir

    msf_settings = msf_get_config(session)
    response.title = "%s :: Import Metasploit Pro Report XML" % (settings.title)
    filedir = os.path.join(request.folder,'data','scanfiles')
    fields = []
    alert = False
    error = None

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append( [ user.id, user.username ] )

    fields.append(Field('f_filename', 'upload', uploadfolder=filedir, label=T('Metasploit XML File')))

    # check to see if we have a Metasploit Pro instance configured and talking
    # if so pull a list of the workspaces and present them
    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
        msf = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
    except ImportError, error:
        msf = None
Exemple #7
0
def import_report():
    """
    Import a MSF Pro XML Report.

    TODO: FINISH HIM!
    """

    msf_settings = msf_get_config(session)
    if msf_settings['workspace'] is None:
        redirect(URL('api_settings'))

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    if not msf.login():
        response.flash = "Error logging into Metasploit, check your settings"
        redirect(URL('api_settings'))

    form = SQLFORM.factory(
        Field('whitelist', 'text', label=T('Whitelist hosts/nets')),
        Field('blacklist', 'text', label=T('Blacklist hosts/nets')),
    )

    if form.accepts(request, sesssion):
        # build the configuration hash
        rpt_data = {}
        rpt_data['DS_REPORT_TYPE'] = 'XML'
        rpt_data['DS_WHITELIST_HOSTS'] = form.vars.whitelist
        rpt_data['DS_BLACKLIST_HOSTS'] = form.vars.blacklist
        rpt_data['Workdspace'] = msf_settings['workspace']

        # send the report request and get the task id
        rpt_taskid = msf.pro_start_report(rpt_data)
Exemple #8
0
def import_report_xml():
    """
    Upload/import Metasploit XML export file
    """
    import time
    import os
    from skaldship.general import check_datadir

    msf_settings = msf_get_config(session)
    response.title = "%s :: Import Metasploit Pro Report XML" % (settings.title)
    filedir = os.path.join(request.folder,'data','scanfiles')
    fields = []
    alert = False
    error = None

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append( [ user.id, user.username ] )

    fields.append(Field('f_filename', 'upload', uploadfolder=filedir, label=T('Metasploit XML File')))

    # check to see if we have a Metasploit Pro instance configured and talking
    # if so pull a list of the workspaces and present them
    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
        msf = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
    except ImportError, error:
        msf = None
Exemple #9
0
def task_stop():
    """Stop a running task"""
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #10
0
def task_stop():
    """Stop a running task"""
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #11
0
def import_screenshots():
    """
    Import Screenshot files from Metasploit Pro into Kvasir
    """
    response.title = "%s :: Import Metasploit Screenshots" % (settings.title)
    msf_settings = msf_get_config(session)
    loot_apidata = {}

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(form=None, error=str(error), alert=True)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
        loot_apidata = msf.loot_list(msf_settings['workspace'])
    except MSFProAPIError as error:
        return dict(form=None, error=str(error), alert=True)

    loot_list = []
    loot_dict = {}
    loot_hosts = {}
    for k, v in loot_apidata.items():
        if v['ltype'] == 'host.windows.screenshot':
            loot_list.append([k, v['host']])
            loot_dict.setdefault(k, v['host'])
            loot_hosts.setdefault(v['host'], k)

    form = SQLFORM.factory(
        Field('host',
              'list',
              requires=IS_IN_SET(loot_list, multiple=True),
              label=T('Host')),
        Field('host_text', 'text', label=T('Host list (1 per line)')),
    )

    if form.accepts(request, session):
        loots = []
        # based on which form data is entered, make a new loot_list
        if form.vars.hosts:
            loot_list = form.vars.hosts
        elif form.vars.host_text:
            for ip in form.vars.host_text.split('\n'):
                try:
                    loot_list.append(loot_hosts[ip])
                except:
                    logging.debug("%s not found in MSF loot list" % (ip))
                    continue

        loot_count = process_screenshot_loot(loot_list, msf)
        repsonse.flash = 'Screenshots added for %s host(s)' % (loot_count)

    elif form.errors:
        response.flash = "Errors in your form"

    return dict(form=form, alert=False, error=None)
Exemple #12
0
def task_log():
    """Show the details and log file of a specifc task"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task Log" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, data=None)
Exemple #13
0
def send_accounts():
    """Builds a list of username:passwords and sends it to Metasploit"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Send Kvasir Passwords to Metasploit Pro" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #14
0
def task_list():
    """Obtains a list of tasks"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task List" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, tasks=None)
Exemple #15
0
def api_settings():
    """Settings Metasploit API"""

    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit API Settings" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, form=None)

    error = None
    alert = False
    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        workspaces = [w for w in list(msf.pro_workspaces().keys())]
        users = [u for u in list(msf.pro_users().get('users').keys())]
    except MSFProAPIError as e:
        error = str(e)
        alert = True
        workspaces = []
        users = []

    form = SQLFORM.factory(
        Field('workspace',
              'string',
              default=msf_settings['workspace'],
              label=T('Workspace Name'),
              requires=IS_IN_SET(workspaces)),
        Field('workspace_num',
              'string',
              default=msf_settings['ws_num'],
              label=T('Workspace Number')),
        Field('user',
              'string',
              default=msf_settings['user'],
              label=T('MSF User'),
              requires=IS_IN_SET(users)),
        Field('url', 'string', default=msf_settings['url'],
              label=T('MSF URL')),
        Field('key', 'string', default=msf_settings['key'],
              label=T('API Key')),
    )
    # NOTE: workspace_num must be manually entered since there's no way for us
    # to learn it from the API. We're just guessing otherwise - 1 is the default
    # workspace so it's more likely to exist
    if form.accepts(request, session):
        settings.msf_workspace = form.vars.workspace
        settings.msf_workspace_num = form.vars.workspace_num
        session.msf_key = form.vars.key
        session.msf_url = form.vars.url
        session.msf_user = form.vars.user
        response.flash = "MSF Settings updated"
    elif form.errors:
        response.flash = "Errors in your form!"
    return dict(form=form, error=str(error), alert=False)
Exemple #16
0
def send_accounts():
    """Builds a list of username:passwords and sends it to Metasploit"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Send Kvasir Passwords to Metasploit Pro" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #17
0
def task_log():
    """Show the details and log file of a specifc task"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task Log" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, data=None)
Exemple #18
0
def task_status():
    """Show details of a specifc task (but not the log file)"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task Status" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, data=None)
Exemple #19
0
def task_status():
    """Show details of a specifc task (but not the log file)"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task Status" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, data=None)
Exemple #20
0
def task_list():
    """Obtains a list of tasks"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit Task List" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, tasks=None)
Exemple #21
0
def api_settings():
    """Settings Metasploit API"""

    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit API Settings" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #22
0
def api_settings():
    """Settings Metasploit API"""

    msf_settings = msf_get_config(session)
    response.title = "%s :: Metasploit API Settings" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #23
0
def exploit_host():
    """
    Build an exploit for a specific target
    """

    msf_settings = msf_get_config(session)
    try:
        from MetasploitAPI import MetasploitAPI, MSFAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #24
0
def send_scanxml():
    """Sends scan XML output file to MSF Pro for importing"""
    import os

    response.title = "%s :: Send Scan XML Data to Metasploit" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #25
0
def import_pwdump():
    """Downloads a pwdump loot and processes it"""
    msf_settings = msf_get_config(session)
    alert = False
    error = None
    response.title = "%s :: Import Metasploit PWDUMP Loot" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(alert=True, error=str(error), form=None)
Exemple #26
0
def import_pwdump():
    """Downloads a pwdump loot and processes it"""
    msf_settings = msf_get_config(session)
    alert = False
    error = None
    response.title = "%s :: Import Metasploit PWDUMP Loot" % (settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(alert=True, error=str(error), form=None)
Exemple #27
0
def send_scanxml():
    """Sends scan XML output file to MSF Pro for importing"""
    import os

    response.title = "%s :: Send Scan XML Data to Metasploit" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(error=str(error), alert=True, form=None)
Exemple #28
0
def bruteforce():
    """
    Launches a Metasploit Pro Bruteforce based upon a list of host records
    """
    response.title = "%s :: Metasploit Pro Bruteforce" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(alert=True, error=str(error), form=None)
Exemple #29
0
def bruteforce():
    """
    Launches a Metasploit Pro Bruteforce based upon a list of host records
    """
    response.title = "%s :: Metasploit Pro Bruteforce" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(alert=True, error=str(error), form=None)
Exemple #30
0
def import_scan():
    """
    Upload and import Nexpose Scan file
    """
    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI
        msf_api = MetasploitProAPI(host=msf_settings['url'],
                                   apikey=msf_settings['key'])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    from skaldship.general import check_datadir
    import time
    import os

    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    response.title = "%s :: Import Nessus Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    nessus_config = nessus_get_config()
    # {'ignored_vulnids': [19506, 11219, 34277],
    #  'servers': {'server_1': {'password': '******',
    #                           'url': 'https://localhost:8834/',
    #                           'user': '******'}}}
    nessusreports = [[0, None]]
    import NessusAPI
    #if auth.user.f_nessus_host is not None:
    servers = nessus_config.get('servers', {})
    for k, v in servers.iteritems():
        try:
            # check to see if NessusAPI is working
            nessus = NessusAPI.NessusConnection(v.get('user'),
                                                v.get('password'),
                                                url=v.get('url'))
            reports = nessus.list_reports()
            for report in reports:
                ts = time.ctime(float(report.timestamp))
                nessusreports.append([
                    "%s:%s" % (k, report.name),
                    "%s: %s - %s (%s)" %
                    (k, report.readablename, ts, report.status)
                ])
        except Exception, e:
            logger.error("Error communicating with %s: %s" % (k, str(e)))
Exemple #31
0
def import_screenshots():
    """
    Import Screenshot files from Metasploit Pro into Kvasir
    """
    response.title = "%s :: Import Metasploit Screenshots" % (settings.title)
    msf_settings = msf_get_config(session)
    loot_apidata={}

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(form=None, error=str(error), alert=True)
Exemple #32
0
def import_screenshots():
    """
    Import Screenshot files from Metasploit Pro into Kvasir
    """
    response.title = "%s :: Import Metasploit Screenshots" % (settings.title)
    msf_settings = msf_get_config(session)
    loot_apidata={}

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError, error:
        return dict(form=None, error=str(error), alert=True)
Exemple #33
0
def import_scan():
    """
    Upload and import Nexpose Scan file
    """
    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitAPI import MetasploitAPI

        msf_api = MetasploitAPI(host=msf_settings["url"], apikey=msf_settings["key"])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    from skaldship.general import check_datadir
    import time
    import os

    filedir = os.path.join(request.folder, "data", "scanfiles")
    response.title = "%s :: Import Nessus Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    nessus_config = nessus_get_config(session)
    # {'ignored_vulnids': [19506, 11219, 34277],
    #  'servers': {'server_1': {'password': '******',
    #                           'url': 'https://localhost:8834/',
    #                           'user': '******'}}}
    nessusreports = [[0, None]]
    import NessusAPI

    # if auth.user.f_nessus_host is not None:
    servers = nessus_config.get("servers", {})
    for k, v in servers.iteritems():
        try:
            # check to see if NessusAPI is working
            nessus = NessusAPI.NessusConnection(v.get("user"), v.get("password"), url=v.get("url"))
            reports = nessus.list_reports()
            for report in reports:
                ts = time.ctime(float(report.timestamp))
                nessusreports.append(
                    ["%s:%s" % (k, report.name), "%s: %s - %s (%s)" % (k, report.readablename, ts, report.status)]
                )
        except Exception, e:
            logger.error("Error communicating with %s: %s" % (k, str(e)))
Exemple #34
0
def import_xml_scan():
    """
    Upload/import Nexpose XML Scan file via scheduler task
    """
    from NexposeAPI import NexposeAPI, Sites, Report
    from skaldship.general import check_datadir
    from skaldship.metasploit import msf_get_config
    import time
    import os
    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI
        msf_api = MetasploitProAPI(host=msf_settings['url'],
                                   apikey=msf_settings['key'])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    response.title = "%s :: Import Nexpose XML Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    # check to see if nexpose is configured/active and get site listing
    nexpose_config = nexpose_get_config()
    nxsitelist = []
    if nexpose_config['host'] is not None and nexpose_config[
            'user'] is not None:
        # see if the host is open/active first
        if nexpose_config['host'] is not None:
            sites = Sites()
            sites.host = nexpose_config['host']
            sites.port = nexpose_config['port']
            try:
                if sites.login(user_id=nexpose_config['user'],
                               password=nexpose_config['password']):
                    sites = sites.listings()
                    nxsitelist.append([0, None])
                    for k, v in sites.iteritems():
                        nxsitelist.append([int(k), sites[k]['name']])
            except Exception, e:
                pass
Exemple #35
0
def import_xml_scan():
    """
    Upload/import Nexpose XML Scan file via scheduler task
    """
    from NexposeAPI import NexposeAPI, Sites, Report
    from skaldship.general import check_datadir
    from skaldship.metasploit import msf_get_config
    import time
    import os

    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI

        msf_api = MetasploitProAPI(host=msf_settings["url"], apikey=msf_settings["key"])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    filedir = os.path.join(request.folder, "data", "scanfiles")
    response.title = "%s :: Import Nexpose XML Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    # check to see if nexpose is configured/active and get site listing
    nexpose_config = nexpose_get_config()
    nxsitelist = []
    if nexpose_config["host"] is not None and nexpose_config["user"] is not None:
        # see if the host is open/active first
        if nexpose_config["host"] is not None:
            sites = Sites()
            sites.host = nexpose_config["host"]
            sites.port = nexpose_config["port"]
            try:
                if sites.login(user_id=nexpose_config["user"], password=nexpose_config["password"]):
                    sites = sites.listings()
                    nxsitelist.append([0, None])
                    for k, v in sites.iteritems():
                        nxsitelist.append([int(k), sites[k]["name"]])
            except Exception, e:
                pass
Exemple #36
0
def task_stop():
    """Stop a running task"""
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, form=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(error=str(error), alert=True, form=None)

    if 'taskid' not in request.vars:
        tasks = msf.task_list()
        task_list = []
        for taskid, task in tasks.items():
            if tasks[taskid]['status'] == 'running':
                task_list.append([
                    taskid,
                    "%s (%s) :: %s :: %s" % (
                        taskid,
                        tasks[taskid]['status'],
                        tasks[taskid]['description'],
                        tasks[taskid]['info'],
                    )
                ])
        form = SQLFORM.factory(
            Field('taskid',
                  'string',
                  requires=IS_IN_SET(task_list),
                  label=T('Task ID')))
        return dict(form=form)

    response.title = "%s :: Stop Metasploit Task" % (settings.title)
    data = msf.task_stop(request.vars.taskid)
    return dict(data=data)
Exemple #37
0
def exploit_host():
    """
    Build an exploit for a specific target
    TODO: Finish metasploit.exploit_host
    """

    msf_settings = msf_get_config(session)
    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, form=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(error=str(error), alert=True, form=None)

    target = request.vars.f_target or None
    exploit = request.vars.f_exploit or None

    form = SQLFORM.factory()
Exemple #38
0
def exploit():
    """
    Launches Metasploit Pro Exploit based upon a list of host records
    """
    response.title = "%s :: Metasploit Pro Exploit" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(alert=True, error=str(error), form=None)

    host_records = request.vars.host_records
    if host_records:

        def host_to_ip(host_rec):
            if isinstance(host_rec, (int, str)):
                host_rec = get_host_record(host_rec)
            if not host_rec:
                return None
            return host_rec.get('f_ipaddr')

        target_ips = '\n'.join(
            [host_to_ip(x) for x in host_records.split('|')])
    else:
        target_ips = ''

    module_list = []
    alert = False
    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        module_list = msf.module_list(modtype='exploits').get('modules')
    except MSFProAPIError as error:
        return dict(alert=True, error=str(error), form=None)

    form = SQLFORM.factory(
        Field(
            'targets',
            'text',
            default=target_ips,
            label=T('Targets'),
            requires=IS_NOT_EMPTY(),
            comment=
            T('Targets to scan can be IP Addresses, ranged lists or subnets. One per line.'
              )),
        Field(
            'blacklist_hosts',
            'text',
            label=T('Blacklisted Targets'),
            comment=
            T('Targets to blacklist can be IP Addresses, ranged lists or subnets. One per line.'
              )),
        Field(
            'ports',
            'string',
            default='1-65535',
            label=T('Ports'),
            requires=IS_NOT_EMPTY(),
            comment=
            T('List of ports to match exploits to. Example: 21-23,80,443,8000-8999'
              )),
        Field(
            'blacklist_ports',
            'string',
            label=T('Blacklisted Ports'),
            comment=T(
                'List of ports to not exploit. Example: 21-23,80,443,8000-8999'
            )),
        Field('min_rank',
              'string',
              default='great',
              label=T('Minmum Exploit Rank'),
              requires=IS_IN_SET(
                  ['low', 'average', 'normal', 'good', 'great', 'excellent']),
              comment=T('Minimum reliability level of exploits to include')),
        Field('exploit_speed',
              'integer',
              default=5,
              label=T('Parallel Exploits'),
              requires=IS_INT_IN_RANGE(1, 11),
              comment=T('How many exploits to run in parallel (1-10)')),
        Field('exploit_timeout',
              'integer',
              default=5,
              label=T('Timeout (in minutes)'),
              requires=IS_INT_IN_RANGE(0, 1440),
              comment=T(
                  'Maximum time (in minutes) an exploit is allowed to run')),
        Field('limit_sessions',
              'boolean',
              default=True,
              label=T('Limit sessions'),
              comment=T('Limit sessions to only one per exploited host')),
        Field(
            'ignore_fragile',
            'boolean',
            default=True,
            label=T('Skip "fragile" devices'),
            comment=
            T('Avoid exploit attempts on fragile systems such as network devices and printers.'
              )),
        Field(
            'filter_by_os',
            'boolean',
            default=True,
            label=T('OS'),
            comment=
            T('Match exploits to Operating System, known vulnerabilities or ports'
              )),
        Field('filter_by_vuln',
              'boolean',
              default=True,
              label=T('Vulnerabilities')),
        Field('filter_by_ports', 'boolean', default=True, label=T('Ports')),
        Field('dry_run',
              'boolean',
              default=False,
              label=T('Dry run'),
              comment=T('Prepare for execution but do nothing')),
        Field('payload',
              'string',
              default='auto',
              label=T('Payload method'),
              requires=IS_IN_SET(['auto', 'reverse', 'bind'])),
        Field('payload_type',
              'string',
              default='meterpreter',
              label=T('Paylod type'),
              requires=IS_IN_SET(['meterpreter', 'shell'])),
        Field('payload_ports',
              'string',
              default='4000-5000',
              label=T('Payload ports'),
              requires=IS_NOT_EMPTY(),
              comment=T('Port range for reverse/connect payloads')),
        Field('evasion_tcp',
              'integer',
              default=0,
              label=T('TCP Evasion Level'),
              requires=IS_INT_IN_RANGE(0, 4)),
        Field('evasion_app',
              'integer',
              default=0,
              label=T('Application Evasion'),
              requires=IS_INT_IN_RANGE(0, 4)),
        Field(
            'modules',
            'list:string',
            label=T('Specifc Module(s)'),
            requires=IS_EMPTY_OR(IS_IN_SET(module_list, multiple=True)),
            comment=
            T('A whitelist of modules to execute, by default all that match are tried'
              )),
        table_name='msfpro_exploit',
        _class="form-horizontal")

    if form.process().accepted:
        args = {
            'workspace': msf_settings['workspace'],
            'username': msf_settings['user'],
            'DS_WHITELIST_HOSTS': form.vars.targets,
            'DS_BLACKLIST_HOSTS': form.vars.blacklist_hosts,
            'DS_WHITELIST_PORTS': form.vars.ports,
            'DS_BLACKLIST_PORTS': form.vars.blacklist_ports,
            'DS_MinimumRank': form.vars.min_rank,
            'DS_EXPLOIT_SPEED': form.vars.exploit_speed,
            'DS_EXPLOIT_TIMEOUT': form.vars.exploit_timeout,
            'DS_LimitSessions': form.vars.limit_sessions,
            'DS_IgnoreFragileDevices': form.vars.ignore_fragile,
            'DS_FilterByOS': form.vars.filter_by_os,
            'DS_MATCH_VULNS': form.vars.filter_by_vuln,
            'DS_MATCH_PORTS': form.vars.filter_by_ports,
            'DS_OnlyMatch': form.vars.dry_run,
            'DS_PAYLOAD_METHOD': form.vars.payload,
            'DS_PAYLOAD_TYPE': form.vars.payload_type,
            'DS_PAYLOAD_PORTS': form.vars.payload_ports,
            'DS_EVASION_LEVEL_TCP': form.vars.evasion_tcp,
            'DS_EVASION_LEVEL_APP': form.vars.evasion_app,
            #'DS_ModuleFilter': form.vars.filter_by_os,
        }
        task = msf.start_exploit(args)
        msfurl = os.path.join(msf_settings['url'], 'workspaces',
                              msf_settings['workspace_num'], 'tasks',
                              task['task_id'])
        redirect(msfurl)
    elif form.errors:
        response.flash = "Error in form"

    return dict(form=form, alert=alert)
Exemple #39
0
def vulndata_by_host():
    """
    Returns a list of vulnerabilties based upon an host identifier
    (id, ipv4, ipv6)
    """
    from skaldship.metasploit import msf_get_config
    msf_settings = msf_get_config(session)

    record = get_host_record(request.args(0))
    if record is None:
        redirect(URL('default', 'error', vars={'msg': T('Host record not found')}))

    response.title = "%s :: Vulnerabilities for %s" % (settings.title, host_title_maker(record))
    services = db(db.t_services.f_hosts_id==record.id).select(db.t_services.id,
                                                              db.t_services.f_proto, db.t_services.f_number)

    if request.extension == "json":
        aaData = []
        for svc in services:
            # service info
            q = db(db.t_service_vulns.f_services_id == svc.id).select()
            for vulninfo in q:
                atxt = {}
                exploit_list = []
                vulndetails = db(db.t_vulndata.id == vulninfo.f_vulndata_id).select(cache=(cache.ram, 300)).first()
                exploits = db(db.t_exploit_references.f_vulndata_id == vulninfo.f_vulndata_id).select(orderby=~db.t_exploit_references.id)
                if len(exploits) > 0:
                    expl_count = "Yes (%d)" % (len(exploits))
                    for expl in exploits:
                        for expl_data in db(db.t_exploits.id == expl.f_exploit_id).select(cache=(cache.ram, 300)):
                            exp_link = expl_data.f_name
                            if expl_data.f_source == 'exploitdb':
                                if db.t_exploitdb[expl_data.f_title]:
                                    exploitdb_href = URL('exploitdb', 'detail.html', args=expl_data.f_title)
                                else:
                                    exploitdb_href = URL('default', 'redirect', extension='html', vars={'url': 'http://www.exploit-db.com/exploits/%s' % expl_data.f_title})
                                exp_link = A(IMG(_align="absmiddle", _width=16, _height=16, _src=URL('static','images/exploitdb.ico')), ' exploitdb - ' + expl_data.f_name,_href=exploitdb_href, _target="exploitdb_%s" % (expl_data.f_name))
                            elif expl_data.f_source == 'metasploit':
                                if session.msf_workspace:
                                    msf_uri = os.path.join(msf_settings['url'], 'workspaces', session.msf_workspace_num, 'modules', expl_data.f_title)
                                else:
                                    msf_uri = URL('default', 'redirect', extension='html', vars={'url': 'http://www.rapid7.com/db/modules/%s' % expl_data.f_title})
                                exp_link = A(IMG(_align="absmiddle", _width=16, _height=16, _src=URL('static','images/msf.gif')), ' metasploit - ' + expl_data.f_name, _href=msf_uri, _target="msf_%s" % (expl_data.f_name))
                            elif expl_data.f_source == 'canvas':
                                exp_link = SPAN(IMG(_align="absmiddle", _width=16, _height=16, _src=URL('static','images/canvas.png')), ' canvas - ' + expl_data.f_name)

                            exploit_list.append("%s : %s (%s/%s)" % (expl_data.f_title, exp_link, expl_data.f_rank, expl_data.f_level))
                else:
                    expl_count = ""

                atxt['0'] = IMG(_src=URL(request.application,'static','images/details_open.png')).xml()
                atxt['1'] = A('edit', _target="service_vuln_update_%s" % (vulninfo.id), _href=URL('vulns', 'service_vulns_edit', args=vulninfo.id, extension='html')).xml()
                if vulninfo.f_exploited:
                    atxt['2'] = '<input id="exploited" value="' + str(vulninfo.id) + '" type="checkbox", checked>'
                else:
                    atxt['2'] = '<input id="exploited" value="' + str(vulninfo.id) + '" type="checkbox">'
                atxt['3'] = "%s/%s" % (svc.f_proto, svc.f_number)
                atxt['4'] = A(vulndetails.f_vulnid, _target="vulndata_%s" % (vulndetails.id), _href=URL('vulns', 'vulninfo_by_vulnid', args=vulndetails.f_vulnid, extension='html')).xml()
                atxt['5'] = vulndetails.f_severity
                atxt['6'] = vulndetails.f_cvss_score
                atxt['7'] = SPAN(vulninfo.f_status,_id="vulninfo_status",_vulnstatus=vulninfo.f_status).xml()
                atxt['8'] = expl_count
                atxt['9'] = MARKMIN(vulninfo.f_proof).xml()
                atxt['10'] = MARKMIN(vulndetails.f_description).xml()
                atxt['11'] = vulndetails.f_title
                atxt['12'] = "<br />\n".join(exploit_list)
                atxt['DT_RowId'] = vulninfo.id
                aaData.append(atxt)

        result = { 'sEcho': request.vars.sEcho,
                   'iTotalRecords': len(aaData),
                   'aaData': aaData,
                   }

        return result

    add = AddModal(
        db.t_service_vulns, 'Add', 'Add', 'Add Vulnerability',
        #fields=[
        #],
        cmd='vulntable.fnReloadAjax();'
    )
    #db.t_service_vulns.f_services_id.default = svc.id
    svc_set = []
    for svc in services:
        svc_set.append([svc.id, "%s :: %s/%s" % (host_title_maker(db.t_hosts[record.id]), svc.f_proto, svc.f_number)])
    db.t_service_vulns.f_services_id.requires = IS_IN_SET(svc_set)
    db.t_service_vulns.id.comment = add.create()

    form = TABLE(THEAD(TR(TH('', _width="5%"),
                          TH(T(''), _width="5%"),
                          TH(T('Pwned'), width="5%"),
                          TH(T('Port')),
                          TH(T('Vuln ID')),
                          TH(T('Sev')),
                          TH(T('CVSS')),
                          TH(T('Status')),
                          TH(T('Exploits')),
                          TH(T('Proof')),
                          TH(T('Description')),
                          TH(T('Title')),
                          TH(T('Exploit List')),
                          )  ),
                 _class="datatable",
                 _id="vulntable",
                 _style="width:100%")

    return dict(form=form, host=record, add=add)
Exemple #40
0
def import_scan():
    """
    Upload and import Nessus Scan file
    """
    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI
        msf_api = MetasploitProAPI(host=msf_settings['url'],
                                   apikey=msf_settings['key'])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    from skaldship.general import check_datadir
    import time
    import os

    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    response.title = "%s :: Import Nessus Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    nessus_config = nessus_get_config()
    # {'ignored_vulnids': [19506, 11219, 34277],
    #  'servers': {'server_1': {'password': '******',
    #                           'url': 'https://localhost:8834/',
    #                           'user': '******'}}}
    nessusreports = [[0, None]]
    import NessusAPI
    from skaldship.nessus.ness6api import Nessus6API

    servers = nessus_config.get('servers', {})
    for k, v in servers.items():
        if v.get('version') == 6:
            # nessus >= 6
            try:
                nessus = Nessus6API(url=v.get('url'),
                                    username=v.get('username'),
                                    password=v.get('password'),
                                    access_key=v.get('access_key'),
                                    secret_key=v.get('secret_key'),
                                    verify=v.get('verify_ssl'),
                                    proxies=v.get('proxies'))
            except Exception as e:
                logger.error("Error communicating with %s: %s" % (k, str(e)))

            try:
                for report in nessus.get_scans():
                    ts = time.ctime(
                        float(report.get('last_modification_date', 0)))
                    nessusreports.append([
                        "%s:%s" % (k, report.get('id')),
                        "%s: %s - %s (%s)" %
                        (k, report.get('name'), ts, report.get('status'))
                    ])
            except Exception as e:
                logger.error("Error making scan list: %s" % (str(e)))
        else:
            # nessus <= 5
            try:
                # check to see if NessusAPI is working
                nessus = NessusAPI.NessusConnection(v.get('user'),
                                                    v.get('password'),
                                                    url=v.get('url'))
                reports = nessus.list_reports()
                for report in reports:
                    ts = time.ctime(float(report.timestamp))
                    nessusreports.append([
                        "%s:%s" % (k, report.name),
                        "%s: %s - %s (%s)" %
                        (k, report.readablename, ts, report.status)
                    ])
            except Exception as e:
                logger.error("Error communicating with %s: %s" % (k, str(e)))

    if len(nessusreports) > 1:
        fields.append(
            Field('f_nessus_report',
                  type='integer',
                  label=T('Nessus Report'),
                  requires=IS_IN_SET(nessusreports, zero=None)))

    fields.append(
        Field('f_filename',
              'upload',
              uploadfolder=filedir,
              label=T('Nessus Scan File')))
    fields.append(
        Field('f_engineer',
              type='integer',
              label=T('Engineer'),
              default=auth.user.id,
              requires=IS_IN_SET(userlist)))
    fields.append(
        Field('f_asset_group',
              type='string',
              label=T('Asset Group'),
              requires=IS_NOT_EMPTY()))

    # check to see if we have a Metasploit Pro instance configured and talking
    # if so pull a list of the workspaces and present them
    if working_msf_api:
        msf_workspaces = ["None"]
        for w in list(msf_api.pro_workspaces().keys()):
            msf_workspaces.append(w)
        fields.append(
            Field('f_msf_workspace',
                  type='string',
                  label=T('MSF Pro Workspace'),
                  requires=IS_EMPTY_OR(IS_IN_SET(msf_workspaces, zero=None))))

    fields.append(
        Field('f_include_list', type='text', label=T('Hosts to Only Include')))
    fields.append(
        Field('f_ignore_list', type='text', label=T('Hosts to Ignore')))
    fields.append(
        Field('f_update_hosts',
              type='boolean',
              label=T('Update Host Information'),
              default=False))
    fields.append(
        Field('f_taskit',
              type='boolean',
              default=auth.user.f_scheduler_tasks,
              label=T('Run in background task')))
    form = SQLFORM.factory(*fields, table_name='nessus_scan')

    # form processing
    if form.errors:
        response.flash = 'Error in form'
    elif form.accepts(request.vars, session):
        # if no Nessus servers configured or valid, set report_name to 0
        if nessusreports == [[0, None]]:
            report_name = '0'
        else:
            if form.vars.f_nessus_report != "0":
                # If a nessus report is selected, try to parse it to set report_name
                try:
                    (server,
                     report_name) = form.vars.f_nessus_report.split(':')
                except ValueError as e:
                    msg = "Invalid report name sent: %s" % (
                        form.vars.f_nessus_report)
                    response.flash = msg
                    logging.error(msg)
                    return dict(form=form)
            else:
                # set report_name to 0 if no f_nessus_report sent
                report_name = '0'

        if report_name != '0':
            # download a report from a Nessus server
            n_server = nessus_config.get('servers').get(server)
            filename = os.path.join(
                filedir, "nessus-%s-%s.xml" %
                (form.vars.f_asset_group, int(time.time())))
            check_datadir(request.folder)

            if n_server.get('version') == 6:
                # nessus version => 6
                try:

                    nessus = Nessus6API(url=n_server.get('url'),
                                        username=n_server.get('username'),
                                        password=n_server.get('password'),
                                        access_key=n_server.get('access_key'),
                                        secret_key=n_server.get('secret_key'),
                                        verify=n_server.get('verify_ssl'),
                                        proxies=n_server.get('proxies'))
                    nessus_report = nessus.report_download(report_name)
                    fout = open(filename, "w")
                    fout.write(nessus_report)
                    fout.close()
                except Exception as e:
                    msg = ("Error download Nessus report: %s" % (e))
                    logger.error(msg)
                    response.flash = msg
                    return dict(form=form)

            else:
                # nessus version <= 5
                try:
                    # build a new nessus connection with the configured server details and download the report
                    n_server = nessus_config.get('servers').get(server)
                    nessus = NessusAPI.NessusConnection(
                        n_server.get('user'),
                        n_server.get('password'),
                        url=n_server.get('url'))
                    fout = open(filename, "w")
                    nessus.download_report(report_name, fout)
                    fout.close()
                except Exception as e:
                    msg = ("Error download Nessus report: %s" % (e))
                    logger.error(msg)
                    response.flash = msg
                    return dict(form=form)
        else:
            filename = os.path.join(filedir, form.vars.f_filename)

        # build the hosts only/exclude list
        ip_exclude = []
        data = form.vars.get('f_ignore_list')
        if data:
            ip_exclude = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals
        ip_include = []
        data = form.vars.get('f_include_list')
        if data:
            ip_include = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals

        if form.vars.f_msf_workspace:
            msf_workspace = form.vars.f_msf_workspace
            if msf_workspace == "None":
                msf_workspace = None
        else:
            msf_workspace = None
        msf_settings = {
            'workspace': msf_workspace,
            'url': msf_settings['url'],
            'key': msf_settings['key']
        }

        if form.vars.f_taskit:
            task = scheduler.queue_task(
                scanner_import,
                pvars=dict(
                    scanner='nessus',
                    filename=filename,
                    asset_group=form.vars.f_asset_group,
                    engineer=form.vars.f_engineer,
                    msf_settings=msf_settings,
                    ip_ignore_list=ip_exclude,
                    ip_include_list=ip_include,
                    update_hosts=form.vars.f_update_hosts,
                ),
                group_name=settings.scheduler_group_name,
                sync_output=5,
                timeout=settings.scheduler_timeout)
            if task.id:
                redirect(URL('tasks', 'status', args=task.id))
            else:
                response.flash = "Error submitting job: %s" % (task.errors)
        else:
            from skaldship.nessus.processor import process_scanfile
            logger.info("Starting Nessus Report Import")
            response.flash = process_scanfile(
                filename=filename,
                asset_group=form.vars.f_asset_group,
                engineer=form.vars.f_engineer,
                msf_settings=msf_settings,
                ip_ignore_list=ip_exclude,
                ip_include_list=ip_include,
                update_hosts=form.vars.f_update_hosts,
            )
            redirect(URL('default', 'index'))

    return dict(form=form)
Exemple #41
0
                     "--msfidx",
                     dest="msfidx",
                     action="store",
                     default=0,
                     help="Metasploit workspace index")

(options, params) = optparser.parse_args()

rows = db(db.auth_user.username == options.engineer)

if rows.count() != 1:
    exit(
        "An error was encountered when selecting a user. Please try with a valid user name."
    )

msf_settings = msf_get_config(session)

msf_workspaces = [None]

try:
    # check to see if we have a Metasploit RPC instance configured and talking
    from MetasploitProAPI import MetasploitProAPI

    msf_api = MetasploitProAPI(host=msf_settings['url'],
                               apikey=msf_settings['key'])
    working_msf_api = msf_api.login()
except:
    working_msf_api = False

if working_msf_api:
    for w in msf_api.pro_workspaces().keys():
Exemple #42
0
def send_scanxml():
    """Sends scan XML output file to MSF Pro for importing"""
    import os

    response.title = "%s :: Send Scan XML Data to Metasploit" % (
        settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, form=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(error=str(error), alert=True, form=None)

    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    try:
        scanfiles = os.listdir(filedir)
    except OSError:
        scanfiles = []
    file_select = []
    count = 0
    for fn in scanfiles:
        file_select.append([count, fn])
        count += 1

    form = SQLFORM.factory(
        Field('fname',
              'string',
              requires=IS_IN_SET(file_select),
              label=T('Scan File')),
        Field(
            'blacklist',
            'text',
            label=T('Blacklisted hosts'),
            comment=
            T('Targets to blacklist can be IP Addresses, ranged lists or subnets. One per line.'
              )),
        Field('preserve_hosts',
              'boolean',
              default=False,
              label=T('Preserve existing hosts')),
    )

    if form.accepts(request, session):
        fname = file_select[int(form.vars.fname)][1]
        fname = os.path.join(filedir, fname)

        try:
            scan_data = open(fname, "r+").readlines()
        except Exception as error:
            return dict(form=form, error=str(error), alert=True)

        task = msf.pro_import_data(
            msf_workspace,
            "".join(scan_data),
            {
                'preserve_hosts': form.vars.preserve_hosts,
                'blacklist_hosts': "\n".join(form.vars.blacklist)
            },
        )
        """
        # documented in API but not valid yet @9/6/13
        #validate = msf.pro_validate_import_file(fname)
        task = msf.pro_start_import({
                  'workspace': msf_workspace,
                  'username': msf_settings['user'],
                  'DS_PATH': fname,
                  'DS_PRESERVE_HOSTS': form.vars.preserve_hosts,
                  'DS_BLACKLIST_HOSTS': "\n".join(form.vars.blacklist),
                  'DS_REMOVE_FILE': False,
                  'DS_ImportTags': True,
                })
        """
        msfurl = os.path.join(msf_settings['url'], 'workspaces',
                              msf_settings['workspace_num'], 'tasks',
                              task['task_id'])
        redirect(msfurl)
    elif form.errors:
        response.flash = "Errors in your form"

    return dict(form=form, alert=False, error=None)
Exemple #43
0
def bruteforce():
    """
    Launches a Metasploit Pro Bruteforce based upon a list of host records
    """
    response.title = "%s :: Metasploit Pro Bruteforce" % (settings.title)
    msf_settings = msf_get_config(session)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(alert=True, error=str(error), form=None)

    host_records = request.vars.host_records
    if host_records:

        def host_to_ip(host_rec):
            if isinstance(host_rec, (int, str)):
                host_rec = get_host_record(host_rec)
            if not host_rec:
                return None
            return host_rec.get('f_ipaddr')

        target_ips = '\n'.join(
            [host_to_ip(x) for x in host_records.split('|')])
    else:
        target_ips = ''

    loot_list = []  # list of loot IDs and IPs
    alert = False
    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(alert=True, error=str(error), form=None)

    form = SQLFORM.factory(
        Field(
            'targets',
            'text',
            default=target_ips,
            label=T('Targets'),
            requires=IS_NOT_EMPTY(),
            comment=
            T('Targets to scan can be IP Addresses, ranged lists or subnets. One per line.'
              ),
        ),
        Field(
            'blacklist',
            'text',
            label=T('Blacklisted hosts'),
            comment=
            T('Targets to blacklist can be IP Addresses, ranged lists or subnets. One per line.'
              )),
        Field(
            'stop_on_success',
            'boolean',
            default=True,
            label=T('Stop on success'),
            comment=T('Stop scanning a host after first user login success')),
        Field('verbose', 'boolean', default=False, label=T('Verbose')),
        Field('include_known',
              'boolean',
              default=True,
              label=T('Include known'),
              comment=T('Include known credentials from the Workspace')),
        Field('dry_run',
              'boolean',
              default=False,
              label=T('Dry run'),
              comment=T('Prepare for execution but do nothing')),
        Field(
            'scope',
            'string',
            default='normal',
            label=T('Scope'),
            requires=IS_IN_SET([
                'quick', 'defaults', 'normal', 'deep', 'known', 'imported',
                '50k'
            ]),
        ),
        Field('speed',
              'string',
              default=3,
              label=T('Speed'),
              requires=IS_IN_SET([[0, 'Glacial'], [1, 'Slow'], [2, 'Stealthy'],
                                  [3, 'Normal'], [4, 'Fast'], [5, 'Turbo']])),
        Field(
            'services',
            'list:string',
            label=T('Services'),
            requires=IS_EMPTY_OR(
                IS_IN_SET([
                    'Telnet',
                    'SSH',
                    'SMB',
                    'VNC',
                    'SNMP',
                    'Postgres',
                    'MySQL',
                    'MSSQL',
                    'Oracle',
                    'DB2',
                    'FTP',
                    'HTTP',
                    'HTTPS',
                    'EXEC',
                    'LOGIN',
                    'SHELL',
                ],
                          multiple=(1, 17))),
            comment=T('List of services to bruteforce, multiples permitted')),
        Field(
            'addl_creds',
            'text',
            label=T('Additional credentals'),
            comment=
            T('List additional credentials to test. One per line with space between username and password.'
              )),
        Field('getsession',
              'boolean',
              default=True,
              label=T('Execute session'),
              comment=T(
                  'On successful access pop a shell or meterpreter session')),
        Field('payload',
              'string',
              default='auto',
              label=T('Payload method'),
              requires=IS_IN_SET(['auto', 'reverse', 'bind'])),
        Field('payload_type',
              'string',
              default='meterpreter',
              label=T('Paylod type'),
              requires=IS_IN_SET(['meterpreter', 'shell'])),
        Field(
            'payload_ports',
            'string',
            default='4000-5000',
            label=T('Payload ports'),
            requires=IS_NOT_EMPTY(),
            comment=T('Port range for reverse/connect payloads'),
        ),
        Field('smb_domains',
              'string',
              label=T('SMB Domains'),
              comment=T('List of SMB domains, separated by spaces, to use')),
        Field(
            'preverse_domains',
            'boolean',
            default=True,
            label=T('Preserve Domains'),
            comment=T('Use previously identified SMB Domains with usernames')),
        Field('mssql_windows_auth',
              'boolean',
              default=False,
              label=T('MSSQL Windows Auth'),
              comment=T(
                  'MSSQL attempts should use NTLM instead of Standard mode')),
        Field('skip_blank_pw', 'boolean', default=False, label=T('Blanks')),
        Field('skip_machine_names',
              'boolean',
              default=False,
              label=T('Machine names')),
        Field('skip_builtin_windows',
              'boolean',
              default=False,
              label=T('Built-in Windows')),
        Field('skip_builtin_unix',
              'boolean',
              default=False,
              label=T('Built-in UNIX')),
        Field('recombine_creds',
              'boolean',
              default=False,
              label=T('Recombine credentials')),
        Field('max_guess_per_svc',
              'integer',
              default=0,
              label=T('Per service'),
              requires=IS_INT_IN_RANGE(0, 65535)),
        Field('max_guess_per_user',
              'integer',
              default=0,
              label=T('Per user'),
              requires=IS_INT_IN_RANGE(0, 65535)),
        Field('max_guess_overall',
              'integer',
              default=0,
              label=T('Overall'),
              requires=IS_INT_IN_RANGE(0, 65535)),
        Field('max_time_per_svc',
              'integer',
              default=0,
              label=T('Per service'),
              requires=IS_INT_IN_RANGE(0, 1440),
              comment=T('Maximum time to bruteforce per service (in minutes')),
        Field('max_time',
              'integer',
              default=0,
              label=T('Overall'),
              requires=IS_INT_IN_RANGE(0, 65535),
              comment=T('Maximum time to run brute force (in minutes)')),
        table_name='msfpro_bruteforce',
        _class="form-horizontal")

    if form.process().accepted:
        args = {
            'workspace': msf_settings['msf_workspace'],
            'username': msf_settings['user'],
            'DS_WHITELIST_HOSTS': form.vars.targets,
            'DS_BLACKLIST_HOSTS': form.vars.blacklist,
            'DS_STOP_ON_SUCCESS': form.vars.stop_on_success,
            'DS_VERBOSE': form.vars.verbose,
            'DS_INCLUDE_KNOWN': form.vars.include_known,
            'DS_DRY_RUN': form.vars.dry_run,
            'DS_BRUTEFORCE_SCOPE': form.vars.scope,
            'DS_BRUTEFORCE_SPEED': form.vars.speed,
            'DS_BRUTEFORCE_SERVICES': " ".join(form.vars.services),
            'DS_BRUTEFORCE_GETSESSION': form.vars.getsession,
            'DS_QUICKMODE_CREDS': form.vars.addl_creds,
            'DS_PAYLOAD_METHOD': form.vars.payload,
            'DS_PAYLOAD_TYPE': form.vars.payload_type,
            'DS_PAYLOAD_PORTS': form.vars.payload_ports,
            'DS_SMB_DOMAINS': form.vars.smb_domains,
            'DS_PRESERVE_DOMAINS': form.vars.preverse_domains,
            'DS_MAXGUESSESPERSERVICE': form.vars.max_guess_per_svc,
            'DS_MAXGUESSESPERUSER': form.vars.max_guess_per_user,
            'DS_MAXGUESSESOVERALL': form.vars.max_guess_overall,
            'DS_MAXMINUTESPERSERVICE': form.vars.max_time_per_svc,
            'DS_MAXMINUTESOVERALL': form.vars.max_time,
            'DS_BRUTEFORCE_SKIP_BLANK_PASSWORDS': form.vars.skip_blank_pw,
            'DS_BRUTEFORCE_SKIP_MACHINE_NAMES': form.vars.skip_machine_names,
            'DS_BRUTEFORCE_SKIP_BUILTIN_WINDOWS_ACCOUNTS':
            form.vars.skip_builtin_windows,
            'DS_BRUTEFORCE_SKIP_BLANK_BUILTIN_UNIX_ACCOUNTS':
            form.vars.skip_builtin_unix,
            'DS_BRUTEFORCE_RECOMBINE_CREDS': form.vars.recombine_creds,
            'DS_MSSQL_WINDOWS_AUTH': form.vars.mssql_windows_auth
        }
        task = msf.start_bruteforce(args)
        msfurl = os.path.join(msf_settings['url'], 'workspaces',
                              msf_settings['workspace_num'], 'tasks',
                              task['task_id'])
        redirect(msfurl)
    elif form.errors:
        response.flash = "Error in form"

    return dict(form=form, alert=alert, error=False)
Exemple #44
0
def import_report_xml():
    """
    Upload/import Metasploit XML export file
    """
    import time
    import os
    from skaldship.general import check_datadir

    msf_settings = msf_get_config(session)
    response.title = "%s :: Import Metasploit Pro Report XML" % (
        settings.title)
    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    fields = []
    alert = False
    error = None

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    fields.append(
        Field('f_filename',
              'upload',
              uploadfolder=filedir,
              label=T('Metasploit XML File')))

    # check to see if we have a Metasploit Pro instance configured and talking
    # if so pull a list of the workspaces and present them
    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
        msf = MetasploitProAPI(host=msf_settings['url'],
                               apikey=msf_settings['key'])
    except ImportError as error:
        msf = None

    if msf:
        try:
            msf_reports_res = msf.report_list(
                workspace=msf_settings['workspace'])
        except MSFProAPIError as error:
            msf_reports_res = None

    if msf_reports_res:
        from datetime import datetime
        msf_reports = []
        for rpt in list(msf_reports_res.keys()):
            report_name = "Generated: %s" % (datetime.strftime(
                datetime.fromtimestamp(msf_reports_res[rpt]['created_at']),
                "%m-%d-%y %H:%M:%S"))
            msf_reports.append([rpt, report_name])
        fields.append(
            Field('f_msf_report',
                  type='string',
                  label=T('MSF Pro Report'),
                  requires=IS_EMPTY_OR(IS_IN_SET(msf_reports, zero=None))))

    fields.append(
        Field('f_engineer',
              type='integer',
              label=T('Engineer'),
              default=auth.user.id,
              requires=IS_IN_SET(userlist)))
    fields.append(
        Field('f_asset_group',
              type='string',
              label=T('Asset Group for new Hosts'),
              default="Metasploit Import",
              requires=IS_NOT_EMPTY()))
    fields.append(
        Field('f_include_list', type='text', label=T('Hosts to Only Include')))
    fields.append(
        Field('f_ignore_list', type='text', label=T('Hosts to Ignore')))
    fields.append(
        Field('f_update_hosts',
              type='boolean',
              default=True,
              label=T('Update Existing Hosts')))
    fields.append(
        Field('f_taskit',
              type='boolean',
              default=auth.user.f_scheduler_tasks,
              label=T('Run in background task')))
    form = SQLFORM.factory(*fields, table_name='metasploit_xml')

    if form.errors:
        response.flash = 'Error in form'
    elif form.accepts(request.vars, session):
        # build the hosts only/exclude list
        ip_exclude = []
        data = form.vars.get('f_ignore_list')
        if data:
            ip_exclude = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals
        ip_include = []
        data = form.vars.get('f_include_list')
        if data:
            ip_include = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals

        if form.vars.f_msf_report:
            try:
                msf_report = msf.report_download(rptid=form.vars.f_msf_report)
            except MSFProAPIError as error:
                error = "Unable to download report from Metasploit Pro: %s" % (
                    str(error))
                return dict(form=form, alert=True, error=error)
            check_datadir(request.folder)
            filename = os.path.join(
                filedir, "msfpro-%s-%s.xml" %
                (msf_settings['workspace'], int(time.time())))
            fout = open(filename, "w")
            fout.write(msf_report['data'])
            fout.close()
            del (msf_report)
        else:
            filename = os.path.join(filedir, form.vars.f_filename)

        if form.vars.f_taskit:
            task = scheduler.queue_task(
                scanner_import,
                pvars=dict(
                    scanner='metasploit',
                    filename=filename,
                    asset_group=form.vars.f_asset_group,
                    engineer=form.vars.f_engineer,
                    ip_ignore_list=ip_exclude,
                    ip_include_list=ip_include,
                    update_hosts=form.vars.f_update_hosts,
                ),
                group_name=settings.scheduler_group_name,
                sync_output=5,
                timeout=settings.scheduler_timeout)
            if task.id:
                redirect(URL('tasks', 'status', args=task.id))
            else:
                response.flash = "Error submitting job: %s" % (task.errors)
        else:
            from skaldship.metasploit.pro import process_report_xml
            logger.info("Starting Metasploit XML Import")
            result = process_report_xml(
                filename=filename,
                asset_group=form.vars.f_asset_group,
                engineer=form.vars.f_engineer,
                ip_ignore_list=ip_exclude,
                ip_include_list=ip_include,
                update_hosts=form.vars.f_update_hosts,
            )
            response.flash = result
            redirect(URL('default', 'index'))

    return dict(form=form, alert=alert, error=error)
Exemple #45
0
                     action="store", default=getpass.getuser(), help="User to import data.")
optparser.add_option("-n", "--noports", dest="noports",
                     action="store_true", default=False, help="Add hosts without ports.")
optparser.add_option("-u", "--update", dest="update_hosts",
                     action="store_true", default=False, help="Update hosts.")
optparser.add_option("-m", "--msfidx", dest="msfidx",
                     action="store", default=0, help="Metasploit workspace index")

(options, params) = optparser.parse_args()

rows = db(db.auth_user.username == options.engineer)

if rows.count() != 1:
    exit("An error was encountered when selecting a user. Please try with a valid user name.")

msf_settings = msf_get_config(session)

msf_workspaces = [None]

try:
    # check to see if we have a Metasploit RPC instance configured and talking
    from MetasploitProAPI import MetasploitProAPI

    msf_api = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
    working_msf_api = msf_api.login()
except:
    working_msf_api = False

if working_msf_api:
    for w in msf_api.pro_workspaces().keys():
        msf_workspaces.append(w)
Exemple #46
0
def list_lootfiles():
    """
    Lists local loot files for import processing into Kvasir. This does not
    use the Metasploit API and depends upon a directory being local to the
    web2py server instance. The API is used to check if pro is installed
    and sets the loot_dir to Linux or Windows path
    """
    import os
    import re
    response.title = "%s :: Metasploit Loots" % (settings.title)
    msf_settings = msf_get_config(session)

    dbsvcs = db.t_services
    loot_dir = request.args(0)

    if not loot_dir:
        try:
            from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
            msf = MetasploitProAPI(host=msf_settings['url'],
                                   apikey=msf_settings['key'])
            if msf.pro_about():
                if platform in ["linux", "linux2"]:
                    loot_dir = "/opt/metasploit_pro/apps/pro/loot"
                else:
                    loot_dir = "C:\\Metasploit\\apps\\pro\\loot"
        except ImportError as error:
            pass

    if not loot_dir:
        from sys import platform
        if platform in ["linux", "linux2", "darwin", "freebsd"]:
            loot_dir = os.path.join(os.environ.get('HOME'), '.msf4/loot')
        elif platform in ["win32", "cygwin"]:
            loot_dir = '$FINDYOUR/msf4/loot/path'

    try:
        os.chdir(loot_dir)
        loot_files = os.listdir(loot_dir)
    except OSError:
        loot_files = []

    loot_file_details = []
    for loot in loot_files:
        try:
            (timestamp, workspace, ipaddr, filetype,
             extension) = re.split('_', loot)
        except ValueError:
            logging.warn("Invalid loot file: %s" % (loot))
            continue

        # TODO: service_list = get_services(ipaddr)
        host_rec = get_host_record(ipaddr)
        services = []
        for service in db(dbsvcs.f_hosts_id == host_rec).select(
                dbsvcs.id, dbsvcs.f_proto, dbsvcs.f_number,
                cache=(cache.ram, 120)):
            services.append(
                [service.id,
                 "%s/%s" % (service.f_proto, service.f_number)])
        loot_file_details.append([workspace, ipaddr, services, filetype])

    form_lootdir = SQLFORM.factory(
        Field('lootdir',
              'string',
              default=loot_dir,
              requires=IS_NOT_EMPTY(),
              label=T('Metasploit Loot Directory')), )

    return dict(form_lootdir=form_lootdir, loot_file_details=loot_file_details)
Exemple #47
0
def import_scan():
    """
    Upload and import Nessus Scan file
    """
    msf_settings = msf_get_config(session)
    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI
        msf_api = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    from skaldship.general import check_datadir
    import time
    import os

    filedir = os.path.join(request.folder, 'data', 'scanfiles')
    response.title = "%s :: Import Nessus Scan Results" % (settings.title)
    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append([user.id, user.username])

    nessus_config = nessus_get_config()
    # {'ignored_vulnids': [19506, 11219, 34277],
    #  'servers': {'server_1': {'password': '******',
    #                           'url': 'https://localhost:8834/',
    #                           'user': '******'}}}
    nessusreports = [[0, None]]
    import NessusAPI
    from skaldship.nessus.ness6api import Nessus6API

    servers = nessus_config.get('servers', {})
    for k, v in servers.iteritems():
        if v.get('version') == 6:
            # nessus >= 6
            try:
                nessus = Nessus6API(
                    url=v.get('url'),
                    username=v.get('username'),
                    password=v.get('password'),
                    access_key=v.get('access_key'),
                    secret_key=v.get('secret_key'),
                    verify=v.get('verify_ssl'),
                    proxies=v.get('proxies')
                )
            except Exception, e:
                logger.error("Error communicating with %s: %s" % (k, str(e)))

            try:
                for report in nessus.get_scans():
                    ts = time.ctime(float(report.get('last_modification_date', 0)))
                    nessusreports.append([
                        "%s:%s" % (k, report.get('id')),
                        "%s: %s - %s (%s)" % (k, report.get('name'), ts, report.get('status'))
                    ])
            except Exception, e:
                logger.error("Error making scan list: %s" % (str(e)))
Exemple #48
0
def import_xml_scan():
    """
    Upload/import Nmap XML Scan file via scheduler task
    """
    import time
    from skaldship.general import check_datadir
    from skaldship.metasploit import msf_get_config
    msf_settings = msf_get_config(session)

    try:
        # check to see if we have a Metasploit RPC instance configured and talking
        from MetasploitProAPI import MetasploitProAPI
        msf_api = MetasploitProAPI(host=msf_settings['url'], apikey=msf_settings['key'])
        working_msf_api = msf_api.login()
    except:
        working_msf_api = False

    filedir = os.path.join(request.folder,'data','scanfiles')
    check_datadir(request.folder)
    response.title = "%s :: Import Nmap XML Scan Results" % (settings.title)

    fields = []

    # buld the dropdown user list
    users = db(db.auth_user).select()
    userlist = []
    for user in users:
        userlist.append( [ user.id, user.username ] )

    fields.append(Field('f_filename', 'upload', uploadfolder=filedir, label=T('Nmap XML File')))
    fields.append(Field('f_engineer', type='integer', label=T('Engineer'), default=auth.user.id, requires=IS_IN_SET(userlist)))
    fields.append(Field('f_asset_group', type='string', label=T('Asset Group'), requires=IS_NOT_EMPTY()))

    # If Metasploit available, pull a list of the workspaces and present them
    if working_msf_api:
        msf_workspaces = []
        msf_workspaces.append( "None" )
        for w in msf_api.pro_workspaces().keys():
            msf_workspaces.append(w)
        fields.append(Field('f_msf_workspace', type='string', label=T('MSF Pro Workspace'), requires=IS_EMPTY_OR(IS_IN_SET(msf_workspaces, zero=None))))

    fields.append(Field('f_addnoports', type='boolean', label=T('Add Hosts w/o Ports'), default=False))
    fields.append(Field('f_include_list', type='text', label=T('Hosts to Only Include')))
    fields.append(Field('f_ignore_list', type='text', label=T('Hosts to Ignore')))
    fields.append(Field('f_update_hosts', type='boolean', label=T('Update Host Information'), default=False))
    fields.append(Field('f_taskit', type='boolean', default=auth.user.f_scheduler_tasks, label=T('Run in background task')))
    form = SQLFORM.factory(*fields, table_name='nmap_xml')

    if form.errors:
        response.flash = 'Error in form'
    elif form.accepts(request.vars, session):
        # process a nmap file
        filename = os.path.join(filedir, form.vars.f_filename)

        # build the hosts only/exclude list
        ip_exclude = []
        data = form.vars.get('f_ignore_list')
        if data:
            ip_exclude = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals
        ip_include = []
        data = form.vars.get('f_include_list')
        if data:
            ip_include = data.split('\r\n')
            # TODO: check for ip subnet/range and break it out to individuals

        if form.vars.f_msf_workspace:
            msf_workspace = form.vars.f_msf_workspace
            if msf_workspace == "None":
                msf_workspace = None
        else:
            msf_workspace = None
        msf_settings = {'workspace': msf_workspace, 'url': msf_settings['url'], 'key': msf_settings['key']}

        if form.vars.f_taskit:
            task = scheduler.queue_task(
                scanner_import,
                pvars=dict(
                    scanner='nmap',
                    filename=filename,
                    addnoports=form.vars.f_addnoports,
                    asset_group=form.vars.f_asset_group,
                    engineer=form.vars.f_engineer,
                    msf_settings=msf_settings,
                    ip_ignore_list=ip_exclude,
                    ip_include_list=ip_include,
                    update_hosts=form.vars.f_update_hosts,
                ),
                group_name=settings.scheduler_group_name,
                sync_output=5,
                timeout=settings.scheduler_timeout
            )
            if task.id:
                redirect(URL('tasks', 'status', args=task.id))
            else:
                response.flash = "Error submitting job: %s" % (task.errors)
        else:
            from skaldship.nmap import process_xml
            print("Starting Nmap XML Import")
            process_xml(
                filename=filename,
                addnoports=form.vars.f_addnoports,
                asset_group=form.vars.f_asset_group,
                engineer=form.vars.f_engineer,
                msf_settings=msf_settings,
                ip_ignore_list=ip_exclude,
                ip_include_list=ip_include,
                update_hosts=form.vars.f_update_hosts,
            )
            response.flash = "Nmap XML upload complete"
            redirect(URL('default', 'index'))

    return dict(form=form)
Exemple #49
0
def send_accounts():
    """Builds a list of username:passwords and sends it to Metasploit"""
    msf_settings = msf_get_config(session)
    response.title = "%s :: Send Kvasir Passwords to Metasploit Pro" % (
        settings.title)

    try:
        from MetasploitProAPI import MetasploitProAPI, MSFProAPIError
    except ImportError as error:
        return dict(error=str(error), alert=True, form=None)

    msf = MetasploitProAPI(host=msf_settings['url'],
                           apikey=msf_settings['key'])
    try:
        msf.login()
    except MSFProAPIError as error:
        return dict(error=str(error), alert=True, form=None)

    form = SQLFORM.factory(
        Field('userpass', 'boolean', default=True,
              label=T('User/Pass Combos')),
        Field('pwdump', 'boolean', default=True, label=T('PWDUMP Hashes')),
    )

    if form.accepts(request, session):
        pass
    elif form.errors:
        reseponse.flash = "Error in your form"
        return dict(form=form, alert=False, error=None)
    else:
        return dict(form=form, alert=False, error=None)
    """
    First build a list of username:passwords from the t_accounts database and
    make a temporary file, then start_import_creds the file

    Second build a pwdump list for LM/NT hashes, make a temporary file, then
    start_import_creds that file!

    Requires MSFPRO and Kvasir be on the same workstation.
    """
    tasks = {}
    import tempfile
    if form.vars.userpass:
        # build username:password file
        rows = db(db.t_accounts.f_compromised == True).select(
            db.t_accounts.f_username,
            db.t_accounts.f_password,
            cache=(cache.ram, 60))
        if rows is not None:
            tmpfile = tempfile.NamedTemporaryFile(delete=False)
            fname = tmpfile.name
            for row in rows:
                tmpfile.write("%s %s\n" % (row.f_username, row.f_password))
            tmpfile.close()
            opts = {
                'workspace': msf_workspace,
                'DS_FTYPE': 'userpass',
                'DS_IMPORT_PATH': fname,
                'DS_NAME': 'Kvasir import %s' % (fname),
                'DS_DESC': 'Kvasir import',
                'DS_REMOVE_FILE': True,
            }
            task = msf.pro_start_import_creds(opts)
            redirect(URL('task_log', args=task.get('id')))
        else:
            response.flash = "No user:pass combos to import"

    if form.vars.pwdump:
        # build pwdump file
        rows = db(db.t_accounts.f_hash1_type == "LM").select(
            db.t_accounts.f_username,
            db.t_accounts.f_uid,
            db.t_accounts.f_hash1,
            db.t_accounts.f_hash2,
            cache=(cache.ram, 60))
        if rows is not None:
            tmpfile = tempfile.NamedTemporaryFile(delete=False)
            fname = tmpfile.name
            for row in rows:
                tmpfile.write(
                    "%s:%s:%s:%s:::\n" %
                    (row.f_username, row.f_uid, row.f_hash1, row.f_hash2))

            tmpfile.close()
            opts = {
                'workspace': msf_workspace,
                'DS_FTYPE': 'pwdump',
                'DS_IMPORT_PATH': fname,
                'DS_NAME': 'Kvasir pwdump import %s' % (fname),
                'DS_DESC': 'Kvasir pwdump import',
                'DS_REMOVE_FILE': True,
            }
            task = msf.pro_start_import_creds(opts)
            redirect(URL('task_log', args=task.get('id')))
        else:
            response.flash = "No pwdump hashes to import"

    return dict(form=form, alert=False, error=None)