Skip to content

rp2: Random lockups on soft reboot if core 1 was running #8494

Closed
@czietz

Description

@czietz

Running the following minimal example on the Raspberry Pi Pico:

import _thread
def burn():
    while True:
        pass

_thread.start_new_thread(burn, [])

... starts an endless loop on the second CPU core (aka core 1). If a soft reboot via Ctrl+D is then performed, Micropython sometimes locks up to the point where only a hardware reset of the Pico helps. (You might have to try this several times, it does not happen every soft reboot.)

I've traced this to an endless wait for the spinlock in _osal_q_lock. I think, this is because the TinyUSB task is called on both cores via MICROPY_HW_USBDEV_TASK_HOOK:

#define MICROPY_HW_USBDEV_TASK_HOOK extern void tud_task(void); tud_task();

... which is called via MICROPY_VM_HOOK_LOOP in vm.c.

Therefore, I think this is what happens: During a soft reboot, core 1 is reset:

multicore_reset_core1();

If this happens at an unfavorable moment, when core 1 holds the Tiny USB spinlock, said lock is never released and core 0 hangs indefinitely when trying to acquire the lock the next time.

At first glance, only calling the TinyUSB task on core 0:

#define MICROPY_HW_USBDEV_TASK_HOOK extern void tud_task(void); if (get_core_num() == 0) tud_task();

... seems to fix the problem, as I cannot observe any random lockups.

However, I'm not familiar enough with Micropython's internals to know if there are situations in which the task needs to run on core 1, too. Therefore, I did not propose this tentative fix as a PR.

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions