Beispiel #1
0
    def process_vts(self, vts):
        """ Add single VTs and their parameters. """
        vts_list = []
        vts_params = []
        vtgroups = vts.pop('vt_groups')

        ctx = openvas_db.db_find(nvti.NVTICACHE_STR)
        openvas_db.set_global_redisctx(ctx)
        if vtgroups:
            vts_list = self.get_vts_in_groups(ctx, vtgroups)

        for vtid, vt_params in vts.items():
            vts_list.append(vtid)
            nvt_name = self.vts[vtid].get('name')
            for vt_param_id, vt_param_value in vt_params.items():
                param_type = self.get_vt_param_type(vtid, vt_param_id)
                if vt_param_id == 'timeout':
                    type_aux = 'integer'
                else:
                    type_aux = param_type
                if self.check_param_type(vt_param_value, type_aux):
                    logger.debug(
                        'Expected {} type for parameter value {}'.format(
                            type_aux, str(vt_param_value)))
                param = [
                    "{0}[{1}]:{2}".format(nvt_name, param_type, vt_param_id),
                    str(vt_param_value)
                ]
                vts_params.append(param)
        return vts_list, vts_params
Beispiel #2
0
    def __init__(self, certfile, keyfile, cafile):
        """ Initializes the ospd-openvas daemon's internal data. """

        super(OSPDopenvas, self).__init__(certfile=certfile,
                                          keyfile=keyfile,
                                          cafile=cafile)
        self.server_version = __version__
        self.scanner_info['name'] = 'openvassd'
        self.scanner_info['version'] = ''  # achieved during self.check()
        self.scanner_info['description'] = OSPD_DESC
        for name, param in OSPD_PARAMS.items():
            self.add_scanner_param(name, param)

        if openvas_db.db_init() is False:
            logger.error('OpenVAS Redis Error: Not possible '
                         'to find db_connection.')
            raise Exception

        self.pending_feed = None
        ctx = openvas_db.db_find(nvti.NVTICACHE_STR)
        if not ctx:
            self.redis_nvticache_init()
            ctx = openvas_db.db_find(nvti.NVTICACHE_STR)
        openvas_db.set_global_redisctx(ctx)
        self.load_vts()
Beispiel #3
0
 def scan_is_stopped(self, scan_id):
     """ Check if the parent process has received the stop_scan order.
     @in scan_id: ID to identify the scan to be stopped.
     @return 1 if yes, None in other case.
     """
     ctx = openvas_db.kb_connect(dbnum=MAIN_KBINDEX)
     openvas_db.set_global_redisctx(ctx)
     status = openvas_db.item_get_single(('internal/%s' % scan_id))
     return status == 'stop_all'
Beispiel #4
0
 def stop_scan(global_scan_id):
     """ Set a key in redis to indicate the wrapper is stopped.
     It is done through redis because it is a new multiprocess
     instance and it is not possible to reach the variables
     of the grandchild process. Send SIGUSR2 to openvas to stop
     each running scan."""
     ctx = openvas_db.kb_connect()
     for current_kbi in range(0, openvas_db.MAX_DBINDEX):
         ctx.execute_command('SELECT ' + str(current_kbi))
         openvas_db.set_global_redisctx(ctx)
         scan_id = openvas_db.item_get_single(
             ('internal/%s/globalscanid' % global_scan_id))
         if scan_id:
             openvas_db.item_set_single(('internal/%s' % scan_id), [
                 'stop_all',
             ])
             ovas_pid = openvas_db.item_get_single('internal/ovas_pid')
             parent = psutil.Process(int(ovas_pid))
             openvas_db.release_db(current_kbi)
             parent.send_signal(signal.SIGUSR2)
             logger.debug('Stopping process: {0}'.format(parent))
