Overclock makes more of a difference to startup time than moving from MicroPython to C++ -
from MicroPython to C++ is 50ms faster
raising clock early: MicroPython is 87.6ms faster
raising clock early: C++ is 88ms faster
raising clock early: gains ~88ms in both cases
Moving from C++ to pico_runtime/runtime.c is much faster again
vsys high to GPIO set MicroPython: 77.6ms
vsys high to GPIO set C++: 26.8ms
vsys high to GPIO set pico_runtime/runtime.c: 8.2ms
If we want to read or set GPIO earlier than 26ms from power-on, we must patch pico_runtime/runtime.c and run our code before all the other bring-up.
A plain C++ approach gets us around 26.8ms to pin read. This is fine for Badger 2040 and actually functions as a sort-of debounce.
Summary
Setting a pin in MicroPython will take ~77ms from power on in the absolute best case. A larger MicroPython main.py with more complicated code will affect this.
Setting a pin in C++ (using __attribute__ ((init_priority (101))) on a struct instance) will take ~27ms from power on in the absolute best case. Adding any other C++ modules that are init before the wakeup module will affect this. (Though I have taken pains to remove all C++ init since it will try to allocate memory.)
As part of the discovery process for dropping our complex Pico SDK runtime patches, I ran some tests of startup times under the following conditions:
I also tested the first two cases with and without our clock config patches.
Basic clock config patch: https://github.com/pimoroni/badger2040/blob/v0.0.2/firmware/startup_overclock.patch
Full runtime patch: https://github.com/pimoroni/pimoroni-pico/blob/v1.19.18/micropython/_board/picow_enviro/wakeup_gpio.patch
Findings:
Overclock makes more of a difference to startup time than moving from MicroPython to C++ -
Moving from C++ to
pico_runtime/runtime.c
is much faster againIf we want to read or set GPIO earlier than 26ms from power-on, we must patch
pico_runtime/runtime.c
and run our code before all the other bring-up.A plain C++ approach gets us around 26.8ms to pin read. This is fine for Badger 2040 and actually functions as a sort-of debounce.
Summary
Setting a pin in MicroPython will take ~77ms from power on in the absolute best case. A larger MicroPython main.py with more complicated code will affect this.
Setting a pin in C++ (using
__attribute__ ((init_priority (101)))
on a struct instance) will take ~27ms from power on in the absolute best case. Adding any other C++ modules that are init before the wakeup module will affect this. (Though I have taken pains to remove all C++ init since it will try to allocate memory.)Captures
VSys to GPIO15 High: MicroPython
VSys to GPIO14 High: C++
VSys to GPIO12 High: pico_runtime/runtime.c patch