STM32 BootLoader 刷新项目 (十二) Option Byte之FLASH_OPTCR-命令0x58

news/2024/12/2 13:08:14/

STM32 BootLoader 刷新项目 (十二) Option Byte之FLASH_OPTCR-命令0x58

STM32F407芯片的OPTION Byte全面解析

STM32F407芯片是STMicroelectronics推出的一款功能强大的微控制器,广泛应用于工业控制、通信和消费电子等领域。其中,OPTION Byte(选项字节)是STM32系列芯片的重要配置功能,允许用户通过配置特定的寄存器,控制芯片的关键特性,例如启动模式、读保护和写保护等。

本文将分为8个章节,全面解析STM32F407芯片的OPTION Byte功能。


第一章:OPTION Byte 概述

1.1 什么是OPTION Byte?

OPTION Byte 是 STM32 系列芯片中一种特殊的配置区域,存储在片内闪存(Flash memory)中。它的主要作用是提供芯片启动、保护和工作模式等关键参数的配置选项。这些字节在系统启动时被加载到对应的配置寄存器中,影响芯片的行为。

1.2 OPTION Byte 的作用

OPTION Byte 的主要功能包括:

  1. 启动模式配置:选择芯片从主Flash、系统存储器或SRAM启动。
  2. 读保护(Read Out Protection, ROP):保护芯片中的数据不被非法读取。
  3. 写保护(Write Protection, WP):保护指定的Flash区域不被擦除或写入。
  4. BOR(Brown-Out Reset)电压等级:设置芯片的掉电检测电压等级。
  5. Watchdog配置:使能或禁止独立看门狗(IWDG)在芯片复位后启动。

Option Byte由最终用户根据应用需求进行配置。表14显示了这些字节在用户配置扇区内的组织结构。

image-20241128212547464

image-20241128212606075

image-20241128212713019

image-20241128212758865


1.3 Programming user option bytes

要在该扇区上执行任何操作,必须清除Flash选项控制寄存器(FLASH_OPTCR)中的选项锁定位(OPTLOCK)。为了允许清除此位,您需要按照以下步骤进行操作:

  1. 将Flash选项密钥寄存器(FLASH_OPTKEYR)中的OPTKEY1设置为0x0819 2A3B。

  2. 将Flash选项密钥寄存器(FLASH_OPTKEYR)中的OPTKEY2设置为0x4C5D 6E7F。

用户选项字节可以通过软件设置OPTLOCK位来防止不必要的擦除/编程操作。

Modifying user option bytes on STM32F405xx/07xx and STM32F415xx/17xx

要修改用户选项值,请按照以下顺序进行操作:

  1. 检查FLASH_SR寄存器中的BSY位,确保没有正在进行的Flash内存操作。
  2. 将所需的选项值写入FLASH_OPTCR寄存器。
  3. 在FLASH_OPTCR寄存器中设置选项启动位(OPTSTRT)。
  4. 等待BSY位被清除。
1.4 Write protections

FLASH_OPTCR 是 STM32F407 芯片中用于控制和配置 Option Byte 的关键寄存器。通过操作该寄存器,可以设置各种与芯片启动模式、安全性以及电压保护相关的功能。以下是对 FLASH_OPTCR 寄存器的详细介绍。

Flash存储器中最多可以保护24个用户扇区,以防止由于程序计数器上下文丢失而导致的不必要写操作。当FLASH_OPTCR或FLASH_OPTCR1寄存器中的非写保护nWRPi位(0 ≤ i ≤ 11)为低电平时,相应的扇区将无法被擦除或编程。因此,如果其中一个扇区受到写保护,则无法进行全片擦除。如果尝试对Flash存储器中受写保护部分(由写保护位、OTP部分锁定或永远不能被写入的ICP组成)进行擦除/编程操作,则会在FLASH_SR寄存器中设置写保护错误标志(WRPERR)。

image-20241128214504565

image-20241128214609809

image-20241128214622556


FLASH_OPTCR 寄存器定义

FLASH_OPTCR 是一个 32 位寄存器,其各位或各位段控制特定的 Option Byte 配置。

