Testing Round Trip USB Serial Latency using Python

Originally posted February 26, 2019.

One important consideration when using a 1000 Hz USB Serial device interface is the delay from when a Serial message is sent to the device to the time when the Serial reply is received by the program. We call this the round trip, or end to end, USB Serial latency of the device.

Here is a simple Python script that tests the round trip USB Serial latency of the first detected MilliKey or USB2TTL8 device.

This example uses a fixed Serial port address that needs to be manually changed to the correct Serial port of the device being tested. For an example of how to programmatically detect your LabHackers’ device serial port from within Python checkout this post.

#!/usr/bin/env python
# -*- coding: utf-8 -*-
from __future__ import division, print_function

import serial
import numpy
from timeit import default_timer as getTime

SERIAL_PORT = 'COM138'
ITERATION_COUNT = 10000

try:
    sconn = serial.Serial(SERIAL_PORT, baudrate=128000, timeout=0.1)
except serial.SerialException as e:
    print("Check SERIAL_PORT variable is correct for device being tested.")
    raise e
    
#clear anything in serial rx
while sconn.readline():
    pass

# Test time it takes to send a serial message to the labhackers device
# and receive the serial reply.
results = numpy.zeros(ITERATION_COUNT, dtype=numpy.float64)
for i in range(ITERATION_COUNT):
    tx_time = getTime()
    sconn.write(b"PING\n")
    r = sconn.readline()
    rx_time = getTime()
    if r:
        results[i] = rx_time-tx_time
    else:
        raise RuntimeError("Serial RX Timeout.")

sconn.close()

# Convert times to msec.
results = results * 1000.0

print("LabHackers' USB Serial Rx - Tx Latency Stats")
print("\tCount: {}".format(results.shape))
print("\tAverage: {:.3f} msec".format(results.mean()))
print("\tMedian: {:.3f} msec".format(numpy.median(results)))
print("\tMin: {:.3f} msec".format(results.min()))
print("\tMax: {:.3f} msec".format(results.max()))
print("\tStdev: {:.3f} msec".format(results.std()))

Here is the output from the script when run on Windows, Linux and macOS, showing that the average round trip USB serial delay of a LabHackers’ device is well under 1 msec on all operating systems.

Windows 10

Run using PsychoPy 3.0.5 Coder IDE

LabHackers' USB Serial Rx - Tx Latency Stats
    Count: (10000,)
    Average: 0.391 msec
    Median: 0.379 msec
    Min: 0.352 msec
    Max: 1.840 msec
    Stdev: 0.055 msec

Linux (Mint 18.3)

LabHackers' USB Serial Rx - Tx Latency Stats
	Count: (10000,)
	Average: 0.320 msec
	Median: 0.313 msec
	Min: 0.253 msec
	Max: 0.583 msec
	Stdev: 0.026 msec
	

macOS 10.13.6

Run using PsychoPy 3.0.5 Coder IDE

LabHackers’ USB Serial Rx – Tx Latency Stats
Count: (10000,)
Average: 0.708 msec
Median: 0.719 msec
Min: 0.559 msec
Max: 1.501 msec
Stdev: 0.059 msec

Happy Hacking!