microbit-foundation / python-editor-v3

Micro:bit Educational Foundation Python Editor V3
https://python.microbit.org
MIT License
54 stars 36 forks source link

WebUSB Partial Flashing: UICR not updated #1131

Open microbit-carlos opened 9 months ago

microbit-carlos commented 9 months ago

Bug Description

I encountered this with a couple of users during the Kids Day at PyCon UK 2023.

I don't know exactly how it happened, but I would guess that this was probably triggered with a WebUSB full flash that failed (or the micro:bit was disconnected) during the last stages, which placed most of the data to flash, but didn't get to the UICR area (address 0x1000_1000, the last few lines in an Intel/Universal hex file).

At this point, every time we tried to WebUSB flash, it did a partial flash, it looked like everything went well, but the micro:bit never run the programme, and the device seemed "dead".

Today I've analysed one micro:bit in this state, and I've noticed that the UICR area was empty, which was blocking the programme from starting (an address goes there placed or needed for the SoftDevice/bootloader).

This can be fixed by flashing the micro:bit via drag&drop, but this is not obvious for the user, which might have never done that before.

How To Reproduce

Steps to reproduce the behaviour:

  1. Erase the micro:bit flash, or flash a MakeCode programme
  2. Go to the Python Editor
  3. Click on Download, a full flash should start
  4. Wait until the progress bar is at around ~85%
  5. At this point disconnect the micro:bit USB cable
  6. Reconnect it, and click download again
  7. Partial flashing should complete successfully but the programme would not be running on the device

Expected behavior

The python programme to run.

Screenshots

N/A

Environment

N/A

Additional context

UICR partial flashing is skipped in the code, I guess the answer to this TODO (probably added by me in the editor v2 😅) would be "yes".

https://github.com/microbit-foundation/python-editor-v3/blob/cc28c29724111ed9f4f08fcc78872fe4cdcf8d42/src/device/partial-flashing.ts#L152-L160

Each bit in the UICR can only be flipped once, the way to clear it is with a full release. However, the nRF52833 has a NVM controller command to clear the UICR (which the V1 nrf51822 doesn't have), so technically that could be used in V2 to clear the UICR and write to it.

Nevertheless, at least for V1, we could compare the contents of UICR vs the hex file and if different we could trigger a full flash.