Subversion Repositories DashDisplay

Rev

Rev 61 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
77 mjames 1
/**
2
  ******************************************************************************
3
  * @file    stm32l1xx_hal_flash.c
4
  * @author  MCD Application Team
5
  * @brief   FLASH HAL module driver.
6
  *          This file provides firmware functions to manage the following
7
  *          functionalities of the internal FLASH memory:
8
  *           + Program operations functions
9
  *           + Memory Control functions
10
  *           + Peripheral State functions
11
  *        
12
  @verbatim
13
  ==============================================================================
14
                        ##### FLASH peripheral features #####
15
  ==============================================================================
16
  [..] The Flash memory interface manages CPU AHB I-Code and D-Code accesses
17
       to the Flash memory. It implements the erase and program Flash memory operations
18
       and the read and write protection mechanisms.
19
 
20
  [..] The Flash memory interface accelerates code execution with a system of instruction
21
      prefetch.
22
 
23
  [..] The FLASH main features are:
24
      (+) Flash memory read operations
25
      (+) Flash memory program/erase operations
26
      (+) Read / write protections
27
      (+) Prefetch on I-Code
28
      (+) Option Bytes programming
29
 
30
 
31
                     ##### How to use this driver #####
32
  ==============================================================================
33
  [..]                            
34
      This driver provides functions and macros to configure and program the FLASH
35
      memory of all STM32L1xx devices.
36
 
37
      (#) FLASH Memory I/O Programming functions: this group includes all needed
38
          functions to erase and program the main memory:
39
        (++) Lock and Unlock the FLASH interface
40
        (++) Erase function: Erase page
41
        (++) Program functions: Fast Word and Half Page(should be
42
        executed from internal SRAM).
43
 
44
      (#) DATA EEPROM Programming functions: this group includes all
45
          needed functions to erase and program the DATA EEPROM memory:
46
        (++) Lock and Unlock the DATA EEPROM interface.
47
        (++) Erase function: Erase Byte, erase HalfWord, erase Word, erase
48
             Double Word (should be executed from internal SRAM).
49
        (++) Program functions: Fast Program Byte, Fast Program Half-Word,
50
             FastProgramWord, Program Byte, Program Half-Word,
51
             Program Word and Program Double-Word (should be executed
52
             from internal SRAM).
53
 
54
      (#) FLASH Option Bytes Programming functions: this group includes all needed
55
          functions to manage the Option Bytes:
56
        (++) Lock and Unlock the Option Bytes
57
        (++) Set/Reset the write protection
58
        (++) Set the Read protection Level
59
        (++) Program the user Option Bytes
60
        (++) Launch the Option Bytes loader
61
        (++) Set/Get the Read protection Level.
62
        (++) Set/Get the BOR level.
63
        (++) Get the Write protection.
64
        (++) Get the user option bytes.
65
 
66
      (#) Interrupts and flags management functions : this group
67
          includes all needed functions to:
68
        (++) Handle FLASH interrupts
69
        (++) Wait for last FLASH operation according to its status
70
        (++) Get error flag status
71
 
72
    (#) FLASH Interface configuration functions: this group includes
73
      the management of following features:
74
      (++) Enable/Disable the RUN PowerDown mode.
75
      (++) Enable/Disable the SLEEP PowerDown mode.  
76
 
77
    (#) FLASH Peripheral State methods: this group includes
78
      the management of following features:
79
      (++) Wait for the FLASH operation
80
      (++)  Get the specific FLASH error flag
81
 
82
  [..] In addition to these function, this driver includes a set of macros allowing
83
       to handle the following operations:
84
 
85
      (+) Set/Get the latency
86
      (+) Enable/Disable the prefetch buffer
87
      (+) Enable/Disable the 64 bit Read Access.
88
      (+) Enable/Disable the Flash power-down
89
      (+) Enable/Disable the FLASH interrupts
90
      (+) Monitor the FLASH flags status
91
 
92
                 ##### Programming operation functions #####
93
  ===============================================================================  
94
     [..]
95
     This subsection provides a set of functions allowing to manage the FLASH
96
     program operations.
97
 
98
    [..] The FLASH Memory Programming functions, includes the following functions:
99
     (+) HAL_FLASH_Unlock(void);
100
     (+) HAL_FLASH_Lock(void);
101
     (+) HAL_FLASH_Program(uint32_t TypeProgram, uint32_t Address, uint32_t Data)
102
     (+) HAL_FLASH_Program_IT(uint32_t TypeProgram, uint32_t Address, uint32_t Data)
103
 
104
     [..] Any operation of erase or program should follow these steps:
105
     (#) Call the HAL_FLASH_Unlock() function to enable the flash control register and
106
         program memory access.
107
     (#) Call the desired function to erase page or program data.
108
     (#) Call the HAL_FLASH_Lock() to disable the flash program memory access
109
        (recommended to protect the FLASH memory against possible unwanted operation).
110
 
111
               ##### Option Bytes Programming functions #####
112
   ==============================================================================  
113
 
114
     [..] The FLASH_Option Bytes Programming_functions, includes the following functions:
115
     (+) HAL_FLASH_OB_Unlock(void);
116
     (+) HAL_FLASH_OB_Lock(void);
117
     (+) HAL_FLASH_OB_Launch(void);
118
     (+) HAL_FLASHEx_OBProgram(FLASH_OBProgramInitTypeDef *pOBInit);
119
     (+) HAL_FLASHEx_OBGetConfig(FLASH_OBProgramInitTypeDef *pOBInit);
120
 
121
     [..] Any operation of erase or program should follow these steps:
122
     (#) Call the HAL_FLASH_OB_Unlock() function to enable the Flash option control
123
         register access.
124
     (#) Call the following functions to program the desired option bytes.
125
         (++) HAL_FLASHEx_OBProgram(FLASH_OBProgramInitTypeDef *pOBInit);      
126
     (#) Once all needed option bytes to be programmed are correctly written, call the
127
         HAL_FLASH_OB_Launch(void) function to launch the Option Bytes programming process.
128
     (#) Call the HAL_FLASH_OB_Lock() to disable the Flash option control register access (recommended
129
         to protect the option Bytes against possible unwanted operations).
130
 
131
    [..] Proprietary code Read Out Protection (PcROP):    
132
    (#) The PcROP sector is selected by using the same option bytes as the Write
133
        protection. As a result, these 2 options are exclusive each other.
134
    (#) To activate PCROP mode for Flash sectors(s), you need to follow the sequence below:
135
        (++) Use this function HAL_FLASHEx_AdvOBProgram with PCROPState = OB_PCROP_STATE_ENABLE.
136
 
137
  @endverbatim
138
  ******************************************************************************
139
  * @attention
140
  *
141
  * Copyright (c) 2017 STMicroelectronics.
142
  * All rights reserved.
143
  *
144
  * This software is licensed under terms that can be found in the LICENSE file in
145
  * the root directory of this software component.
146
  * If no LICENSE file comes with this software, it is provided AS-IS.
147
  ******************************************************************************
148
  */
