Add support for stm32h7b3xx MCU's flash
This commit is contained in:
parent
81ff16c675
commit
663bf4d968
@ -70,7 +70,8 @@
|
||||
defined (CONFIG_ARCH_CHIP_STM32H753II) || \
|
||||
defined (CONFIG_ARCH_CHIP_STM32H753VI) || \
|
||||
defined (CONFIG_ARCH_CHIP_STM32H753XI) || \
|
||||
defined (CONFIG_ARCH_CHIP_STM32H753ZI)
|
||||
defined (CONFIG_ARCH_CHIP_STM32H753ZI) || \
|
||||
defined (CONFIG_ARCH_CHIP_STM32H7B3LI)
|
||||
#elif defined(CONFIG_ARCH_CHIP_STM32H747XI)
|
||||
#else
|
||||
# error STM32 H7 chip not identified
|
||||
@ -116,6 +117,60 @@
|
||||
# error CONFIG_STM32H7_IO_CONFIG_x Not Set
|
||||
# endif
|
||||
|
||||
# define STM32H7_NDMA (4) /* (4) DMA1, DMA2, BDMA and MDMA */
|
||||
# define STM32H7_NADC (3) /* (3) ADC1-3*/
|
||||
# define STM32H7_NDAC (2) /* (2) DAC1-2*/
|
||||
# define STM32H7_NCMP (2) /* (2) ultra-low power comparators */
|
||||
# define STM32H7_NPGA (2) /* (2) Operational amplifiers: OPAMP */
|
||||
# define STM32H7_NDFSDM (1) /* (1) digital filters for sigma delta modulator */
|
||||
# define STM32H7_NUSART (4) /* (4) USART1-3, 6 */
|
||||
# define STM32H7_NSPI (6) /* (6) SPI1-6 */
|
||||
# define STM32H7_NI2S (3) /* (3) I2S1-3 */
|
||||
# define STM32H7_NUART (4) /* (4) UART4-5, 7-8 */
|
||||
# define STM32H7_NI2C (4) /* (4) I2C1-4 */
|
||||
# define STM32H7_NSAI (4) /* (4) SAI1-4*/
|
||||
# define STM32H7_NCAN (2) /* (2) CAN1-2 */
|
||||
# define STM32H7_NSDIO (2) /* (2) SDIO */
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
/* Memory */
|
||||
|
||||
# define STM32H7_SRAM_SIZE (1024*1024) /* 1024Kb SRAM on AXI bus Matrix (D1) */
|
||||
# define STM32H7_SRAM1_SIZE (64*1024) /* 64Kb SRAM1 on AHB bus Matrix (D2) */
|
||||
# define STM32H7_SRAM2_SIZE (64*1024) /* 64Kb SRAM2 on AHB bus Matrix (D2) */
|
||||
# define STM32H7_SRAM3_SIZE (0*1024) /* No SRAM3 on AHB bus Matrix (D2) */
|
||||
# define STM32H7_SRAM123_SIZE (128*1024) /* 128Kb SRAM123 on AHB bus Matrix (D2) */
|
||||
# define STM32H7_SRAM4_SIZE (32*1024) /* 32Kb SRAM2 on AHB bus Matrix (D3) */
|
||||
# if defined(CONFIG_ARMV7M_HAVE_DTCM)
|
||||
# define STM32H7_DTCM_SRAM_SIZE (128*1024) /* 128Kb DTCM SRAM on TCM interface */
|
||||
# else
|
||||
# define STM32H7_DTCM_SRAM_SIZE (0) /* No DTCM SRAM on TCM interface */
|
||||
# endif
|
||||
# if defined(CONFIG_ARMV7M_HAVE_ITCM)
|
||||
# define STM32H7_ITCM_SRAM_SIZE (64*1024) /* 64b ITCM SRAM on TCM interface */
|
||||
# else
|
||||
# define STM32H7_ITCM_SRAM_SIZE (0) /* No ITCM SRAM on TCM interface */
|
||||
# endif
|
||||
|
||||
/* Peripherals */
|
||||
|
||||
# if defined(CONFIG_STM32H7_IO_CONFIG_A)
|
||||
# define STM32H7_NGPIO (10) /* GPIOA-GPIOJ */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_B)
|
||||
# define STM32H7_NGPIO (11) /* GPIOA-GPIOK */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_I)
|
||||
# define STM32H7_NGPIO (9) /* GPIOA-GPIOI */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_L)
|
||||
# define STM32H7_NGPIO (11) /* GPIOA-GPIOK */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_V)
|
||||
# define STM32H7_NGPIO (8) /* GPIOA-GPIOH, missing GPIOF-GPIOG */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_X)
|
||||
# define STM32H7_NGPIO (11) /* GPIOA-GPIOK */
|
||||
# elif defined(CONFIG_STM32H7_IO_CONFIG_Z)
|
||||
# define STM32H7_NGPIO (8) /* GPIOA-GPIOH */
|
||||
# else
|
||||
# error CONFIG_STM32H7_IO_CONFIG_x Not Set
|
||||
# endif
|
||||
|
||||
# define STM32H7_NDMA (4) /* (4) DMA1, DMA2, BDMA and MDMA */
|
||||
# define STM32H7_NADC (3) /* (3) ADC1-3*/
|
||||
# define STM32H7_NDAC (2) /* (2) DAC1-2*/
|
||||
|
@ -69,6 +69,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include <arch/stm32h7/stm32h7x3xx_irq.h>
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include <arch/stm32h7/stm32h7x3xx_irq.h>
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include <arch/stm32h7/stm32h7x7xx_irq.h>
|
||||
#else
|
||||
|
@ -215,8 +215,29 @@ config ARCH_CHIP_STM32H753ZI
|
||||
STM32 H7 Cortex M7, 2048 Kb FLASH, 1024K Kb SRAM,
|
||||
with cryptographic accelerator, LQFP144
|
||||
|
||||
config ARCH_CHIP_STM32H7B3LI
|
||||
bool "STM32H7B3LI"
|
||||
select STM32H7_STM32H7B3XX
|
||||
select STM32H7_FLASH_CONFIG_I
|
||||
select STM32H7_IO_CONFIG_L
|
||||
select STM32H7_HAVE_FDCAN1
|
||||
select STM32H7_HAVE_FDCAN2
|
||||
select STM32H7_HAVE_SMPS
|
||||
---help---
|
||||
STM32 H7 Cortex M7, 2048 Kb FLASH, 1376 Kb SRAM,
|
||||
with cryptographic accelerator, TFBGA225
|
||||
|
||||
endchoice # STM32 H7 Chip Selection
|
||||
|
||||
config STM32H7_HAVE_SMPS
|
||||
bool
|
||||
default n
|
||||
|
||||
config STM32H7_PWR_DIRECT_SMPS_SUPPLY
|
||||
bool "Use direct SMPS supply mode"
|
||||
depends on STM32H7_HAVE_SMPS
|
||||
default n
|
||||
|
||||
config STM32H7_IO_CONFIG_A
|
||||
bool
|
||||
default n
|
||||
@ -229,6 +250,10 @@ config STM32H7_IO_CONFIG_I
|
||||
bool
|
||||
default n
|
||||
|
||||
config STM32H7_IO_CONFIG_L
|
||||
bool
|
||||
default n
|
||||
|
||||
config STM32H7_IO_CONFIG_V
|
||||
bool
|
||||
default n
|
||||
@ -258,6 +283,23 @@ config STM32H7_STM32H7X3XX
|
||||
select STM32H7_HAVE_SPI5 if !STM32H7_IO_CONFIG_V
|
||||
select STM32H7_HAVE_SPI6
|
||||
|
||||
config STM32H7_STM32H7B3XX
|
||||
bool
|
||||
default n
|
||||
select ARCH_HAVE_FPU
|
||||
select ARCH_HAVE_DPFPU
|
||||
select ARMV7M_HAVE_ICACHE
|
||||
select ARMV7M_HAVE_DCACHE
|
||||
select ARMV7M_HAVE_ITCM
|
||||
select ARMV7M_HAVE_DTCM
|
||||
select STM32H7_HAVE_ETHERNET
|
||||
select STM32H7_HAVE_FMC
|
||||
select STM32H7_HAVE_GPIOF if !STM32H7_IO_CONFIG_V
|
||||
select STM32H7_HAVE_GPIOG if !STM32H7_IO_CONFIG_V
|
||||
select STM32H7_HAVE_SPI4
|
||||
select STM32H7_HAVE_SPI5 if !STM32H7_IO_CONFIG_V
|
||||
select STM32H7_HAVE_SPI6
|
||||
|
||||
config STM32H7_STM32H7X7XX
|
||||
bool
|
||||
default n
|
||||
|
@ -203,6 +203,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_dmamux.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_dmamux.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_dmamux.h"
|
||||
#else
|
||||
|
@ -31,7 +31,7 @@
|
||||
* families
|
||||
*/
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -674,5 +674,5 @@ struct eth_desc_s
|
||||
****************************************************************************/
|
||||
|
||||
#endif /* __ASSEMBLY__ */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32_ETHERNET_H */
|
||||
|
@ -33,7 +33,7 @@
|
||||
* families
|
||||
*/
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -237,5 +237,5 @@
|
||||
#define EXTI_EVENT_ETHWKUP 86 /* Ethernet wakeup */
|
||||
#define EXTI_EVENT_HSECSS 87 /* HSECSS interrupt */
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32_EXTI_H */
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_flash.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7b3xx_flash.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_flash.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_gpio.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_gpio.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_gpio.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_i2c.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_i2c.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_i2c.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_memorymap.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_memorymap.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_memorymap.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_pinmap.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_pinmap.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_pinmap.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_pwr.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_pwr.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_pwr.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_rcc.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_rcc.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_rcc.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "stm32h7x3xx_sdmmc.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "stm32h7x3xx_sdmmc.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "stm32h7x3xx_sdmmc.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_spi.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_spi.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_spi.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_syscfg.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_syscfg.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_syscfg.h"
|
||||
#else
|
||||
|
@ -30,6 +30,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "hardware/stm32h7x3xx_uart.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "hardware/stm32h7x3xx_uart.h"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "hardware/stm32h7x3xx_uart.h"
|
||||
#else
|
||||
|
298
arch/arm/src/stm32h7/hardware/stm32h7b3xx_flash.h
Normal file
298
arch/arm/src/stm32h7/hardware/stm32h7b3xx_flash.h
Normal file
@ -0,0 +1,298 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/stm32h7/hardware/stm32h7b3xx_flash.h
|
||||
*
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership. The
|
||||
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the
|
||||
* License. You may obtain a copy of the License at
|
||||
*
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
#ifndef __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7B3XX_FLASH_H
|
||||
#define __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7B3XX_FLASH_H
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
|
||||
/* Register Offsets *********************************************************/
|
||||
|
||||
#define STM32_FLASH_ACR_OFFSET 0x0000 /* Access control register */
|
||||
#define STM32_FLASH_KEYR_OFFSET 0x0004 /* Key register for bank 1 */
|
||||
#define STM32_FLASH_OPTKEYR_OFFSET 0x0008 /* Option key register */
|
||||
#define STM32_FLASH_CR_OFFSET 0x000c /* Control register for bank 1 */
|
||||
#define STM32_FLASH_SR_OFFSET 0x0010 /* Status register for bank 1 */
|
||||
#define STM32_FLASH_CCR_OFFSET 0x0014 /* Clear control register for bank 1 */
|
||||
#define STM32_FLASH_OPTCR_OFFSET 0x0018 /* Option control register */
|
||||
#define STM32_FLASH_OPTSR_CUR_OFFSET 0x001c /* Option status register (CUR) */
|
||||
#define STM32_FLASH_OPTSR_PRG_OFFSET 0x0020 /* Option status register (PRG) */
|
||||
#define STM32_FLASH_OPTCCR_OFFSET 0x0024 /* Option clear control register */
|
||||
#define STM32_FLASH_PRAR_CUR_OFFSET 0x0028 /* Protection address for bank 1 */
|
||||
#define STM32_FLASH_PRAR_PRG_OFFSET 0x002C /* Protection address for bank 1 */
|
||||
#define STM32_FLASH_SCAR_CUR_OFFSET 0x0030 /* Secure address for bank 1 (CUR) */
|
||||
#define STM32_FLASH_SCAR_PRG_OFFSET 0x0034 /* Secure address for bank 1 (PRG) */
|
||||
#define STM32_FLASH_WPSN_CURR_OFFSET 0x0038 /* Write sector protection for bank 1 (CUR) */
|
||||
#define STM32_FLASH_WPSN_PRGR_OFFSET 0x003C /* Write sector protection for bank 1 (PRG) */
|
||||
#define STM32_FLASH_BOOT_CUR_OFFSET 0x0040 /* Boot address (CUR) */
|
||||
#define STM32_FLASH_BOOT_PRGR_OFFSET 0x0044 /* Boot address (PRG) */
|
||||
#define STM32_FLASH_CRCCR_OFFSET 0x0050 /* CRC control register for bank 1 */
|
||||
#define STM32_FLASH_CRCSADDR_OFFSET 0x0054 /* CRC start address register for bank 1 */
|
||||
#define STM32_FLASH_CRCEADDR_OFFSET 0x0058 /* CRC end address register for bank 1 */
|
||||
#define STM32_FLASH_CRCDATAR_OFFSET 0x005C /* CRC data register */
|
||||
#define STM32_FLASH_ECC_FAR_OFFSET 0x0060 /* ECC fail address register for bank 1 */
|
||||
#define STM32_FLASH_OTPBL_CUR_OFFSET 0x0068 /* current values of option bits */
|
||||
#define STM32_FLASH_OTPBL_PRG_OFFSET 0x006C /* program values in option bits */
|
||||
|
||||
#define STM32_FLASH_BANK1_OFFSET 0x0000 /* Bank 1 registers offset */
|
||||
#define STM32_FLASH_BANK2_OFFSET 0x0100 /* Bank 2 registers offset */
|
||||
|
||||
/* Register Addresses *******************************************************/
|
||||
|
||||
#define STM32_FLASH_ACR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_ACR_OFFSET)
|
||||
#define STM32_FLASH_KEYR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_KEYR1_OFFSET)
|
||||
#define STM32_FLASH_OPTKEYR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OPTKEYR_OFFSET)
|
||||
#define STM32_FLASH_CR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CR1_OFFSET)
|
||||
#define STM32_FLASH_SR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_SR1_OFFSET)
|
||||
#define STM32_FLASH_CCR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CCR1_OFFSET)
|
||||
#define STM32_FLASH_OPTCR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OPTCR_OFFSET)
|
||||
#define STM32_FLASH_OPTSR_CUR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OPTSR_CUR_OFFSET)
|
||||
#define STM32_FLASH_OPTSR_PRG (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OPTSR_PRG_OFFSET)
|
||||
#define STM32_FLASH_OPTCCR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OPTCCR_OFFSET)
|
||||
#define STM32_FLASH_PRAR_CUR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_PRAR_CUR1_OFFSET)
|
||||
#define STM32_FLASH_PRAR_PRG1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_PRAR_PRG1_OFFSET)
|
||||
#define STM32_FLASH_SCAR_CUR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_SCAR_CUR1_OFFSET)
|
||||
#define STM32_FLASH_SCAR_PRG1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_SCAR_PRG1_OFFSET)
|
||||
#define STM32_FLASH_WPSN_CUR1R (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_WPSN_CUR1R_OFFSET)
|
||||
#define STM32_FLASH_WPSN_PRG1R (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_WPSN_PRG1R_OFFSET)
|
||||
#define STM32_FLASH_BOOT_CUR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_BOOT_CUR_OFFSET)
|
||||
#define STM32_FLASH_BOOT_PRGR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_BOOT_PRGR_OFFSET)
|
||||
#define STM32_FLASH_CRCCR1 (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CRCCR1_OFFSET)
|
||||
#define STM32_FLASH_CRCSADD1R (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CRCSADD1R_OFFSET)
|
||||
#define STM32_FLASH_CRCEADD1R (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CRCEADD1R_OFFSET)
|
||||
#define STM32_FLASH_CRCDATAR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_CRCDATAR_OFFSET)
|
||||
#define STM32_FLASH_ECC_FA1R (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_ECC_FA1R_OFFSET)
|
||||
#define STM32_FLASH_OTPBL_CUR (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OTPBL_CUR_OFFSET)
|
||||
#define STM32_FLASH_OTPBL_PRG (STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET + STM32_FLASH_OTPBL_PRG_OFFSET)
|
||||
|
||||
#define STM32_FLASH_KEYR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_KEYR2_OFFSET)
|
||||
#define STM32_FLASH_CR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_CR2_OFFSET)
|
||||
#define STM32_FLASH_SR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_SR2_OFFSET)
|
||||
#define STM32_FLASH_CCR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_CCR2_OFFSET)
|
||||
#define STM32_FLASH_PRAR_CUR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_PRAR_CUR2_OFFSET)
|
||||
#define STM32_FLASH_PRAR_PRG2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_PRAR_PRG2_OFFSET)
|
||||
#define STM32_FLASH_SCAR_CUR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_SCAR_CUR2_OFFSET)
|
||||
#define STM32_FLASH_SCAR_PRG2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_SCAR_PRG2_OFFSET)
|
||||
#define STM32_FLASH_WPSN_CUR2R (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_WPSN_CUR2R_OFFSET)
|
||||
#define STM32_FLASH_WPSN_PRG2R (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_WPSN_PRG2R_OFFSET)
|
||||
#define STM32_FLASH_CRCCR2 (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_CRCCR2_OFFSET)
|
||||
#define STM32_FLASH_CRCSADD2R (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_CRCSADD2R_OFFSET)
|
||||
#define STM32_FLASH_CRCEADD2R (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_CRCEADD2R_OFFSET)
|
||||
#define STM32_FLASH_ECC_FA2R (STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET + STM32_FLASH_ECC_FA2R_OFFSET)
|
||||
|
||||
/* Register Bitfield Definitions ********************************************/
|
||||
|
||||
/* Flash Access Control Register (ACR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_ACR_LATENCY_SHIFT (0) /* Bits 0-3: Latency */
|
||||
#define FLASH_ACR_LATENCY_MASK (15 << FLASH_ACR_LATENCY_SHIFT)
|
||||
# define FLASH_ACR_LATENCY(n) ((n) << FLASH_ACR_LATENCY_SHIFT) /* n wait states */
|
||||
# define FLASH_ACR_LATENCY_0 (0 << FLASH_ACR_LATENCY_SHIFT) /* 0000: Zero wait states */
|
||||
# define FLASH_ACR_LATENCY_1 (1 << FLASH_ACR_LATENCY_SHIFT) /* 0001: One wait state */
|
||||
# define FLASH_ACR_LATENCY_2 (2 << FLASH_ACR_LATENCY_SHIFT) /* 0010: Two wait states */
|
||||
# define FLASH_ACR_LATENCY_3 (3 << FLASH_ACR_LATENCY_SHIFT) /* 0011: Three wait states */
|
||||
# define FLASH_ACR_LATENCY_4 (4 << FLASH_ACR_LATENCY_SHIFT) /* 0100: Four wait states */
|
||||
# define FLASH_ACR_LATENCY_5 (5 << FLASH_ACR_LATENCY_SHIFT) /* 0101: Five wait states */
|
||||
# define FLASH_ACR_LATENCY_6 (6 << FLASH_ACR_LATENCY_SHIFT) /* 0110: Six wait states */
|
||||
#define FLASH_ACR_WRHIGHFREQ_SHIFT (4) /* Bitd 4-5: Flash signal delay */
|
||||
#define FLASH_ACR_WRHIGHFREQ_MASK (3 << FLASH_ACR_WRHIGHFREQ_SHIFT)
|
||||
# define FLASH_ACR_WRHIGHFREQ(n) ((n) << FLASH_ACR_WRHIGHFREQ_SHIFT)
|
||||
|
||||
/* Flash Control Register (CR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_CR_LOCK (1 << 0) /* Bit 0: Lock */
|
||||
#define FLASH_CR_PG (1 << 1) /* Bit 1: Programming */
|
||||
#define FLASH_CR_SER (1 << 2) /* Bit 2: Sector erase */
|
||||
#define FLASH_CR_BER (1 << 3) /* Bit 3: Bank erase */
|
||||
#define FLASH_CR_FW (1 << 4) /* Bit 4: Force write */
|
||||
#define FLASH_CR_START (1 << 5) /* Bit 5: Erase start */
|
||||
#define FLASH_CR_SSN_SHIFT (6) /* Bits 6-12: Sector number */
|
||||
#define FLASH_CR_SSN_MASK (0x7f << FLASH_CR_SSN_SHIFT) /* Used to clear FLASH_CR_SSN bits */
|
||||
|
||||
# define FLASH_CR_SSN(n) ((uint32_t)((n) & 0x7f) << FLASH_CR_SSN_SHIFT) /* Sector n, n=0..127 */
|
||||
|
||||
#define FLASH_CR_CRCEN (1 << 15) /* Bit 15: CRC control enable */
|
||||
#define FLASH_CR_EOPIE (1 << 16) /* Bit 16: End-of-program interrupt enable */
|
||||
#define FLASH_CR_WRPERRIE (1 << 17) /* Bit 17: Write protection error interrupt enable */
|
||||
#define FLASH_CR_PGSERRIE (1 << 18) /* Bit 18: Programming sequence error interrupt enable */
|
||||
#define FLASH_CR_STRBERRIE (1 << 19) /* Bit 19: Strobe error interrupt enable */
|
||||
#define FLASH_CR_INCERRIE (1 << 21) /* Bit 21: Inconsistency error interrupt enable */
|
||||
#define FLASH_CR_RDPERRIE (1 << 23) /* Bit 23: Read protection error interrupt enable */
|
||||
#define FLASH_CR_RDSERRIE (1 << 24) /* Bit 24: Secure error interrupt enable */
|
||||
#define FLASH_CR_SNECCERRIE (1 << 25) /* Bit 25: ECC single correction error interrupt enable */
|
||||
#define FLASH_CR_DBECCERRIE (1 << 26) /* Bit 26: ECC double detection error interrupt enable */
|
||||
#define FLASH_CR_CRCENDIE (1 << 27) /* Bit 27: CRC end of calculation interrupt enable */
|
||||
#define FLASH_CR_CRCRDERRIE (1 << 28) /* Bit 28: CRC read error interrupt enable bit */
|
||||
|
||||
/* Flash Status Register (SR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_SR_BSY (1 << 0) /* Bit 0: Busy */
|
||||
#define FLASH_SR_WBNE (1 << 1) /* Bit 1: write buffer not empty */
|
||||
#define FLASH_SR_QW (1 << 2) /* Bit 2: wait queue flag */
|
||||
#define FLASH_SR_CRCBUSY (1 << 3) /* Bit 3: CRC busy flag */
|
||||
/* Bits 4-15: Reserved */
|
||||
#define FLASH_SR_EOP (1 << 16) /* Bit 16: End of program */
|
||||
#define FLASH_SR_WRPERR (1 << 17) /* Bit 17: Write protection error */
|
||||
#define FLASH_SR_PGSERR (1 << 18) /* Bit 18: Programming sequence error */
|
||||
#define FLASH_SR_STRBERR (1 << 19) /* Bit 19: Strobe error */
|
||||
/* Bit 20: Reserved */
|
||||
#define FLASH_SR_INCERR (1 << 21) /* Bit 21: Inconsistency error */
|
||||
#define FLASH_SR_RDPERR (1 << 23) /* Bit 23: Read protection error */
|
||||
#define FLASH_SR_RDSERR (1 << 24) /* Bit 24: Secure error */
|
||||
#define FLASH_SR_SNECCERR (1 << 25) /* Bit 25: ECC single error */
|
||||
#define FLASH_SR_DBECCERR (1 << 26) /* Bit 26: ECC double detection error */
|
||||
#define FLASH_SR_CRCEND (1 << 27) /* Bit 27: CRC end of calculation */
|
||||
#define FLASH_SR_CRCRDERR (1 << 28) /* Bit 28: CRC read error flag */
|
||||
|
||||
/* Flash Clear control register Bank 1 or 2 */
|
||||
|
||||
#define FLASH_CLR_EOP (1 << 16) /* Bit 16: Clear end of program */
|
||||
#define FLASH_CLR_WRPERR (1 << 17) /* Bit 17: Clear write protection error */
|
||||
#define FLASH_CLR_PGSERR (1 << 18) /* Bit 18: Clear programming sequence error */
|
||||
#define FLASH_CLR_STRBERR (1 << 19) /* Bit 19: Clear strobe error */
|
||||
/* Bit 20: Reserved */
|
||||
#define FLASH_CLR_INCERR (1 << 21) /* Bit 21: Clear inconsistency error */
|
||||
#define FLASH_CLR_RDPERR (1 << 23) /* Bit 23: Clear read protection error */
|
||||
#define FLASH_CLR_RDSERR (1 << 24) /* Bit 24: Clear secure error */
|
||||
#define FLASH_CLR_SNECCERR (1 << 25) /* Bit 25: Clear ECC single error */
|
||||
#define FLASH_CLR_DBECCERR (1 << 26) /* Bit 26: Clear ECC double detection error */
|
||||
#define FLASH_CLR_CRCEND (1 << 27) /* Bit 27: Clear CRC end of calculation */
|
||||
#define FLASH_CLR_CRCRDERR (1 << 28) /* Bit 28: Clear CRC read error flag */
|
||||
|
||||
/* Flash Option Control Register (OPTCR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_OPTCR_OPTLOCK (1 << 0) /* Bit 0: Option lock */
|
||||
#define FLASH_OPTCR_OPTSTRT (1 << 1) /* Bit 1: Option start */
|
||||
/* Bits 2-3: Reserved */
|
||||
#define FLASH_OPTCR_MER (1 << 4) /* Bit 4: Mass erase */
|
||||
#define FLASH_OPTCR_PGOTP (1 << 5) /* Bit 5: Enable OTP write */
|
||||
/* Bits 6-29: Reserved */
|
||||
#define FLASH_OPTCR_CHANGEERRIE (1 << 30) /* Bit 30: Option byte change error interrupt enable */
|
||||
#define FLASH_OPTCR_SWAPBANK (1 << 31) /* Bit 31: Bank swapping */
|
||||
|
||||
/* Flash Option Status Register (OPTSR) */
|
||||
|
||||
#define FLASH_OPTSR_BUSYV (1 << 0) /* Bit 0: Option byte change busy */
|
||||
/* Bit 1: Reserved */
|
||||
#define FLASH_OPTSR_BORLEV_SHIFT (2) /* Bits 2-3: Brownout level option */
|
||||
#define FLASH_OPTSR_BORLEV_MASK (3 << FLASH_OPTSR_BORLEV_SHIFT)
|
||||
# define FLASH_OPTSR_BORLEV_0 (0 << FLASH_OPTSR_BORLEV_SHIFT)
|
||||
# define FLASH_OPTSR_BORLEV_1 (1 << FLASH_OPTSR_BORLEV_SHIFT)
|
||||
# define FLASH_OPTSR_BORLEV_2 (2 << FLASH_OPTSR_BORLEV_SHIFT)
|
||||
# define FLASH_OPTSR_BORLEV_3 (3 << FLASH_OPTSR_BORLEV_SHIFT)
|
||||
#define FLASH_OPTSR_IWDGSW (1 << 4) /* Bit 4: IWDG control mode */
|
||||
/* Bit 5: Reserved */
|
||||
#define FLASH_OPTSR_NRSTSTOP (1 << 6) /* Bit 6: DStop entry reset */
|
||||
#define FLASH_OPTSR_NRSTSTDY (1 << 7) /* Bit 7: DStandby entry reset */
|
||||
#define FLASH_OPTSR_RDP_SHIFT (8) /* Bits 8-15: Readout protection level */
|
||||
#define FLASH_OPTSR_RDP_MASK (0xff << FLASH_OPTSR_RDP_SHIFT)
|
||||
# define FLASH_OPTSR_RDP(n) ((uint32_t)(n) << FLASH_OPTSR_RDP_SHIFT)
|
||||
#define FLASH_OPTSR_VDDMMCHSLV (1 << 16) /* Bit 16: high-speed at low-voltage status bit */
|
||||
#define FLASH_OPTSR_IWDGFZSTOP (1 << 17) /* Bit 17: IWDG Stop mode freeze */
|
||||
#define FLASH_OPTSR_IWDGFZSTBY (1 << 18) /* Bit 18: IWDG Standby mode freeze */
|
||||
#define FLASH_OPTSR_STRAMSIZE_SHIFT (19) /* Bits 19-20: ST RAM size */
|
||||
#define FLASH_OPTSR_STRAMSIZE_MASK (3 << FLASH_OPTSR_STRAMSIZE_SHIFT)
|
||||
# define FLASH_OPTSR_STRAMSIZE_2 (0 << FLASH_OPTSR_STRAMSIZE_SHIFT)
|
||||
# define FLASH_OPTSR_STRAMSIZE_4 (1 << FLASH_OPTSR_STRAMSIZE_SHIFT)
|
||||
# define FLASH_OPTSR_STRAMSIZE_8 (2 << FLASH_OPTSR_STRAMSIZE_SHIFT)
|
||||
# define FLASH_OPTSR_STRAMSIZE_16 (3 << FLASH_OPTSR_STRAMSIZE_SHIFT)
|
||||
#define FLASH_OPTSR_SECURITY (1 << 21) /* Bit 21: Security enable*/
|
||||
/* Bits 22-28: Reserved */
|
||||
#define FLASH_OPTSR_IOHSLV (1 << 29) /* Bit 29: IO high-speed at low-volateg */
|
||||
#define FLASH_OPTSR_CHANGEERR (1 << 30) /* Bit 30: Option byte change error */
|
||||
#define FLASH_OPTSR_SWAPBANK (1 << 31) /* Bit 31: Bank swapping status */
|
||||
|
||||
/* Flash Option Clear Control Register (OPTCCR) */
|
||||
|
||||
/* Bits 0-29: Reserved */
|
||||
#define FLASH_OPTCCR_OPTCHANGEERR (1 << 30) /* Bit 30: OPTCHANGEERR reset */
|
||||
/* Bit 31: Reserved */
|
||||
|
||||
/* Flash Protection Address (PRAR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_PRAR_START_SHIFT (0) /* Bits 0-11 Bank PCROP area start status bits */
|
||||
#define FLASH_PRAR_START_MASK (0xfff << FLASH_PRAR_START_SHIFT)
|
||||
/* Bits 12-15: Reserved */
|
||||
#define FLASH_PRAR_END_SHIFT (16) /* Bits 16-27 Bank PCROP area end configuration bits */
|
||||
#define FLASH_PRAR_END_MASK (0xfff << FLASH_PRAR_END_SHIFT)
|
||||
/* Bits 28-30: Reserved */
|
||||
#define FLASH_PRAR_DMEP (1 << 31) /* Bit 31: Bank PCROP protected erase enable option configuration bit */
|
||||
|
||||
/* Flash Secure Address (SCAR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_SCAR_START_SHIFT (0) /* Bits 0-11 Bank secure-only area start status bits */
|
||||
#define FLASH_SCAR_START_MASK (0xfff << FLASH_SCAR_START_SHIFT)
|
||||
/* Bits 12-15: Reserved */
|
||||
#define FLASH_SCAR_END_SHIFT (16) /* Bits 16-27 Bank secure-only area end configuration bits */
|
||||
#define FLASH_SCAR_END_MASK (0xfff << FLASH_SCAR_END_SHIFT)
|
||||
/* Bits 28-30: Reserved */
|
||||
#define FLASH_SCAR_DMES (1 << 31) /* Bit 31: Bank secure access protected erase enable option status bit */
|
||||
|
||||
/* Flash Write Sector Group Protection (WPSGN) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_WPSGN_SHIFT (0) /* Bits 0-31: Sector group write protection option */
|
||||
#define FLASH_WPSGN_MASK (0xffffffff << FLASH_WPSGN_SHIFT)
|
||||
|
||||
/* Flash Register Boot Address (BOOT) */
|
||||
|
||||
#define FLASH_BOOT_ADD0_SHIFT (0) /* Bits 0-15: Boot address 0 */
|
||||
#define FLASH_BOOT_ADD0_MASK (0xffff << FLASH_BOOT_ADD0_SHIFT)
|
||||
#define FLASH_BOOT_ADD1_SHIFT (16) /* Bits 16-31: Boot address 1 */
|
||||
#define FLASH_BOOT_ADD1_MASK (0xffff << FLASH_BOOT_ADD1_SHIFT)
|
||||
|
||||
/* Flash CRC Control Register (CRCCR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_CRCCR_CRC_SEC_SHIFT (0) /* Bits 0-6: CRC sector number */
|
||||
#define FLASH_CRCCR_CRC_SEC_MASK (0x7f << FLASH_CRCCR_CRC_SEC_SHIFT)
|
||||
#define FLASH_CRCCR_CRC_BY_SECT (1 << 8) /* Bit 9: Bank CRC sector mode select bit */
|
||||
#define FLASH_CRCCR_ADD_SECT (1 << 9) /* Bit 9: Bank CRC sector select bit */
|
||||
#define FLASH_CRCCR_CLEAN_SECT (1 << 10) /* Bit 10: Bank CRC sector list clear bit */
|
||||
#define FLASH_CRCCR_START_CRC (1 << 16) /* Bit 16: Bank CRC start bit */
|
||||
#define FLASH_CRCCR_CLEAN_CRC (1 << 17) /* Bit 16: Bank CRC clean bit */
|
||||
#define FLASH_CRCCR_BURST_SHIFT (20) /* Bits 20-21: Bank CRC burst size */
|
||||
#define FLASH_CRCCR_BURST_MASK (3 << FLASH_CRCCR_BURST_SHIFT)
|
||||
# define FLASH_CRCCR_BURST_4 (0 << FLASH_CRCCR_BURST_SHIFT)
|
||||
# define FLASH_CRCCR_BURST_16 (1 << FLASH_CRCCR_BURST_SHIFT)
|
||||
# define FLASH_CRCCR_BURST_64 (2 << FLASH_CRCCR_BURST_SHIFT)
|
||||
# define FLASH_CRCCR_BURST_256 (3 << FLASH_CRCCR_BURST_SHIFT)
|
||||
#define FLASH_CRCCR_ALL_BANK (1 << 22) /* Bit 22: Bank CRC select bit */
|
||||
|
||||
/* Flash CRC Start Address Register (CRCSADDR) Bank 1 or 2 */
|
||||
|
||||
/* Bits 0-1: Reserved */
|
||||
#define FLASH_CRCSADDR_START_SHIFT (2) /* Bits 2-19 CRC start address on bank */
|
||||
#define FLASH_CRCSADDR_START_MASK (0x3ffff << FLASH_CRCSADDR_START_SHIFT)
|
||||
/* Bits 20-31: Reserved */
|
||||
|
||||
/* Flash CRC End Address Register (CRCSEDDR) Bank 1 or 2 */
|
||||
|
||||
/* Bits 0-1: Reserved */
|
||||
#define FLASH_CRCSEDDR_START_SHIFT (2) /* Bits 2-19 CRC end address on bank */
|
||||
#define FLASH_CRCSEDDR_START_MASK (0x3ffff << FLASH_CRCSEDDR_START_SHIFT)
|
||||
/* Bits 20-31: Reserved */
|
||||
|
||||
/* Flash ECC fail Address(FAnR) Bank 1 or 2 */
|
||||
|
||||
#define FLASH_ECC_FAR_SHIFT (0) /* Bits 0-15 Bank 1 ECC error add */
|
||||
#define FLASH_ECC_FAR_MASK (0xffff << FLASH_CRCSEDDR_START_SHIFT)
|
||||
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7B3XX_FLASH_H */
|
@ -28,7 +28,7 @@
|
||||
#include <nuttx/config.h>
|
||||
#include <arch/stm32h7/chip.h>
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -384,5 +384,5 @@
|
||||
#define GPIO_AFRH15_SHIFT (28)
|
||||
#define GPIO_AFRH15_MASK (15 << GPIO_AFRH15_SHIFT)
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_GPIO_H */
|
||||
|
@ -29,7 +29,7 @@
|
||||
|
||||
#include "stm32_gpio.h"
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -1532,5 +1532,5 @@
|
||||
#define GPIO_UART8_TX_1 (GPIO_ALT|GPIO_AF8|GPIO_SPEED_100MHz|GPIO_PUSHPULL|GPIO_PULLUP|GPIO_PORTE|GPIO_PIN1)
|
||||
#define GPIO_UART8_TX_2 (GPIO_ALT|GPIO_AF8|GPIO_SPEED_100MHz|GPIO_PUSHPULL|GPIO_PULLUP|GPIO_PORTJ|GPIO_PIN8)
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_PINMAP_H */
|
||||
|
@ -21,6 +21,12 @@
|
||||
#ifndef __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_PWR_H
|
||||
#define __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_PWR_H
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
@ -121,16 +127,25 @@
|
||||
|
||||
/* Power control register 3 (CR3) */
|
||||
|
||||
#define STM32_PWR_CR3_BYPASS (1 << 0) /* Bit 0: Power management unit bypass */
|
||||
#define STM32_PWR_CR3_LDOEN (1 << 1) /* Bit 1: Low drop-out regulator enable */
|
||||
#define STM32_PWR_CR3_LDOESCUEN (1 << 2) /* Bit 2: Supply configuration update enable */
|
||||
/* Bits 3-7: Reserved */
|
||||
#define STM32_PWR_CR3_VBE (1 << 8) /* Bit 8: VBAT charging enable */
|
||||
#define STM32_PWR_CR3_VBRS (1 << 9) /* Bit 9: VBAT charging resistor selection */
|
||||
/* Bits 10-23: Reserved */
|
||||
#define STM32_PWR_CR3_USB33DEN (1 << 24) /* Bit 24: VDD33USB voltage level detector enable */
|
||||
#define STM32_PWR_CR3_USBREGEN (1 << 25) /* Bit 25: USB regulator enable */
|
||||
#define STM32_PWR_CR3_USB33RDY (1 << 26) /* Bit 26: USB supply ready */
|
||||
#define STM32_PWR_CR3_BYPASS (1 << 0) /* Bit 0: Power management unit bypass */
|
||||
#define STM32_PWR_CR3_LDOEN (1 << 1) /* Bit 1: Low drop-out regulator enable */
|
||||
#define STM32_PWR_CR3_LDOESCUEN (1 << 2) /* Bit 2: Supply configuration update enable */
|
||||
#ifdef CONFIG_STM32H7_HAVE_SMPS
|
||||
#define STM32_PWR_CR3_SMPSEXTHP (1 << 3) /* Bit 3: SMPS step-down converter external power delivery selection */
|
||||
#define STM32_PWR_CR3_SMPSLEVEL_SHIFT (4) /* BitS 4-5: SMPS step-down converter voltage output level selection */
|
||||
# define STM32_PWR_CR3_SMPSLEVEL_MASK (3 << STM32_PWR_CR3_SMPSLEVEL_SHIFT)
|
||||
# define STM32_PWR_CR3_SMPSLEVEL_R (0 << STM32_PWR_CR3_SMPSLEVEL_SHIFT) /* 00: */
|
||||
# define STM32_PWR_CR3_SMPSLEVEL_1V8 (1 << STM32_PWR_CR3_SMPSLEVEL_SHIFT) /* 01 */
|
||||
# define STM32_PWR_CR3_SMPSLEVEL_2V5 (2 << STM32_PWR_CR3_SMPSLEVEL_SHIFT) /* 10: */
|
||||
# define STM32_PWR_CR3_SMPSLEVEL_2V5B (3 << STM32_PWR_CR3_SMPSLEVEL_SHIFT) /* 11: */
|
||||
#endif
|
||||
/* Bits 6-7: Reserved */
|
||||
#define STM32_PWR_CR3_VBE (1 << 8) /* Bit 8: VBAT charging enable */
|
||||
#define STM32_PWR_CR3_VBRS (1 << 9) /* Bit 9: VBAT charging resistor selection */
|
||||
/* Bits 10-23: Reserved */
|
||||
#define STM32_PWR_CR3_USB33DEN (1 << 24) /* Bit 24: VDD33USB voltage level detector enable */
|
||||
#define STM32_PWR_CR3_USBREGEN (1 << 25) /* Bit 25: USB regulator enable */
|
||||
#define STM32_PWR_CR3_USB33RDY (1 << 26) /* Bit 26: USB supply ready */
|
||||
|
||||
/* Power CPU control register (CPUCR) */
|
||||
|
||||
|
@ -27,7 +27,7 @@
|
||||
|
||||
#include <nuttx/config.h>
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -460,5 +460,5 @@
|
||||
|
||||
/* TODO: SPI/I2S configuration register */
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_SPI_H */
|
||||
|
@ -29,7 +29,7 @@
|
||||
#include "chip.h"
|
||||
#include "hardware/stm32_memorymap.h"
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
@ -410,5 +410,5 @@
|
||||
# define USART_PRESC_DIV128 (10 << USART_PRESC_SHIFT) /* Input clock divided by 128 */
|
||||
# define USART_PRESC_DIV256 (11 << USART_PRESC_SHIFT) /* Input clock divided by 256 */
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
#endif /* __ARCH_ARM_SRC_STM32H7_HARDWARE_STM32H7X3XX_UART_H */
|
||||
|
@ -42,7 +42,7 @@
|
||||
* families
|
||||
*/
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Private Types
|
||||
@ -372,4 +372,4 @@ int stm32_gpiosetevent(uint32_t pinset, bool risingedge, bool fallingedge,
|
||||
return OK;
|
||||
}
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
|
@ -1,977 +1,39 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/stm32h7/stm32_flash.c
|
||||
*
|
||||
* Copyright (C) 2019 Gregory Nutt. All rights reserved.
|
||||
* Authors: Gregory Nutt <gnutt@nuttx.org>
|
||||
* David Sidrane <david.sidrane@nscdg.com>
|
||||
* Licensed to the Apache Software Foundation (ASF) under one or more
|
||||
* contributor license agreements. See the NOTICE file distributed with
|
||||
* this work for additional information regarding copyright ownership. The
|
||||
* ASF licenses this file to you under the Apache License, Version 2.0 (the
|
||||
* "License"); you may not use this file except in compliance with the
|
||||
* License. You may obtain a copy of the License at
|
||||
*
|
||||
* Ported from stm32f7_flash.c, this is the original license:
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Copyright (C) 2018 Wolpike LLC. All rights reserved.
|
||||
* Author: Evgeniy Bobkov <evgen@wolpike.com>
|
||||
*
|
||||
* Ported from stm32f20xxf40xx_flash.c, this is the original license:
|
||||
*
|
||||
* Copyright (C) 2011 Uros Platise. All rights reserved.
|
||||
* Author: Uros Platise <uros.platise@isotel.eu>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
* 3. Neither the name NuttX nor the names of its contributors may be
|
||||
* used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
||||
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
|
||||
* COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
||||
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
|
||||
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
|
||||
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
* License for the specific language governing permissions and limitations
|
||||
* under the License.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/* Provides standard flash access functions, to be used by the flash mtd
|
||||
* driver. The interface is defined in the include/nuttx/progmem.h
|
||||
*
|
||||
* Requirements during write/erase operations on FLASH:
|
||||
* - HSI must be ON.
|
||||
* - Low Power Modes are not permitted during write/erase
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
#include <nuttx/arch.h>
|
||||
#include <nuttx/mutex.h>
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "barriers.h"
|
||||
|
||||
#include "hardware/stm32_flash.h"
|
||||
#include "arm_internal.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
|
||||
/* Flash size is known from the chip selection:
|
||||
*
|
||||
* When CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT is set the
|
||||
* CONFIG_STM32H7_FLASH_CONFIG_x selects the default FLASH size based on
|
||||
* the chip part number. This value can be overridden with
|
||||
* CONFIG_STM32H7_FLASH_OVERRIDE_x
|
||||
*
|
||||
* Parts STM32H74xxE have 512Kb of FLASH
|
||||
* Parts STM32H74xxG have 1024Kb of FLASH
|
||||
* Parts STM32H74xxI have 2048Kb of FLASH
|
||||
*
|
||||
* N.B. Only Single bank mode is supported
|
||||
*/
|
||||
|
||||
#define _K(x) ((x)*1024)
|
||||
#define FLASH_SECTOR_SIZE _K(128)
|
||||
#define FLASH_PAGE_SIZE 32
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_B) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_I) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_B) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
# define CONFIG_STM32H7_FLASH_OVERRIDE_B
|
||||
# warning "Flash size not defined defaulting to 128KiB (B)"
|
||||
#endif
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT)
|
||||
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_B
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# if defined(CONFIG_STM32H7_FLASH_OVERRIDE_B)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_B
|
||||
|
||||
# elif defined(CONFIG_STM32H7_FLASH_OVERRIDE_G)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
|
||||
# elif defined(CONFIG_STM32H7_FLASH_OVERRIDE_I)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_STM32H7_FLASH_CONFIG_B)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 1
|
||||
# define STM32_FLASH_SIZE _K(1 * 128)
|
||||
|
||||
#elif defined(CONFIG_STM32H7_FLASH_CONFIG_G)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 8
|
||||
# define STM32_FLASH_SIZE _K(8 * 128)
|
||||
|
||||
#elif defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 16
|
||||
# define STM32_FLASH_SIZE _K(16 * 128)
|
||||
# define STM32_DUAL_BANK 1
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef CONFIG_STM32H7_FLASH_CR_PSIZE
|
||||
#define FLASH_CR_PSIZE FLASH_CR_PSIZE_X64
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "stm32h743xx_flash.c"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "stm32h7b3xx_flash.c"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "stm32h743xx_flash.c"
|
||||
#else
|
||||
#define FLASH_CR_PSIZE (CONFIG_STM32H7_FLASH_CR_PSIZE << FLASH_CR_PSIZE_SHIFT)
|
||||
#endif
|
||||
|
||||
#define FLASH_KEY1 0x45670123
|
||||
#define FLASH_KEY2 0xcdef89ab
|
||||
#define FLASH_OPTKEY1 0x08192a3b
|
||||
#define FLASH_OPTKEY2 0x4c5d6e7f
|
||||
#define FLASH_ERASEDVALUE 0xffu
|
||||
#define FLASH_ERASEDVALUE_DW 0xffffffff
|
||||
#define PROGMEM_NBLOCKS STM32_FLASH_NBLOCKS
|
||||
#define FLASH_NPAGES (STM32_FLASH_SIZE / FLASH_PAGE_SIZE)
|
||||
|
||||
#define FLASH_TIMEOUT_VALUE 5000000 /* 5s */
|
||||
|
||||
/****************************************************************************
|
||||
* Private Types
|
||||
****************************************************************************/
|
||||
|
||||
struct stm32h7_flash_priv_s
|
||||
{
|
||||
mutex_t lock; /* Bank exclusive */
|
||||
uint32_t ifbase; /* FLASHIF interface base address */
|
||||
uint32_t base; /* FLASH base address */
|
||||
uint32_t stblock; /* The first Block Number */
|
||||
uint32_t stpage; /* The first Page Number */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Private Data
|
||||
****************************************************************************/
|
||||
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank1_priv =
|
||||
{
|
||||
.lock = NXMUTEX_INITIALIZER,
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET,
|
||||
.base = STM32_FLASH_BANK1,
|
||||
.stblock = 0,
|
||||
.stpage = 0,
|
||||
};
|
||||
#if STM32_DUAL_BANK
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank2_priv =
|
||||
{
|
||||
.lock = NXMUTEX_INITIALIZER,
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET,
|
||||
.base = STM32_FLASH_BANK2,
|
||||
.stblock = PROGMEM_NBLOCKS / 2,
|
||||
.stpage = FLASH_NPAGES / 2,
|
||||
};
|
||||
# error "Unsupported STM32 H7 chip"
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Private Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getreg32
|
||||
*
|
||||
* Description:
|
||||
* Get a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_getreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset)
|
||||
{
|
||||
return getreg32(priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_putreg32
|
||||
*
|
||||
* Description:
|
||||
* Put a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_putreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t value)
|
||||
{
|
||||
putreg32(value, priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_modifyreg32
|
||||
*
|
||||
* Description:
|
||||
* Modify a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_modifyreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t clearbits,
|
||||
uint32_t setbits)
|
||||
{
|
||||
modifyreg32(priv->ifbase + offset, clearbits, setbits);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flash
|
||||
*
|
||||
* Description:
|
||||
* Unlock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_unlock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_CR1_OFFSET) & FLASH_CR_LOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR1_OFFSET, FLASH_KEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR1_OFFSET, FLASH_KEY2);
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flash
|
||||
*
|
||||
* Description:
|
||||
* Lock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_LOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_size
|
||||
*
|
||||
* Description:
|
||||
* Returns the size in bytes of FLASH
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_size(
|
||||
struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE * PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_bank
|
||||
*
|
||||
* Description:
|
||||
* Returns the priv pointer to the correct bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline
|
||||
struct stm32h7_flash_priv_s * stm32h7_flash_bank(size_t address)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv = NULL;
|
||||
|
||||
uint32_t bank_size;
|
||||
#ifdef STM32_DUAL_BANK
|
||||
bank_size = stm32h7_flash_size(priv) / 2;
|
||||
#else
|
||||
bank_size = stm32h7_flash_size(priv);
|
||||
#endif
|
||||
|
||||
if (address >= stm32h7_flash_bank1_priv.base &&
|
||||
address < stm32h7_flash_bank1_priv.base + bank_size)
|
||||
{
|
||||
priv = &stm32h7_flash_bank1_priv;
|
||||
}
|
||||
|
||||
#ifdef STM32_DUAL_BANK
|
||||
else if (address >= stm32h7_flash_bank2_priv.base &&
|
||||
address < stm32h7_flash_bank2_priv.base + bank_size)
|
||||
{
|
||||
priv = &stm32h7_flash_bank2_priv;
|
||||
}
|
||||
#endif
|
||||
|
||||
return priv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_israngeerased
|
||||
*
|
||||
* Description:
|
||||
* Returns count of non-erased words
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_israngeerased(size_t startaddress, size_t size)
|
||||
{
|
||||
uint32_t *addr;
|
||||
uint8_t *baddr;
|
||||
size_t count = 0;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (!stm32h7_flash_bank(startaddress) ||
|
||||
!stm32h7_flash_bank(startaddress + size - 1))
|
||||
{
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
addr = (uint32_t *)startaddress;
|
||||
while (count + 4 <= size)
|
||||
{
|
||||
if (getreg32(addr) != FLASH_ERASEDVALUE_DW)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
addr++;
|
||||
count += 4;
|
||||
}
|
||||
|
||||
baddr = (uint8_t *)startaddress;
|
||||
while (count < size)
|
||||
{
|
||||
if (getreg8(baddr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
baddr++;
|
||||
count++;
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_wait_for_last_operation()
|
||||
*
|
||||
* Description:
|
||||
* Wait for last write/erase operation to finish
|
||||
* Return error in case of timeout
|
||||
*
|
||||
* Input Parameters:
|
||||
* priv - Flash bank based config
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero or error value
|
||||
*
|
||||
* ETIME: Timeout while waiting for previous write/erase operation to
|
||||
* complete
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_wait_for_last_operation(struct stm32h7_flash_priv_s
|
||||
*priv)
|
||||
{
|
||||
int i;
|
||||
bool timeout = true;
|
||||
|
||||
ARM_DSB();
|
||||
|
||||
for (i = 0; i < FLASH_TIMEOUT_VALUE; i++)
|
||||
{
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) &
|
||||
(FLASH_SR_QW | FLASH_SR_BSY | FLASH_SR_WBNE)))
|
||||
{
|
||||
timeout = false;
|
||||
break;
|
||||
}
|
||||
|
||||
up_udelay(1);
|
||||
}
|
||||
|
||||
if (timeout)
|
||||
{
|
||||
return -EBUSY;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Unlock the flash option bytes
|
||||
* Returns true if the flash was locked before, false otherwise
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static bool stm32h7_unlock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY2);
|
||||
|
||||
/* Was locked before and now unlocked */
|
||||
|
||||
ret = true;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Lock the flash option bytes
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTLOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_save_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Save the flash option bytes to non-volatile storage.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_save_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) &
|
||||
(FLASH_SR_BSY | FLASH_SR_CRCBUSY))
|
||||
{
|
||||
}
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR2_OFFSET) &
|
||||
(FLASH_SR_BSY | FLASH_SR_CRCBUSY))
|
||||
{
|
||||
}
|
||||
|
||||
/* Can only write flash options if the option control reg is unlocked */
|
||||
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTSTRT);
|
||||
}
|
||||
|
||||
/* Wait for the update to complete */
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET) &
|
||||
FLASH_OPTSR_BUSYV)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_unlock
|
||||
*
|
||||
* Description:
|
||||
* Unlocks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_unlock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
nxmutex_unlock(&priv->lock);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_lock
|
||||
*
|
||||
* Description:
|
||||
* Locks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_lock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_lock_flash(priv);
|
||||
nxmutex_unlock(&priv->lock);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_writeprotect
|
||||
*
|
||||
* Description:
|
||||
* Enable or disable the write protection of a flash sector.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_writeprotect(size_t block, bool enabled)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t setbits = 0;
|
||||
uint32_t clearbits = 0;
|
||||
int rv = -ENODEV;
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE));
|
||||
|
||||
if (priv)
|
||||
{
|
||||
if (enabled)
|
||||
{
|
||||
clearbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
else
|
||||
{
|
||||
setbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_WPSN_PRG1R_OFFSET,
|
||||
clearbits, setbits);
|
||||
rv = OK;
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getopt
|
||||
*
|
||||
* Description:
|
||||
* Returns the current flash option bytes from the FLASH_OPTSR_CR register.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
uint32_t stm32h7_flash_getopt(void)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
return stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_optmodify
|
||||
*
|
||||
* Description:
|
||||
* Modifies the current flash option bytes, given bits to set and clear.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_optmodify(uint32_t clear, uint32_t set)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
bool was_locked;
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
was_locked = stm32h7_unlock_flashopt(priv);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTSR_PRG_OFFSET,
|
||||
clear, set);
|
||||
stm32h7_save_flashopt(priv);
|
||||
if (was_locked)
|
||||
{
|
||||
stm32h7_lock_flashopt(priv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_swapbanks
|
||||
*
|
||||
* Description:
|
||||
* Swaps banks 1 and 2 in the processor's memory map. Takes effect
|
||||
* the next time the system is reset.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_swapbanks(void)
|
||||
{
|
||||
uint32_t opts = stm32h7_flash_getopt();
|
||||
if (opts & FLASH_OPTCR_SWAPBANK)
|
||||
{
|
||||
stm32h7_flash_optmodify(FLASH_OPTCR_SWAPBANK, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
stm32h7_flash_optmodify(0, FLASH_OPTCR_SWAPBANK);
|
||||
}
|
||||
}
|
||||
|
||||
size_t up_progmem_pagesize(size_t page)
|
||||
{
|
||||
return FLASH_PAGE_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_getpage(size_t addr)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
return priv->stpage + ((addr - priv->base) / FLASH_PAGE_SIZE);
|
||||
}
|
||||
|
||||
size_t up_progmem_getaddress(size_t page)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
if (page >= FLASH_NPAGES)
|
||||
{
|
||||
return SIZE_MAX;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (page * FLASH_PAGE_SIZE));
|
||||
return priv->base + (page - priv->stpage) * FLASH_PAGE_SIZE;
|
||||
}
|
||||
|
||||
size_t up_progmem_neraseblocks(void)
|
||||
{
|
||||
return PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
bool up_progmem_isuniform(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_ispageerased(size_t page)
|
||||
{
|
||||
size_t addr;
|
||||
size_t count;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (page >= FLASH_NPAGES)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Verify */
|
||||
|
||||
for (addr = up_progmem_getaddress(page), count = up_progmem_pagesize(page);
|
||||
count; count--, addr++)
|
||||
{
|
||||
if (getreg8(addr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
size_t up_progmem_erasesize(size_t block)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_eraseblock(size_t block)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
int ret;
|
||||
size_t block_address = STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE);
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(block_address);
|
||||
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_lock;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin erasing single block */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_SER);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SNB_MASK,
|
||||
FLASH_CR_SNB(block - priv->stblock));
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_START);
|
||||
|
||||
/* Wait for erase operation to complete */
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SER, 0);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SNB_MASK,
|
||||
0);
|
||||
ret = 0;
|
||||
|
||||
exit_with_unlock:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
exit_with_lock:
|
||||
nxmutex_unlock(&priv->lock);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (ret == 0 &&
|
||||
stm32h7_israngeerased(block_address, up_progmem_erasesize(block)) == 0)
|
||||
{
|
||||
ret = up_progmem_erasesize(block); /* success */
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = -EIO; /* failure */
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_write(size_t addr, const void *buf, size_t count)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t *fp;
|
||||
uint32_t *rp;
|
||||
uint32_t *ll = (uint32_t *) buf;
|
||||
size_t faddr;
|
||||
size_t written = count;
|
||||
int ret;
|
||||
const size_t pagesize = up_progmem_pagesize(0); /* 256 bit, 32 bytes per page */
|
||||
const size_t llperpage = pagesize / sizeof(uint32_t);
|
||||
size_t pcount = count / pagesize;
|
||||
uint32_t sr;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Check for valid address range */
|
||||
|
||||
if (addr < priv->base ||
|
||||
addr + count > priv->base + (STM32_FLASH_SIZE / 2))
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
/* Check address and count alignment */
|
||||
|
||||
DEBUGASSERT(!(addr % pagesize));
|
||||
DEBUGASSERT(!(count % pagesize));
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_lock;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin flashing */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET,
|
||||
FLASH_CR_PSIZE_MASK, FLASH_CR_PSIZE);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_PG);
|
||||
|
||||
for (ll = (uint32_t *) buf, faddr = addr; pcount;
|
||||
pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
/* Write 8 32 bit word and wait to complete */
|
||||
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
|
||||
/* Data synchronous Barrier (DSB) just after the write operation. This
|
||||
* will force the CPU to respect the sequence of instruction (no
|
||||
* optimization).
|
||||
*/
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET,
|
||||
FLASH_CR_PG,
|
||||
0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
ret = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_PG, 0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
exit_with_unlock:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (written > 0)
|
||||
{
|
||||
for (ll = (uint32_t *) buf, faddr = addr, pcount = count / pagesize;
|
||||
pcount; pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
if ((*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
}
|
||||
|
||||
exit_with_lock:
|
||||
nxmutex_unlock(&priv->lock);
|
||||
return written;
|
||||
}
|
||||
|
||||
uint8_t up_progmem_erasestate(void)
|
||||
{
|
||||
return FLASH_ERASEDVALUE;
|
||||
}
|
||||
|
@ -41,7 +41,7 @@
|
||||
* families
|
||||
*/
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX) || defined(CONFIG_STM32H7_STM32H7X7XX) || defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
|
||||
/****************************************************************************
|
||||
* Public Data
|
||||
@ -530,4 +530,4 @@ void stm32_iocompensation(void)
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX */
|
||||
#endif /* CONFIG_STM32H7_STM32H7X3XX || CONFIG_STM32H7_STM32H7X7XX || CONFIG_STM32H7_STM32H7B3XX */
|
||||
|
@ -56,6 +56,8 @@
|
||||
|
||||
#if defined(CONFIG_STM32H7_STM32H7X3XX)
|
||||
# include "stm32h7x3xx_rcc.c"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7B3XX)
|
||||
# include "stm32h7x3xx_rcc.c"
|
||||
#elif defined(CONFIG_STM32H7_STM32H7X7XX)
|
||||
# include "stm32h7x7xx_rcc.c"
|
||||
#else
|
||||
|
978
arch/arm/src/stm32h7/stm32h743xx_flash.c
Normal file
978
arch/arm/src/stm32h7/stm32h743xx_flash.c
Normal file
@ -0,0 +1,978 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/stm32h7/stm32h743xx_flash.c
|
||||
*
|
||||
* Copyright (C) 2019 Gregory Nutt. All rights reserved.
|
||||
* Authors: Gregory Nutt <gnutt@nuttx.org>
|
||||
* David Sidrane <david.sidrane@nscdg.com>
|
||||
*
|
||||
* Ported from stm32f7_flash.c, this is the original license:
|
||||
*
|
||||
* Copyright (C) 2018 Wolpike LLC. All rights reserved.
|
||||
* Author: Evgeniy Bobkov <evgen@wolpike.com>
|
||||
*
|
||||
* Ported from stm32f20xxf40xx_flash.c, this is the original license:
|
||||
*
|
||||
* Copyright (C) 2011 Uros Platise. All rights reserved.
|
||||
* Author: Uros Platise <uros.platise@isotel.eu>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
* 3. Neither the name NuttX nor the names of its contributors may be
|
||||
* used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
||||
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
|
||||
* COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
||||
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
|
||||
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
|
||||
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/* Provides standard flash access functions, to be used by the flash mtd
|
||||
* driver. The interface is defined in the include/nuttx/progmem.h
|
||||
*
|
||||
* Requirements during write/erase operations on FLASH:
|
||||
* - HSI must be ON.
|
||||
* - Low Power Modes are not permitted during write/erase
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
#include <nuttx/arch.h>
|
||||
#include <nuttx/mutex.h>
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "barriers.h"
|
||||
|
||||
#include "hardware/stm32_flash.h"
|
||||
#include "arm_internal.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
|
||||
/* Flash size is known from the chip selection:
|
||||
*
|
||||
* When CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT is set the
|
||||
* CONFIG_STM32H7_FLASH_CONFIG_x selects the default FLASH size based on
|
||||
* the chip part number. This value can be overridden with
|
||||
* CONFIG_STM32H7_FLASH_OVERRIDE_x
|
||||
*
|
||||
* Parts STM32H74xxE have 512Kb of FLASH
|
||||
* Parts STM32H74xxG have 1024Kb of FLASH
|
||||
* Parts STM32H74xxI have 2048Kb of FLASH
|
||||
*
|
||||
* N.B. Only Single bank mode is supported
|
||||
*/
|
||||
|
||||
#define _K(x) ((x)*1024)
|
||||
#define FLASH_SECTOR_SIZE _K(128)
|
||||
#define FLASH_PAGE_SIZE 32
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_B) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_I) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_B) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
# define CONFIG_STM32H7_FLASH_OVERRIDE_B
|
||||
# warning "Flash size not defined defaulting to 128KiB (B)"
|
||||
#endif
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT)
|
||||
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_B
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# if defined(CONFIG_STM32H7_FLASH_OVERRIDE_B)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_B
|
||||
|
||||
# elif defined(CONFIG_STM32H7_FLASH_OVERRIDE_G)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
|
||||
# elif defined(CONFIG_STM32H7_FLASH_OVERRIDE_I)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_STM32H7_FLASH_CONFIG_B)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 1
|
||||
# define STM32_FLASH_SIZE _K(1 * 128)
|
||||
|
||||
#elif defined(CONFIG_STM32H7_FLASH_CONFIG_G)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 8
|
||||
# define STM32_FLASH_SIZE _K(8 * 128)
|
||||
|
||||
#elif defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 16
|
||||
# define STM32_FLASH_SIZE _K(16 * 128)
|
||||
# define STM32_DUAL_BANK 1
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef CONFIG_STM32H7_FLASH_CR_PSIZE
|
||||
#define FLASH_CR_PSIZE FLASH_CR_PSIZE_X64
|
||||
#else
|
||||
#define FLASH_CR_PSIZE (CONFIG_STM32H7_FLASH_CR_PSIZE << FLASH_CR_PSIZE_SHIFT)
|
||||
#endif
|
||||
|
||||
#define FLASH_KEY1 0x45670123
|
||||
#define FLASH_KEY2 0xcdef89ab
|
||||
#define FLASH_OPTKEY1 0x08192a3b
|
||||
#define FLASH_OPTKEY2 0x4c5d6e7f
|
||||
#define FLASH_ERASEDVALUE 0xffu
|
||||
#define FLASH_ERASEDVALUE_DW 0xffffffff
|
||||
#define PROGMEM_NBLOCKS STM32_FLASH_NBLOCKS
|
||||
#define FLASH_NPAGES (STM32_FLASH_SIZE / FLASH_PAGE_SIZE)
|
||||
|
||||
#define FLASH_TIMEOUT_VALUE 5000000 /* 5s */
|
||||
|
||||
/****************************************************************************
|
||||
* Private Types
|
||||
****************************************************************************/
|
||||
|
||||
struct stm32h7_flash_priv_s
|
||||
{
|
||||
mutex_t lock; /* Bank exclusive */
|
||||
uint32_t ifbase; /* FLASHIF interface base address */
|
||||
uint32_t base; /* FLASH base address */
|
||||
uint32_t stblock; /* The first Block Number */
|
||||
uint32_t stpage; /* The first Page Number */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Private Data
|
||||
****************************************************************************/
|
||||
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank1_priv =
|
||||
{
|
||||
.lock = NXMUTEX_INITIALIZER,
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET,
|
||||
.base = STM32_FLASH_BANK1,
|
||||
.stblock = 0,
|
||||
.stpage = 0,
|
||||
};
|
||||
#if STM32_DUAL_BANK
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank2_priv =
|
||||
{
|
||||
.lock = NXMUTEX_INITIALIZER,
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET,
|
||||
.base = STM32_FLASH_BANK2,
|
||||
.stblock = PROGMEM_NBLOCKS / 2,
|
||||
.stpage = FLASH_NPAGES / 2,
|
||||
};
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Private Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getreg32
|
||||
*
|
||||
* Description:
|
||||
* Get a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_getreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset)
|
||||
{
|
||||
return getreg32(priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_putreg32
|
||||
*
|
||||
* Description:
|
||||
* Put a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_putreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t value)
|
||||
{
|
||||
putreg32(value, priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_modifyreg32
|
||||
*
|
||||
* Description:
|
||||
* Modify a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_modifyreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t clearbits,
|
||||
uint32_t setbits)
|
||||
{
|
||||
modifyreg32(priv->ifbase + offset, clearbits, setbits);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flash
|
||||
*
|
||||
* Description:
|
||||
* Unlock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_unlock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_CR1_OFFSET) & FLASH_CR_LOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR1_OFFSET, FLASH_KEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR1_OFFSET, FLASH_KEY2);
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flash
|
||||
*
|
||||
* Description:
|
||||
* Lock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_LOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_size
|
||||
*
|
||||
* Description:
|
||||
* Returns the size in bytes of FLASH
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_size(
|
||||
struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE * PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_bank
|
||||
*
|
||||
* Description:
|
||||
* Returns the priv pointer to the correct bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline
|
||||
struct stm32h7_flash_priv_s * stm32h7_flash_bank(size_t address)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv = NULL;
|
||||
|
||||
uint32_t bank_size;
|
||||
#ifdef STM32_DUAL_BANK
|
||||
bank_size = stm32h7_flash_size(priv) / 2;
|
||||
#else
|
||||
bank_size = stm32h7_flash_size(priv);
|
||||
#endif
|
||||
|
||||
if (address >= stm32h7_flash_bank1_priv.base &&
|
||||
address < stm32h7_flash_bank1_priv.base + bank_size)
|
||||
{
|
||||
priv = &stm32h7_flash_bank1_priv;
|
||||
}
|
||||
|
||||
#ifdef STM32_DUAL_BANK
|
||||
else if (address >= stm32h7_flash_bank2_priv.base &&
|
||||
address < stm32h7_flash_bank2_priv.base + bank_size)
|
||||
{
|
||||
priv = &stm32h7_flash_bank2_priv;
|
||||
}
|
||||
#endif
|
||||
|
||||
return priv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_israngeerased
|
||||
*
|
||||
* Description:
|
||||
* Returns count of non-erased words
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_israngeerased(size_t startaddress, size_t size)
|
||||
{
|
||||
uint32_t *addr;
|
||||
uint8_t *baddr;
|
||||
size_t count = 0;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (!stm32h7_flash_bank(startaddress) ||
|
||||
!stm32h7_flash_bank(startaddress + size - 1))
|
||||
{
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
addr = (uint32_t *)startaddress;
|
||||
while (count + 4 <= size)
|
||||
{
|
||||
if (getreg32(addr) != FLASH_ERASEDVALUE_DW)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
addr++;
|
||||
count += 4;
|
||||
}
|
||||
|
||||
baddr = (uint8_t *)startaddress;
|
||||
while (count < size)
|
||||
{
|
||||
if (getreg8(baddr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
baddr++;
|
||||
count++;
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_wait_for_last_operation()
|
||||
*
|
||||
* Description:
|
||||
* Wait for last write/erase operation to finish
|
||||
* Return error in case of timeout
|
||||
*
|
||||
* Input Parameters:
|
||||
* priv - Flash bank based config
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero or error value
|
||||
*
|
||||
* ETIME: Timeout while waiting for previous write/erase operation to
|
||||
* complete
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_wait_for_last_operation(struct stm32h7_flash_priv_s
|
||||
*priv)
|
||||
{
|
||||
int i;
|
||||
bool timeout = true;
|
||||
|
||||
ARM_DSB();
|
||||
|
||||
for (i = 0; i < FLASH_TIMEOUT_VALUE; i++)
|
||||
{
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) &
|
||||
(FLASH_SR_QW | FLASH_SR_BSY | FLASH_SR_WBNE)))
|
||||
{
|
||||
timeout = false;
|
||||
break;
|
||||
}
|
||||
|
||||
up_udelay(1);
|
||||
}
|
||||
|
||||
if (timeout)
|
||||
{
|
||||
return -EBUSY;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Unlock the flash option bytes
|
||||
* Returns true if the flash was locked before, false otherwise
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static bool stm32h7_unlock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY2);
|
||||
|
||||
/* Was locked before and now unlocked */
|
||||
|
||||
ret = true;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Lock the flash option bytes
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTLOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_save_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Save the flash option bytes to non-volatile storage.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_save_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET) &
|
||||
(FLASH_SR_BSY | FLASH_SR_CRCBUSY))
|
||||
{
|
||||
}
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR2_OFFSET) &
|
||||
(FLASH_SR_BSY | FLASH_SR_CRCBUSY))
|
||||
{
|
||||
}
|
||||
|
||||
/* Can only write flash options if the option control reg is unlocked */
|
||||
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTSTRT);
|
||||
}
|
||||
|
||||
/* Wait for the update to complete */
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET) &
|
||||
FLASH_OPTSR_BUSYV)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_unlock
|
||||
*
|
||||
* Description:
|
||||
* Unlocks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_unlock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
nxmutex_unlock(&priv->lock);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_lock
|
||||
*
|
||||
* Description:
|
||||
* Locks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_lock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_lock_flash(priv);
|
||||
nxmutex_unlock(&priv->lock);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_writeprotect
|
||||
*
|
||||
* Description:
|
||||
* Enable or disable the write protection of a flash sector.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_writeprotect(size_t block, bool enabled)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t setbits = 0;
|
||||
uint32_t clearbits = 0;
|
||||
int rv = -ENODEV;
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE));
|
||||
|
||||
if (priv)
|
||||
{
|
||||
if (enabled)
|
||||
{
|
||||
clearbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
else
|
||||
{
|
||||
setbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_WPSN_PRG1R_OFFSET,
|
||||
clearbits, setbits);
|
||||
rv = OK;
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getopt
|
||||
*
|
||||
* Description:
|
||||
* Returns the current flash option bytes from the FLASH_OPTSR_CR register.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
uint32_t stm32h7_flash_getopt(void)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
return stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_optmodify
|
||||
*
|
||||
* Description:
|
||||
* Modifies the current flash option bytes, given bits to set and clear.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_optmodify(uint32_t clear, uint32_t set)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
bool was_locked;
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
was_locked = stm32h7_unlock_flashopt(priv);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTSR_PRG_OFFSET,
|
||||
clear, set);
|
||||
stm32h7_save_flashopt(priv);
|
||||
if (was_locked)
|
||||
{
|
||||
stm32h7_lock_flashopt(priv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_swapbanks
|
||||
*
|
||||
* Description:
|
||||
* Swaps banks 1 and 2 in the processor's memory map. Takes effect
|
||||
* the next time the system is reset.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_swapbanks(void)
|
||||
{
|
||||
uint32_t opts = stm32h7_flash_getopt();
|
||||
if (opts & FLASH_OPTCR_SWAPBANK)
|
||||
{
|
||||
stm32h7_flash_optmodify(FLASH_OPTCR_SWAPBANK, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
stm32h7_flash_optmodify(0, FLASH_OPTCR_SWAPBANK);
|
||||
}
|
||||
}
|
||||
|
||||
size_t up_progmem_pagesize(size_t page)
|
||||
{
|
||||
return FLASH_PAGE_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_getpage(size_t addr)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
return priv->stpage + ((addr - priv->base) / FLASH_PAGE_SIZE);
|
||||
}
|
||||
|
||||
size_t up_progmem_getaddress(size_t page)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
if (page >= FLASH_NPAGES)
|
||||
{
|
||||
return SIZE_MAX;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (page * FLASH_PAGE_SIZE));
|
||||
return priv->base + (page - priv->stpage) * FLASH_PAGE_SIZE;
|
||||
}
|
||||
|
||||
size_t up_progmem_neraseblocks(void)
|
||||
{
|
||||
return PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
bool up_progmem_isuniform(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_ispageerased(size_t page)
|
||||
{
|
||||
size_t addr;
|
||||
size_t count;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (page >= FLASH_NPAGES)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Verify */
|
||||
|
||||
for (addr = up_progmem_getaddress(page), count = up_progmem_pagesize(page);
|
||||
count; count--, addr++)
|
||||
{
|
||||
if (getreg8(addr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
size_t up_progmem_erasesize(size_t block)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_eraseblock(size_t block)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
int ret;
|
||||
size_t block_address = STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE);
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(block_address);
|
||||
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_lock;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin erasing single block */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_SER);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SNB_MASK,
|
||||
FLASH_CR_SNB(block - priv->stblock));
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_START);
|
||||
|
||||
/* Wait for erase operation to complete */
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SER, 0);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_SNB_MASK,
|
||||
0);
|
||||
ret = 0;
|
||||
|
||||
exit_with_unlock:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
exit_with_lock:
|
||||
nxmutex_unlock(&priv->lock);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (ret == 0 &&
|
||||
stm32h7_israngeerased(block_address, up_progmem_erasesize(block)) == 0)
|
||||
{
|
||||
ret = up_progmem_erasesize(block); /* success */
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = -EIO; /* failure */
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_write(size_t addr, const void *buf, size_t count)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t *fp;
|
||||
uint32_t *rp;
|
||||
uint32_t *ll = (uint32_t *) buf;
|
||||
size_t faddr;
|
||||
size_t written = count;
|
||||
int ret;
|
||||
const size_t pagesize = up_progmem_pagesize(0); /* 256 bit, 32 bytes per page */
|
||||
const size_t llperpage = pagesize / sizeof(uint32_t);
|
||||
size_t pcount = count / pagesize;
|
||||
uint32_t sr;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Check for valid address range */
|
||||
|
||||
if (addr < priv->base ||
|
||||
addr + count > priv->base + (STM32_FLASH_SIZE / 2))
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
ret = nxmutex_lock(&priv->lock);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
/* Check address and count alignment */
|
||||
|
||||
DEBUGASSERT(!(addr % pagesize));
|
||||
DEBUGASSERT(!(count % pagesize));
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_lock;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin flashing */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET,
|
||||
FLASH_CR_PSIZE_MASK, FLASH_CR_PSIZE);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, 0, FLASH_CR_PG);
|
||||
|
||||
for (ll = (uint32_t *) buf, faddr = addr; pcount;
|
||||
pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
/* Write 8 32 bit word and wait to complete */
|
||||
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
|
||||
/* Data synchronous Barrier (DSB) just after the write operation. This
|
||||
* will force the CPU to respect the sequence of instruction (no
|
||||
* optimization).
|
||||
*/
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET,
|
||||
FLASH_CR_PG,
|
||||
0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
ret = -EIO;
|
||||
goto exit_with_unlock;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR1_OFFSET, FLASH_CR_PG, 0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
exit_with_unlock:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (written > 0)
|
||||
{
|
||||
for (ll = (uint32_t *) buf, faddr = addr, pcount = count / pagesize;
|
||||
pcount; pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
if ((*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR1_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR1_OFFSET,
|
||||
0, ~0);
|
||||
}
|
||||
|
||||
exit_with_lock:
|
||||
nxmutex_unlock(&priv->lock);
|
||||
return written;
|
||||
}
|
||||
|
||||
uint8_t up_progmem_erasestate(void)
|
||||
{
|
||||
return FLASH_ERASEDVALUE;
|
||||
}
|
||||
|
968
arch/arm/src/stm32h7/stm32h7b3xx_flash.c
Normal file
968
arch/arm/src/stm32h7/stm32h7b3xx_flash.c
Normal file
@ -0,0 +1,968 @@
|
||||
/****************************************************************************
|
||||
* arch/arm/src/stm32h7/stm32h7b3xx_flash.c
|
||||
*
|
||||
* Copyright (C) 2019 Gregory Nutt. All rights reserved.
|
||||
* Authors: Gregory Nutt <gnutt@nuttx.org>
|
||||
* David Sidrane <david.sidrane@nscdg.com>
|
||||
*
|
||||
* Ported from stm32f7_flash.c, this is the original license:
|
||||
*
|
||||
* Copyright (C) 2018 Wolpike LLC. All rights reserved.
|
||||
* Author: Evgeniy Bobkov <evgen@wolpike.com>
|
||||
*
|
||||
* Ported from stm32h743xx_flash.c, this is the original license:
|
||||
*
|
||||
* Copyright (C) 2011 Uros Platise. All rights reserved.
|
||||
* Author: Uros Platise <uros.platise@isotel.eu>
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
*
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in
|
||||
* the documentation and/or other materials provided with the
|
||||
* distribution.
|
||||
* 3. Neither the name NuttX nor the names of its contributors may be
|
||||
* used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
|
||||
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
|
||||
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
|
||||
* FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
|
||||
* COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
|
||||
* BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
|
||||
* OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
|
||||
* AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
|
||||
* ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
* POSSIBILITY OF SUCH DAMAGE.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
/* Provides standard flash access functions, to be used by the flash mtd
|
||||
* driver. The interface is defined in the include/nuttx/progmem.h
|
||||
*
|
||||
* Requirements during write/erase operations on FLASH:
|
||||
* - HSI must be ON.
|
||||
* - Low Power Modes are not permitted during write/erase
|
||||
*/
|
||||
|
||||
/****************************************************************************
|
||||
* Included Files
|
||||
****************************************************************************/
|
||||
|
||||
#include <nuttx/config.h>
|
||||
#include <nuttx/arch.h>
|
||||
#include <nuttx/semaphore.h>
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <assert.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include "barriers.h"
|
||||
|
||||
#include "hardware/stm32_flash.h"
|
||||
#include "arm_internal.h"
|
||||
|
||||
/****************************************************************************
|
||||
* Pre-processor Definitions
|
||||
****************************************************************************/
|
||||
|
||||
/* Flash size is known from the chip selection:
|
||||
*
|
||||
* When CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT is set the
|
||||
* CONFIG_STM32H7_FLASH_CONFIG_x selects the default FLASH size based on
|
||||
* the chip part number. This value can be overridden with
|
||||
* CONFIG_STM32H7_FLASH_OVERRIDE_x
|
||||
*
|
||||
* Parts STM32H7x3xG have 1024Kb of FLASH
|
||||
* Parts STM32H7x3xI have 2048Kb of FLASH
|
||||
*
|
||||
* N.B. Only Single bank mode is supported
|
||||
*/
|
||||
|
||||
#define _K(x) ((x)*1024)
|
||||
|
||||
#define FLASH_SECTOR_SIZE _K(8)
|
||||
|
||||
#define FLASH_PAGE_SIZE 16
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_OVERRIDE_I) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_G) && \
|
||||
!defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
# define CONFIG_STM32H7_FLASH_OVERRIDE_G
|
||||
# warning "Flash size not defined defaulting to 1024KiB (G)"
|
||||
#endif
|
||||
|
||||
#if !defined(CONFIG_STM32H7_FLASH_OVERRIDE_DEFAULT)
|
||||
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_B
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
# undef CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# if defined(CONFIG_STM32H7_FLASH_OVERRIDE_G)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_G
|
||||
|
||||
# elif defined(CONFIG_STM32H7_FLASH_OVERRIDE_I)
|
||||
|
||||
# define CONFIG_STM32H7_FLASH_CONFIG_I
|
||||
|
||||
# endif
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_STM32H7_FLASH_CONFIG_G)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 128
|
||||
# define STM32_FLASH_SIZE _K(128 * 8)
|
||||
|
||||
#elif defined(CONFIG_STM32H7_FLASH_CONFIG_I)
|
||||
|
||||
# define STM32_FLASH_NBLOCKS 256
|
||||
# define STM32_FLASH_SIZE _K(256 * 8)
|
||||
|
||||
#endif
|
||||
|
||||
#define FLASH_KEY1 0x45670123
|
||||
#define FLASH_KEY2 0xcdef89ab
|
||||
#define FLASH_OPTKEY1 0x08192a3b
|
||||
#define FLASH_OPTKEY2 0x4c5d6e7f
|
||||
#define FLASH_ERASEDVALUE 0xffu
|
||||
#define FLASH_ERASEDVALUE_DW 0xffffffff
|
||||
#define PROGMEM_NBLOCKS STM32_FLASH_NBLOCKS
|
||||
#define FLASH_NPAGES (STM32_FLASH_SIZE / FLASH_PAGE_SIZE)
|
||||
|
||||
#define FLASH_TIMEOUT_VALUE 5000000 /* 5s */
|
||||
|
||||
/****************************************************************************
|
||||
* Private Types
|
||||
****************************************************************************/
|
||||
|
||||
struct stm32h7_flash_priv_s
|
||||
{
|
||||
sem_t sem; /* Bank exclusive */
|
||||
uint32_t ifbase; /* FLASHIF interface base address */
|
||||
uint32_t base; /* FLASH base address */
|
||||
uint32_t stblock; /* The first Block Number */
|
||||
uint32_t stpage; /* The first Page Number */
|
||||
};
|
||||
|
||||
/****************************************************************************
|
||||
* Private Data
|
||||
****************************************************************************/
|
||||
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank1_priv =
|
||||
{
|
||||
.sem = SEM_INITIALIZER(1),
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK1_OFFSET,
|
||||
.base = STM32_FLASH_BANK1,
|
||||
.stblock = 0,
|
||||
.stpage = 0,
|
||||
};
|
||||
#if STM32_FLASH_NBLOCKS > 1
|
||||
static struct stm32h7_flash_priv_s stm32h7_flash_bank2_priv =
|
||||
{
|
||||
.sem = SEM_INITIALIZER(1),
|
||||
.ifbase = STM32_FLASHIF_BASE + STM32_FLASH_BANK2_OFFSET,
|
||||
.base = STM32_FLASH_BANK2,
|
||||
.stblock = PROGMEM_NBLOCKS / 2,
|
||||
.stpage = FLASH_NPAGES / 2,
|
||||
};
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Private Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getreg32
|
||||
*
|
||||
* Description:
|
||||
* Get a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_getreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset)
|
||||
{
|
||||
return getreg32(priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_putreg32
|
||||
*
|
||||
* Description:
|
||||
* Put a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_putreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t value)
|
||||
{
|
||||
putreg32(value, priv->ifbase + offset);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_modifyreg32
|
||||
*
|
||||
* Description:
|
||||
* Modify a 32-bit register value by offset
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_modifyreg32(struct stm32h7_flash_priv_s
|
||||
*priv, uint32_t offset,
|
||||
uint32_t clearbits,
|
||||
uint32_t setbits)
|
||||
{
|
||||
modifyreg32(priv->ifbase + offset, clearbits, setbits);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_sem_lock
|
||||
*
|
||||
* Description:
|
||||
* Take the Bank exclusive access semaphore
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_flash_sem_lock(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
return nxsem_wait_uninterruptible(&priv->sem);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_sem_unlock
|
||||
*
|
||||
* Description:
|
||||
* Release the Bank exclusive access semaphore
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline void stm32h7_flash_sem_unlock(struct stm32h7_flash_priv_s
|
||||
*priv)
|
||||
{
|
||||
nxsem_post(&priv->sem);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flash
|
||||
*
|
||||
* Description:
|
||||
* Unlock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_unlock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_CR_OFFSET) & FLASH_CR_LOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR_OFFSET, FLASH_KEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_KEYR_OFFSET, FLASH_KEY2);
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flash
|
||||
*
|
||||
* Description:
|
||||
* Lock the Bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flash(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET, 0, FLASH_CR_LOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_size
|
||||
*
|
||||
* Description:
|
||||
* Returns the size in bytes of FLASH
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline uint32_t stm32h7_flash_size(
|
||||
struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE * PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_bank
|
||||
*
|
||||
* Description:
|
||||
* Returns the priv pointer to the correct bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static inline
|
||||
struct stm32h7_flash_priv_s * stm32h7_flash_bank(size_t address)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv = &stm32h7_flash_bank1_priv;
|
||||
if (address < priv->base || address >=
|
||||
priv->base + stm32h7_flash_size(priv))
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
#if STM32_FLASH_NBLOCKS > 1
|
||||
if (address >= stm32h7_flash_bank2_priv.base)
|
||||
{
|
||||
priv = &stm32h7_flash_bank2_priv;
|
||||
}
|
||||
#endif
|
||||
|
||||
return priv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_israngeerased
|
||||
*
|
||||
* Description:
|
||||
* Returns count of non-erased words
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_israngeerased(size_t startaddress, size_t size)
|
||||
{
|
||||
uint32_t *addr;
|
||||
uint8_t *baddr;
|
||||
size_t count = 0;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (!stm32h7_flash_bank(startaddress) ||
|
||||
!stm32h7_flash_bank(startaddress + size))
|
||||
{
|
||||
return -EIO;
|
||||
}
|
||||
|
||||
addr = (uint32_t *)startaddress;
|
||||
while (count + 4 <= size)
|
||||
{
|
||||
if (getreg32(addr) != FLASH_ERASEDVALUE_DW)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
addr++;
|
||||
count += 4;
|
||||
}
|
||||
|
||||
baddr = (uint8_t *)addr;
|
||||
while (count < size)
|
||||
{
|
||||
if (getreg8(baddr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
|
||||
count++;
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_wait_for_last_operation()
|
||||
*
|
||||
* Description:
|
||||
* Wait for last write/erase operation to finish
|
||||
* Return error in case of timeout
|
||||
*
|
||||
* Input Parameters:
|
||||
* priv - Flash bank based config
|
||||
*
|
||||
* Returned Value:
|
||||
* Zero or error value
|
||||
*
|
||||
* ETIME: Timeout while waiting for previous write/erase operation to
|
||||
* complete
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static int stm32h7_wait_for_last_operation(struct stm32h7_flash_priv_s
|
||||
*priv)
|
||||
{
|
||||
int i;
|
||||
bool timeout = true;
|
||||
|
||||
ARM_DSB();
|
||||
|
||||
for (i = 0; i < FLASH_TIMEOUT_VALUE; i++)
|
||||
{
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET) &
|
||||
(FLASH_SR_QW | FLASH_SR_BSY | FLASH_SR_WBNE)))
|
||||
{
|
||||
timeout = false;
|
||||
break;
|
||||
}
|
||||
|
||||
up_udelay(1);
|
||||
}
|
||||
|
||||
if (timeout)
|
||||
{
|
||||
return -EBUSY;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_unlock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Unlock the flash option bytes
|
||||
* Returns true if the flash was locked before, false otherwise
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static bool stm32h7_unlock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
bool ret = false;
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET) & FLASH_SR_BSY)
|
||||
{
|
||||
}
|
||||
|
||||
if (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK)
|
||||
{
|
||||
/* Unlock sequence */
|
||||
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY1);
|
||||
stm32h7_flash_putreg32(priv, STM32_FLASH_OPTKEYR_OFFSET,
|
||||
FLASH_OPTKEY2);
|
||||
|
||||
/* Was locked before and now unlocked */
|
||||
|
||||
ret = true;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_lock_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Lock the flash option bytes
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_lock_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTLOCK);
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_save_flashopt
|
||||
*
|
||||
* Description:
|
||||
* Save the flash option bytes to non-volatile storage.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
static void stm32h7_save_flashopt(struct stm32h7_flash_priv_s *priv)
|
||||
{
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET) &
|
||||
(FLASH_SR_BSY | FLASH_SR_CRCBUSY))
|
||||
{
|
||||
}
|
||||
|
||||
/* Can only write flash options if the option control reg is unlocked */
|
||||
|
||||
if (!(stm32h7_flash_getreg32(priv, STM32_FLASH_OPTCR_OFFSET) &
|
||||
FLASH_OPTCR_OPTLOCK))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTCR_OFFSET, 0,
|
||||
FLASH_OPTCR_OPTSTRT);
|
||||
}
|
||||
|
||||
/* Wait for the update to complete */
|
||||
|
||||
while (stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET) &
|
||||
FLASH_OPTSR_BUSYV)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_unlock
|
||||
*
|
||||
* Description:
|
||||
* Unlocks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_unlock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = stm32h7_flash_sem_lock(priv);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
stm32h7_flash_sem_unlock(priv);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_lock
|
||||
*
|
||||
* Description:
|
||||
* Locks a bank
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_lock(size_t addr)
|
||||
{
|
||||
int ret = -ENODEV;
|
||||
struct stm32h7_flash_priv_s *priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv)
|
||||
{
|
||||
ret = stm32h7_flash_sem_lock(priv);
|
||||
if (ret < 0)
|
||||
{
|
||||
return ret;
|
||||
}
|
||||
|
||||
stm32h7_lock_flash(priv);
|
||||
stm32h7_flash_sem_unlock(priv);
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_writeprotect
|
||||
*
|
||||
* Description:
|
||||
* Enable or disable the write protection of a flash sector.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
int stm32h7_flash_writeprotect(size_t block, bool enabled)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t setbits = 0;
|
||||
uint32_t clearbits = 0;
|
||||
int rv = -ENODEV;
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE));
|
||||
|
||||
if (priv)
|
||||
{
|
||||
if (enabled)
|
||||
{
|
||||
clearbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
else
|
||||
{
|
||||
setbits = 1 << block % (STM32_FLASH_NBLOCKS / 2);
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_WPSN_PRGR_OFFSET,
|
||||
clearbits, setbits);
|
||||
rv = OK;
|
||||
}
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_getopt
|
||||
*
|
||||
* Description:
|
||||
* Returns the current flash option bytes from the FLASH_OPTSR_CR register.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
uint32_t stm32h7_flash_getopt(void)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
return stm32h7_flash_getreg32(priv, STM32_FLASH_OPTSR_CUR_OFFSET);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_optmodify
|
||||
*
|
||||
* Description:
|
||||
* Modifies the current flash option bytes, given bits to set and clear.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_optmodify(uint32_t clear, uint32_t set)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
bool was_locked;
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1);
|
||||
if (priv)
|
||||
{
|
||||
was_locked = stm32h7_unlock_flashopt(priv);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_OPTSR_PRG_OFFSET,
|
||||
clear, set);
|
||||
stm32h7_save_flashopt(priv);
|
||||
if (was_locked)
|
||||
{
|
||||
stm32h7_lock_flashopt(priv);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: stm32h7_flash_swapbanks
|
||||
*
|
||||
* Description:
|
||||
* Swaps banks 1 and 2 in the processor's memory map. Takes effect
|
||||
* the next time the system is reset.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void stm32h7_flash_swapbanks(void)
|
||||
{
|
||||
uint32_t opts = stm32h7_flash_getopt();
|
||||
if (opts & FLASH_OPTCR_SWAPBANK)
|
||||
{
|
||||
stm32h7_flash_optmodify(FLASH_OPTCR_SWAPBANK, 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
stm32h7_flash_optmodify(0, FLASH_OPTCR_SWAPBANK);
|
||||
}
|
||||
}
|
||||
|
||||
size_t up_progmem_pagesize(size_t page)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_getpage(size_t addr)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
return priv->stpage + ((addr - priv->base) / FLASH_PAGE_SIZE);
|
||||
}
|
||||
|
||||
size_t up_progmem_getaddress(size_t block)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
if (block >= STM32_FLASH_NBLOCKS)
|
||||
{
|
||||
return SIZE_MAX;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE));
|
||||
return priv->base + (block - priv->stblock) * FLASH_SECTOR_SIZE;
|
||||
}
|
||||
|
||||
size_t up_progmem_neraseblocks(void)
|
||||
{
|
||||
return PROGMEM_NBLOCKS;
|
||||
}
|
||||
|
||||
bool up_progmem_isuniform(void)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_ispageerased(size_t page)
|
||||
{
|
||||
size_t addr;
|
||||
size_t count;
|
||||
size_t bwritten = 0;
|
||||
|
||||
if (page >= FLASH_NPAGES)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Verify */
|
||||
|
||||
for (addr = up_progmem_getaddress(page), count = up_progmem_pagesize(page);
|
||||
count; count--, addr++)
|
||||
{
|
||||
if (getreg8(addr) != FLASH_ERASEDVALUE)
|
||||
{
|
||||
bwritten++;
|
||||
}
|
||||
}
|
||||
|
||||
return bwritten;
|
||||
}
|
||||
|
||||
size_t up_progmem_erasesize(size_t block)
|
||||
{
|
||||
return FLASH_SECTOR_SIZE;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_eraseblock(size_t block)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
int ret;
|
||||
size_t block_address = STM32_FLASH_BANK1 + (block * FLASH_SECTOR_SIZE);
|
||||
|
||||
if (block >= PROGMEM_NBLOCKS)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
priv = stm32h7_flash_bank(block_address);
|
||||
|
||||
ret = stm32h7_flash_sem_lock(priv);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
up_invalidate_dcache((uintptr_t)block_address,
|
||||
(uintptr_t)(block_address + FLASH_SECTOR_SIZE - 1));
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_sem;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin erasing single block */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET, 0, FLASH_CR_SER);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET, FLASH_CR_SSN_MASK,
|
||||
FLASH_CR_SSN(block - priv->stblock));
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET,
|
||||
0, FLASH_CR_SER | FLASH_CR_START);
|
||||
|
||||
/* Wait for erase operation to complete */
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
ret = -EIO;
|
||||
goto exit_with_lock_sem;
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET,
|
||||
FLASH_CR_SER, 0);
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET,
|
||||
FLASH_CR_SSN_MASK, 0);
|
||||
|
||||
ret = 0;
|
||||
|
||||
exit_with_lock_sem:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
exit_with_sem:
|
||||
stm32h7_flash_sem_unlock(priv);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (ret == 0 &&
|
||||
stm32h7_israngeerased(block_address, up_progmem_erasesize(block)) == 0)
|
||||
{
|
||||
ret = up_progmem_erasesize(block); /* success */
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = -EIO; /* failure */
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
ssize_t up_progmem_write(size_t addr, const void *buf, size_t count)
|
||||
{
|
||||
struct stm32h7_flash_priv_s *priv;
|
||||
uint32_t *fp;
|
||||
uint32_t *rp;
|
||||
uint32_t *ll = (uint32_t *) buf;
|
||||
size_t faddr;
|
||||
size_t written = count;
|
||||
int ret;
|
||||
const size_t pagesize = 16; /* 128 bit, 16 bytes per page */
|
||||
const size_t llperpage = pagesize / sizeof(uint32_t);
|
||||
size_t pcount = count / pagesize;
|
||||
uint32_t sr;
|
||||
|
||||
priv = stm32h7_flash_bank(addr);
|
||||
|
||||
if (priv == NULL)
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
/* Check for valid address range */
|
||||
|
||||
if (addr < priv->base ||
|
||||
addr + count > priv->base + (STM32_FLASH_SIZE / 2))
|
||||
{
|
||||
return -EFAULT;
|
||||
}
|
||||
|
||||
ret = stm32h7_flash_sem_lock(priv);
|
||||
if (ret < 0)
|
||||
{
|
||||
return (ssize_t)ret;
|
||||
}
|
||||
|
||||
/* Check address and count alignment */
|
||||
|
||||
DEBUGASSERT(!(addr % pagesize));
|
||||
DEBUGASSERT(!(count % pagesize));
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_sem;
|
||||
}
|
||||
|
||||
/* Get flash ready and begin flashing */
|
||||
|
||||
stm32h7_unlock_flash(priv);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET, 0, FLASH_CR_PG);
|
||||
|
||||
for (ll = (uint32_t *) buf, faddr = addr; pcount;
|
||||
pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
/* Write 4 32 bit word and wait to complete */
|
||||
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
*fp++ = *rp++;
|
||||
|
||||
/* Data synchronous Barrier (DSB) just after the write operation. This
|
||||
* will force the CPU to respect the sequence of instruction (no
|
||||
* optimization).
|
||||
*/
|
||||
|
||||
ARM_DSB();
|
||||
ARM_ISB();
|
||||
|
||||
if (stm32h7_wait_for_last_operation(priv))
|
||||
{
|
||||
written = -EIO;
|
||||
goto exit_with_lock_sem;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET,
|
||||
FLASH_CR_PG,
|
||||
0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR_OFFSET,
|
||||
0, ~0);
|
||||
ret = -EIO;
|
||||
goto exit_with_lock_sem;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CR_OFFSET, FLASH_CR_PG, 0);
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR_OFFSET,
|
||||
0, ~0);
|
||||
exit_with_lock_sem:
|
||||
stm32h7_lock_flash(priv);
|
||||
|
||||
/* Verify */
|
||||
|
||||
if (written > 0)
|
||||
{
|
||||
for (ll = (uint32_t *) buf, faddr = addr, pcount = count / pagesize;
|
||||
pcount; pcount -= 1, ll += llperpage, faddr += pagesize)
|
||||
{
|
||||
fp = (uint32_t *) faddr;
|
||||
rp = ll;
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR_OFFSET,
|
||||
0, ~0);
|
||||
if ((*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++) ||
|
||||
(*fp++ != *rp++))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
|
||||
sr = stm32h7_flash_getreg32(priv, STM32_FLASH_SR_OFFSET);
|
||||
if (sr & (FLASH_SR_SNECCERR | FLASH_SR_DBECCERR))
|
||||
{
|
||||
written = -EIO;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
stm32h7_flash_modifyreg32(priv, STM32_FLASH_CCR_OFFSET,
|
||||
0, ~0);
|
||||
}
|
||||
|
||||
exit_with_sem:
|
||||
stm32h7_flash_sem_unlock(priv);
|
||||
return written;
|
||||
}
|
||||
|
||||
uint8_t up_progmem_erasestate(void)
|
||||
{
|
||||
return FLASH_ERASEDVALUE;
|
||||
}
|
@ -837,9 +837,17 @@ void stm32_stdclockconfig(void)
|
||||
* N.B. The system shall be power cycled before writing a new value.
|
||||
*/
|
||||
|
||||
#if defined(CONFIG_STM32H7_PWR_DIRECT_SMPS_SUPPLY)
|
||||
regval = getreg32(STM32_PWR_CR3);
|
||||
regval &= ~(STM32_PWR_CR3_BYPASS | STM32_PWR_CR3_LDOEN |
|
||||
STM32_PWR_CR3_SMPSEXTHP | STM32_PWR_CR3_SMPSLEVEL_MASK);
|
||||
regval |= STM32_PWR_CR3_LDOESCUEN;
|
||||
putreg32(regval, STM32_PWR_CR3);
|
||||
#else
|
||||
regval = getreg32(STM32_PWR_CR3);
|
||||
regval |= STM32_PWR_CR3_LDOEN | STM32_PWR_CR3_LDOESCUEN;
|
||||
putreg32(regval, STM32_PWR_CR3);
|
||||
#endif
|
||||
|
||||
/* Set the voltage output scale */
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user