位段名称说明
[0]OPTLOCK选项锁位(Option Lock)
[1]OPTSTRT选项启动位(Option Start)
[2:3]BOR_LEV掉电复位电压等级(Brown-Out Reset Level)
[4]Reserved保留位
[5]WDG_SW独立看门狗模式选择(Software or Hardware IWDG)
[6]nRST_STOPSTOP模式复位禁用
[7]nRST_STDBYStandby模式复位禁用
[8:15]RDP读保护等级(Read Protection Level)
[16:27]WRP写保护配置(Write Protection for Flash Sectors)
[28:31]Reserved保留位

各字段详细解析
1. OPTLOCK(Option Lock) [0]
  • 说明:选项字节锁定位,用于保护 FLASH_OPTCR 寄存器不被意外修改。
    • 1:锁定 Option Byte。
    • 0:解锁 Option Byte。
  • 操作:需要先写入解锁密钥到 FLASH_OPTKEYR 寄存器,才能将此位清零解锁。
2. OPTSTRT(Option Start) [1]
  • 说明:选项启动位,用于触发 Option Byte 的写入操作。
    • 1:启动 Option Byte 写入。
    • 0:无操作。
  • 操作:在修改完 Option Byte 配置后,需将该位设置为 1 以启动写入。
3. BOR_LEV(Brown-Out Reset Level) [2:3]
  • 说明:配置 BOR 掉电复位的电压阈值。
    • 0000:BOR Level 0(最低电压复位,1.8V 至 2.1V)。
    • 0001:BOR Level 1(1.9V 至 2.4V)。
    • 0010:BOR Level 2(2.1V 至 2.7V)。
    • 0011:BOR Level 3(2.4V 至 2.9V)。
    • 其他值:保留。
  • 应用:在电源不稳定的场景中,可通过调整 BOR Level 确保 MCU 在电压异常时安全复位。
4. WDG_SW(Independent Watchdog Selection) [5]
  • 说明:独立看门狗模式选择。
    • 0:硬件模式(独立看门狗由硬件启动,不能由软件禁用)。
    • 1:软件模式(独立看门狗由软件启动,可以由软件控制)。
  • 应用:在安全关键场景中,硬件模式更可靠;而软件模式适合需要灵活控制的应用。
5. nRST_STOP(Stop Mode Reset Disable) [6]
  • 说明:STOP模式复位禁用。
    • 0:启用 STOP 模式下的复位。
    • 1:禁用 STOP 模式下的复位。
  • 应用:用于控制在进入 STOP 模式后,是否允许复位信号。
6. nRST_STDBY(Standby Mode Reset Disable) [7]
  • 说明:Standby模式复位禁用。
    • 0:启用 Standby 模式下的复位。
    • 1:禁用 Standby 模式下的复位。
  • 应用:与 nRST_STOP 类似,用于控制芯片在 Standby 模式的复位行为。
7. RDP(Read Protection Level) [8:15]
  • 说明:读保护等级。
    • 0xAA:无保护(Level 0)。
    • 0xBB:读保护(Level 1)。
    • 其他:高强度保护(Level 2,数据不可访问且不可恢复)。
  • 注意
    • 一旦进入 Level 2,芯片的 Flash 区域永久锁定。
    • 从 Level 1 回到 Level 0 需要擦除整个 Flash。
8. WRP(Write Protection) [16:27]
  • 说明:写保护设置,指定哪些 Flash 扇区受写保护。
  • :每个位对应一个扇区,1 表示受保护,0 表示不受保护。
  • 应用:在固件更新或调试时防止误擦写关键代码区域。

image-20241129081300295

使用 FLASH_OPTCR 的关键操作
1. 解锁 OPTION Byte

在写入 FLASH_OPTCR 之前,必须解锁 Option Byte:

FLASH->OPTKEYR = 0x08192A3B; // 解锁密钥1
FLASH->OPTKEYR = 0x4C5D6E7F; // 解锁密钥2
2. 配置 FLASH_OPTCR

修改寄存器中对应的字段。例如,启用读保护并设置 BOR 为 Level 3:

FLASH->OPTCR |= FLASH_OPTCR_RDP_0;       // 设置 RDP 为 Level 1
FLASH->OPTCR &= ~FLASH_OPTCR_BOR_LEV;    // 清除 BOR 配置
FLASH->OPTCR |= FLASH_OPTCR_BOR_LEV_2;   // 设置 BOR 为 Level 3
3. 启动写入