149
 
150
/* Includes ------------------------------------------------------------------*/
151
#include "stm32l1xx_hal.h"
152
 
153
/** @addtogroup STM32L1xx_HAL_Driver
154
  * @{
155
  */
156
 
157
#ifdef HAL_FLASH_MODULE_ENABLED
158
 
159
/** @defgroup FLASH FLASH
160
  * @brief FLASH HAL module driver
161
  * @{
162
  */
163
 
164
/* Private typedef -----------------------------------------------------------*/
165
/* Private define ------------------------------------------------------------*/
166
/** @defgroup FLASH_Private_Constants FLASH Private Constants
167
  * @{
168
  */
169
/**
170
  * @}
171
  */
172
 
173
/* Private macro ---------------------------- ---------------------------------*/
174
/** @defgroup FLASH_Private_Macros FLASH Private Macros
175
  * @{
176
  */
177
 
178
/**
179
  * @}
180
  */
181
 
182
/* Private variables ---------------------------------------------------------*/
183
/** @defgroup FLASH_Private_Variables FLASH Private Variables
184
  * @{
185
  */
186
/* Variables used for Erase pages under interruption*/
187
FLASH_ProcessTypeDef pFlash;
188
/**
189
  * @}
190
  */
191
 
192
/* Private function prototypes -----------------------------------------------*/
193
/** @defgroup FLASH_Private_Functions FLASH Private Functions
194
  * @{
195
  */
