@@ -37,7 +37,7 @@ static void RAMFUNCTION flash_set_waitstates(unsigned int waitstates)
3737 while ((FLASH_ACR & FLASH_ACR_LATENCY_MASK ) != waitstates );
3838}
3939
40- void RAMFUNCTION hal_flash_wait_complete (uint8_t bank )
40+ static void RAMFUNCTION hal_flash_wait_complete (void )
4141{
4242 while ((FLASH_SR & FLASH_SR_BSY ) == FLASH_SR_BSY )
4343 ;
@@ -48,6 +48,17 @@ void RAMFUNCTION hal_flash_wait_complete(uint8_t bank)
4848
4949}
5050
51+ static void RAMFUNCTION hal_flash_wait_buffer_empty (void )
52+ {
53+ while ((FLASH_SR & FLASH_SR_DBNE ) == FLASH_SR_DBNE )
54+ ;
55+ #if (TZ_SECURE ())
56+ while ((FLASH_NS_SR & FLASH_SR_DBNE ) == FLASH_SR_DBNE )
57+ ;
58+ #endif
59+
60+ }
61+
5162void RAMFUNCTION hal_flash_clear_errors (uint8_t bank )
5263{
5364 FLASH_CCR |= ( FLASH_CCR_CLR_WBNE | FLASH_CCR_CLR_DBNE | FLASH_CCR_CLR_INCE |
@@ -85,7 +96,7 @@ int RAMFUNCTION hal_flash_write(uint32_t address, const uint8_t *data, int len)
8596 dst [i >> 2 ] = dword [0 ];
8697 ISB ();
8798 dst [(i >> 2 ) + 1 ] = dword [1 ];
88- hal_flash_wait_complete (0 );
99+ hal_flash_wait_complete ();
89100 if ((* sr & FLASH_SR_EOP ) != 0 )
90101 * sr |= FLASH_SR_EOP ;
91102 * cr &= ~FLASH_CR_PG ;
@@ -99,7 +110,7 @@ int RAMFUNCTION hal_flash_write(uint32_t address, const uint8_t *data, int len)
99110
100111void RAMFUNCTION hal_flash_unlock (void )
101112{
102- hal_flash_wait_complete (0 );
113+ hal_flash_wait_complete ();
103114 if ((FLASH_CR & FLASH_CR_LOCK ) != 0 ) {
104115 FLASH_KEYR = FLASH_KEY1 ;
105116 DMB ();
@@ -112,14 +123,14 @@ void RAMFUNCTION hal_flash_unlock(void)
112123
113124void RAMFUNCTION hal_flash_lock (void )
114125{
115- hal_flash_wait_complete (0 );
126+ hal_flash_wait_complete ();
116127 if ((FLASH_CR & FLASH_CR_LOCK ) == 0 )
117128 FLASH_CR |= FLASH_CR_LOCK ;
118129}
119130
120131void RAMFUNCTION hal_flash_opt_unlock (void )
121132{
122- hal_flash_wait_complete (0 );
133+ hal_flash_wait_complete ();
123134 if ((FLASH_OPTCR & FLASH_OPTCR_OPTLOCK ) != 0 ) {
124135 FLASH_OPTKEYR = FLASH_OPTKEY1 ;
125136 DMB ();
@@ -134,7 +145,7 @@ void RAMFUNCTION hal_flash_opt_unlock(void)
134145void RAMFUNCTION hal_flash_opt_lock (void )
135146{
136147 FLASH_OPTCR |= FLASH_OPTCR_OPTSTRT ;
137- hal_flash_wait_complete (0 );
148+ hal_flash_wait_complete ();
138149 if ((FLASH_OPTCR & FLASH_OPTCR_OPTLOCK ) == 0 )
139150 FLASH_OPTCR |= FLASH_OPTCR_OPTLOCK ;
140151}
@@ -149,7 +160,7 @@ int RAMFUNCTION hal_flash_erase(uint32_t address, int len)
149160 if (len == 0 )
150161 return -1 ;
151162
152- if (address < ARCH_FLASH_OFFSET )
163+ if (address < 0x08000000 )
153164 return -1 ;
154165
155166 end_address = address + len - 1 ;
@@ -176,7 +187,7 @@ int RAMFUNCTION hal_flash_erase(uint32_t address, int len)
176187 FLASH_CR = reg ;
177188 DMB ();
178189 FLASH_CR |= FLASH_CR_STRT ;
179- hal_flash_wait_complete (0 );
190+ hal_flash_wait_complete ();
180191 }
181192 /* If the erase operation is completed, disable the associated bits */
182193 FLASH_CR &= ~FLASH_CR_SER ;
@@ -421,3 +432,72 @@ void hal_prepare_boot(void)
421432#endif
422433}
423434
435+ #ifdef FLASH_OTP_ROT
436+
437+ /* Public API */
438+
439+ int hal_flash_otp_write (uint32_t flashAddress , const void * data , uint16_t length )
440+ {
441+ volatile uint16_t tmp ;
442+ uint16_t * pdata = (uint16_t * )data ;
443+ uint16_t idx = 0 , len_align ;
444+ uint16_t last_word ;
445+ if (!(flashAddress >= FLASH_OTP_BASE && flashAddress <= FLASH_OTP_END )) {
446+ return -1 ;
447+ }
448+
449+ hal_flash_wait_complete ();
450+ hal_flash_wait_buffer_empty ();
451+ hal_flash_unlock ();
452+ hal_flash_clear_errors (0 );
453+
454+
455+ /* Truncate to 2B alignment */
456+ length = (length / 2 * 2 );
457+
458+ while (idx < length && flashAddress <= FLASH_OTP_END - 1 ) {
459+ hal_flash_wait_complete ();
460+ /* Set PG bit */
461+ FLASH_CR |= FLASH_CR_PG ;
462+ /* Program an OTP word (32 bits) */
463+ * (volatile uint16_t * )flashAddress = * pdata ;
464+ ISB ();
465+ DSB ();
466+ /* Read it back */
467+ tmp = * (volatile uint16_t * )flashAddress ;
468+ if (tmp != * pdata ) {
469+ /* Provisioning failed. OTP already programmed? */
470+ while (1 )
471+ ;
472+ }
473+
474+ /* Clear PG bit */
475+ FLASH_CR &= ~FLASH_CR_PG ;
476+ flashAddress += sizeof (uint16_t );
477+ pdata ++ ;
478+ idx += sizeof (uint16_t );
479+ }
480+
481+ hal_flash_lock ();
482+ return 0 ;
483+ }
484+
485+ int hal_flash_otp_read (uint32_t flashAddress , void * data , uint32_t length )
486+ {
487+ uint16_t i ;
488+ uint16_t * pdata = (uint16_t * )data ;
489+ if (!(flashAddress >= FLASH_OTP_BASE && flashAddress <= FLASH_OTP_END )) {
490+ return -1 ;
491+ }
492+ for (i = 0 ;
493+ (i < length ) && (flashAddress <= (FLASH_OTP_END - 1 ));
494+ i += sizeof (uint16_t ))
495+ {
496+ * pdata = * (volatile uint16_t * )flashAddress ;
497+ flashAddress += sizeof (uint16_t );
498+ pdata ++ ;
499+ }
500+ return 0 ;
501+ }
502+
503+ #endif /* FLASH_OTP_ROT */
0 commit comments