diff --git a/doc/source/index.rst b/doc/source/index.rst index e605906..a259e2b 100755 --- a/doc/source/index.rst +++ b/doc/source/index.rst @@ -47,4 +47,5 @@ On top of that, some improvement makes v2.x preferable over v1.x - Sending data with a generator is now possible, accommodating use cases with large payloads - The module is fully type-hinted - It is possible to use a busy-wait to achieve even more precise timings. See the :ref:`wait_func parameter` + - Performances on Windows are greatly improved by the usage of ``time.perf_counter`` instead of ``time.monotonic``. See `issue #113 `_ diff --git a/isotp/protocol.py b/isotp/protocol.py index f197fe7..535436a 100755 --- a/isotp/protocol.py +++ b/isotp/protocol.py @@ -259,7 +259,7 @@ def update(self) -> None: self.reset() return - t = time.monotonic() + t = time.perf_counter() while len(self.burst_time) > 0: t2 = self.burst_time[0] @@ -283,7 +283,7 @@ def allowed_bytes(self) -> int: def inform_byte_sent(self, datalen: int) -> None: if self.enabled: bytelen = datalen * 8 - t = time.monotonic() + t = time.perf_counter() self.bit_total += bytelen if len(self.burst_time) == 0: self.burst_time.append(t) @@ -689,7 +689,7 @@ def load_params(self) -> None: def send(self, data: Union[bytes, bytearray, SendGenerator], target_address_type: Optional[Union[isotp.address.TargetAddressType, int]] = None, - send_timeout: float = 0): + send_timeout: Optional[float] = None): """ Enqueue an IsoTP frame to be sent over CAN network. When performing a blocking send, this method returns only when the transmission is complete or raise an exception when a failure or a timeout occurs. @@ -704,7 +704,7 @@ def send(self, :type target_address_type: int :param send_timeout: Timeout value for blocking send. Unused if :ref:`blocking_send` is ``False`` - :type send_timeout: float + :type send_timeout: float or None :raises ValueError: Given data is not a bytearray, a tuple (generator,size) or the size is too big :raises RuntimeError: Transmit queue is full @@ -1583,9 +1583,9 @@ def _relay_thread_fn(self) -> None: self.events.relay_thread_ready.set() while not self.events.stop_requested.is_set(): rx_timeout = 0.0 if self.is_tx_throttled() else self.default_read_timeout - t1 = time.monotonic() + t1 = time.perf_counter() data = self.user_rxfn(rx_timeout) - diff = time.monotonic() - t1 + diff = time.perf_counter() - t1 if data is not None: self.rx_relay_queue.put(data) else: # No data received. Sleep if user is not blocking diff --git a/isotp/tools.py b/isotp/tools.py index 0e48173..33f4a89 100644 --- a/isotp/tools.py +++ b/isotp/tools.py @@ -20,20 +20,20 @@ def set_timeout(self, timeout: float) -> None: def start(self, timeout=None) -> None: if timeout is not None: self.set_timeout(timeout) - self.start_time = time.monotonic_ns() + self.start_time = time.perf_counter_ns() def stop(self) -> None: self.start_time = None def elapsed(self) -> float: if self.start_time is not None: - return float(time.monotonic_ns() - self.start_time) / 1.0e9 + return float(time.perf_counter_ns() - self.start_time) / 1.0e9 else: return 0 def elapsed_ns(self) -> int: if self.start_time is not None: - return time.monotonic_ns() - self.start_time + return time.perf_counter_ns() - self.start_time else: return 0