196
static  void   FLASH_SetErrorCode(void);
197
extern void    FLASH_PageErase(uint32_t PageAddress);
198
/**
199
  * @}
200
  */
201
 
202
/* Exported functions ---------------------------------------------------------*/
203
/** @defgroup FLASH_Exported_Functions FLASH Exported Functions
204
  * @{
205
  */
206
 
207
/** @defgroup FLASH_Exported_Functions_Group1 Programming operation functions
208
  *  @brief   Programming operation functions
209
  *
210
@verbatim  
211
@endverbatim
212
  * @{
213
  */
214
 
215
/**
216
  * @brief  Program word at a specified address
217
  * @note   To correctly run this function, the HAL_FLASH_Unlock() function
218
  *         must be called before.
219
  *         Call the HAL_FLASH_Lock() to disable the flash memory access
220
  *         (recommended to protect the FLASH memory against possible unwanted operation).
221
  *
222
  * @param  TypeProgram   Indicate the way to program at a specified address.
223
  *                       This parameter can be a value of @ref FLASH_Type_Program
224
  * @param  Address       Specifie the address to be programmed.
225
  * @param  Data          Specifie the data to be programmed
226
  *
227
  * @retval HAL_StatusTypeDef HAL Status
228
  */
229
HAL_StatusTypeDef HAL_FLASH_Program(uint32_t TypeProgram, uint32_t Address, uint32_t Data)
230
{
231
  HAL_StatusTypeDef status = HAL_ERROR;
232
 
233
  /* Process Locked */
234
  __HAL_LOCK(&pFlash);
235
 
236
  /* Check the parameters */
237
  assert_param(IS_FLASH_TYPEPROGRAM(TypeProgram));
238
  assert_param(IS_FLASH_PROGRAM_ADDRESS(Address));
239
 
240
  /* Wait for last operation to be completed */
241
  status = FLASH_WaitForLastOperation(FLASH_TIMEOUT_VALUE);
242
 
243
  if(status == HAL_OK)
244
  {
245
    /* Clean the error context */
246
    pFlash.ErrorCode = HAL_FLASH_ERROR_NONE;
247
 
248
    /*Program word (32-bit) at a specified address.*/
249
    *(__IO uint32_t *)Address = Data;
250
 
251
    /* Wait for last operation to be completed */
252
    status = FLASH_WaitForLastOperation(FLASH_TIMEOUT_VALUE);
253
  }
254
 
255
  /* Process Unlocked */
256
  __HAL_UNLOCK(&pFlash);
257
 
258
  return status;
259
}
260
 
261
/**
262
  * @brief   Program word at a specified address  with interrupt enabled.
263
  *
264
  * @param  TypeProgram  Indicate the way to program at a specified address.
265
  *                      This parameter can be a value of @ref FLASH_Type_Program
266
  * @param  Address      Specifie the address to be programmed.
267
  * @param  Data         Specifie the data to be programmed
268
  *
269
  * @retval HAL_StatusTypeDef HAL Status
270
  */
271
HAL_StatusTypeDef HAL_FLASH_Program_IT(uint32_t TypeProgram, uint32_t Address, uint32_t Data)
272
{
273
  HAL_StatusTypeDef status = HAL_OK;
274
 
275
  /* Process Locked */
276
  __HAL_LOCK(&pFlash);
277
 
278
  /* Check the parameters */
279
  assert_param(IS_FLASH_TYPEPROGRAM(TypeProgram));
280
  assert_param(IS_FLASH_PROGRAM_ADDRESS(Address));
281
 
282
  /* Enable End of FLASH Operation and Error source interrupts */
283
  __HAL_FLASH_ENABLE_IT(FLASH_IT_EOP | FLASH_IT_ERR);
284
 
285
  pFlash.Address = Address;
286
  pFlash.ProcedureOnGoing = FLASH_PROC_PROGRAM;
287
  /* Clean the error context */
288
  pFlash.ErrorCode = HAL_FLASH_ERROR_NONE;
289
 
290
  if(TypeProgram == FLASH_TYPEPROGRAM_WORD)
291
  {
292
    /* Program word (32-bit) at a specified address. */
293
    *(__IO uint32_t *)Address = Data;
294
  }
295
  return status;
296
}
297
 
