---
title: Recovering the STM32L4R5
description: Learn how to recover the STM32L4R5 from corruption of the Option Bytes in the _FLASH_ registers
source_url: https://dev.blues.io/feather-mcus/swan/recovering-the-stm32l4r5/
canonical_url: https://dev.blues.io/feather-mcus/swan/recovering-the-stm32l4r5/
markdown_url: https://dev.blues.io/feather-mcus/swan/recovering-the-stm32l4r5.md
---

# Recovering the STM32L4R5

We discovered an SWD configuration error was present in older versions of the ST Board Support Package (BSP) for the Arduino IDE. The configuration error would occasionally cause corruption of the **Option Bytes** in the *FLASH* registers. Below we outline the steps required to repair the **Option Bytes** of the Swan.

> **Note:**
>
> The configuration error was resolved in the Arduino BSP, **STM32 MCU based boards**, version 2.3.0.

## Prerequisites

You'll need an SWD-capable ST-LINK programmer (e.g. the [STLINK-V3MINI](https://shop.blues.com/products/stlink-v3mini?utm_source=dev-blues\&utm_medium=web\&utm_campaign=store-link)) and a copy of [STM32CubeProgrammer](https://www.st.com/en/development-tools/stm32cubeprog.html#get-software) installed on your computer. The GUI procedure below uses STM32CubeProgrammer directly; the CLI procedure uses `STM32_Programmer_CLI`, which ships as part of the same package. If you don't already have STM32CubeProgrammer installed, follow the [installation notes](https://dev.blues.io/notecard/notecard-walkthrough/updating-notecard-firmware.md#stm32cubeprogrammer-installation-notes) before continuing.

## Hardware Setup

1. Connect the ST-LINK programmer to the Swan's Cortex-Debug connector with the included ribbon cable, then connect the programmer to your computer via USB.
2. Apply power to the Swan via the micro USB port (your computer or any other USB power source will do).

## Update with STM32CubeProgrammer (GUI)

1. Launch STM32CubeProgrammer, set the connection mode to **ST-LINK** at the top right, and click **Connect**.
2. Open the **OB** (Option Bytes) panel from the left navigation, then expand the **\[REG]** group to view the FLASH option-byte registers.
3. Compare the current register values against the **Invalid FLASH Registers** table below. If your device's registers match (or otherwise differ from the **Valid FLASH Registers** values further down), proceed to update them.

**Invalid FLASH Registers**

| **Register** | **Value**  |
| ------------ | ---------- |
| `OPTR`       | 0x08000000 |
| `PCROP1SR`   | 0xFFFE0000 |
| `PCROP1ER`   | 0xFFFE0000 |
| `WRP1AR`     | 0xFF00FF00 |
| `WRP2AR`     | 0xFF00FF00 |
| `PCROP2SR`   | 0xFFFFFFFF |
| `PCROP2ER`   | 0xFFFF0000 |
| `WRP1BR`     | 0xFF00FFFF |
| `WRP2BR`     | 0xFF00FFFF |

When the Option Byte registers get into this state, the STM32L4R5 will no longer execute firmware or allow programming.

Fortunately, the STM32L4R5 can be recovered using STM32CubeProgrammer by updating each register in the **\[REG]** tab to the value shown in the **Valid FLASH Registers** table below, then clicking **Apply** to commit the change.

![STM32CubeProgrammer REG Menu](https://dev.blues.io/images/quickstart/swan/stmcubeprogrammer-reg-menu.png?v=3c6ae7b7)

**Valid FLASH Registers**

| **Register** | **Value**  |
| ------------ | ---------- |
| `OPTR`       | 0xFFEF98AA |
| `PCROP1SR`   | 0xFFFFFFFF |
| `PCROP1ER`   | 0xFFFF0000 |
| `WRP1AR`     | 0xFF00FFFF |
| `WRP2AR`     | 0xFF00FFFF |
| `PCROP2SR`   | 0xFFFFFFFF |
| `PCROP2ER`   | 0xFFFF0000 |
| `WRP1BR`     | 0xFF00FFFF |
| `WRP2BR`     | 0xFF00FFFF |

After updating the option bytes, the STM32L4R5 can now be programmed using the STM32CubeProgrammer and execute firmware. Once you have updated the ST BSP, the device can be debugged and programmed normally via `SWD` again.

## Update with `STM32_Programmer_CLI`

1. Apply the following commands in order:

   ```bash
   STM32_Programmer_CLI --connect port=SWD --optionbytes RDP=0xBB
   STM32_Programmer_CLI --connect port=SWD --optionbytes RDP=0xAA
   STM32_Programmer_CLI --connect port=SWD --optionbytes nRST_STOP=1 IWDG_SW=1 IWDG_STOP=1 IWDG_STDBY=1 WWDG_SW=1 DBANK=1 nBOOT1=1 SRAM2_PE=1 SRAM2_RST=1 nSWBOOT0=01 PCROP1_STRT=0x1FFFF PCROP1_END=0x10000 WRP1A_STRT=0xFF WRP1A_END=0 WRP1B_STRT=0xFF WRP1B_END=0
   STM32_Programmer_CLI --connect port=SWD --optionbytes PCROP_RDP=1
   ```

2. Verify the option byte values by displaying them to the command prompt.

   ```bash
   STM32_Programmer_CLI --connect port=SWD --optionbytes displ
   ```

3. Compare the response to the following...

   ```plaintext
   UPLOADING OPTION BYTES DATA ...

     Bank          : 0x00
     Address       : 0x40022020
     Size          : 20 Bytes

   ██████████████████████████████████████████████████ 100%

     Bank          : 0x01
     Address       : 0x40022044
     Size          : 16 Bytes

   ██████████████████████████████████████████████████ 100%


   OPTION BYTES BANK: 0

      Read Out Protection:

        RDP          : 0xAA (Level 0, no protection)

      BOR Level:

        BOR_LEV      : 0x0 (BOR Level 0, reset level threshold is around 1.7 V)

      User Configuration:

        nRST_STOP    : 0x1 (No reset generated when entering Stop mode)
        nRST_STDBY   : 0x0 (Reset generated when entering Standby mode)
        nRST_SHDW    : 0x0 (Reset generated when entering the Shutdown mode)
        IWDG_SW      : 0x1 (Software independant watchdog)
        IWDG_STOP    : 0x1 (IWDG counter active in stop mode)
        IWDG_STDBY   : 0x1 (IWDG counter active in standby mode)
        WWDG_SW      : 0x1 (Software window watchdog)
        BFB2         : 0x0 (Dual-bank boot disable)
        DBANK        : 0x1 (Dual bank mode with 64 bits data)
        nBOOT1       : 0x1 (Boot from system memory when BOOT0=1)
        SRAM2_PE     : 0x1 (SRAM2 parity check disable)
        SRAM2_RST    : 0x1 (SRAM2 is not erased when a system reset occurs)
        nSWBOOT0     : 0x1 (BOOT0 taken from PH3/BOOT0 pin)
        nBOOT0       : 0x1 (BOOT0 = 0, boot from system memory when nSWBOOT0=1 and main flash is empty,otherwise, boot from main flash memory)

      PCROP Protection (Bank 1):

        PCROP1_STRT  : 0x1FFFF  (0x80FFFF8)
        PCROP1_END   : 0x10000  (0x8080000)
        PCROP_RDP    : 0x1 (PCROP zone is erased when RDP is decreased)

      Write Protection (Bank 1):

        WRP1A_STRT   : 0xFF  (0x80FF000)
        WRP1A_END    : 0x0  (0x8000000)
        WRP1B_STRT   : 0xFF  (0x80FF000)
        WRP1B_END    : 0x0  (0x8000000)

   OPTION BYTES BANK: 1

      PCROP Protection  (Bank 2):

        PCROP2_STRT  : 0x1FFFF  (0x81FFFF8)
        PCROP2_END   : 0x10000  (0x8180000)

      Write Protection (Bank 2):

        WRP2A_STRT   : 0xFF  (0x81FF000)
        WRP2A_END    : 0x0  (0x8100000)
        WRP2B_STRT   : 0xFF  (0x81FF000)
        WRP2B_END    : 0x0  (0x8100000)
   ```

> **Note:**
>
> Recovery documentation created based on [original Blues forum post](https://discuss.blues.com/t/cannot-communicate-with-swan-over-usb/478).
>
> If you are still experiencing difficulties, please contact <support@blues.com>.
