Example #1
0
    def event_history(self, columns, *, sieve=None, repres=None, quiet=None):
        if columns:
            table_data = [[COLUMN_NAMES[name] for name in columns]]
        else:
            columns = [key for key in COLUMN_NAMES.keys()]
            table_data = [[val for val in COLUMN_NAMES.values()]]

        self._events_to_show = _filter_events(self._all_events, sieve)
        if not self._events_to_show:
            print_info('No USB events found!')
            return

        if not quiet:
            try:
                number, filename = _output_choice('event history',
                                                  'history.json', 'history/')
            except USBRipError as e:
                print_critical(str(e), initial_error=e.errors['initial_error'])
                return

            if number == '1':
                _json_dump(self._events_to_show, 'event history', filename)
                return

        _represent_events(self._events_to_show, columns, table_data,
                          'USB-History-Events', repres)
Example #2
0
    def generate_auth_json(self, output_auth):
        try:
            os_makedirs(os.path.dirname(output_auth))
        except USBRipError as e:
            print_critical(str(e), initial_error=e.errors['initial_error'])
            return

        try:
            auth_json = open(output_auth, 'w')
        except PermissionError as e:
            print_critical('Permission denied: \'{}\''.format(output_auth),
                           initial_error=str(e))
            return

        print_info('Generating authorized device list (JSON)')

        auth = defaultdict(list)
        for event in self._all_events:
            for key, val in event.items():
                if key in ('vid', 'pid', 'prod', 'manufact', 'serial') and \
                               val is not None                                     and \
                               val not in auth[key]:
                    auth[key].append(val)

        for key in auth.keys():
            auth[key].sort()

        json.dump(auth, auth_json, sort_keys=True, indent=4)
        auth_json.close()

        print_info('New authorized device list: \'{}\''.format(output_auth))
Example #3
0
	def search_ids(vid, pid, *, offline=True):
		if offline:
			print_warning('Offline mode')

		try:
			usb_ids = USBIDs.prepare_database(offline=offline)
		except USBRipError as e:
			print_critical(str(e), errcode=e.errors['errcode'], initial_error=e.errors['initial_error'])
		else:
			_search_ids_helper(usb_ids, vid, pid)
			usb_ids.close()
Example #4
0
def _output_choice(list_name, default_filename, dirname):
    while True:
        print('[?] How would you like your {} list to be generated?\n'.format(
            list_name))

        print('    1. JSON-file')
        print('    2. Terminal stdout')

        number = input('\n[>] Please enter the number of your choice: ')

        if number == '1':
            while True:
                filename = input('[>] Please enter the base name for the output file ' \
                                             '(default is \'{}\'): '.format(default_filename))

                if all(c in printable
                       for c in filename) and len(filename) < 256:
                    if not filename:
                        filename = default_filename
                    elif filename[-5:] != '.json':
                        filename = filename + '.json'

                    filename = root_dir_join(dirname + filename)

                    try:
                        dirname = os.path.dirname(filename)
                        os_makedirs(dirname)
                    except USBRipError as e:
                        print_critical(str(e),
                                       initial_error=e.errors['initial_error'])
                        return (None, '')
                    else:
                        print_info('Created \'{}\''.format(dirname))

                    overwrite = True
                    if os.path.exists(filename):
                        while True:
                            overwrite = input(
                                '[?] File exists. Would you like to overwrite it? [Y/n]: '
                            )
                            if len(overwrite) == 1 and overwrite in 'Yy':
                                overwrite = True
                                break
                            elif len(overwrite) == 1 and overwrite in 'Nn':
                                overwrite = False
                                break

                    if overwrite:
                        return (int(number), filename)

        elif number == '2':
            return (int(number), '')
Example #5
0
    def search_violations(self,
                          input_auth,
                          columns,
                          *,
                          sieve=None,
                          repres=None):
        try:
            auth = _process_auth_json(input_auth)
        except json.decoder.JSONDecodeError as e:
            print_critical('Failed to decode authorized device list (JSON)',
                           initial_error=str(e))
            return

        if columns:
            table_data = [[COLUMN_NAMES[name] for name in columns]]
        else:
            columns = [key for key in COLUMN_NAMES.keys()]
            table_data = [[val for val in COLUMN_NAMES.values()]]

        print_info('Searching for violations', quiet=USBEvents.QUIET)

        for event in self._all_events:
            try:
                if any(event[key] not in vals and event[key] is not None
                       for key, vals in auth.items()):
                    self._violations.append(event)
            except KeyError as e:
                print_critical(
                    'Invalid structure of authorized device list (JSON)',
                    initial_error=str(e))
                return

        self._events_to_show = _filter_events(self._violations, sieve)
        if not self._events_to_show:
            print_info('No USB violation events found!', quiet=USBEvents.QUIET)
            json.dump([], auth_json)
            auth_json.close()
            return

        if not USBEvents.QUIET and ISATTY:
            number, filename = _output_choice('violation', 'viol.json',
                                              'violations/')
            if number is None:
                return
            elif number == 1:
                _json_dump(self._events_to_show, 'violation', filename)
                return

        _represent_events(self._events_to_show, columns, table_data,
                          'USB-Violation-Events', repres)
