Using nrfutil to program an off-the-shelf XIAO nRF52840 module

System Details:

  • Chip: nRF52840, XIAO Module
  • nRF5 SDK: Version 16.0.0
  • mdk version: 8.46.0
  • nrfjprog version: 10.15.4 external
  • nrfutil version: 6.1.3
  • JLinkARM.dll version: 7.64d

Hello,

I have tested an nRF SDK example application (usbd_generic_hids) on my nRF52840 DK board, and I now would like to try and flash this application onto my off-the-shelf XIAO nRF52840 modules. I have used nrfutil in the past in order to perform DFU, but it has always been for OTA DFU via BLE. I want to know how I can program just the application itself. I believe this usbd_generic_hids example does not require a SoftDevice to be present, and I am not sure if it needs a bootloader (I dont think so).

I havent programmed an off-the-shelf module like this before, so I have a few questions:

  1. I know that the XIAO module comes with a USB bootloader built-in, and I was recommended to leave that bootloader intact for easier programming. However, as I said before, I am familiar with OTA DFU and secure dfu bootloaders on the nRF52840, so I should be able to program this device wirelessly and not have to worry about overwriting the default XIAO bootloader with a nRF-based bootloader. I would personally prefer to use our normal dfu secure bootloader, with softdevice, because this is more consistent with the other versions of this device that I have been developing. Is this possible? Is there anything I should be aware of in this process?
  2. I have tried using nrfutil to generate a package of the application code by itself. It compiles and creates the .zip package just fine, but it fails to actually perform the DFU (error message included below). Is it even possible to do what I am trying? I feel like I need the dfu bootloader on-board in order to perform this usb-based dfu process.
    + nrfutil pkg generate --hw-version 52 --sd-req 0xCA --application-version 1 --application ../nrf-sdk/examples/peripheral/usbd_hid_generic/pca10056/blank/armgcc/_build/nrf52840_xxaa.hex usbd_hid.zip                         
                                                                                                                                                                                                                                   
    |===============================================================|                                                                                                                                                              
    |##      ##    ###    ########  ##    ## #### ##    ##  ######  |                                                                                                                                                              
    |##  ##  ##   ## ##   ##     ## ###   ##  ##  ###   ## ##    ## |                                                                                                                                                              
    |##  ##  ##  ##   ##  ##     ## ####  ##  ##  ####  ## ##       |                                                                                                                                                              
    |##  ##  ## ##     ## ########  ## ## ##  ##  ## ## ## ##   ####|                                                                                                                                                              
    |##  ##  ## ######### ##   ##   ##  ####  ##  ##  #### ##    ## |                                                                                                                                                              
    |##  ##  ## ##     ## ##    ##  ##   ###  ##  ##   ### ##    ## |                                                                                                                                                              
    | ###  ###  ##     ## ##     ## ##    ## #### ##    ##  ######  |                                                                                                                                                              
    |===============================================================|                                                                                                                                                              
    |You are not providing a signature key, which means the DFU     |                                                                                                                                                              
    |files will not be signed, and are vulnerable to tampering.     |                                               
    |This is only compatible with a signature-less bootloader and is|                                               
    |not suitable for production environments.                      |                                               
    |===============================================================|                                               
                                                                                                                    
    Zip created at usbd_hid.zip                                                                                     
    + nrfutil dfu usb-serial -pkg usbd_hid.zip -p /dev/cu.usbmodem14301 -b 115200                                   
      [------------------------------------]    0%                                                                  
    Traceback (most recent call last):                                                                              
      File "/usr/local/bin/nrfutil", line 8, in <module>                                                            
        sys.exit(cli())                                                                                             
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1128, in __call__                           
        return self.main(*args, **kwargs)                                                                           
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1053, in main                               
        rv = self.invoke(ctx)                                                                                       
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1659, in invoke                             
        return _process_result(sub_ctx.command.invoke(sub_ctx))                                                     
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1659, in invoke                             
        return _process_result(sub_ctx.command.invoke(sub_ctx))                                                     
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 1395, in invoke                             
        return ctx.invoke(self.callback, **ctx.params)                                                              
      File "/usr/local/lib/python3.9/site-packages/click/core.py", line 754, in invoke                              
        return __callback(*args, **kwargs)                                                                          
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/__main__.py", line 1022, in usb_serial
        do_serial(package, port, connect_delay, flow_control, packet_receipt_notification, baud_rate, serial_number, False,
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/__main__.py", line 978, in do_serial                                                                                                                                 
        dfu.dfu_send_images()                               
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/dfu/dfu.py", line 127, in dfu_send_images
        self._dfu_send_image(self.manifest.application)     
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/dfu/dfu.py", line 88, in _dfu_send_image                                                                                                                             
        self.dfu_transport.open()                           
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/dfu/dfu_transport_serial.py", line 217, in open                                                                                                                      
        self.__get_mtu()                                                                                            
      File "/usr/local/lib/python3.9/site-packages/nordicsemi/dfu/dfu_transport_serial.py", line 366, in __get_mtu                                                                                                                 
        self.mtu = struct.unpack('<H', bytearray(response))[0]                       
    TypeError: cannot convert 'NoneType' object to bytearray  
  3. Any general advice on what resources will help me learn how to do this?

Thank you in advance :)

  • Hello,

    I was not able to find any documentation that confirmed what bootloader this module shipped with either, but the fact that it enumerates as a mass storage device indicates that it is not executing our bootloader, at least . Maybe it supports drag&drop programming instead?

    Another alternative to DFU over USB is to use one of the Debug outputs from your nRF52840DK to program the module. Just remember that the module must have the same VDD voltage as the DK because the OB Jlink doesn't have a built-in level shifter like you will find in a standalone J-link programmer.

  • So it could be the bootloader issue....or possibly the DFU state, since I have not done anything to step it into DFU state so far.

    Yeah, I would wonder whether the bootloader is running, or if it has transferred control to an app that enables the USB CDC ACM functionality but doesn't accept the SLIP command format.  That would explain why you're able to open the USB serial device, but the board isn't responding to commands.

    The Xiao BLE docs say:

    On my nRF52840 Dongles, I also have to hit the reset button (just once) to get it back to the Open Bootloader so I can upload new code via nrfutil.

    I grounded the RST pin, and that is actually what got the second of the 2 error messages I just shared to display.

    I would guess that if you asserted RST and never released it, you won't even see the /dev/cu.* device node anymore because the USB interface on the nRF52840 chip is inactive.

  • the fact that it enumerates as a mass storage device indicates that it is not executing our bootloader, at least .

    Why is this the case? For example, when I plug in the nRF52840 DK, it also appears as a flash storage icon. So why does this fact help us distinguish that it is not a Nordic bootloader?

    Maybe it supports drag&drop programming instead?

    I can try. In this case, would I just be simply Drag/Dropping the compiled .HEX file for my application, or would I Drag/Drop the newly created .ZIP package from the attempts with nrfutil dfu?

    I would guess that if you asserted RST and never released it, you won't even see the /dev/cu.* device

    I would agree. To be clear, I only temporarily grounded the RST pin with a jumper cable (unsoldered) - I didnt leave it grounded. I would have liked to simultaneously ground the "DFU pin" temporarily as well, given that is what the error message suggests. But I dont know what the "DFU pin" is, so I just tried it with only the RST pin. The temporary grounding is what seems to have stepped the XIAO module into a different mode, which is what produced the second of the two error messages that I shared from the adafruit-nrfutil output. For now, I can keep trying to play with the Reset Button, and see if that can get anywhere.

    Otherwise, it is looking more and more likely that I will just solder up some connections to the SWD pads on the module and program it using a JLINK like I have done with other boards. Using the Debug Outputs from the nRF52840 DK seems more difficult than this JLINK/SWD option...I just feel like I am very close to getting it to work with the USB....

  • To be clear, I only temporarily grounded the RST pin with a jumper cable (unsoldered) - I didnt leave it grounded.

    If the device node is still present, and you're getting "Device not configured" (ENXIO) when you try to talk to it, that suggests to me that you might have successfully activated the bootloader but your host isn't able to talk to it due to USB interop bugs.  e.g. maybe the bootloader has a different version of the USB stack from the main app

    If you have a Linux box or Raspberry Pi lying around, maybe try flashing with one of those?

    Otherwise, it is looking more and more likely that I will just solder up some connections to the SWD pads on the module and program it using a JLINK like I have done with other boards.

    IMO the support for these USB bootloaders is pretty half-baked, even on the official Nordic dongles.  I wonder if they'd accept a pull request to clean it up.

  • Hello  and ,

    I am having trouble replying to the most recent comment left by Mytzjay, but I was able to learn a bit more about the device. I found some information on board my XIAO module that mentions the bootloader, as well as some other high level details. Take a look:

    UF2 Bootloader 0.6.2-12-g459adc9-dirty lib/nrfx (v2.0.0) lib/tinyusb (0.10.1-293-gaf8e5a90) lib/uf2 (remotes/origin/configupdate-9-gadbb8c7)
    Model: Seeed XIAO nRF52840
    Board-ID: Seeed_XIAO_nRF52840_Sense
    Date: Nov 30 2021
    SoftDevice: S140 7.3.0
    

    Right off the bat, I notice that my SoftDevice s140 is version 7.0.1, while this XIAO module has s140 version 7.0.3. Could this difference in version be causing these issues?

    Aside from that, I am not entirely sure how to make sense of the bootloader information. Do these bootloader details give us a better understanding of what is going on? Any help is greatly appreciated.

    EDIT: I connected a JLINK to the XIAO module by soldering wires to the SWDIO, SWDCLK, RST, GND and 3.3V pins. This method is working for me and I am getting all of my code onto the device as expected. Thank you for working with me to try and help debug using the USB as a means of DFU. If this bootloader information that I shared sheds light on my previous failures, I would still love to learn what is going on...plus I have to program a handful of these boards and it would be easier over USB, though not needed.

Related