Evaluated Uno Q Router / Bridge Latency with MAX31855

I recently posted a arduino-app-lab project to github that when installed will provide a python script to measure the latency of the Arduino router / bridge that is in place.

https://github.com/majones-services/arduino-uno-q-MAX31855
There is likely a more precise way to evaluate hardware latency but in the end, we're all interested in how long it takes for a python call on the debian instance to get data back from the MCU. Here is the data that I'm seeing:

Running RAW Latency Test
Performing 10 test calls...

Raw Latency Results
Min Latency: 6.72 ms
Max Latency: 7.84 ms
Avg Latency: 7.04 ms

Running Temperature Latency Test
Performing 10 test calls to get_temp1
Execution 1: Latency: 8.87 ms, Temp: 22.00 °C
Execution 2: Latency: 7.78 ms, Temp: 22.00 °C
Execution 3: Latency: 7.91 ms, Temp: 22.00 °C
Execution 4: Latency: 7.31 ms, Temp: 22.00 °C
Execution 5: Latency: 8.21 ms, Temp: 22.00 °C
Execution 6: Latency: 7.76 ms, Temp: 22.00 °C
Execution 7: Latency: 8.10 ms, Temp: 22.00 °C
Execution 8: Latency: 7.54 ms, Temp: 22.00 °C
Execution 9: Latency: 7.65 ms, Temp: 22.00 °C
Execution 10: Latency: 8.20 ms, Temp: 22.00 °C

Temp Latency Results

Min Latency: 7.31 ms
Max Latency: 8.87 ms
Avg Latency: 7.93 ms

App is starting
2026-01-07 16:58:10.387 INFO - [MainThread] App: App started
Requesting temperatures
THERMO1: 22.00 °C
THERMO2: 22.75 °C
THERMO3: 22.50 °C

Requesting temperatures
THERMO1: 22.00 °C
THERMO2: 22.75 °C
THERMO3: 22.50 °C

Summary:

For design purposes, python should not attempt calls to the router/bridge faster than every 7.84 ms. In my case, I also included a thermocouple in the testing to determine how fast can I call a function on the MCU that is "provided" to the bridge. I concluded that I could collect data at max: 122 hz. However, MAX31855 updates it's register every 100 ms or 10hz so, I can poll the device at 122 hz but the returned will be the last stored value until it's updated (10Hz).

Could you please test how much data can you send each call? This is very interesting. If using String for example. And how much latency degrading with bigger chunks of data

Hummm..... I have been thinking that I I had, say, 15 devices all connected to the Q, I really don't want the MCU constantly looping and collecting data (unless it specially needed for control). Additionally, running 15 separate Bridge.Call commands seems to be expensive vs. on the the MCU, collect all the data and return an array or equivalent. I'd need to know about the "size" of the array. Maybe. Right now, I'll make 15 sperate calls, based on my overall python design.

@extender777 - @KurtE

Was testing latency with different string lengths from the MCU→MPU using a hacked up version of the initial latency sketch with and without the serial hack: Performance of Interprocessor communication - UNO Family / UNO Q - Arduino Forum

Results - no speed hack

--- Running RAW Latency Test 10 chars ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 6.72 ms
Max Latency: 11.94 ms
Avg Latency: 8.20 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 6.53 ms
Max Latency: 8.31 ms
Avg Latency: 7.74 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 7.51 ms
Max Latency: 8.41 ms
Avg Latency: 7.99 ms

String len = 80

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 13.71 ms
Max Latency: 16.39 ms
Avg Latency: 14.50 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 14.25 ms
Max Latency: 14.81 ms
Avg Latency: 14.51 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 13.68 ms
Max Latency: 14.92 ms
Avg Latency: 14.31 ms

String len = 160

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 20.13 ms
Max Latency: 23.91 ms
Avg Latency: 21.55 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 21.04 ms
Max Latency: 22.72 ms
Avg Latency: 21.66 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 20.49 ms
Max Latency: 22.05 ms
Avg Latency: 21.44 ms

With speed hack setting serial to 460800

---------------- none ----------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 3.67 ms
Max Latency: 5.02 ms
Avg Latency: 4.45 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 3.73 ms
Max Latency: 5.12 ms
Avg Latency: 4.61 ms

--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 4.39 ms
Max Latency: 5.31 ms
Avg Latency: 4.75 ms

---- 10 ======================
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 4.44 ms
Max Latency: 4.96 ms
Avg Latency: 4.68 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 4.05 ms
Max Latency: 5.15 ms
Avg Latency: 4.67 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 4.13 ms
Max Latency: 5.09 ms
Avg Latency: 4.66 ms
----------------------------

---- 160 ------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 7.94 ms
Max Latency: 10.84 ms
Avg Latency: 8.69 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 7.73 ms
Max Latency: 9.21 ms
Avg Latency: 8.28 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 7.33 ms
Max Latency: 8.95 ms
Avg Latency: 8.05 ms
----------------------------

Quite a bit of improvement but…