Example #6
0
    def __init__(self, files=None):
        if files:
            raw_history = DefaultOrderedDict(list)
            for file in files:
                raw_history.update(_read_log_file(file))
        else:
            try:
                raw_history = _get_raw_history()
            except USBRipError as e:
                print_critical(str(e))

        divided_history = _divide_history(raw_history)

        self._all_events = _parse_history(divided_history)
        self._violations, self._events_to_show = [], None
Example #7
0
def _update_database(filename):
    try:
        usb_ids = open(filename, 'r+')
    except PermissionError as e:
        print_critical('Permission denied: \'{}\''.format(filename),
                       initial_error=str(e))
        return

    curr_ver, curr_date = _get_current_version(usb_ids)

    print_info('Getting current database version')
    print('Version:  {}'.format(curr_ver))
    print('Date:     {}'.format(curr_date))

    print_info('Checking local database for update')
    db, latest_ver, latest_date, error, e = _get_latest_version()

    if error:
        if error == USBIDs._INTERNET_CONNECTION_ERROR:
            print_warning('No internet connection, using current version',
                          errcode=error)
        elif error == USBIDs._SERVER_TIMEOUT_ERROR:
            print_warning('Server timeout, using current version',
                          errcode=error,
                          initial_error=e)
        elif error == USBIDs._SERVER_CONTENT_ERROR:
            print_warning('Server error, using current version',
                          errcode=error,
                          initial_error=e)
        return usb_ids

    if curr_ver != latest_ver and curr_date != latest_date:  # if there's newer database version
        print('Updating database... ', end='')

        usb_ids.write(db)
        usb_ids.seek(0)
        usb_ids.truncate()

        print('Done\n')

        print('Version:  {}'.format(latest_ver))
        print('Date:     {}'.format(latest_date))

    print_info('Local database is up-to-date')

    return usb_ids
Example #8
0
def _download_database(filename):
    try:
        os_makedirs(os.path.dirname(filename))
    except USBRipError as e:
        print_critical(str(e), initial_error=e.errors['initial_error'])
        return

    try:
        usb_ids = open(filename, 'w+')
    except PermissionError as e:
        print_critical('Permission denied: \'{}\''.format(filename),
                       initial_error=str(e))
        return

    db, latest_ver, latest_date, error, e = _get_latest_version()

    if error:
        usb_ids.close()
        os.remove(filename)
        if error == USBIDs._INTERNET_CONNECTION_ERROR:
            raise USBRipError('No internet connection')
        elif error == USBIDs._SERVER_TIMEOUT_ERROR:
            raise USBRipError('Server timeout',
                              errors={
                                  'errcode': error,
                                  'initial_error': e
                              })
        elif error == USBIDs._SERVER_CONTENT_ERROR:
            raise USBRipError('Server content error: no version or date found',
                              errors={
                                  'errcode': error,
                                  'initial_error': e
                              })

    usb_ids.write(db)
    usb_ids.seek(0)

    print_info('Database downloaded')

    print('Version:  {}'.format(latest_ver))
    print('Date:     {}'.format(latest_date))

    return usb_ids
Example #9
0
def _json_dump(events_to_show, list_name, filename):
    print_info('Generating {} list (JSON)'.format(list_name))

    out = OrderedDict()
    for event in events_to_show:
        out[event['conn']] = OrderedDict()
        for key, val in sorted(event.items()):
            if key != 'conn':
                out[event['conn']][key] = val

    try:
        with open(filename, 'w') as out_json:
            json.dump(out, out_json, indent=4)
    except PermissionError as e:
        print_critical('Permission denied: \'{}\''.format(filename),
                       initial_error=str(e))
        return

    print_info('New {} list: \'{}\''.format(list_name, filename))
Example #10
0
    def generate_auth_json(self, output_auth, *, sieve=None):
        try:
            dirname = os.path.dirname(filename)
            os_makedirs(dirname)
        except USBRipError as e:
            print_critical(str(e), initial_error=e.errors['initial_error'])
            return
        else:
            print_info('Created \'{}\''.format(dirname))

        try:
            auth_json = open(output_auth, 'w')
        except PermissionError as e:
            print_critical('Permission denied: \'{}\''.format(output_auth),
                           initial_error=str(e))
            return

        self._events_to_show = _filter_events(self._all_events, sieve)
        if not self._events_to_show:
            print_info('No USB violation events found!', quiet=USBEvents.QUIET)
            json.dump([], auth_json)
            auth_json.close()
            return

        print_info('Generating authorized device list (JSON)',
                   quiet=USBEvents.QUIET)

        auth = defaultdict(list)
        for event in self._events_to_show:
            for key, val in event.items():
                if key in ('vid', 'pid', 'prod', 'manufact', 'serial') and \
                               val is not None                                     and \
                               val not in auth[key]:
                    auth[key].append(val)

        for key in auth.keys():
            auth[key].sort()

        json.dump(auth, auth_json, sort_keys=True, indent=4)
        auth_json.close()

        print_info('New authorized device list: \'{}\''.format(output_auth),
                   quiet=USBEvents.QUIET)