298
/**
299
  * @brief This function handles FLASH interrupt request.
300
  * @retval None
301
  */
302
void HAL_FLASH_IRQHandler(void)
303
{
304
  uint32_t addresstmp = 0U;
305
 
306
  /* Check FLASH operation error flags */
307
  if( __HAL_FLASH_GET_FLAG(FLASH_FLAG_WRPERR)     ||
308
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_PGAERR)     ||
309
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_SIZERR)     ||
310
#if defined(FLASH_SR_RDERR)
311
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_RDERR)      ||
312
#endif /* FLASH_SR_RDERR */
313
#if defined(FLASH_SR_OPTVERRUSR)
314
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERRUSR) ||
315
#endif /* FLASH_SR_OPTVERRUSR */
316
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERR) )
317
  {
318
    if(pFlash.ProcedureOnGoing == FLASH_PROC_PAGEERASE)
319
    {
320
      /* Return the faulty sector */
321
      addresstmp = pFlash.Page;
322
      pFlash.Page = 0xFFFFFFFFU;
323
    }
324
    else
325
    {
326
      /* Return the faulty address */
327
      addresstmp = pFlash.Address;
328
    }
329
    /* Save the Error code */
330
    FLASH_SetErrorCode();
331
 
332
    /* FLASH error interrupt user callback */
333
    HAL_FLASH_OperationErrorCallback(addresstmp);
334
 
335
    /* Stop the procedure ongoing */
336
    pFlash.ProcedureOnGoing = FLASH_PROC_NONE;
337
  }
338
 
339
  /* Check FLASH End of Operation flag  */
340
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_EOP))
341
  {
342
    /* Clear FLASH End of Operation pending bit */
343
    __HAL_FLASH_CLEAR_FLAG(FLASH_FLAG_EOP);
344
 
345
    /* Process can continue only if no error detected */
346
    if(pFlash.ProcedureOnGoing != FLASH_PROC_NONE)
347
    {
348
      if(pFlash.ProcedureOnGoing == FLASH_PROC_PAGEERASE)
349
      {
350
        /* Nb of pages to erased can be decreased */
351
        pFlash.NbPagesToErase--;
352
 
353
        /* Check if there are still pages to erase */
354
        if(pFlash.NbPagesToErase != 0U)
355
        {
356
          addresstmp = pFlash.Page;
357
          /*Indicate user which sector has been erased */
358
          HAL_FLASH_EndOfOperationCallback(addresstmp);
359
 
360
          /*Increment sector number*/
361
          addresstmp = pFlash.Page + FLASH_PAGE_SIZE;
362
          pFlash.Page = addresstmp;
363
 
364
          /* If the erase operation is completed, disable the ERASE Bit */
365
          CLEAR_BIT(FLASH->PECR, FLASH_PECR_ERASE);
366
 
367
          FLASH_PageErase(addresstmp);
368
        }
369
        else
370
        {
371
          /* No more pages to Erase, user callback can be called. */
372
          /* Reset Sector and stop Erase pages procedure */
373
          pFlash.Page = addresstmp = 0xFFFFFFFFU;
374
          pFlash.ProcedureOnGoing = FLASH_PROC_NONE;
375
          /* FLASH EOP interrupt user callback */
376
          HAL_FLASH_EndOfOperationCallback(addresstmp);
377
        }
378
      }
379
      else
380
      {
381
          /* If the program operation is completed, disable the PROG Bit */
382
          CLEAR_BIT(FLASH->PECR, FLASH_PECR_PROG);
383
 
384
          /* Program ended. Return the selected address */
385
          /* FLASH EOP interrupt user callback */
386
          HAL_FLASH_EndOfOperationCallback(pFlash.Address);
387
 
388
          /* Reset Address and stop Program procedure */
389
          pFlash.Address = 0xFFFFFFFFU;
390
          pFlash.ProcedureOnGoing = FLASH_PROC_NONE;
391
      }
392
    }
393
  }
