7. Flash your Pico#

Enough with the simulations. Let’s work with some real hardware! You’ll need a physical Raspberry Pi Pico for the rest of the tutorial. You can use either the Pico 1 or Pico 2; we support both.

If you don’t have a Pico, you can just skim the remaining pages of the tutorial without actually doing the workflows, or skip ahead to 16. Wrapping up.

Set up your hardware#

You can use any of the following hardware setups.

Caution

The Pico W is untested. We are still in the process of verifying that all parts of the tutorial work with the Pico W. You are welcome to try the tutorial with a Pico W, but please remember that some things may not work yet.

Option: Basic setup#

You can connect your development host directly to a Pico via a USB cable.

USB connected to Pico, no Enviro+ Pack involved

If you have an Enviro+ Pack, you connect the Enviro+ Pack to the headers of your Pico. The Pico is still connected to your development host over USB, same as before.

USB connected to Pico, with Pico connected to Enviro+

Option: Full setup#

For the most robust long-term setup, use a Raspberry Pi Debug Probe and Pico Omnibus in combination with your Pico and Enviro+ Pack:

  1. Connect the Debug Probe to your host over USB.

  2. Update the firmware on the Debug Probe. You just need to download the latest release and drag-and-drop the UF2 file onto your Debug Probe. You want the debugprobe.uf2 file from the releases page. It only takes a minute or two.

  3. Connect the Enviro+ to DECK 1 on the Omnibus.

  4. Connect the Pico to the middle landing area on the Omnibus. Make sure that the USB port on your Pico is lined up with the USB label on the Omnibus.

  5. Connect the Pico and Debug Probe together with the 3-pin debug to 0.1-inch header female cable (the yellow, black, and orange cable). On deck 2 connect the yellow wire to pin 0 (Pico TX, Debug Probe RX), the orange wire to pin 1 (Pico RX, Debug Probe TX), and the black wire to - (GND). See the next image.

  6. Connect the Pico and Debug Probe together with the 3-pin debug to 3-pin debug cable (the grey and red cable). See the image below.

  7. Connect the Pico’s micro USB port to a power supply.

    You can supply power to the Pico by connecting it to a USB port on your host. Later on this will make your flashing process a little more complex. So it’s simpler to provide power to the Pico separately, if you can.

Full hardware setup with Debug Probe, Pico, Omnibus, and Enviro+ Pack

The full hardware setup#

Set up udev rules#

Configure your host to properly detect Raspberry Pi hardware.

  1. Add the following rules to /etc/udev/rules.d/49-pico.rules or /usr/lib/udev/rules.d/49-pico.rules. Create the file if it doesn’t exist.

    # RaspberryPi Debug probe: https://github.com/raspberrypi/debugprobe
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000c", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000c", MODE:="0666"
    # RaspberryPi Legacy Picoprobe (early Debug probe version)
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0004", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0004", MODE:="0666"
    
    # RP2040 Bootloader mode
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0003", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0003", MODE:="0666"
    # RP2040 USB Serial
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000a", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000a", MODE:="0666"
    
    # RP2350 Bootloader mode
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000f", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="000f", MODE:="0666"
    # RP2350 USB Serial
    SUBSYSTEMS=="usb", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0009", MODE:="0666"
    KERNEL=="ttyACM*", ATTRS{idVendor}=="2e8a", ATTRS{idProduct}=="0009", MODE:="0666"
    
  2. Reload the rules:

    sudo udevadm control --reload-rules
    sudo udevadm trigger
    
  3. If your Pico is already connected to your host, unplug it and plug it back in again.

No extra setup needed.

Flash an application binary to your Pico#

  1. If your Pico’s firmware is not in good working order, put your Pico into BOOTSEL mode. See Your First Binaries. If your Pico is in working order (i.e. you have functioning app running correctly on your Pico) you can skip this step.

  2. Flash the blinky binary to your Pico.

    In Bazel Build Targets expand //apps/blinky, then right-click :flash (alias), then select Run target.

    A successful flash looks similar to this:

    https://storage.googleapis.com/pigweed-media/sense/20240802/flash.png
    $ bazelisk run //apps/blinky:flash
    INFO: Analyzed target //apps/blinky:flash (0 packages loaded, 0 targets configured).
    INFO: Found 1 target...
    Target //apps/blinky:flash_rp2040 up-to-date:
      bazel-bin/apps/blinky/flash_rp2040.exe
    INFO: Elapsed time: 0.129s, Critical Path: 0.00s
    INFO: 1 process: 1 internal.
    INFO: Build completed successfully, 1 total action
    INFO: Running command line: bazel-bin/apps/blinky/flash_rp2040.exe apps/blinky/rp2040_blinky.elf
    20240806 18:16:58 INF Only one device detected.
    20240806 18:16:58 INF Flashing bus 3 port 6
    

If you see an interactive prompt asking you to select a device, see Appendix: Interactive prompt selection.

You should see your Raspberry Pi Pico’s LED start blinking on and off at a 1-second interval.

Troubleshooting

If you see A connected device has an inaccessible serial number: The device has no langid (permission issue, no string descriptors supported or device error) it probably means you need to update your udev rules. See Set up udev rules.

Summary#

In a Bazel-based project like Sense there is no separate flashing tool or command that you need to memorize; flashing is a Bazel target just like everything else.

As mentioned in Summary, you actually don’t need to build binaries before running flashing targets like this. You can just skip straight to running the flash target and Bazel will figure out what binaries to build before attempting to flash.

Next, head over to 8. Run on-device tests to try out on-device unit tests.

Appendix: Interactive prompt selection#

If you’re using the full setup you’ll see an interactive prompt asking you to select a device. Choose Raspberry Pi - Debug Probe (CMSIS-DAP), not Raspberry Pi - Pico. When the Debug Probe receives the flashing command, it knows that the command is intended for the Pico it’s connected to, not itself.

INFO: Running command line: bazel-bin/apps/blinky/flash_rp2040.exe apps/blinky/rp2040_blinky.elf
Multiple devices detected. Please select one:
  1 - bus 3, port 1 (Raspberry Pi - Pico)
  2 - bus 3, port 6 (Raspberry Pi - Debug Probe (CMSIS-DAP))

Enter an item index or press up/down (Ctrl-C to cancel)
> 2
20240729 16:29:46 INF Flashing bus 3 port 6