Beispiel #5
0
    def exec_scan(self, scan_id, target):
        """ Starts the OpenVAS scanner for scan_id scan. """
        if self.pending_feed:
            logger.info('%s: There is a pending feed update. '
                        'The scan can not be started.' % scan_id)
            self.add_scan_error(
                scan_id,
                name='',
                host=target,
                value=('It was not possible to start the scan,'
                       'because a pending feed update. Please try later'))
            return 2

        global MAIN_KBINDEX
        ports = self.get_scan_ports(scan_id, target)
        if not ports:
            self.add_scan_error(scan_id,
                                name='',
                                host=target,
                                value='No port list defined.')
            return 2

        # Get scan options
        options = self.get_scan_options(scan_id)
        prefs_val = []
        ctx = openvas_db.kb_new()
        openvas_db.set_global_redisctx(ctx)
        MAIN_KBINDEX = openvas_db.DB_INDEX

        # To avoid interference between scan process during a parallel scanning
        # new uuid is used internally for each scan.
        openvas_scan_id = str(uuid.uuid4())
        openvas_db.item_add_single(('internal/%s' % openvas_scan_id), [
            'new',
        ])
        openvas_db.item_add_single(('internal/%s/globalscanid' % scan_id), [
            openvas_scan_id,
        ])

        # Set scan preferences
        for item in options.items():
            item_type = ''
            if item[0] in OSPD_PARAMS:
                item_type = OSPD_PARAMS[item[0]].get('type')
            if item_type == 'boolean' and item[1] == 1:
                val = 'yes'
            else:
                val = str(item[1])
            prefs_val.append(item[0] + "|||" + val)
        openvas_db.item_add_single(
            str('internal/%s/scanprefs' % (openvas_scan_id)), prefs_val)

        # Store MAIN_KBINDEX as global preference
        ov_maindbid = ('ov_maindbid|||%d' % MAIN_KBINDEX)
        openvas_db.item_add_single(('internal/%s/scanprefs' % openvas_scan_id),
                                   [
                                       ov_maindbid,
                                   ])

        # Set target
        target_aux = ('TARGET|||%s' % target)
        openvas_db.item_add_single(('internal/%s/scanprefs' % openvas_scan_id),
                                   [
                                       target_aux,
                                   ])
        # Set port range
        port_range = ('port_range|||%s' % ports)
        openvas_db.item_add_single(('internal/%s/scanprefs' % openvas_scan_id),
                                   [
                                       port_range,
                                   ])

        # Set credentials
        credentials = self.get_scan_credentials(scan_id, target)
        if credentials:
            cred_prefs = self.build_credentials_as_prefs(credentials)
            openvas_db.item_add_single(
                str('internal/%s/scanprefs' % openvas_scan_id), cred_prefs)

        # Set plugins to run
        nvts = self.get_scan_vts(scan_id)
        if nvts != '':
            nvts_list, nvts_params = self.process_vts(nvts)
            # Select the scan KB again.
            ctx.execute_command('SELECT ' + str(MAIN_KBINDEX))
            openvas_db.set_global_redisctx(ctx)
            # Add nvts list
            separ = ';'
            plugin_list = ('plugin_set|||%s' % separ.join(nvts_list))
            openvas_db.item_add_single(
                ('internal/%s/scanprefs' % openvas_scan_id), [
                    plugin_list,
                ])
            # Add nvts parameters
            for elem in nvts_params:
                item = ('%s|||%s' % (elem[0], elem[1]))
                openvas_db.item_add_single(
                    ('internal/%s/scanprefs' % openvas_scan_id), [
                        item,
                    ])
        else:
            openvas_db.release_db(MAIN_KBINDEX)
            self.add_scan_error(scan_id,
                                name='',
                                host=target,
                                value='No VTS to run.')
            return 2

        # Create a general log entry about executing OpenVAS
        # It is important to send at least one result, otherwise
        # the host details won't be stored.
        self.add_scan_log(scan_id,
                          host=target,
                          name='OpenVAS summary',
                          value='An OpenVAS Scanner was started for %s.' %
                          target)

        self.add_scan_log(scan_id,
                          host=target,
                          name='KB location Found',
                          value='KB location path was found: %s.' %
                          openvas_db.DB_ADDRESS)

        self.add_scan_log(scan_id,
                          host=target,
                          name='Feed Update',
                          value='Feed version: %s.' % nvti.get_feed_version())

        cmd = ['openvassd', '--scan-start', openvas_scan_id]
        try:
            result = subprocess.Popen(cmd, shell=False)
        except OSError:
            # the command is not available
            return False

        ovas_pid = result.pid
        logger.debug('pid = {0}'.format(ovas_pid))
        openvas_db.item_add_single(('internal/ovas_pid'), [
            ovas_pid,
        ])

        # Wait until the scanner starts and loads all the preferences.
        while openvas_db.item_get_single('internal/' +
                                         openvas_scan_id) == 'new':
            time.sleep(1)

        no_id_found = False
        while True:
            time.sleep(3)

            # Check if the client stopped the whole scan
            if self.scan_is_stopped(openvas_scan_id):
                return 1

            ctx = openvas_db.kb_connect(MAIN_KBINDEX)
            openvas_db.set_global_redisctx(ctx)
            dbs = openvas_db.item_get_set('internal/dbindex')
            for i in list(dbs):
                if i == MAIN_KBINDEX:
                    continue
                ctx.execute_command('SELECT ' + str(i))
                openvas_db.set_global_redisctx(ctx)
                id_aux = ctx.execute_command('srandmember internal/scan_id')
                if not id_aux:
                    continue
                if id_aux == openvas_scan_id:
                    no_id_found = False
                    self.get_openvas_timestamp_scan_host(scan_id, target)
                    self.get_openvas_result(scan_id)
                    self.get_openvas_status(scan_id, target)
                    if self.scan_is_finished(openvas_scan_id):
                        ctx.execute_command('SELECT ' + str(MAIN_KBINDEX))
                        openvas_db.remove_set_member('internal/dbindex', i)
                        openvas_db.release_db(i)

            # Scan end. No kb in use for this scan id
            if no_id_found:
                break
            no_id_found = True

        # Delete keys from KB related to this scan task.
        openvas_db.release_db(MAIN_KBINDEX)
        return 1