394
 
395
 
396
  if(pFlash.ProcedureOnGoing == FLASH_PROC_NONE)
397
  {
398
    /* Operation is completed, disable the PROG and ERASE */
399
    CLEAR_BIT(FLASH->PECR, (FLASH_PECR_ERASE | FLASH_PECR_PROG));
400
 
401
    /* Disable End of FLASH Operation and Error source interrupts */
402
    __HAL_FLASH_DISABLE_IT(FLASH_IT_EOP | FLASH_IT_ERR);
403
 
404
    /* Process Unlocked */
405
    __HAL_UNLOCK(&pFlash);
406
  }
407
}
408
 
409
/**
410
  * @brief  FLASH end of operation interrupt callback
411
  * @param  ReturnValue The value saved in this parameter depends on the ongoing procedure
412
  *                 - Pages Erase: Address of the page which has been erased
413
  *                    (if 0xFFFFFFFF, it means that all the selected pages have been erased)
414
  *                 - Program: Address which was selected for data program
415
  * @retval none
416
  */
417
__weak void HAL_FLASH_EndOfOperationCallback(uint32_t ReturnValue)
418
{
419
  /* Prevent unused argument(s) compilation warning */
420
  UNUSED(ReturnValue);
421
 
422
  /* NOTE : This function Should not be modified, when the callback is needed,
423
            the HAL_FLASH_EndOfOperationCallback could be implemented in the user file
424
   */
425
}
426
 
427
/**
428
  * @brief  FLASH operation error interrupt callback
429
  * @param  ReturnValue The value saved in this parameter depends on the ongoing procedure
430
  *                 - Pages Erase: Address of the page which returned an error
431
  *                 - Program: Address which was selected for data program
432
  * @retval none
433
  */
434
__weak void HAL_FLASH_OperationErrorCallback(uint32_t ReturnValue)
435
{
436
  /* Prevent unused argument(s) compilation warning */
437
  UNUSED(ReturnValue);
438
 
439
  /* NOTE : This function Should not be modified, when the callback is needed,
440
            the HAL_FLASH_OperationErrorCallback could be implemented in the user file
441
   */
442
}
443
 
444
/**
445
  * @}
446
  */
447
 
448
/** @defgroup FLASH_Exported_Functions_Group2 Peripheral Control functions
449
 *  @brief   management functions
450
 *
451
@verbatim  
452
 ===============================================================================
453
                      ##### Peripheral Control functions #####
454
 ===============================================================================  
455
    [..]
456
    This subsection provides a set of functions allowing to control the FLASH
457
    memory operations.
458
 
459
@endverbatim
460
  * @{
461
  */
462
 
463
/**
464
  * @brief  Unlock the FLASH control register access
465
  * @retval HAL Status
466
  */
467
HAL_StatusTypeDef HAL_FLASH_Unlock(void)
468
{
469
  if (HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PRGLOCK))
470
  {
471
    /* Unlocking FLASH_PECR register access*/
472
    if(HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PELOCK))
473
    {  
474
      WRITE_REG(FLASH->PEKEYR, FLASH_PEKEY1);
475
      WRITE_REG(FLASH->PEKEYR, FLASH_PEKEY2);
476
 
477
      /* Verify that PELOCK is unlocked */
478
      if(HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PELOCK))
479
      {
480
        return HAL_ERROR;
481
      }
482
    }
483
 
484
    /* Unlocking the program memory access */
485
    WRITE_REG(FLASH->PRGKEYR, FLASH_PRGKEY1);
486
    WRITE_REG(FLASH->PRGKEYR, FLASH_PRGKEY2);  
487
 
488
    /* Verify that PRGLOCK is unlocked */
489
    if (HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PRGLOCK))
490
    {
491
      return HAL_ERROR;
492
    }