Example #11
0
    def search_violations(self,
                          input_auth,
                          *,
                          sieve=None,
                          repres=None,
                          quiet=None):
        try:
            auth = _process_auth_json(input_auth)
        except json.decoder.JSONDecodeError as e:
            print_critical('Failed to decode authorized device list (JSON)',
                           initial_error=str(e))
            return

        print_info('Searching for violations')

        for event in self._all_events:
            try:
                if any(event[key] not in vals and event[key] is not None
                       for key, vals in auth.items()):
                    self._violations.append(event)
            except KeyError as e:
                print_critical(
                    'Invalid structure of authorized device list (JSON)',
                    initial_error=str(e))
                return

        columns = [key for key in COLUMN_NAMES.keys()]
        table_data = [[val for val in COLUMN_NAMES.values()]]

        self._events_to_show = _filter_events(self._violations, sieve)
        if not self._events_to_show:
            print_info('No USB violation events found!')
            return

        if not quiet:
            try:
                number, filename = _output_choice('violation', 'viol.json',
                                                  'violations/')
            except USBRipError as e:
                print_critical(str(e), initial_error=e.errors['initial_error'])
                return

            if number == '1':
                _json_dump(self._events_to_show, 'violation', filename)
                return

        _represent_events(self._events_to_show, columns, table_data,
                          'USB-Violation-Events', repres)
Example #12
0
def main():
    if not len(sys.argv) > 1:
        print(BANNER + '\n')
        usbrip_error('No arguments were passed')

    parser = cmd_line_options()
    args = parser.parse_args()

    if 'quiet' in args and not args.quiet:
        print(BANNER + '\n')

    # ----------------------------------------------------------
    # ------------------------- Banner -------------------------
    # ----------------------------------------------------------

    if args.subparser == 'banner':
        print(BANNER)

    # ----------------------------------------------------------
    # ----------------------- USB Events -----------------------
    # ----------------------------------------------------------

    elif args.subparser == 'events' and args.ue_subparser:
        if 'columns' in args and args.columns:
            for name in args.columns:
                if name not in COLUMN_NAMES.keys():
                    usbrip_error(name + ': Invalid column name')

        if 'date' in args and args.date:
            re_date = re.compile(
                r'^(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec) [\s1-3][0-9]$'
            )
            for date in args.date:
                if not re_date.search(date):
                    usbrip_error(date + ': Wrong date format')

        if 'file' in args and args.file:
            for file in args.file:
                if not os.path.exists(file):
                    usbrip_error(file + ': Path does not exist')

        sieve = dict(
            zip(('external', 'number', 'date'),
                (args.external, args.number, args.date)))
        repres = dict.fromkeys(('table', 'list', 'smart'), False)

        if 'table' in args and args.table:
            repres['table'] = True
        elif 'list' in args and args.list:
            repres['list'] = True
        else:
            repres['smart'] = True

        # ------------------- USB Events History -------------------

        if args.ue_subparser == 'history':
            ueh = USBEvents(args.file, quiet=args.quiet)
            ueh.event_history(args.columns, sieve=sieve, repres=repres)

        # ---------------- USB Events Gen Auth JSON ----------------

        elif args.ue_subparser == 'gen_auth':
            if os.path.exists(args.output):
                usbrip_error(args.output + ': Path already exists')

            ueg = USBEvents(args.file, quiet=args.quiet)
            ueg.generate_auth_json(args.output, sieve=sieve)

        # ----------------- USB Events Violations ------------------

        elif args.ue_subparser == 'violations':
            if not os.path.exists(args.input):
                usbrip_error(args.input + ': Path does not exist')

            uev = USBEvents(args.file, quiet=args.quiet)
            uev.search_violations(args.input,
                                  args.columns,
                                  sieve=sieve,
                                  repres=repres)

    # ----------------------------------------------------------
    # ------------------------ USB IDs -------------------------
    # ----------------------------------------------------------

    elif args.subparser == 'ids' and args.ui_subparser:
        ui = USBIDs(quiet=args.quiet)

        # --------------------- USB IDs Search ---------------------

        if args.ui_subparser == 'search':
            if not args.vid and not args.pid:
                usbrip_error(
                    'At least one of --vid/--pid or --download option should be specified'
                )

            ui.search_ids(args.vid, args.pid, offline=args.offline)

        # -------------------- USB IDs Download --------------------

        elif args.ui_subparser == 'download':
            try:
                usb_ids = ui.prepare_database(offline=False)
            except USBRipError as e:
                print_critical(str(e),
                               errcode=e.errors['errcode'],
                               initial_error=e.error['initial_error'])
            else:
                usb_ids.close()

    else:
        subparser = ' ' + args.subparser + ' '
        usbrip_error('Choose one of the usbrip {} actions'.format(
            args.subparser),
                     subparser=subparser)