完成配置后,启动 Option Byte 写入:

FLASH->OPTCR |= FLASH_OPTCR_OPTSTRT; // 启动写入
while (FLASH->SR & FLASH_SR_BSY);    // 等待操作完成
4. 锁定 OPTION Byte

写入完成后,重新锁定寄存器:

FLASH->OPTCR |= FLASH_OPTCR_OPTLOCK;

注意事项
  1. 配置不可逆性

    • 启用高强度读保护(RDP Level 2)后,Flash 数据无法访问且不可恢复。
    • 写保护或 RDP 配置的更改可能需要擦除整个芯片。
  2. 操作期间电源稳定

    • 写入 FLASH_OPTCR 时,如果电源中断可能导致芯片配置不完整,甚至不可用。
  3. 调试工具可能受限

    • 启用读保护或写保护后,调试接口(如 JTAG/SWD)可能受限或失效。

总结

FLASH_OPTCR 是 STM32F407 OPTION Byte 配置的核心寄存器,允许用户灵活控制芯片的关键功能。通过正确配置该寄存器,可以在安全性、电源稳定性和启动模式等方面大大增强 STM32 应用的可靠性。

第二章:OPTION Byte 的应用场景

1. 安全数据保护

在需要对数据高度保护的场景,例如密码存储或商业机密数据处理,启用读保护功能(ROP)可以有效防止未经授权的访问。

2. 启动模式选择

在嵌入式开发中,不同应用可能需要芯片从不同的存储介质启动。例如:

  • 开发阶段,可以选择从系统存储器启动,以便使用ST的内置Bootloader进行固件更新。
  • 生产阶段,可以配置从主Flash启动,以运行正式固件。
3. 固件更新保护

通过启用写保护功能(WP),开发者可以锁定Flash的某些区域,防止意外或恶意擦写,从而保护固件的完整性。

4. 电源稳定性管理

在电源波动较大的场景中,通过调整BOR电压等级,确保芯片在特定电压下安全复位,避免错误行为。


第三章:OPTION Byte 配置操作步骤

1. 确认配置需求

在更改OPTION Byte之前,确定需要配置的功能,例如启用读保护或调整BOR电压等级。

2. 解锁Flash控制器

在STM32F407中,OPTION Byte 存储在Flash中,因此需要解锁Flash控制器(Flash Control Register, FLASH_CR)以允许修改。

3. 修改OPTION Byte

通过操作特定寄存器(FLASH_OPTCR 或 FLASH_OPTCR1),将所需的配置值写入OPTION Byte。

4. 启动OPTION Byte 加载

配置完成后,触发重新加载以使更改生效。

5. 验证配置

通过读取相关寄存器,确认OPTION Byte的配置已成功应用。


第四章:代码实现(详细注释)Demo示例

以下代码展示如何配置STM32F407的OPTION Byte,以启用读保护和调整BOR电压等级。