493
  }
494
 
495
  return HAL_OK;
496
}
497
 
498
/**
499
  * @brief  Locks the FLASH control register access
500
  * @retval HAL Status
501
  */
502
HAL_StatusTypeDef HAL_FLASH_Lock(void)
503
{
504
  /* Set the PRGLOCK Bit to lock the FLASH Registers access */
505
  SET_BIT(FLASH->PECR, FLASH_PECR_PRGLOCK);
506
 
507
  return HAL_OK;  
508
}
509
 
510
/**
511
  * @brief  Unlock the FLASH Option Control Registers access.
512
  * @retval HAL Status
513
  */
514
HAL_StatusTypeDef HAL_FLASH_OB_Unlock(void)
515
{
516
  if(HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_OPTLOCK))
517
  {
518
    /* Unlocking FLASH_PECR register access*/
519
    if(HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PELOCK))
520
    {  
521
      /* Unlocking FLASH_PECR register access*/
522
      WRITE_REG(FLASH->PEKEYR, FLASH_PEKEY1);
523
      WRITE_REG(FLASH->PEKEYR, FLASH_PEKEY2);
524
 
525
      /* Verify that PELOCK is unlocked */
526
      if(HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_PELOCK))
527
      {
528
        return HAL_ERROR;
529
      }
530
    }
531
 
532
    /* Unlocking the option bytes block access */
533
    WRITE_REG(FLASH->OPTKEYR, FLASH_OPTKEY1);
534
    WRITE_REG(FLASH->OPTKEYR, FLASH_OPTKEY2);
535
 
536
    /* Verify that OPTLOCK is unlocked */
537
    if (HAL_IS_BIT_SET(FLASH->PECR, FLASH_PECR_OPTLOCK))
538
    {
539
      return HAL_ERROR;
540
    }
541
  }
542
 
543
  return HAL_OK;  
544
}
545
 
546
/**
547
  * @brief  Lock the FLASH Option Control Registers access.
548
  * @retval HAL Status
549
  */
550
HAL_StatusTypeDef HAL_FLASH_OB_Lock(void)
551
{
552
  /* Set the OPTLOCK Bit to lock the option bytes block access */
553
  SET_BIT(FLASH->PECR, FLASH_PECR_OPTLOCK);
554
 
555
  return HAL_OK;  
556
}
557
 
558
/**
559
  * @brief  Launch the option byte loading.
560
  * @note   This function will reset automatically the MCU.
561
  * @retval HAL Status
562
  */
563
HAL_StatusTypeDef HAL_FLASH_OB_Launch(void)
564
{
565
  /* Set the OBL_Launch bit to launch the option byte loading */
566
  SET_BIT(FLASH->PECR, FLASH_PECR_OBL_LAUNCH);
567
 
568
  /* Wait for last operation to be completed */
569
  return(FLASH_WaitForLastOperation(FLASH_TIMEOUT_VALUE));
570
}
571
 
572
/**
573
  * @}
574
  */  
575
 
576
/** @defgroup FLASH_Exported_Functions_Group3 Peripheral errors functions
577
 *  @brief    Peripheral errors functions
578
 *
579
@verbatim  
580
 ===============================================================================
581
                      ##### Peripheral Errors functions #####
582
 ===============================================================================  
583
    [..]
584
    This subsection permit to get in run-time errors of  the FLASH peripheral.
585
 
586
@endverbatim
587
  * @{
588
  */
589
 
590
/**
591
  * @brief  Get the specific FLASH error flag.
592
  * @retval FLASH_ErrorCode The returned value can be:
593
  *            @ref FLASH_Error_Codes
594
  */
595
uint32_t HAL_FLASH_GetError(void)
596
{
597
   return pFlash.ErrorCode;
598
}
599
 
600
/**
601
  * @}
602
  */
603
 
604
/**
605
  * @}
606
  */
607
 
608
/** @addtogroup FLASH_Private_Functions
609
 * @{
610
 */
611
 
612
/**
613
  * @brief  Wait for a FLASH operation to complete.
614
  * @param  Timeout  maximum flash operation timeout
615
  * @retval HAL Status
616
  */
