Пример #1
0
    def __iter__(self):  # pylint: disable=too-many-branches
        """Iterate over messages in the file"""
        logger.debug("Starting File Read")
        logger.debug("File Position: %d File Counter: %d File Name: %s",
                     self.file_position, self.counter, self.filename)
        cached_mtime = 0
        cached_file_pos = 0
        corruption_check_try = True

        self._open_file()

        found_data = False
        while not self.stop_reading.isSet() or corruption_check_try:  # pylint: disable=too-many-nested-blocks
            os_stat = os.stat(self.filename)
            mtime = os_stat.st_mtime

            if mtime != cached_mtime and os_stat.st_size or corruption_check_try:
                cached_mtime = mtime
                corruption_check_try = False

                while dltlib.dlt_file_read(ctypes.byref(self), self.verbose) >= DLT_RETURN_OK:
                    found_data = True
                    if self.filter and dltlib.dlt_message_filter_check(
                            ctypes.byref(self.msg), self.filter, 0) != DLT_RETURN_TRUE:
                        continue

                    index = self.position
                    msg = self[index]
                    if not index % 100000:
                        self._log_message_progress()
                    yield msg

                if cached_file_pos != self.file_position:
                    # We were able to read messages, don't do a corrupt message check yet.
                    corruption_check_try = True
                    cached_file_pos = self.file_position
                else:
                    next_header_position = self._find_next_header()
                    if next_header_position:
                        if self.file_position == next_header_position:
                            if not self.live_run:
                                logger.warning("Incomplete message while parsing DLT file at %s", self.file_position)
                                break
                        else:
                            logger.warning("Found a corrupt message at %s, skipping it", self.file_position)
                            self.file_position = next_header_position
                            self.corrupt_msg_count += 1
                            corruption_check_try = True
                    # Wait for further messages to determine if corrupt, else just end of file
                    else:
                        if not self.live_run:
                            logger.info("End of file reached at %s", self.file_position)
                            break

            time.sleep(0.1)

        if not found_data:
            raise IOError(DLT_EMPTY_FILE_ERROR)
Пример #2
0
    def compare(self, other=None):  # pylint: disable=too-many-return-statements,too-many-branches
        """Compare messages by given attributes

        :param [DLTMessage|DLTFilter|dict] other: DLTMessage object (or DLTFilter or a dict with selected keys)
            to compare with. Use DLTFilter object with APID,CTID pairs for the best performance.
        :returns: True if all attributes match or False if any of the given attributes differs
        :rtype: bool
        :raises TypeError: if other is neither DLTMessage nor a dictionary

        Example:
        message.compare(other=message2)
        message.compare(message2)
        message.compare(other=dict(apid="AP1", ctid="CT1"))
        message.compare(dict(apid="AP1", ctid="CT1"))
        message.compare(dict(apid=re.compile(r"^A.*"))  # match all messages which apid starting with A
        message.compare(dict(apid="AP1", ctid="CT1", payload_decoded=re.compile(r".connected.*")))
        """
        if hasattr(other, "apid") and hasattr(other, "ctid") and hasattr(other, "payload_decoded"):
            # other is DLTMessage - full compare
            return self.apid == other.apid and self.ctid == other.ctid and self.__eq__(other)

        # pylint: disable=protected-access
        if hasattr(other, "_fields_") and [x[0] for x in other._fields_] == ["apid", "ctid", "counter"]:
            # other id DLTFilter
            return dltlib.dlt_message_filter_check(ctypes.byref(self), ctypes.byref(other), 0)

        if not isinstance(other, dict):
            raise TypeError("other must be instance of mgu_dlt.dlt.DLTMessage, mgu_dlt.dlt.DLTFilter or a dictionary"
                            " found: {}".format(type(other)))

        other = other.copy()
        apid = other.get("apid", None)
        if apid and not isinstance(apid, re._pattern_type) and self.apid != apid:  # pylint: disable=protected-access
            return False

        ctid = other.get("ctid", None)
        if ctid and not isinstance(ctid, re._pattern_type) and self.ctid != ctid:  # pylint: disable=protected-access
            return False

        for key, val in other.items():
            if val is None:
                continue
            key = key.rsplit(".", 1)[-1]  # In case the obsolete "extendedheader.apid" notation is used
            msg_val = getattr(self, key, "")
            if not msg_val:
                return False
            if isinstance(val, re._pattern_type):  # pylint: disable=protected-access
                if not val.search(msg_val):
                    return False
            elif msg_val != val:
                return False
        return True