You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
When PM management with DFS is enabled, the RMT doesn't work correctly. E.g., when send data to a neopixel LED, the sequence starts correctly, but then the timing becomes off when the DFS lowers the APB clock frequency.
This is caused by DFS changing the APB frequency while the system is idle waiting for the RMT to send the sequence. The RMT is configured to use the APB as its source clock, and so this changes the timing of the pulses.
The ESP-IDF documentation says the RMT driver is DFS aware and use the necessary PM locks to prevent this. This isn't working.
The reason is doesn't work is because Micropython uses the rmt-legacy driver, not the current rmt driver, and the legacy driver is not PM aware.
It could be fixed by manually adding the PM locks, but this means the holding the chip at a higher power state while using the RMT.
Lower power will be possible by using a clock that does not change frequency with DFS, e.g. use RMT_BASECLK_XTAL. Then the APB can be slowed without affecting the RMT clock. And no code for pm locks is needed.
I tried adding a call to rmt_set_source_clk(config.channel, RMT_BASECLK_XTAL), but this ends up triggering a bug in ESP-IDF. The rmt-legacy driver has a method to report the rmt clock frequency, rmt_get_counter_clock() and this uses the frequency of the source clock used when the rmt was first configured. This frequency is not updated when rmt_set_source_clk() changes the base clock. And so the reported counter clock is off since it's still using the APB frequency instead of the XTAL frequency.
Another way to do it is to set a flag to request a DFS aware clock when configuring the rmt. E.g., config.flags |= RMT_CHANNEL_FLAGS_AWARE_DFS. This works! The ESP-IDF code knows a/the platform specific clock to use that will not be affected by DFS.
But there are still some issues:
The code in machine_bitstream.c hard-codes the clock divider. Since the XTAL clock is slower than the APB clock (on ESP32-S3, 40 vs 80), a different divider should be used to achieve the same counter frequency. It could instead get the frequency with a divider of 1, then adjust the divider if that is faster than desired.
On some platforms, the DFS aware clock is a lot slower. I think on ESP32, it will use a 2 MHz reftick clock. It is probably undesirable to always use the DFS aware clock on platforms where it might be too slow.
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
Uh oh!
There was an error while loading. Please reload this page.
-
When PM management with DFS is enabled, the RMT doesn't work correctly. E.g., when send data to a neopixel LED, the sequence starts correctly, but then the timing becomes off when the DFS lowers the APB clock frequency.
This is caused by DFS changing the APB frequency while the system is idle waiting for the RMT to send the sequence. The RMT is configured to use the APB as its source clock, and so this changes the timing of the pulses.
The ESP-IDF documentation says the RMT driver is DFS aware and use the necessary PM locks to prevent this. This isn't working.
The reason is doesn't work is because Micropython uses the rmt-legacy driver, not the current rmt driver, and the legacy driver is not PM aware.
It could be fixed by manually adding the PM locks, but this means the holding the chip at a higher power state while using the RMT.
Lower power will be possible by using a clock that does not change frequency with DFS, e.g. use
RMT_BASECLK_XTAL
. Then the APB can be slowed without affecting the RMT clock. And no code for pm locks is needed.I tried adding a call to
rmt_set_source_clk(config.channel, RMT_BASECLK_XTAL)
, but this ends up triggering a bug in ESP-IDF. The rmt-legacy driver has a method to report the rmt clock frequency,rmt_get_counter_clock()
and this uses the frequency of the source clock used when the rmt was first configured. This frequency is not updated whenrmt_set_source_clk()
changes the base clock. And so the reported counter clock is off since it's still using the APB frequency instead of the XTAL frequency.Another way to do it is to set a flag to request a DFS aware clock when configuring the rmt. E.g.,
config.flags |= RMT_CHANNEL_FLAGS_AWARE_DFS
. This works! The ESP-IDF code knows a/the platform specific clock to use that will not be affected by DFS.But there are still some issues:
Beta Was this translation helpful? Give feedback.
All reactions