617
HAL_StatusTypeDef FLASH_WaitForLastOperation(uint32_t Timeout)
618
{
619
  /* Wait for the FLASH operation to complete by polling on BUSY flag to be reset.
620
     Even if the FLASH operation fails, the BUSY flag will be reset and an error
621
     flag will be set */
622
 
623
  uint32_t tickstart = HAL_GetTick();
624
 
625
  while(__HAL_FLASH_GET_FLAG(FLASH_FLAG_BSY))
626
  {
627
    if (Timeout != HAL_MAX_DELAY)
628
    {
629
      if((Timeout == 0U) || ((HAL_GetTick()-tickstart) > Timeout))
630
      {
631
        return HAL_TIMEOUT;
632
      }
633
    }
634
  }
635
 
636
  /* Check FLASH End of Operation flag  */
637
  if (__HAL_FLASH_GET_FLAG(FLASH_FLAG_EOP))
638
  {
639
    /* Clear FLASH End of Operation pending bit */
640
    __HAL_FLASH_CLEAR_FLAG(FLASH_FLAG_EOP);
641
  }
642
 
643
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_WRPERR)  ||
644
     __HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERR) ||
645
#if defined(FLASH_SR_RDERR)
646
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_RDERR) ||
647
#endif /* FLASH_SR_RDERR */
648
#if defined(FLASH_SR_OPTVERRUSR)
649
      __HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERRUSR) ||
650
#endif /* FLASH_SR_OPTVERRUSR */
651
     __HAL_FLASH_GET_FLAG(FLASH_FLAG_SIZERR) ||
652
     __HAL_FLASH_GET_FLAG(FLASH_FLAG_PGAERR))
653
  {
654
    /*Save the error code*/
655
    FLASH_SetErrorCode();
656
    return HAL_ERROR;
657
  }
658
 
659
  /* There is no error flag set */
660
  return HAL_OK;
661
}
662
 
663
 
664
/**
665
  * @brief  Set the specific FLASH error flag.
666
  * @retval None
667
  */
668
static void FLASH_SetErrorCode(void)
669
{
670
  uint32_t flags = 0U;
671
 
672
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_WRPERR))
673
  {
674
    pFlash.ErrorCode |= HAL_FLASH_ERROR_WRP;
675
    flags |= FLASH_FLAG_WRPERR;
676
  }
677
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_PGAERR))
678
  {
679
    pFlash.ErrorCode |= HAL_FLASH_ERROR_PGA;
680
    flags |= FLASH_FLAG_PGAERR;
681
  }
682
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERR))
683
  {
684
    pFlash.ErrorCode |= HAL_FLASH_ERROR_OPTV;
685
    flags |= FLASH_FLAG_OPTVERR;
686
  }
687
 
688
#if defined(FLASH_SR_RDERR)
689
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_RDERR))
690
  {
691
    pFlash.ErrorCode |= HAL_FLASH_ERROR_RD;
692
    flags |= FLASH_FLAG_RDERR;
693
  }
694
#endif /* FLASH_SR_RDERR */
695
#if defined(FLASH_SR_OPTVERRUSR)
696
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_OPTVERRUSR))
697
  {
698
    pFlash.ErrorCode |= HAL_FLASH_ERROR_OPTVUSR;
699
    flags |= FLASH_FLAG_OPTVERRUSR;
700
  }
701
#endif /* FLASH_SR_OPTVERRUSR */
702
  if(__HAL_FLASH_GET_FLAG(FLASH_FLAG_SIZERR))
703
  {
704
    pFlash.ErrorCode |= HAL_FLASH_ERROR_SIZE;
705
    flags |= FLASH_FLAG_SIZERR;
706
  }
707
  /* Clear FLASH error pending bits */
708
  __HAL_FLASH_CLEAR_FLAG(flags);
709
}
710
/**
711
  * @}
712
  */
713
 
714
/**
715
  * @}
716
  */
717
 
718
#endif /* HAL_FLASH_MODULE_ENABLED */
719
 
720
/**
721
  * @}
722
  */
723