This adds new compile-time infrastructure to parse source code files for
`MP_REGISTER_ROOT_POINTER()` and generates a new `root_pointers.h` header
file containing the collected declarations. This works the same as the
existing `MP_REGISTER_MODULE()` feature.
Signed-off-by: David Lechner <david@pybricks.com>
Zero effect on non debug builds, and also usually optimized out even in
debug builds as mp_obj_is_type() is called with a compile-time known type.
I'm not sure we even have dynamic uses of mp_obj_is_type() at the moment,
but if we ever will they will be protected from now on.
Signed-off-by: Yonatan Goldschmidt <yon.goldschmidt@gmail.com>
Commit d96cfd13e3 introduced a regression by breaking existing
users of mp_obj_is_type(.., &mp_obj_bool). This function (and associated
helpers like mp_obj_is_int()) have some specific nuances, and mistakes like
this one can happen again.
This commit adds mp_obj_is_exact_type() which behaves like the the old
mp_obj_is_type(). The new mp_obj_is_type() has the same prototype but it
attempts to statically assert that it's not called with types which should
be checked using mp_obj_is_type(). If called with any of these types: int,
str, bool, NoneType - it will cause a compilation error. Additional
checked types (e.g function types) can be added in the future.
Existing users of mp_obj_is_type() with the now "invalid" types, were
translated to use mp_obj_is_exact_type().
The use of MP_STATIC_ASSERT() is not bulletproof - usually GCC (and other
compilers) can't statically check conditions that are only known during
link-time (like variables' addresses comparison). However, in this case,
GCC is able to statically detect these conditions, probably because it's
the exact same object - `&mp_type_int == &mp_type_int` is detected.
Misuses of this function with runtime-chosen types (e.g:
`mp_obj_type_t *x = ...; mp_obj_is_type(..., x);` won't be detected. MSC
is unable to detect this, so we use MP_STATIC_ASSERT_NOT_MSC().
Compiling with this commit and without the fix for d96cfd13e3 shows
that it detects the problem.
Signed-off-by: Yonatan Goldschmidt <yon.goldschmidt@gmail.com>
Some devices, such as the LightBlue BTLE app on iOS, try to use Bluetooth 5
when connecting to a device. This means that they will send a
BLE_GAP_EVT_PHY_UPDATE_REQUEST message to shift to a new physical layer.
If this event isn't handled, LightBlue (and likely other Bluetooth 5.0
central devices) will try to connect and then fail, staying in
"Connecting..." state forever. This message should be replied to with
sd_ble_gap_phy_update, as documented in
drivers/bluetooth/s140_nrf52_6.1.1/s140_nrf52_6.1.1_API/include/ble_gap.h.
This commit handles the event. LightBlue can now successfully connect to a
BTLE device on a P10059 nRF52840 dongle running MicroPython. Two other
related events have logging added in case they are needed in the future.
The empty tuple is usually a constant object, but named tuples must be
allocated to allow modification. Added explicit allocation to fix this.
Also added a regression test to verify creating an empty named tuple works.
Fixes issue #7870.
Signed-off-by: Lars Haulin <lars.haulin@gmail.com>
Commit 0e28a1f0e5 made it possible to set
-march=armv6m. It needs to be used when freezing for rp2.
Signed-off-by: Jim Mussared <jim.mussared@gmail.com>
The GENERATOR_EXIT_IF_NEEDED macro is only used once and it's easier to
read and understand the code if this macro body is written in the code.
Then the comment just before it makes more sense.
Signed-off-by: Damien George <damien@micropython.org>
This check for code_state->ip being NULL was added in
a7c02c4538 with a commit message that "When
generator raises exception, it is automatically terminated (by setting its
code_state.ip to 0)". It was also added without any tests to test for this
particular case. (The commit did mention that CPython's test_pep380.py
triggered a bug, but upon re-running this test it did not show any need for
this NULL check of code_state->ip.)
It is true that generators that have completed (either by running to their
end or raising an exception) set "code_state.ip = 0". But there is an
explicit check at the start of mp_obj_gen_resume() to return immediately
for any attempt to resume an already-stopped generator. So the VM can
never execute a generator with NULL ip (and this was true at the time of
the above-referenced commit).
Furthermore, the other parts of the VM just before and after this piece
of code do require (or at least assume) code_state->ip is non-NULL.
Signed-off-by: Damien George <damien@micropython.org>
Since nlr_jump_fail() exits the process, it can leave the terminal in raw
mode which means characters are not echoed. Fix this by restoring the
original terminal mode.
Signed-off-by: David Lechner <david@pybricks.com>
Change the default DNS to match the gateway IP of a board running in access
point mode (or otherwise acting as a "server").
This fixes the rather meaningless use of "8.8.8.8" as the default DNS
server address offered up to access point clients via the DHCP server.
Since most devices wont be able to proxy access to the real "8.8.8.8".
It allows for a DNS responder to run and provide a catchall response for
captive portal functionality, or just a quality-of-life response to a
friendly URL for access-point based configuration and other applications.
Signed-off-by: Phil Howard <phil@gadgetoid.com>
When a flash write/erase is in progress, we need to ensure that the
other core cannot be using XIP.
This also implements MICROPY_BEGIN_ATOMIC_SECTION as a full mutex, which
is necessary as it's used to syncronise access to things like the scheduler
queue.
Signed-off-by: Jim Mussared <jim.mussared@gmail.com>
The goal is to avoid a situation where core 1 is shut down while holding
the tinyusb spinlock, which could happen during soft reset if
mp_thread_deinit is called while core1 is running tud_task().
This also fixes a latent race where the two cores are competing to
decrement and compare `vm_hook_divisor` with no mem fence or atomic
protection -- only core0 will now do this.
Signed-off-by: Jim Mussared <jim.mussared@gmail.com>
The optimisation that allows a single check in the VM for either a pending
exception or non-empty scheduler queue doesn't work when threading is
enabled, as one thread can clear the sched_state if it has no pending
exception, meaning the thread with the pending exception will never see it.
This removes that optimisation for threaded builds.
Also fixes a race in non-scheduler builds where get-and-clear of the
pending exception is not protected by the atomic section.
Also removes the bulk of the inlining of pending exceptions and scheduler
handling from the VM. This just costs code size and complexity at no
performance benefit.
Signed-off-by: Jim Mussared <jim.mussared@gmail.com>
To override it a board must define MICROPY_BOARD_FATAL_ERROR to a function
that takes a string message and does not return.
Signed-off-by: Damien George <damien@micropython.org>
The file `ports/unix/moduos.c` uses `errno` so it needs to include
`errno.h`, otherwise a compiler error can occur.
Signed-off-by: David Lechner <david@pybricks.com>
Ensure that nimble and cyw43-driver are initialised when the board requires
it. Also make these work with `make submodules`.
Signed-off-by: Jim Mussared <jim.mussared@gmail.com>