Very Good. Thank you. So, let me sum to make sure I've got it right: Speed hack improves the performance of small strings, performance falls off as the string size increases., still a 2-3X improvement over the lower baud rate.

Thanks @Merlin513,

Another simple question, what is the highest BAUD rate that we can use?
I have not found any documentation yet on that, except N times some
input clock speed.

Several years ago - I made some RPI shields or the like with a Teensy processor
on it. I had one with T3.2 later 3.6 later 4.1, and I had communications
setup between the two boards. In my case I had it setup for either USB (it plugged into one of the USB ports), or over a Serial port. I believe at that time we may
have been able to drive the Serial port at maybe 2mhz, or maybe higher?

Going through that video 460800 is the max - haven’t verified it myself. Possible limitation right now of zephyr implementation - just a wild guess.

Another thing that is many times overlooked is packet size. I checked into that and found this: packet size is negotiated on the internet, particularly during the TCP handshake process where devices agree on the Maximum Segment Size (MSS). This ensures that packets sent between devices do not exceed the Maximum Transmission Unit (MTU) of the network, preventing fragmentation.

This link may prove interesting: https://www.cloudflare.com/learning/network-layer/what-is-mtu/

Just did another wacky test this time sending a packet to the MCU and then requesting a string of floats - size 787 string lent back to the MPU:

----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 90.77 ms
Max Latency: 92.05 ms
Avg Latency: 91.26 ms
----------------------------
Loop Time for 10 iterations:
1016.3381090001167
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 88.20 ms
Max Latency: 92.47 ms
Avg Latency: 91.08 ms
----------------------------
Loop Time for 10 iterations:
1014.3064060000597
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 89.94 ms
Max Latency: 91.10 ms
Avg Latency: 90.67 ms
----------------------------
Loop Time for 10 iterations:
1010.7626090000394
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 90.27 ms
Max Latency: 91.83 ms
Avg Latency: 90.93 ms
----------------------------
Loop Time for 10 iterations:
1012.2899899999993
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 90.51 ms
Max Latency: 92.62 ms
Avg Latency: 91.34 ms
----------------------------
Loop Time for 10 iterations:
1016.3942629999383
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 89.14 ms
Max Latency: 92.55 ms
Avg Latency: 90.87 ms
----------------------------

Just another data point

Inspired by what @KurtE did for the weather2 app I changed from sending a string to the MPU and decided to use vector to send 90 floats to the MPU. Doing this the latency dropped by almost half as compared to sending the string equivalent:

----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 47.59 ms
Max Latency: 50.47 ms
Avg Latency: 49.41 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 48.71 ms
Max Latency: 50.50 ms
Avg Latency: 49.70 ms
----------------------------
--- Running RAW Latency Test ---
Performing 10 test calls...
--- Raw Latency Results ---
Min Latency: 48.76 ms
Max Latency: 49.90 ms
Avg Latency: 49.45 ms
----------------------------

Changing array to 180 to simulate 180 1deg measurements from a ping sensor

--- Raw Latency Results ---
Min Latency: 88.32 ms
Max Latency: 92.05 ms
Avg Latency: 90.39 ms

still less time

Good Work! I am new to Arduino AND I'm impressed with this group of imaginative people! Thank you for the details

Hi @Merlin513 could you please share your App here for reference please. Thanks.

No problem here is copy of the app:
test.zip (2.6 KB)

Also take a look at @KurtE's weather2 app ( Arduino_UNO_Q/ArduinoApps/weather2 at main · KurtE/Arduino_UNO_Q ) to see how he is getting array (list) data from the MPU to the MCU.

Thanks a bunch @Merlin513.

Can't get it running.

--- Running RAW Latency Test ---
[main]   Performing 10 test calls...
[main]   Error during ping execution 1: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 2: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 3: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 4: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 5: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 6: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 7: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 8: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 9: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Error during ping execution 10: Request 'get_distance_m' failed: method get_distance_m not available (2)
[main]   Raw Latency test failed: No successful pings.
[main] ----------------------------

Which zephyr are you on? 0.53 was broken with exactly those messages.

Sorry for the late response.

I have been using Core 0.53.1 - the latest release. Also I noticed if for some reason I get those error messages if I power cycle the board it clears what ever is causing them

With that said using 0.53.1 seems to have resolved alot of the issues.

I recall that the UNO R3 hardware Serial works best if the baud rate was a divider of the crystal clock . oscillator, Done a project where 500.000 and 1.000.000 was used.

So I would definitely try 1.000.000.

I know Serial (to me logically Serial1) I could run at 1mhz on the Q driving servos. However the one between the two processors is an LPUART (different subsystem) guessing it can go that high as well.

However back when I was playing with RPI and Teensy connected 3.x/4.x connected, I found that the Teensy could easily Serial could go fast like 2 or 3Mbs maybe 6... But Python Serial could not... Maybe it has improved since then. Also it was mentioned that for higher
speeds maybe it requires flow control to be enabled.

I am on 0.52.0