mattyt wrote: ↑Thu Jan 09, 2020 1:33 am
Huh, that's interesting; I tested RMT into the 10s of MHz range and it appeared
very accurate (two decimal points of precision in the oscilloscope I was using). Bit surprising that you observed such a discrepancy. Was the base frequency accurate with just a high-frequency glitch?
First, RMT is perfectly accurate when we use it as it has been designed.
In my use case, it's a
hack of RMT to be able to generate a specific number of steps at a specific frequency. On top of that I try to synchronize many output to drive any type of
MultiAxis device.
The following tests have been done in
repl on an ESP32 with MicroPython V1.12
esp32-idf3-20191220-v1.12.bin.
Code: Select all
# Test 1
from machine import Pin
from esp32 import RMT
ch1 = RMT(0, pin=Pin(2), clock_div=255)
ch1_wp = ch1.write_pulses
ch1_frame = (32767, 32767) * 3
ch2 = RMT(1, pin=Pin(4), clock_div=255)
ch2_wp = ch2.write_pulses
ch2_frame = (32767, 32767)
steps = range(1000000)
for _ in steps:
ch1_wp(ch1_frame)
ch2_wp(ch2_frame)
ch1: red and
ch2: yellow.
Test 1, expected frequency on
ch1 4.787 Hz, measure: 4.786 Hz
. 3 pulses on
ch1 and 1 pulse on
ch2.
ch1 and
ch2 are synchronized.
250ms per div.
A small delay of 35µs exist between
ch1 and
ch2.
10µs per div.
At 25ms per div, very difficult to see this delay.
Code: Select all
# Test 2
from machine import Pin
from esp32 import RMT
ch1 = RMT(0, pin=Pin(2), clock_div=255)
ch1_wp = ch1.write_pulses
ch1_frame = (1000, 1000) * 3
ch2 = RMT(1, pin=Pin(4), clock_div=255)
ch2_wp = ch2.write_pulses
ch2_frame = (1000, 1000)
steps = range(1000000)
for _ in steps:
ch1_wp(ch1_frame)
ch2_wp(ch2_frame)
Test 2, expected frequency on
ch1 156.86 Hz, measure: 156.9 Hz
.
5ms per div.
Same delay of 35µs exist between
ch1 and
ch2.
10µs per div.
Code: Select all
# Test 3
from machine import Pin
from esp32 import RMT
ch1 = RMT(0, pin=Pin(2), clock_div=255)
ch1_wp = ch1.write_pulses
ch1_frame = (100, 100) * 3
ch2 = RMT(1, pin=Pin(4), clock_div=255)
ch2_wp = ch2.write_pulses
ch2_frame = (100, 100)
steps = range(1000000)
for _ in steps:
ch1_wp(ch1_frame)
ch2_wp(ch2_frame)
Test 3, expected frequency on
ch1 1.568 kHz, measure: 1.487 kHz.
500µs per div.
Same delay of 35µs exist between
ch1 and
ch2.
10µs per div.
Code: Select all
# Test 4
from machine import Pin
from esp32 import RMT
ch1 = RMT(0, pin=Pin(2), clock_div=255)
ch1_wp = ch1.write_pulses
ch1_frame = (10, 10) * 3
ch2 = RMT(1, pin=Pin(4), clock_div=255)
ch2_wp = ch2.write_pulses
ch2_frame = (10, 10)
steps = range(1000000)
for _ in steps:
ch1_wp(ch1_frame)
ch2_wp(ch2_frame)
Here is the limit of this
hack!
Test 4, expected frequency on
ch1 15.686 kHz, measure: 13.26 kHz. This discrepancy is due to the delay to loop. Almost same delay of 35µs exist between
ch1 and
ch2.
50µs per div.
Code: Select all
# Test 5
from machine import Pin
from esp32 import RMT
ch1 = RMT(0, pin=Pin(2), clock_div=255)
ch1_wp = ch1.write_pulses
ch1_frame = (1, 1) * 3
ch2 = RMT(1, pin=Pin(4), clock_div=255)
ch2_wp = ch2.write_pulses
ch2_frame = (1, 1)
steps = range(1000000)
for _ in steps:
ch1_wp(ch1_frame)
ch2_wp(ch2_frame)
Test 5, expected frequency on
ch1 156.86 kHz, measure: 32.35 kHz.
25µs per div.
Delay of 40µs exist between
ch1 and
ch2.
10µs per div.
Conclusion
RMT is very accurate when used as designed
.
Now regarding my need, for
MultiAxis, let me know if you can think to an other solution in pure MicroPython.