2 ******************************************************************************
\r
3 * @file stm32l4xx_hal_flash_ex.c
\r
4 * @author MCD Application Team
\r
5 * @brief Extended FLASH HAL module driver.
\r
6 * This file provides firmware functions to manage the following
\r
7 * functionalities of the FLASH extended peripheral:
\r
8 * + Extended programming operations functions
\r
11 ==============================================================================
\r
12 ##### Flash Extended features #####
\r
13 ==============================================================================
\r
15 [..] Comparing to other previous devices, the FLASH interface for STM32L4xx
\r
16 devices contains the following additional features
\r
18 (+) Capacity up to 2 Mbyte with dual bank architecture supporting read-while-write
\r
20 (+) Dual bank memory organization
\r
21 (+) PCROP protection for all banks
\r
23 ##### How to use this driver #####
\r
24 ==============================================================================
\r
25 [..] This driver provides functions to configure and program the FLASH memory
\r
26 of all STM32L4xx devices. It includes
\r
27 (#) Flash Memory Erase functions:
\r
28 (++) Lock and Unlock the FLASH interface using HAL_FLASH_Unlock() and
\r
29 HAL_FLASH_Lock() functions
\r
30 (++) Erase function: Erase page, erase all sectors
\r
31 (++) There are two modes of erase :
\r
32 (+++) Polling Mode using HAL_FLASHEx_Erase()
\r
33 (+++) Interrupt Mode using HAL_FLASHEx_Erase_IT()
\r
35 (#) Option Bytes Programming function: Use HAL_FLASHEx_OBProgram() to :
\r
36 (++) Set/Reset the write protection
\r
37 (++) Set the Read protection Level
\r
38 (++) Program the user Option Bytes
\r
39 (++) Configure the PCROP protection
\r
41 (#) Get Option Bytes Configuration function: Use HAL_FLASHEx_OBGetConfig() to :
\r
42 (++) Get the value of a write protection area
\r
43 (++) Know if the read protection is activated
\r
44 (++) Get the value of the user Option Bytes
\r
45 (++) Get the value of a PCROP area
\r
48 ******************************************************************************
\r
51 * <h2><center>© Copyright (c) 2017 STMicroelectronics.
\r
52 * All rights reserved.</center></h2>
\r
54 * This software component is licensed by ST under BSD 3-Clause license,
\r
55 * the "License"; You may not use this file except in compliance with the
\r
56 * License. You may obtain a copy of the License at:
\r
57 * opensource.org/licenses/BSD-3-Clause
\r
59 ******************************************************************************
\r
62 /* Includes ------------------------------------------------------------------*/
\r
63 #include "stm32l4xx_hal.h"
\r
65 /** @addtogroup STM32L4xx_HAL_Driver
\r
69 /** @defgroup FLASHEx FLASHEx
\r
70 * @brief FLASH Extended HAL module driver
\r
74 #ifdef HAL_FLASH_MODULE_ENABLED
\r
76 /* Private typedef -----------------------------------------------------------*/
\r
77 /* Private define ------------------------------------------------------------*/
\r
78 /* Private macro -------------------------------------------------------------*/
\r
79 /* Private variables ---------------------------------------------------------*/
\r
80 /* Private function prototypes -----------------------------------------------*/
\r
81 /** @defgroup FLASHEx_Private_Functions FLASHEx Private Functions
\r
84 static void FLASH_MassErase(uint32_t Banks);
\r
85 static HAL_StatusTypeDef FLASH_OB_WRPConfig(uint32_t WRPArea, uint32_t WRPStartOffset, uint32_t WRDPEndOffset);
\r
86 static HAL_StatusTypeDef FLASH_OB_RDPConfig(uint32_t RDPLevel);
\r
87 static HAL_StatusTypeDef FLASH_OB_UserConfig(uint32_t UserType, uint32_t UserConfig);
\r
88 static HAL_StatusTypeDef FLASH_OB_PCROPConfig(uint32_t PCROPConfig, uint32_t PCROPStartAddr, uint32_t PCROPEndAddr);
\r
89 static void FLASH_OB_GetWRP(uint32_t WRPArea, uint32_t * WRPStartOffset, uint32_t * WRDPEndOffset);
\r
90 static uint32_t FLASH_OB_GetRDP(void);
\r
91 static uint32_t FLASH_OB_GetUser(void);
\r
92 static void FLASH_OB_GetPCROP(uint32_t * PCROPConfig, uint32_t * PCROPStartAddr, uint32_t * PCROPEndAddr);
\r
97 /* Exported functions -------------------------------------------------------*/
\r
98 /** @defgroup FLASHEx_Exported_Functions FLASHEx Exported Functions
\r
102 /** @defgroup FLASHEx_Exported_Functions_Group1 Extended IO operation functions
\r
103 * @brief Extended IO operation functions
\r
106 ===============================================================================
\r
107 ##### Extended programming operation functions #####
\r
108 ===============================================================================
\r
110 This subsection provides a set of functions allowing to manage the Extended FLASH
\r
111 programming operations Operations.
\r
117 * @brief Perform a mass erase or erase the specified FLASH memory pages.
\r
118 * @param[in] pEraseInit: pointer to an FLASH_EraseInitTypeDef structure that
\r
119 * contains the configuration information for the erasing.
\r
121 * @param[out] PageError : pointer to variable that contains the configuration
\r
122 * information on faulty page in case of error (0xFFFFFFFF means that all
\r
123 * the pages have been correctly erased)
\r
125 * @retval HAL Status
\r
127 HAL_StatusTypeDef HAL_FLASHEx_Erase(FLASH_EraseInitTypeDef *pEraseInit, uint32_t *PageError)
\r
129 HAL_StatusTypeDef status;
\r
130 uint32_t page_index;
\r
132 /* Process Locked */
\r
133 __HAL_LOCK(&pFlash);
\r
135 /* Check the parameters */
\r
136 assert_param(IS_FLASH_TYPEERASE(pEraseInit->TypeErase));
\r
138 /* Wait for last operation to be completed */
\r
139 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
141 if (status == HAL_OK)
\r
143 pFlash.ErrorCode = HAL_FLASH_ERROR_NONE;
\r
145 /* Deactivate the cache if they are activated to avoid data misbehavior */
\r
146 if(READ_BIT(FLASH->ACR, FLASH_ACR_ICEN) != 0U)
\r
148 /* Disable instruction cache */
\r
149 __HAL_FLASH_INSTRUCTION_CACHE_DISABLE();
\r
151 if(READ_BIT(FLASH->ACR, FLASH_ACR_DCEN) != 0U)
\r
153 /* Disable data cache */
\r
154 __HAL_FLASH_DATA_CACHE_DISABLE();
\r
155 pFlash.CacheToReactivate = FLASH_CACHE_ICACHE_DCACHE_ENABLED;
\r
159 pFlash.CacheToReactivate = FLASH_CACHE_ICACHE_ENABLED;
\r
162 else if(READ_BIT(FLASH->ACR, FLASH_ACR_DCEN) != 0U)
\r
164 /* Disable data cache */
\r
165 __HAL_FLASH_DATA_CACHE_DISABLE();
\r
166 pFlash.CacheToReactivate = FLASH_CACHE_DCACHE_ENABLED;
\r
170 pFlash.CacheToReactivate = FLASH_CACHE_DISABLED;
\r
173 if (pEraseInit->TypeErase == FLASH_TYPEERASE_MASSERASE)
\r
175 /* Mass erase to be done */
\r
176 FLASH_MassErase(pEraseInit->Banks);
\r
178 /* Wait for last operation to be completed */
\r
179 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
181 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
182 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
183 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
184 /* If the erase operation is completed, disable the MER1 and MER2 Bits */
\r
185 CLEAR_BIT(FLASH->CR, (FLASH_CR_MER1 | FLASH_CR_MER2));
\r
187 /* If the erase operation is completed, disable the MER1 Bit */
\r
188 CLEAR_BIT(FLASH->CR, (FLASH_CR_MER1));
\r
193 /*Initialization of PageError variable*/
\r
194 *PageError = 0xFFFFFFFFU;
\r
196 for(page_index = pEraseInit->Page; page_index < (pEraseInit->Page + pEraseInit->NbPages); page_index++)
\r
198 FLASH_PageErase(page_index, pEraseInit->Banks);
\r
200 /* Wait for last operation to be completed */
\r
201 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
203 /* If the erase operation is completed, disable the PER Bit */
\r
204 CLEAR_BIT(FLASH->CR, (FLASH_CR_PER | FLASH_CR_PNB));
\r
206 if (status != HAL_OK)
\r
208 /* In case of error, stop erase procedure and return the faulty address */
\r
209 *PageError = page_index;
\r
215 /* Flush the caches to be sure of the data consistency */
\r
216 FLASH_FlushCaches();
\r
219 /* Process Unlocked */
\r
220 __HAL_UNLOCK(&pFlash);
\r
226 * @brief Perform a mass erase or erase the specified FLASH memory pages with interrupt enabled.
\r
227 * @param pEraseInit: pointer to an FLASH_EraseInitTypeDef structure that
\r
228 * contains the configuration information for the erasing.
\r
230 * @retval HAL Status
\r
232 HAL_StatusTypeDef HAL_FLASHEx_Erase_IT(FLASH_EraseInitTypeDef *pEraseInit)
\r
234 HAL_StatusTypeDef status = HAL_OK;
\r
236 /* Process Locked */
\r
237 __HAL_LOCK(&pFlash);
\r
239 /* Check the parameters */
\r
240 assert_param(IS_FLASH_TYPEERASE(pEraseInit->TypeErase));
\r
242 pFlash.ErrorCode = HAL_FLASH_ERROR_NONE;
\r
244 /* Deactivate the cache if they are activated to avoid data misbehavior */
\r
245 if(READ_BIT(FLASH->ACR, FLASH_ACR_ICEN) != 0U)
\r
247 /* Disable instruction cache */
\r
248 __HAL_FLASH_INSTRUCTION_CACHE_DISABLE();
\r
250 if(READ_BIT(FLASH->ACR, FLASH_ACR_DCEN) != 0U)
\r
252 /* Disable data cache */
\r
253 __HAL_FLASH_DATA_CACHE_DISABLE();
\r
254 pFlash.CacheToReactivate = FLASH_CACHE_ICACHE_DCACHE_ENABLED;
\r
258 pFlash.CacheToReactivate = FLASH_CACHE_ICACHE_ENABLED;
\r
261 else if(READ_BIT(FLASH->ACR, FLASH_ACR_DCEN) != 0U)
\r
263 /* Disable data cache */
\r
264 __HAL_FLASH_DATA_CACHE_DISABLE();
\r
265 pFlash.CacheToReactivate = FLASH_CACHE_DCACHE_ENABLED;
\r
269 pFlash.CacheToReactivate = FLASH_CACHE_DISABLED;
\r
272 /* Enable End of Operation and Error interrupts */
\r
273 __HAL_FLASH_ENABLE_IT(FLASH_IT_EOP | FLASH_IT_OPERR);
\r
275 pFlash.Bank = pEraseInit->Banks;
\r
277 if (pEraseInit->TypeErase == FLASH_TYPEERASE_MASSERASE)
\r
279 /* Mass erase to be done */
\r
280 pFlash.ProcedureOnGoing = FLASH_PROC_MASS_ERASE;
\r
281 FLASH_MassErase(pEraseInit->Banks);
\r
285 /* Erase by page to be done */
\r
286 pFlash.ProcedureOnGoing = FLASH_PROC_PAGE_ERASE;
\r
287 pFlash.NbPagesToErase = pEraseInit->NbPages;
\r
288 pFlash.Page = pEraseInit->Page;
\r
290 /*Erase 1st page and wait for IT */
\r
291 FLASH_PageErase(pEraseInit->Page, pEraseInit->Banks);
\r
298 * @brief Program Option bytes.
\r
299 * @param pOBInit: pointer to an FLASH_OBInitStruct structure that
\r
300 * contains the configuration information for the programming.
\r
302 * @retval HAL Status
\r
304 HAL_StatusTypeDef HAL_FLASHEx_OBProgram(FLASH_OBProgramInitTypeDef *pOBInit)
\r
306 HAL_StatusTypeDef status = HAL_OK;
\r
308 /* Process Locked */
\r
309 __HAL_LOCK(&pFlash);
\r
311 /* Check the parameters */
\r
312 assert_param(IS_OPTIONBYTE(pOBInit->OptionType));
\r
314 pFlash.ErrorCode = HAL_FLASH_ERROR_NONE;
\r
316 /* Write protection configuration */
\r
317 if((pOBInit->OptionType & OPTIONBYTE_WRP) != 0U)
\r
319 /* Configure of Write protection on the selected area */
\r
320 if(FLASH_OB_WRPConfig(pOBInit->WRPArea, pOBInit->WRPStartOffset, pOBInit->WRPEndOffset) != HAL_OK)
\r
322 status = HAL_ERROR;
\r
327 /* Read protection configuration */
\r
328 if((pOBInit->OptionType & OPTIONBYTE_RDP) != 0U)
\r
330 /* Configure the Read protection level */
\r
331 if(FLASH_OB_RDPConfig(pOBInit->RDPLevel) != HAL_OK)
\r
333 status = HAL_ERROR;
\r
337 /* User Configuration */
\r
338 if((pOBInit->OptionType & OPTIONBYTE_USER) != 0U)
\r
340 /* Configure the user option bytes */
\r
341 if(FLASH_OB_UserConfig(pOBInit->USERType, pOBInit->USERConfig) != HAL_OK)
\r
343 status = HAL_ERROR;
\r
347 /* PCROP Configuration */
\r
348 if((pOBInit->OptionType & OPTIONBYTE_PCROP) != 0U)
\r
350 if (pOBInit->PCROPStartAddr != pOBInit->PCROPEndAddr)
\r
352 /* Configure the Proprietary code readout protection */
\r
353 if(FLASH_OB_PCROPConfig(pOBInit->PCROPConfig, pOBInit->PCROPStartAddr, pOBInit->PCROPEndAddr) != HAL_OK)
\r
355 status = HAL_ERROR;
\r
360 /* Process Unlocked */
\r
361 __HAL_UNLOCK(&pFlash);
\r
367 * @brief Get the Option bytes configuration.
\r
368 * @param pOBInit: pointer to an FLASH_OBInitStruct structure that contains the
\r
369 * configuration information.
\r
370 * @note The fields pOBInit->WRPArea and pOBInit->PCROPConfig should indicate
\r
371 * which area is requested for the WRP and PCROP, else no information will be returned
\r
375 void HAL_FLASHEx_OBGetConfig(FLASH_OBProgramInitTypeDef *pOBInit)
\r
377 pOBInit->OptionType = (OPTIONBYTE_RDP | OPTIONBYTE_USER);
\r
379 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
380 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
381 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
382 if((pOBInit->WRPArea == OB_WRPAREA_BANK1_AREAA) || (pOBInit->WRPArea == OB_WRPAREA_BANK1_AREAB) ||
\r
383 (pOBInit->WRPArea == OB_WRPAREA_BANK2_AREAA) || (pOBInit->WRPArea == OB_WRPAREA_BANK2_AREAB))
\r
385 if((pOBInit->WRPArea == OB_WRPAREA_BANK1_AREAA) || (pOBInit->WRPArea == OB_WRPAREA_BANK1_AREAB))
\r
388 pOBInit->OptionType |= OPTIONBYTE_WRP;
\r
389 /* Get write protection on the selected area */
\r
390 FLASH_OB_GetWRP(pOBInit->WRPArea, &(pOBInit->WRPStartOffset), &(pOBInit->WRPEndOffset));
\r
393 /* Get Read protection level */
\r
394 pOBInit->RDPLevel = FLASH_OB_GetRDP();
\r
396 /* Get the user option bytes */
\r
397 pOBInit->USERConfig = FLASH_OB_GetUser();
\r
399 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
400 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
401 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
402 if((pOBInit->PCROPConfig == FLASH_BANK_1) || (pOBInit->PCROPConfig == FLASH_BANK_2))
\r
404 if(pOBInit->PCROPConfig == FLASH_BANK_1)
\r
407 pOBInit->OptionType |= OPTIONBYTE_PCROP;
\r
408 /* Get the Proprietary code readout protection */
\r
409 FLASH_OB_GetPCROP(&(pOBInit->PCROPConfig), &(pOBInit->PCROPStartAddr), &(pOBInit->PCROPEndAddr));
\r
417 #if defined (FLASH_CFGR_LVEN)
\r
418 /** @defgroup FLASHEx_Exported_Functions_Group2 Extended specific configuration functions
\r
419 * @brief Extended specific configuration functions
\r
422 ===============================================================================
\r
423 ##### Extended specific configuration functions #####
\r
424 ===============================================================================
\r
426 This subsection provides a set of functions allowing to manage the Extended FLASH
\r
427 specific configurations.
\r
434 * @brief Configuration of the LVE pin of the Flash (managed by power controller
\r
435 * or forced to low in order to use an external SMPS)
\r
436 * @param ConfigLVE: Configuration of the LVE pin,
\r
437 * This parameter can be one of the following values:
\r
438 * @arg FLASH_LVE_PIN_CTRL: LVE FLASH pin controlled by power controller
\r
439 * @arg FLASH_LVE_PIN_FORCED: LVE FLASH pin enforced to low (external SMPS used)
\r
441 * @note Before enforcing the LVE pin to low, the SOC should be in low voltage
\r
442 * range 2 and the voltage VDD12 should be higher than 1.08V and SMPS is ON.
\r
444 * @retval HAL Status
\r
446 HAL_StatusTypeDef HAL_FLASHEx_ConfigLVEPin(uint32_t ConfigLVE)
\r
448 HAL_StatusTypeDef status;
\r
450 /* Process Locked */
\r
451 __HAL_LOCK(&pFlash);
\r
453 /* Check the parameters */
\r
454 assert_param(IS_FLASH_LVE_PIN(ConfigLVE));
\r
456 /* Wait for last operation to be completed */
\r
457 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
459 if (status == HAL_OK)
\r
461 /* Check that the voltage scaling is range 2 */
\r
462 if (HAL_PWREx_GetVoltageRange() == PWR_REGULATOR_VOLTAGE_SCALE2)
\r
464 /* Configure the LVEN bit */
\r
465 MODIFY_REG(FLASH->CFGR, FLASH_CFGR_LVEN, ConfigLVE);
\r
467 /* Check that the bit has been correctly configured */
\r
468 if (READ_BIT(FLASH->CFGR, FLASH_CFGR_LVEN) != ConfigLVE)
\r
470 status = HAL_ERROR;
\r
475 /* Not allow to force Flash LVE pin if not in voltage range 2 */
\r
476 status = HAL_ERROR;
\r
480 /* Process Unlocked */
\r
481 __HAL_UNLOCK(&pFlash);
\r
489 #endif /* FLASH_CFGR_LVEN */
\r
495 /* Private functions ---------------------------------------------------------*/
\r
497 /** @addtogroup FLASHEx_Private_Functions
\r
501 * @brief Mass erase of FLASH memory.
\r
502 * @param Banks: Banks to be erased
\r
503 * This parameter can be one of the following values:
\r
504 * @arg FLASH_BANK_1: Bank1 to be erased
\r
505 * @arg FLASH_BANK_2: Bank2 to be erased
\r
506 * @arg FLASH_BANK_BOTH: Bank1 and Bank2 to be erased
\r
509 static void FLASH_MassErase(uint32_t Banks)
\r
511 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
512 if (READ_BIT(FLASH->OPTR, FLASH_OPTR_DBANK) != 0U)
\r
515 /* Check the parameters */
\r
516 assert_param(IS_FLASH_BANK(Banks));
\r
518 /* Set the Mass Erase Bit for the bank 1 if requested */
\r
519 if((Banks & FLASH_BANK_1) != 0U)
\r
521 SET_BIT(FLASH->CR, FLASH_CR_MER1);
\r
524 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
525 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
526 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
527 /* Set the Mass Erase Bit for the bank 2 if requested */
\r
528 if((Banks & FLASH_BANK_2) != 0U)
\r
530 SET_BIT(FLASH->CR, FLASH_CR_MER2);
\r
534 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
537 SET_BIT(FLASH->CR, (FLASH_CR_MER1 | FLASH_CR_MER2));
\r
541 /* Proceed to erase all sectors */
\r
542 SET_BIT(FLASH->CR, FLASH_CR_STRT);
\r
546 * @brief Erase the specified FLASH memory page.
\r
547 * @param Page: FLASH page to erase
\r
548 * This parameter must be a value between 0 and (max number of pages in the bank - 1)
\r
549 * @param Banks: Bank(s) where the page will be erased
\r
550 * This parameter can be one of the following values:
\r
551 * @arg FLASH_BANK_1: Page in bank 1 to be erased
\r
552 * @arg FLASH_BANK_2: Page in bank 2 to be erased
\r
555 void FLASH_PageErase(uint32_t Page, uint32_t Banks)
\r
557 /* Check the parameters */
\r
558 assert_param(IS_FLASH_PAGE(Page));
\r
560 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
561 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
562 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
563 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
564 if(READ_BIT(FLASH->OPTR, FLASH_OPTR_DBANK) == 0U)
\r
566 CLEAR_BIT(FLASH->CR, FLASH_CR_BKER);
\r
571 assert_param(IS_FLASH_BANK_EXCLUSIVE(Banks));
\r
573 if((Banks & FLASH_BANK_1) != 0U)
\r
575 CLEAR_BIT(FLASH->CR, FLASH_CR_BKER);
\r
579 SET_BIT(FLASH->CR, FLASH_CR_BKER);
\r
583 /* Prevent unused argument(s) compilation warning */
\r
587 /* Proceed to erase the page */
\r
588 MODIFY_REG(FLASH->CR, FLASH_CR_PNB, ((Page & 0xFFU) << FLASH_CR_PNB_Pos));
\r
589 SET_BIT(FLASH->CR, FLASH_CR_PER);
\r
590 SET_BIT(FLASH->CR, FLASH_CR_STRT);
\r
594 * @brief Flush the instruction and data caches.
\r
597 void FLASH_FlushCaches(void)
\r
599 FLASH_CacheTypeDef cache = pFlash.CacheToReactivate;
\r
601 /* Flush instruction cache */
\r
602 if((cache == FLASH_CACHE_ICACHE_ENABLED) ||
\r
603 (cache == FLASH_CACHE_ICACHE_DCACHE_ENABLED))
\r
605 /* Reset instruction cache */
\r
606 __HAL_FLASH_INSTRUCTION_CACHE_RESET();
\r
607 /* Enable instruction cache */
\r
608 __HAL_FLASH_INSTRUCTION_CACHE_ENABLE();
\r
611 /* Flush data cache */
\r
612 if((cache == FLASH_CACHE_DCACHE_ENABLED) ||
\r
613 (cache == FLASH_CACHE_ICACHE_DCACHE_ENABLED))
\r
615 /* Reset data cache */
\r
616 __HAL_FLASH_DATA_CACHE_RESET();
\r
617 /* Enable data cache */
\r
618 __HAL_FLASH_DATA_CACHE_ENABLE();
\r
621 /* Reset internal variable */
\r
622 pFlash.CacheToReactivate = FLASH_CACHE_DISABLED;
\r
626 * @brief Configure the write protection of the desired pages.
\r
628 * @note When the memory read protection level is selected (RDP level = 1),
\r
629 * it is not possible to program or erase Flash memory if the CPU debug
\r
630 * features are connected (JTAG or single wire) or boot code is being
\r
631 * executed from RAM or System flash, even if WRP is not activated.
\r
632 * @note To configure the WRP options, the option lock bit OPTLOCK must be
\r
633 * cleared with the call of the HAL_FLASH_OB_Unlock() function.
\r
634 * @note To validate the WRP options, the option bytes must be reloaded
\r
635 * through the call of the HAL_FLASH_OB_Launch() function.
\r
637 * @param WRPArea: specifies the area to be configured.
\r
638 * This parameter can be one of the following values:
\r
639 * @arg OB_WRPAREA_BANK1_AREAA: Flash Bank 1 Area A
\r
640 * @arg OB_WRPAREA_BANK1_AREAB: Flash Bank 1 Area B
\r
641 * @arg OB_WRPAREA_BANK2_AREAA: Flash Bank 2 Area A (don't apply for STM32L43x/STM32L44x devices)
\r
642 * @arg OB_WRPAREA_BANK2_AREAB: Flash Bank 2 Area B (don't apply for STM32L43x/STM32L44x devices)
\r
644 * @param WRPStartOffset: specifies the start page of the write protected area
\r
645 * This parameter can be page number between 0 and (max number of pages in the bank - 1)
\r
647 * @param WRDPEndOffset: specifies the end page of the write protected area
\r
648 * This parameter can be page number between WRPStartOffset and (max number of pages in the bank - 1)
\r
650 * @retval HAL Status
\r
652 static HAL_StatusTypeDef FLASH_OB_WRPConfig(uint32_t WRPArea, uint32_t WRPStartOffset, uint32_t WRDPEndOffset)
\r
654 HAL_StatusTypeDef status;
\r
656 /* Check the parameters */
\r
657 assert_param(IS_OB_WRPAREA(WRPArea));
\r
658 assert_param(IS_FLASH_PAGE(WRPStartOffset));
\r
659 assert_param(IS_FLASH_PAGE(WRDPEndOffset));
\r
661 /* Wait for last operation to be completed */
\r
662 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
664 if(status == HAL_OK)
\r
666 /* Configure the write protected area */
\r
667 if(WRPArea == OB_WRPAREA_BANK1_AREAA)
\r
669 MODIFY_REG(FLASH->WRP1AR, (FLASH_WRP1AR_WRP1A_STRT | FLASH_WRP1AR_WRP1A_END),
\r
670 (WRPStartOffset | (WRDPEndOffset << 16)));
\r
672 else if(WRPArea == OB_WRPAREA_BANK1_AREAB)
\r
674 MODIFY_REG(FLASH->WRP1BR, (FLASH_WRP1BR_WRP1B_STRT | FLASH_WRP1BR_WRP1B_END),
\r
675 (WRPStartOffset | (WRDPEndOffset << 16)));
\r
677 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
678 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
679 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
680 else if(WRPArea == OB_WRPAREA_BANK2_AREAA)
\r
682 MODIFY_REG(FLASH->WRP2AR, (FLASH_WRP2AR_WRP2A_STRT | FLASH_WRP2AR_WRP2A_END),
\r
683 (WRPStartOffset | (WRDPEndOffset << 16)));
\r
685 else if(WRPArea == OB_WRPAREA_BANK2_AREAB)
\r
687 MODIFY_REG(FLASH->WRP2BR, (FLASH_WRP2BR_WRP2B_STRT | FLASH_WRP2BR_WRP2B_END),
\r
688 (WRPStartOffset | (WRDPEndOffset << 16)));
\r
693 /* Nothing to do */
\r
696 /* Set OPTSTRT Bit */
\r
697 SET_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
699 /* Wait for last operation to be completed */
\r
700 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
702 /* If the option byte program operation is completed, disable the OPTSTRT Bit */
\r
703 CLEAR_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
710 * @brief Set the read protection level.
\r
712 * @note To configure the RDP level, the option lock bit OPTLOCK must be
\r
713 * cleared with the call of the HAL_FLASH_OB_Unlock() function.
\r
714 * @note To validate the RDP level, the option bytes must be reloaded
\r
715 * through the call of the HAL_FLASH_OB_Launch() function.
\r
716 * @note !!! Warning : When enabling OB_RDP level 2 it's no more possible
\r
717 * to go back to level 1 or 0 !!!
\r
719 * @param RDPLevel: specifies the read protection level.
\r
720 * This parameter can be one of the following values:
\r
721 * @arg OB_RDP_LEVEL_0: No protection
\r
722 * @arg OB_RDP_LEVEL_1: Read protection of the memory
\r
723 * @arg OB_RDP_LEVEL_2: Full chip protection
\r
725 * @retval HAL status
\r
727 static HAL_StatusTypeDef FLASH_OB_RDPConfig(uint32_t RDPLevel)
\r
729 HAL_StatusTypeDef status;
\r
731 /* Check the parameters */
\r
732 assert_param(IS_OB_RDP_LEVEL(RDPLevel));
\r
734 /* Wait for last operation to be completed */
\r
735 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
737 if(status == HAL_OK)
\r
739 /* Configure the RDP level in the option bytes register */
\r
740 MODIFY_REG(FLASH->OPTR, FLASH_OPTR_RDP, RDPLevel);
\r
742 /* Set OPTSTRT Bit */
\r
743 SET_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
745 /* Wait for last operation to be completed */
\r
746 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
748 /* If the option byte program operation is completed, disable the OPTSTRT Bit */
\r
749 CLEAR_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
756 * @brief Program the FLASH User Option Byte.
\r
758 * @note To configure the user option bytes, the option lock bit OPTLOCK must
\r
759 * be cleared with the call of the HAL_FLASH_OB_Unlock() function.
\r
760 * @note To validate the user option bytes, the option bytes must be reloaded
\r
761 * through the call of the HAL_FLASH_OB_Launch() function.
\r
763 * @param UserType: The FLASH User Option Bytes to be modified
\r
764 * @param UserConfig: The FLASH User Option Bytes values:
\r
765 * BOR_LEV(Bit8-10), nRST_STOP(Bit12), nRST_STDBY(Bit13), IWDG_SW(Bit16),
\r
766 * IWDG_STOP(Bit17), IWDG_STDBY(Bit18), WWDG_SW(Bit19), BFB2(Bit20),
\r
767 * DUALBANK(Bit21), nBOOT1(Bit23), SRAM2_PE(Bit24) and SRAM2_RST(Bit25).
\r
769 * @retval HAL status
\r
771 static HAL_StatusTypeDef FLASH_OB_UserConfig(uint32_t UserType, uint32_t UserConfig)
\r
773 uint32_t optr_reg_val = 0;
\r
774 uint32_t optr_reg_mask = 0;
\r
775 HAL_StatusTypeDef status;
\r
777 /* Check the parameters */
\r
778 assert_param(IS_OB_USER_TYPE(UserType));
\r
780 /* Wait for last operation to be completed */
\r
781 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
783 if(status == HAL_OK)
\r
785 if((UserType & OB_USER_BOR_LEV) != 0U)
\r
787 /* BOR level option byte should be modified */
\r
788 assert_param(IS_OB_USER_BOR_LEVEL(UserConfig & FLASH_OPTR_BOR_LEV));
\r
790 /* Set value and mask for BOR level option byte */
\r
791 optr_reg_val |= (UserConfig & FLASH_OPTR_BOR_LEV);
\r
792 optr_reg_mask |= FLASH_OPTR_BOR_LEV;
\r
795 if((UserType & OB_USER_nRST_STOP) != 0U)
\r
797 /* nRST_STOP option byte should be modified */
\r
798 assert_param(IS_OB_USER_STOP(UserConfig & FLASH_OPTR_nRST_STOP));
\r
800 /* Set value and mask for nRST_STOP option byte */
\r
801 optr_reg_val |= (UserConfig & FLASH_OPTR_nRST_STOP);
\r
802 optr_reg_mask |= FLASH_OPTR_nRST_STOP;
\r
805 if((UserType & OB_USER_nRST_STDBY) != 0U)
\r
807 /* nRST_STDBY option byte should be modified */
\r
808 assert_param(IS_OB_USER_STANDBY(UserConfig & FLASH_OPTR_nRST_STDBY));
\r
810 /* Set value and mask for nRST_STDBY option byte */
\r
811 optr_reg_val |= (UserConfig & FLASH_OPTR_nRST_STDBY);
\r
812 optr_reg_mask |= FLASH_OPTR_nRST_STDBY;
\r
815 if((UserType & OB_USER_nRST_SHDW) != 0U)
\r
817 /* nRST_SHDW option byte should be modified */
\r
818 assert_param(IS_OB_USER_SHUTDOWN(UserConfig & FLASH_OPTR_nRST_SHDW));
\r
820 /* Set value and mask for nRST_SHDW option byte */
\r
821 optr_reg_val |= (UserConfig & FLASH_OPTR_nRST_SHDW);
\r
822 optr_reg_mask |= FLASH_OPTR_nRST_SHDW;
\r
825 if((UserType & OB_USER_IWDG_SW) != 0U)
\r
827 /* IWDG_SW option byte should be modified */
\r
828 assert_param(IS_OB_USER_IWDG(UserConfig & FLASH_OPTR_IWDG_SW));
\r
830 /* Set value and mask for IWDG_SW option byte */
\r
831 optr_reg_val |= (UserConfig & FLASH_OPTR_IWDG_SW);
\r
832 optr_reg_mask |= FLASH_OPTR_IWDG_SW;
\r
835 if((UserType & OB_USER_IWDG_STOP) != 0U)
\r
837 /* IWDG_STOP option byte should be modified */
\r
838 assert_param(IS_OB_USER_IWDG_STOP(UserConfig & FLASH_OPTR_IWDG_STOP));
\r
840 /* Set value and mask for IWDG_STOP option byte */
\r
841 optr_reg_val |= (UserConfig & FLASH_OPTR_IWDG_STOP);
\r
842 optr_reg_mask |= FLASH_OPTR_IWDG_STOP;
\r
845 if((UserType & OB_USER_IWDG_STDBY) != 0U)
\r
847 /* IWDG_STDBY option byte should be modified */
\r
848 assert_param(IS_OB_USER_IWDG_STDBY(UserConfig & FLASH_OPTR_IWDG_STDBY));
\r
850 /* Set value and mask for IWDG_STDBY option byte */
\r
851 optr_reg_val |= (UserConfig & FLASH_OPTR_IWDG_STDBY);
\r
852 optr_reg_mask |= FLASH_OPTR_IWDG_STDBY;
\r
855 if((UserType & OB_USER_WWDG_SW) != 0U)
\r
857 /* WWDG_SW option byte should be modified */
\r
858 assert_param(IS_OB_USER_WWDG(UserConfig & FLASH_OPTR_WWDG_SW));
\r
860 /* Set value and mask for WWDG_SW option byte */
\r
861 optr_reg_val |= (UserConfig & FLASH_OPTR_WWDG_SW);
\r
862 optr_reg_mask |= FLASH_OPTR_WWDG_SW;
\r
865 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
866 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
867 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
868 if((UserType & OB_USER_BFB2) != 0U)
\r
870 /* BFB2 option byte should be modified */
\r
871 assert_param(IS_OB_USER_BFB2(UserConfig & FLASH_OPTR_BFB2));
\r
873 /* Set value and mask for BFB2 option byte */
\r
874 optr_reg_val |= (UserConfig & FLASH_OPTR_BFB2);
\r
875 optr_reg_mask |= FLASH_OPTR_BFB2;
\r
878 if((UserType & OB_USER_DUALBANK) != 0U)
\r
880 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
881 /* DUALBANK option byte should be modified */
\r
882 assert_param(IS_OB_USER_DUALBANK(UserConfig & FLASH_OPTR_DB1M));
\r
884 /* Set value and mask for DUALBANK option byte */
\r
885 optr_reg_val |= (UserConfig & FLASH_OPTR_DB1M);
\r
886 optr_reg_mask |= FLASH_OPTR_DB1M;
\r
888 /* DUALBANK option byte should be modified */
\r
889 assert_param(IS_OB_USER_DUALBANK(UserConfig & FLASH_OPTR_DUALBANK));
\r
891 /* Set value and mask for DUALBANK option byte */
\r
892 optr_reg_val |= (UserConfig & FLASH_OPTR_DUALBANK);
\r
893 optr_reg_mask |= FLASH_OPTR_DUALBANK;
\r
898 if((UserType & OB_USER_nBOOT1) != 0U)
\r
900 /* nBOOT1 option byte should be modified */
\r
901 assert_param(IS_OB_USER_BOOT1(UserConfig & FLASH_OPTR_nBOOT1));
\r
903 /* Set value and mask for nBOOT1 option byte */
\r
904 optr_reg_val |= (UserConfig & FLASH_OPTR_nBOOT1);
\r
905 optr_reg_mask |= FLASH_OPTR_nBOOT1;
\r
908 if((UserType & OB_USER_SRAM2_PE) != 0U)
\r
910 /* SRAM2_PE option byte should be modified */
\r
911 assert_param(IS_OB_USER_SRAM2_PARITY(UserConfig & FLASH_OPTR_SRAM2_PE));
\r
913 /* Set value and mask for SRAM2_PE option byte */
\r
914 optr_reg_val |= (UserConfig & FLASH_OPTR_SRAM2_PE);
\r
915 optr_reg_mask |= FLASH_OPTR_SRAM2_PE;
\r
918 if((UserType & OB_USER_SRAM2_RST) != 0U)
\r
920 /* SRAM2_RST option byte should be modified */
\r
921 assert_param(IS_OB_USER_SRAM2_RST(UserConfig & FLASH_OPTR_SRAM2_RST));
\r
923 /* Set value and mask for SRAM2_RST option byte */
\r
924 optr_reg_val |= (UserConfig & FLASH_OPTR_SRAM2_RST);
\r
925 optr_reg_mask |= FLASH_OPTR_SRAM2_RST;
\r
928 #if defined (STM32L412xx) || defined (STM32L422xx) || defined (STM32L431xx) || defined (STM32L432xx) || defined (STM32L433xx) || \
\r
929 defined (STM32L442xx) || defined (STM32L443xx) || defined (STM32L451xx) || defined (STM32L452xx) || defined (STM32L462xx) || \
\r
930 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
931 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
932 if((UserType & OB_USER_nSWBOOT0) != 0U)
\r
934 /* nSWBOOT0 option byte should be modified */
\r
935 assert_param(IS_OB_USER_SWBOOT0(UserConfig & FLASH_OPTR_nSWBOOT0));
\r
937 /* Set value and mask for nSWBOOT0 option byte */
\r
938 optr_reg_val |= (UserConfig & FLASH_OPTR_nSWBOOT0);
\r
939 optr_reg_mask |= FLASH_OPTR_nSWBOOT0;
\r
942 if((UserType & OB_USER_nBOOT0) != 0U)
\r
944 /* nBOOT0 option byte should be modified */
\r
945 assert_param(IS_OB_USER_BOOT0(UserConfig & FLASH_OPTR_nBOOT0));
\r
947 /* Set value and mask for nBOOT0 option byte */
\r
948 optr_reg_val |= (UserConfig & FLASH_OPTR_nBOOT0);
\r
949 optr_reg_mask |= FLASH_OPTR_nBOOT0;
\r
953 /* Configure the option bytes register */
\r
954 MODIFY_REG(FLASH->OPTR, optr_reg_mask, optr_reg_val);
\r
956 /* Set OPTSTRT Bit */
\r
957 SET_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
959 /* Wait for last operation to be completed */
\r
960 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
962 /* If the option byte program operation is completed, disable the OPTSTRT Bit */
\r
963 CLEAR_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
970 * @brief Configure the Proprietary code readout protection of the desired addresses.
\r
972 * @note To configure the PCROP options, the option lock bit OPTLOCK must be
\r
973 * cleared with the call of the HAL_FLASH_OB_Unlock() function.
\r
974 * @note To validate the PCROP options, the option bytes must be reloaded
\r
975 * through the call of the HAL_FLASH_OB_Launch() function.
\r
977 * @param PCROPConfig: specifies the configuration (Bank to be configured and PCROP_RDP option).
\r
978 * This parameter must be a combination of FLASH_BANK_1 or FLASH_BANK_2
\r
979 * with OB_PCROP_RDP_NOT_ERASE or OB_PCROP_RDP_ERASE
\r
981 * @param PCROPStartAddr: specifies the start address of the Proprietary code readout protection
\r
982 * This parameter can be an address between begin and end of the bank
\r
984 * @param PCROPEndAddr: specifies the end address of the Proprietary code readout protection
\r
985 * This parameter can be an address between PCROPStartAddr and end of the bank
\r
987 * @retval HAL Status
\r
989 static HAL_StatusTypeDef FLASH_OB_PCROPConfig(uint32_t PCROPConfig, uint32_t PCROPStartAddr, uint32_t PCROPEndAddr)
\r
991 HAL_StatusTypeDef status;
\r
992 uint32_t reg_value;
\r
993 uint32_t bank1_addr;
\r
994 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
995 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
996 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
997 uint32_t bank2_addr;
\r
1000 /* Check the parameters */
\r
1001 assert_param(IS_FLASH_BANK_EXCLUSIVE(PCROPConfig & FLASH_BANK_BOTH));
\r
1002 assert_param(IS_OB_PCROP_RDP(PCROPConfig & FLASH_PCROP1ER_PCROP_RDP));
\r
1003 assert_param(IS_FLASH_MAIN_MEM_ADDRESS(PCROPStartAddr));
\r
1004 assert_param(IS_FLASH_MAIN_MEM_ADDRESS(PCROPEndAddr));
\r
1006 /* Wait for last operation to be completed */
\r
1007 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
1009 if(status == HAL_OK)
\r
1011 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1012 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1013 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1014 /* Get the information about the bank swapping */
\r
1015 if (READ_BIT(SYSCFG->MEMRMP, SYSCFG_MEMRMP_FB_MODE) == 0U)
\r
1017 bank1_addr = FLASH_BASE;
\r
1018 bank2_addr = FLASH_BASE + FLASH_BANK_SIZE;
\r
1022 bank1_addr = FLASH_BASE + FLASH_BANK_SIZE;
\r
1023 bank2_addr = FLASH_BASE;
\r
1026 bank1_addr = FLASH_BASE;
\r
1029 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1030 if (READ_BIT(FLASH->OPTR, FLASH_OPTR_DBANK) == 0U)
\r
1032 /* Configure the Proprietary code readout protection */
\r
1033 if((PCROPConfig & FLASH_BANK_BOTH) == FLASH_BANK_1)
\r
1035 reg_value = ((PCROPStartAddr - FLASH_BASE) >> 4);
\r
1036 MODIFY_REG(FLASH->PCROP1SR, FLASH_PCROP1SR_PCROP1_STRT, reg_value);
\r
1038 reg_value = ((PCROPEndAddr - FLASH_BASE) >> 4);
\r
1039 MODIFY_REG(FLASH->PCROP1ER, FLASH_PCROP1ER_PCROP1_END, reg_value);
\r
1041 else if((PCROPConfig & FLASH_BANK_BOTH) == FLASH_BANK_2)
\r
1043 reg_value = ((PCROPStartAddr - FLASH_BASE) >> 4);
\r
1044 MODIFY_REG(FLASH->PCROP2SR, FLASH_PCROP2SR_PCROP2_STRT, reg_value);
\r
1046 reg_value = ((PCROPEndAddr - FLASH_BASE) >> 4);
\r
1047 MODIFY_REG(FLASH->PCROP2ER, FLASH_PCROP2ER_PCROP2_END, reg_value);
\r
1051 /* Nothing to do */
\r
1057 /* Configure the Proprietary code readout protection */
\r
1058 if((PCROPConfig & FLASH_BANK_BOTH) == FLASH_BANK_1)
\r
1060 reg_value = ((PCROPStartAddr - bank1_addr) >> 3);
\r
1061 MODIFY_REG(FLASH->PCROP1SR, FLASH_PCROP1SR_PCROP1_STRT, reg_value);
\r
1063 reg_value = ((PCROPEndAddr - bank1_addr) >> 3);
\r
1064 MODIFY_REG(FLASH->PCROP1ER, FLASH_PCROP1ER_PCROP1_END, reg_value);
\r
1066 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1067 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1068 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1069 else if((PCROPConfig & FLASH_BANK_BOTH) == FLASH_BANK_2)
\r
1071 reg_value = ((PCROPStartAddr - bank2_addr) >> 3);
\r
1072 MODIFY_REG(FLASH->PCROP2SR, FLASH_PCROP2SR_PCROP2_STRT, reg_value);
\r
1074 reg_value = ((PCROPEndAddr - bank2_addr) >> 3);
\r
1075 MODIFY_REG(FLASH->PCROP2ER, FLASH_PCROP2ER_PCROP2_END, reg_value);
\r
1080 /* Nothing to do */
\r
1084 MODIFY_REG(FLASH->PCROP1ER, FLASH_PCROP1ER_PCROP_RDP, (PCROPConfig & FLASH_PCROP1ER_PCROP_RDP));
\r
1086 /* Set OPTSTRT Bit */
\r
1087 SET_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
1089 /* Wait for last operation to be completed */
\r
1090 status = FLASH_WaitForLastOperation((uint32_t)FLASH_TIMEOUT_VALUE);
\r
1092 /* If the option byte program operation is completed, disable the OPTSTRT Bit */
\r
1093 CLEAR_BIT(FLASH->CR, FLASH_CR_OPTSTRT);
\r
1100 * @brief Return the FLASH Write Protection Option Bytes value.
\r
1102 * @param[in] WRPArea: specifies the area to be returned.
\r
1103 * This parameter can be one of the following values:
\r
1104 * @arg OB_WRPAREA_BANK1_AREAA: Flash Bank 1 Area A
\r
1105 * @arg OB_WRPAREA_BANK1_AREAB: Flash Bank 1 Area B
\r
1106 * @arg OB_WRPAREA_BANK2_AREAA: Flash Bank 2 Area A (don't apply to STM32L43x/STM32L44x devices)
\r
1107 * @arg OB_WRPAREA_BANK2_AREAB: Flash Bank 2 Area B (don't apply to STM32L43x/STM32L44x devices)
\r
1109 * @param[out] WRPStartOffset: specifies the address where to copied the start page
\r
1110 * of the write protected area
\r
1112 * @param[out] WRDPEndOffset: specifies the address where to copied the end page of
\r
1113 * the write protected area
\r
1117 static void FLASH_OB_GetWRP(uint32_t WRPArea, uint32_t * WRPStartOffset, uint32_t * WRDPEndOffset)
\r
1119 /* Get the configuration of the write protected area */
\r
1120 if(WRPArea == OB_WRPAREA_BANK1_AREAA)
\r
1122 *WRPStartOffset = READ_BIT(FLASH->WRP1AR, FLASH_WRP1AR_WRP1A_STRT);
\r
1123 *WRDPEndOffset = (READ_BIT(FLASH->WRP1AR, FLASH_WRP1AR_WRP1A_END) >> 16);
\r
1125 else if(WRPArea == OB_WRPAREA_BANK1_AREAB)
\r
1127 *WRPStartOffset = READ_BIT(FLASH->WRP1BR, FLASH_WRP1BR_WRP1B_STRT);
\r
1128 *WRDPEndOffset = (READ_BIT(FLASH->WRP1BR, FLASH_WRP1BR_WRP1B_END) >> 16);
\r
1130 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1131 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1132 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1133 else if(WRPArea == OB_WRPAREA_BANK2_AREAA)
\r
1135 *WRPStartOffset = READ_BIT(FLASH->WRP2AR, FLASH_WRP2AR_WRP2A_STRT);
\r
1136 *WRDPEndOffset = (READ_BIT(FLASH->WRP2AR, FLASH_WRP2AR_WRP2A_END) >> 16);
\r
1138 else if(WRPArea == OB_WRPAREA_BANK2_AREAB)
\r
1140 *WRPStartOffset = READ_BIT(FLASH->WRP2BR, FLASH_WRP2BR_WRP2B_STRT);
\r
1141 *WRDPEndOffset = (READ_BIT(FLASH->WRP2BR, FLASH_WRP2BR_WRP2B_END) >> 16);
\r
1146 /* Nothing to do */
\r
1151 * @brief Return the FLASH Read Protection level.
\r
1152 * @retval FLASH ReadOut Protection Status:
\r
1153 * This return value can be one of the following values:
\r
1154 * @arg OB_RDP_LEVEL_0: No protection
\r
1155 * @arg OB_RDP_LEVEL_1: Read protection of the memory
\r
1156 * @arg OB_RDP_LEVEL_2: Full chip protection
\r
1158 static uint32_t FLASH_OB_GetRDP(void)
\r
1160 uint32_t rdp_level = READ_BIT(FLASH->OPTR, FLASH_OPTR_RDP);
\r
1162 if ((rdp_level != OB_RDP_LEVEL_0) && (rdp_level != OB_RDP_LEVEL_2))
\r
1164 return (OB_RDP_LEVEL_1);
\r
1168 return (READ_BIT(FLASH->OPTR, FLASH_OPTR_RDP));
\r
1173 * @brief Return the FLASH User Option Byte value.
\r
1174 * @retval The FLASH User Option Bytes values:
\r
1175 * For STM32L47x/STM32L48x devices :
\r
1176 * BOR_LEV(Bit8-10), nRST_STOP(Bit12), nRST_STDBY(Bit13), nRST_SHDW(Bit14),
\r
1177 * IWDG_SW(Bit16), IWDG_STOP(Bit17), IWDG_STDBY(Bit18), WWDG_SW(Bit19),
\r
1178 * BFB2(Bit20), DUALBANK(Bit21), nBOOT1(Bit23), SRAM2_PE(Bit24) and SRAM2_RST(Bit25).
\r
1179 * For STM32L43x/STM32L44x devices :
\r
1180 * BOR_LEV(Bit8-10), nRST_STOP(Bit12), nRST_STDBY(Bit13), nRST_SHDW(Bit14),
\r
1181 * IWDG_SW(Bit16), IWDG_STOP(Bit17), IWDG_STDBY(Bit18), WWDG_SW(Bit19),
\r
1182 * nBOOT1(Bit23), SRAM2_PE(Bit24), SRAM2_RST(Bit25), nSWBOOT0(Bit26) and nBOOT0(Bit27).
\r
1184 static uint32_t FLASH_OB_GetUser(void)
\r
1186 uint32_t user_config = READ_REG(FLASH->OPTR);
\r
1187 CLEAR_BIT(user_config, FLASH_OPTR_RDP);
\r
1189 return user_config;
\r
1193 * @brief Return the FLASH Write Protection Option Bytes value.
\r
1195 * @param PCROPConfig [inout]: specifies the configuration (Bank to be configured and PCROP_RDP option).
\r
1196 * This parameter must be a combination of FLASH_BANK_1 or FLASH_BANK_2
\r
1197 * with OB_PCROP_RDP_NOT_ERASE or OB_PCROP_RDP_ERASE
\r
1199 * @param PCROPStartAddr [out]: specifies the address where to copied the start address
\r
1200 * of the Proprietary code readout protection
\r
1202 * @param PCROPEndAddr [out]: specifies the address where to copied the end address of
\r
1203 * the Proprietary code readout protection
\r
1207 static void FLASH_OB_GetPCROP(uint32_t * PCROPConfig, uint32_t * PCROPStartAddr, uint32_t * PCROPEndAddr)
\r
1209 uint32_t reg_value;
\r
1210 uint32_t bank1_addr;
\r
1211 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1212 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1213 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1214 uint32_t bank2_addr;
\r
1217 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1218 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1219 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1220 /* Get the information about the bank swapping */
\r
1221 if (READ_BIT(SYSCFG->MEMRMP, SYSCFG_MEMRMP_FB_MODE) == 0U)
\r
1223 bank1_addr = FLASH_BASE;
\r
1224 bank2_addr = FLASH_BASE + FLASH_BANK_SIZE;
\r
1228 bank1_addr = FLASH_BASE + FLASH_BANK_SIZE;
\r
1229 bank2_addr = FLASH_BASE;
\r
1232 bank1_addr = FLASH_BASE;
\r
1235 #if defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1236 if (READ_BIT(FLASH->OPTR, FLASH_OPTR_DBANK) == 0U)
\r
1238 if(((*PCROPConfig) & FLASH_BANK_BOTH) == FLASH_BANK_1)
\r
1240 reg_value = (READ_REG(FLASH->PCROP1SR) & FLASH_PCROP1SR_PCROP1_STRT);
\r
1241 *PCROPStartAddr = (reg_value << 4) + FLASH_BASE;
\r
1243 reg_value = (READ_REG(FLASH->PCROP1ER) & FLASH_PCROP1ER_PCROP1_END);
\r
1244 *PCROPEndAddr = (reg_value << 4) + FLASH_BASE + 0xFU;
\r
1246 else if(((*PCROPConfig) & FLASH_BANK_BOTH) == FLASH_BANK_2)
\r
1248 reg_value = (READ_REG(FLASH->PCROP2SR) & FLASH_PCROP2SR_PCROP2_STRT);
\r
1249 *PCROPStartAddr = (reg_value << 4) + FLASH_BASE;
\r
1251 reg_value = (READ_REG(FLASH->PCROP2ER) & FLASH_PCROP2ER_PCROP2_END);
\r
1252 *PCROPEndAddr = (reg_value << 4) + FLASH_BASE + 0xFU;;
\r
1256 /* Nothing to do */
\r
1262 if(((*PCROPConfig) & FLASH_BANK_BOTH) == FLASH_BANK_1)
\r
1264 reg_value = (READ_REG(FLASH->PCROP1SR) & FLASH_PCROP1SR_PCROP1_STRT);
\r
1265 *PCROPStartAddr = (reg_value << 3) + bank1_addr;
\r
1267 reg_value = (READ_REG(FLASH->PCROP1ER) & FLASH_PCROP1ER_PCROP1_END);
\r
1268 *PCROPEndAddr = (reg_value << 3) + bank1_addr + 0x7U;
\r
1270 #if defined (STM32L471xx) || defined (STM32L475xx) || defined (STM32L476xx) || defined (STM32L485xx) || defined (STM32L486xx) || \
\r
1271 defined (STM32L496xx) || defined (STM32L4A6xx) || \
\r
1272 defined (STM32L4R5xx) || defined (STM32L4R7xx) || defined (STM32L4R9xx) || defined (STM32L4S5xx) || defined (STM32L4S7xx) || defined (STM32L4S9xx)
\r
1273 else if(((*PCROPConfig) & FLASH_BANK_BOTH) == FLASH_BANK_2)
\r
1275 reg_value = (READ_REG(FLASH->PCROP2SR) & FLASH_PCROP2SR_PCROP2_STRT);
\r
1276 *PCROPStartAddr = (reg_value << 3) + bank2_addr;
\r
1278 reg_value = (READ_REG(FLASH->PCROP2ER) & FLASH_PCROP2ER_PCROP2_END);
\r
1279 *PCROPEndAddr = (reg_value << 3) + bank2_addr + 0x7U;
\r
1284 /* Nothing to do */
\r
1288 *PCROPConfig |= (READ_REG(FLASH->PCROP1ER) & FLASH_PCROP1ER_PCROP_RDP);
\r
1298 #endif /* HAL_FLASH_MODULE_ENABLED */
\r
1308 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
\r