#include "stm32f4xx.h"// 函数声明
void Flash_Unlock(void);
void Configure_OPTION_Bytes(void);int main(void) {// 解锁Flash控制器Flash_Unlock();// 配置OPTION ByteConfigure_OPTION_Bytes();while (1) {// 主循环}
}// 解锁Flash控制器函数
void Flash_Unlock(void) {if ((FLASH->CR & FLASH_CR_LOCK) != 0) {// 解锁KEY1FLASH->KEYR = 0x45670123;// 解锁KEY2FLASH->KEYR = 0xCDEF89AB;}
}// 配置OPTION Byte函数
void Configure_OPTION_Bytes(void) {// 解锁OPTION Byteif ((FLASH->OPTCR & FLASH_OPTCR_OPTLOCK) != 0) {FLASH->OPTKEYR = 0x08192A3B; // 解锁KEY1FLASH->OPTKEYR = 0x4C5D6E7F; // 解锁KEY2}// 修改OPTION Byte// 启用读保护(Level 1)FLASH->OPTCR |= FLASH_OPTCR_RDP_0; // 配置BOR电压为Level 3(最严格)FLASH->OPTCR &= ~FLASH_OPTCR_BOR_LEV; // 清除BOR配置FLASH->OPTCR |= FLASH_OPTCR_BOR_LEV_2; // 设置BOR为Level 3// 启动OPTION Byte写入FLASH->OPTCR |= FLASH_OPTCR_OPTSTRT;// 等待操作完成while ((FLASH->SR & FLASH_SR_BSY) != 0);// 锁定OPTION ByteFLASH->OPTCR |= FLASH_OPTCR_OPTLOCK;
}
代码解析
  1. 解锁Flash控制器和OPTION Byte

    • STM32的Flash和OPTION Byte均受锁机制保护,需先解锁后才能修改。
  2. 设置读保护和BOR等级

    • 使用 FLASH_OPTCR 寄存器进行配置。
    • 读保护(RDP)设为 Level 1(禁止非法读取)。
    • BOR电压配置为 Level 3(最高复位电压)。
  3. 触发写入并等待完成

    • 设置 OPTSTRT 位后,硬件会自动将更改写入Flash。

第五章:使用OPTION Byte的注意事项

1. 配置的不可逆性

某些配置(如读保护启用)具有不可逆性。一旦启用,降低保护等级可能需要擦除整个芯片数据。

2. 注意芯片的电源状态

在配置OPTION Byte时,确保芯片电源稳定,否则可能导致写入失败或数据损坏。

3. 调试时的风险

调试过程中,不建议随意更改OPTION Byte,尤其是启用读保护后,调试接口可能失效。

4. 启用写保护的影响

启用写保护后,程序固件的某些部分将无法更新。需提前规划好保护区域。


总结

STM32F407芯片的OPTION Byte功能强大,提供了多种关键配置选项。在实际应用中,开发者需要根据需求谨慎配置,以确保芯片的安全性和稳定性。通过本教程的详细步骤和代码示例,相信您已经掌握了如何在STM32F407上高效使用OPTION Byte功能,为嵌入式项目提供强有力的支持。

下面我们开始介绍BootLoader的使能读写保护命令。

第六章:0x58命令介绍–使能读写保护

在本篇文章,我们的主要是介绍0x58的命令,这个命令主要是在BootLoader中使能Flash Sector的读写保护。

通过上位机发送8 Byte的数据,其中第1 Byte为整个数据的长度,第2Byte为指令码,第3 Byte为写入要保护Sector段,第4 Byte是保护模式,1是写保护,2是读写保护,5-8 Byte为前4 Byte的CRC校验值,上位机通过串口UART发送给下位机,下位机回复地址是否写入成功的标志。

image-20241128220737877

下面是发送命令过程中上位机与BootLoader之间的交互。

image-20241114230607647

第七章:使能读写保护-0x58 命令BootLoader程序设计

代码逻辑和功能解释
1. bootloader_uart_read_data() 函数
void bootloader_uart_read_data(void) 
{ uint8_t rcv_len = 0; printmsg_Host("BL_DEBUG_MSG: Receive CMD\n\r"); // 调试信息:接收命令 while (1) { // 点亮LED,表示进入命令处理HAL_GPIO_WritePin(LED2_GPIO_Port, LED2_Pin, GPIO_PIN_RESET); // 清空接收缓冲区memset(bl_rx_buffer, 0, 200); // 步骤1:接收命令包的第一个字节(长度字段)HAL_UART_Receive(C_UART, bl_rx_buffer, 1, HAL_MAX_DELAY); rcv_len = bl_rx_buffer[0]; // 步骤2:根据长度字段接收剩余的命令包HAL_UART_Receive(C_UART, &bl_rx_buffer[1], rcv_len, HAL_MAX_DELAY); // 步骤3:根据命令代码调用对应的命令处理函数switch (bl_rx_buffer[1]) { case BL_GET_VER: bootloader_handle_getver_cmd(bl_rx_buffer); break; case BL_GET_HELP: bootloader_handle_gethelp_cmd(bl_rx_buffer); break; case BL_GET_CID: bootloader_handle_getcid_cmd(bl_rx_buffer); break; case BL_GET_RDP_STATUS: bootloader_handle_getrdp_cmd(bl_rx_buffer); break; case BL_GO_TO_ADDR: bootloader_handle_go_cmd(bl_rx_buffer); break; case BL_FLASH_ERASE: bootloader_handle_flash_erase_cmd(bl_rx_buffer); break; case BL_MEM_WRITE: bootloader_handle_mem_write_cmd(bl_rx_buffer); break; case BL_EN_RW_PROTECT: bootloader_handle_en_rw_protect(bl_rx_buffer); break; case BL_MEM_READ: bootloader_handle_mem_read(bl_rx_buffer); break; default: // 如果命令无效,打印调试信息printmsg("BL_DEBUG_MSG: Invalid command code received from host \n"); break; } } 
}

功能:

  • 这是引导程序的主要任务循环,负责接收主机通过 UART 发来的命令数据包并调用相应的处理函数。

逻辑解析:

  1. 命令接收:

    • 使用 HAL_UART_Receive 接收数据:
      • 首先接收数据包长度字段(bl_rx_buffer[0])。
      • 然后根据长度接收完整的命令数据包。
    • 通过命令码(bl_rx_buffer[1])解析当前命令。
  2. 命令分发:

    • 根据命令码,调用相应的处理函数:
      • BL_GET_VER 调用 bootloader_handle_getver_cmd()
      • BL_EN_RW_PROTECT 调用 bootloader_handle_en_rw_protect()
    • 如果命令码无效,则打印调试信息。

总结:
bootloader_uart_read_data() 是引导程序的任务调度中心,通过 UART 接收命令并分发到相应的处理逻辑。


2. bootloader_handle_en_rw_protect(uint8_t *pBuffer) 函数
void bootloader_handle_en_rw_protect(uint8_t *pBuffer) 
{ uint8_t status = 0x00; printmsg("BL_DEBUG_MSG: bootloader_handle_endis_rw_protect\n"); // 调试信息:处理读写保护命令 // 计算命令包的总长度uint32_t command_packet_len = bl_rx_buffer[0] + 1; // 提取主机发送的CRC32校验码uint32_t host_crc = *((uint32_t *)(bl_rx_buffer + command_packet_len - 4)); // 步骤1:校验CRC是否正确if (!bootloader_verify_crc(&bl_rx_buffer[0], command_packet_len - 4, host_crc)) { printmsg("BL_DEBUG_MSG: checksum success !!\n"); // CRC校验成功 // 发送ACK响应主机bootloader_send_ack(pBuffer[0], 1); // 步骤2:配置Flash扇区的读写保护status = configure_flash_sector_rw_protection(pBuffer[2], pBuffer[3], 0); printmsg("BL_DEBUG_MSG: flash erase status: %#x\n", status); // 打印保护配置状态 // 步骤3:将配置状态返回给主机bootloader_uart_write_data(&status, 1); } else { printmsg("BL_DEBUG_MSG: checksum fail !!\n"); // CRC校验失败 // 如果校验失败,发送NACKbootloader_send_nack(); } 
}

功能:

  • 解析和处理 BL_EN_RW_PROTECT 命令,用于对闪存扇区进行读写保护的启用。

逻辑解析:

  1. 解析命令数据包:

    • 计算数据包总长度:command_packet_len = bl_rx_buffer[0] + 1
    • 提取数据包中的 CRC 校验值(末尾 4 字节)。
  2. 校验数据完整性:

    • 调用 bootloader_verify_crc 对数据包进行 CRC 校验:
      • 如果校验成功:
        • 调用 bootloader_send_ack() 发送 ACK。
        • 调用 configure_flash_sector_rw_protection() 配置扇区保护。
        • 返回操作状态。
      • 如果校验失败:
        • 调用 bootloader_send_nack() 发送 NACK。
  3. 处理闪存保护配置:

    • 从数据包中解析 pBuffer[2]pBuffer[3],确定扇区选择和保护模式。

总结:
bootloader_handle_en_rw_protect() 负责解析 BL_EN_RW_PROTECT 命令,实现对闪存扇区的读写保护配置,并通过 CRC 校验确保命令数据的完整性。


3. configure_flash_sector_rw_protection(uint8_t sector_details, uint8_t protection_mode, uint8_t disable) 函数
uint8_t configure_flash_sector_rw_protection(uint8_t sector_details, uint8_t protection_mode, uint8_t disable)
{// Flash选项控制寄存器地址volatile uint32_t *pOPTCR = (uint32_t*) 0x40023C14;if(disable){// 禁用所有扇区的读写保护// 解锁选项字节配置HAL_FLASH_OB_Unlock();// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 清除OPTCR寄存器的第31位以禁用保护*pOPTCR &= ~(1 << 31);// 将所有与扇区相关的保护位设置为1(无保护)*pOPTCR |= (0xFF << 16);// 设置OPTSTRT位以启动选项字节编程*pOPTCR |= (1 << 1);// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 锁定选项字节配置HAL_FLASH_OB_Lock();return 0;}if(protection_mode == (uint8_t) 1){// 设置仅写保护// 解锁选项字节配置HAL_FLASH_OB_Unlock();// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 清除OPTCR寄存器的第31位*pOPTCR &= ~(1 << 31);// 设置写保护,修改相应扇区的位(sector_details指定了具体的扇区)*pOPTCR &= ~(sector_details << 16);// 设置OPTSTRT位以启动选项字节编程*pOPTCR |= (1 << 1);// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 锁定选项字节配置HAL_FLASH_OB_Lock();}else if (protection_mode == (uint8_t) 2){// 设置读写保护// 解锁选项字节配置HAL_FLASH_OB_Unlock();// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 设置OPTCR寄存器的第31位以启用读写保护*pOPTCR |= (1 << 31);// 配置选定扇区的读写保护*pOPTCR &= ~(0xff << 16);*pOPTCR |= (sector_details << 16);// 设置OPTSTRT位以启动选项字节编程*pOPTCR |= (1 << 1);// 等待Flash完成当前操作while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY) != RESET);// 锁定选项字节配置HAL_FLASH_OB_Lock();}return 0;
}

功能:

  • 通过修改 FLASH 选项控制寄存器(OPTCR)实现对闪存扇区的读写保护配置。

逻辑解析:

  1. 参数解析:

    • sector_details:扇区选择(通过每个位表示不同扇区)。
    • protection_mode:保护模式:
      • 1 表示仅写保护。
      • 2 表示读写保护。
    • disable:是否禁用所有保护。
  2. 禁用保护:

    • 解锁选项字节(HAL_FLASH_OB_Unlock())。
    • 清除保护位:
      • 清除 OPTCR 寄存器的第 31 位。
      • 设置扇区保护位为默认值(所有扇区解除保护)。
    • 启动保护配置(设置 OPTSTRT 位)。
    • 等待操作完成(检查 FLASH_FLAG_BSY 标志)。
  3. 写保护:

    • 解锁选项字节。
    • 清除第 31 位,表示启用写保护模式。
    • 修改目标扇区的保护位。
    • 设置 OPTSTRT 位,启动保护配置。
  4. 读写保护:

    • 解锁选项字节。
    • 设置第 31 位,表示启用读写保护模式。
    • 修改目标扇区的保护位。
    • 设置 OPTSTRT 位,启动保护配置。

总结:
configure_flash_sector_rw_protection() 实现了对闪存扇区保护配置的底层操作,包括禁用保护、写保护和读写保护的具体实现,直接操控 STM32 的 FLASH 寄存器。


综合总结
  1. 任务调度:
    • bootloader_uart_read_data() 是主任务函数,负责接收主机命令并调用对应处理逻辑。
  2. 命令解析:
    • bootloader_handle_en_rw_protect() 是特定命令处理函数,用于启用闪存扇区保护,包含数据解析、CRC 校验及状态返回。
  3. 硬件操作:
    • configure_flash_sector_rw_protection() 是底层函数,通过直接操作 FLASH 控制寄存器完成保护配置。

通过以上函数协同工作,STM32 引导程序能够接收主机命令并对闪存扇区实现灵活的保护管理。

第八章:BootLoader实战操作

下面是上位机的命令菜单,通过在终端调用Python脚本,然后在终端输入下位机连接的串口号,即可进入命令界面,目前可支持如下命令:

image-20240713104433991

下面选择命令9,输入要保护的Flash的段,向下位机发送信息。

image-20241201090151204

下面判断Flash保护是否成功,发送命令11,读出保护状态,发现Secotr 3,4,5处于写保护状态Write Protection。

image-20241201090320570

下面输入命令13,关闭所有的段保护

image-20241201090430382

在一次判断段保护状态,输入命令11,发现读写保护状态,发现所有保护状态处于No Protection,发现之前的命令13成功。

image-20241201090549140

第九章. 系列文章

STM32 BootLoader 刷新项目 (一) STM32CubeMX UART串口通信工程搭建

STM32 BootLoader 刷新项目 (二) 方案介绍

STM32 BootLoader 刷新项目 (三) 程序框架搭建及刷新演示

STM32 BootLoader 刷新项目 (四) 通信协议

STM32 BootLoader 刷新项目 (五) 获取软件版本号-命令0x51

STM32 BootLoader 刷新项目 (六) 获取帮助-命令0x52

STM32 BootLoader 刷新项目 (七) 获取芯片ID-0x53

STM32 BootLoader 刷新项目 (八) 读取Flash保护ROP-0x54

STM32 BootLoader 刷新项目 (九) 跳转指定地址-命令0x55

[STM32 BootLoader 刷新项目 (十) Flash擦除-命令0x56](STM32 BootLoader 刷新项目 (十) Flash擦除-命令0x56-CSDN博客)

STM32 BootLoader 刷新项目 (十一) Flash写操作-命令0x57


http://www.ppmy.cn/news/1551760.html

相关文章

xiaolin coding 图解网络笔记——IP 篇

1. IP 基本认识 IP 在 TCP/IP 模型中的第三层&#xff0c;网络层。网络层的主要作用是&#xff1a;实现主机与主机之间的通信&#xff0c;也叫点对点&#xff08;end to end&#xff09;通信。 MAC&#xff08;数据链路层&#xff09;的作用是【直连】的两个设备之间的通信&a…

MFC图形函数学习12——位图操作函数

位图即后缀为bmp的图形文件&#xff0c;MFC中有专门的函数处理这种格式的图形文件。这些函数只能处理作为MFC资源的bmp图&#xff0c;没有操作文件的功能&#xff0c;受限较多&#xff0c;一般常作为程序窗口界面图片、显示背景图片等用途。有关位图操作的步骤、相关函数等介绍…

预训练模型与ChatGPT:自然语言处理的革新与前景

目录 一、ChatGPT整体背景认知 &#xff08;一&#xff09;ChatGPT引起关注的原因 &#xff08;二&#xff09;与其他公司的竞争情况 二、NLP学习范式的发展 &#xff08;一&#xff09;规则和机器学习时期 &#xff08;二&#xff09;基于神经网络的监督学习时期 &…

手机上怎么拍证件照,操作简单且尺寸颜色标准的方法

在数字化时代&#xff0c;手机已成为我们日常生活中不可或缺的一部分。它不仅是通讯工具&#xff0c;更是我们拍摄证件照的便捷利器。然而&#xff0c;目前证件照制作工具鱼龙混杂&#xff0c;很多打着免费名号的拍照软件背后却存在着泄漏用户信息、照片制作不规范导致无法使用…

PDF本地显示正常,但是上传系统后,预览显示乱码

问题&#xff1a;PDF本地显示正常&#xff0c;但是上传系统后&#xff0c;预览显示乱码 原因&#xff1a;猜测可能是某些字体或资源的缺失&#xff0c;导致PDF在线上预览显示乱码。经过搜索找到原因&#xff1a;原因是PDF缺少一些嵌入字体1。 解决思路&#xff1a; 使用Adobe…

神经网络中的神经元是什么?

定义 在神经网络中&#xff0c;神经元是基本的计算单元。它模拟了生物神经元的基本功能&#xff0c;接收来自其他神经元或外部输入的信号&#xff0c;对这些信号进行处理&#xff0c;并将处理后的结果输出给其他神经元。从数学和计算的角度来看&#xff0c;神经元是一个多输入单…

统计学 | bootstrap 和 permutation test 的区别与联系?

如果我有两组数字&#xff0c;想做统计检验其差异。 但是样本太小&#xff0c;不确定原始分布&#xff0c;只能做非参数检验。 0. 准备数据集 a1, a2 之间不显著&#xff0c;t test p0.11 a1&#xff0c;a2B 之间显著&#xff0c;t test p0.023 a01:20; a0 a1a0[1:7]; a1 a2…

服务器实现ssh证书登录

1.生成公钥和私钥 ssh-keygen -t rsa 提示默认生成位置为/root/.ssh/id_rsa ,直接回车。(也可以自己修改) 提示输入证书的密码&#xff0c;可以留空&#xff0c;建议输入&#xff0c;如果输入了&#xff0c;则需要再次确认&#xff0c;记住这个证书密码&#xff08;证书再加…