stm32f3xx_hal_nand.c 62 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807
  1. /**
  2. ******************************************************************************
  3. * @file stm32f3xx_hal_nand.c
  4. * @author MCD Application Team
  5. * @brief NAND HAL module driver.
  6. * This file provides a generic firmware to drive NAND memories mounted
  7. * as external device.
  8. *
  9. @verbatim
  10. ==============================================================================
  11. ##### How to use this driver #####
  12. ==============================================================================
  13. [..]
  14. This driver is a generic layered driver which contains a set of APIs used to
  15. control NAND flash memories. It uses the FMC layer functions to interface
  16. with NAND devices. This driver is used as follows:
  17. (+) NAND flash memory configuration sequence using the function HAL_NAND_Init()
  18. with control and timing parameters for both common and attribute spaces.
  19. (+) Read NAND flash memory maker and device IDs using the function
  20. HAL_NAND_Read_ID(). The read information is stored in the NAND_ID_TypeDef
  21. structure declared by the function caller.
  22. (+) Access NAND flash memory by read/write operations using the functions
  23. HAL_NAND_Read_Page_8b()/HAL_NAND_Read_SpareArea_8b(),
  24. HAL_NAND_Write_Page_8b()/HAL_NAND_Write_SpareArea_8b(),
  25. HAL_NAND_Read_Page_16b()/HAL_NAND_Read_SpareArea_16b(),
  26. HAL_NAND_Write_Page_16b()/HAL_NAND_Write_SpareArea_16b()
  27. to read/write page(s)/spare area(s). These functions use specific device
  28. information (Block, page size..) predefined by the user in the HAL_NAND_Info_TypeDef
  29. structure. The read/write address information is contained by the Nand_Address_Typedef
  30. structure passed as parameter.
  31. (+) Perform NAND flash Reset chip operation using the function HAL_NAND_Reset().
  32. (+) Perform NAND flash erase block operation using the function HAL_NAND_Erase_Block().
  33. The erase block address information is contained in the Nand_Address_Typedef
  34. structure passed as parameter.
  35. (+) Read the NAND flash status operation using the function HAL_NAND_Read_Status().
  36. (+) You can also control the NAND device by calling the control APIs HAL_NAND_ECC_Enable()/
  37. HAL_NAND_ECC_Disable() to respectively enable/disable the ECC code correction
  38. feature or the function HAL_NAND_GetECC() to get the ECC correction code.
  39. (+) You can monitor the NAND device HAL state by calling the function
  40. HAL_NAND_GetState()
  41. [..]
  42. (@) This driver is a set of generic APIs which handle standard NAND flash operations.
  43. If a NAND flash device contains different operations and/or implementations,
  44. it should be implemented separately.
  45. @endverbatim
  46. ******************************************************************************
  47. * @attention
  48. *
  49. * <h2><center>&copy; COPYRIGHT(c) 2016 STMicroelectronics</center></h2>
  50. *
  51. * Redistribution and use in source and binary forms, with or without modification,
  52. * are permitted provided that the following conditions are met:
  53. * 1. Redistributions of source code must retain the above copyright notice,
  54. * this list of conditions and the following disclaimer.
  55. * 2. Redistributions in binary form must reproduce the above copyright notice,
  56. * this list of conditions and the following disclaimer in the documentation
  57. * and/or other materials provided with the distribution.
  58. * 3. Neither the name of STMicroelectronics nor the names of its contributors
  59. * may be used to endorse or promote products derived from this software
  60. * without specific prior written permission.
  61. *
  62. * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
  63. * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
  64. * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
  65. * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
  66. * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
  67. * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
  68. * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
  69. * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
  70. * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
  71. * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  72. *
  73. ******************************************************************************
  74. */
  75. /* Includes ------------------------------------------------------------------*/
  76. #include "stm32f3xx_hal.h"
  77. #if defined(STM32F302xE) || defined(STM32F303xE) || defined(STM32F398xx)
  78. /** @addtogroup STM32F3xx_HAL_Driver
  79. * @{
  80. */
  81. #ifdef HAL_NAND_MODULE_ENABLED
  82. /** @defgroup NAND NAND
  83. * @brief NAND HAL module driver
  84. * @{
  85. */
  86. /* Private typedef -----------------------------------------------------------*/
  87. /* Private define ------------------------------------------------------------*/
  88. /** @defgroup NAND_Private_Constants NAND Private Constants
  89. * @{
  90. */
  91. /**
  92. * @}
  93. */
  94. /* Private macro -------------------------------------------------------------*/
  95. /** @defgroup NAND_Private_Macros NAND Private Macros
  96. * @{
  97. */
  98. /**
  99. * @}
  100. */
  101. /* Private variables ---------------------------------------------------------*/
  102. /* Private function prototypes -----------------------------------------------*/
  103. /* Exported functions --------------------------------------------------------*/
  104. /** @defgroup NAND_Exported_Functions NAND Exported Functions
  105. * @{
  106. */
  107. /** @defgroup NAND_Exported_Functions_Group1 Initialization and de-initialization functions
  108. * @brief Initialization and Configuration functions
  109. *
  110. @verbatim
  111. ==============================================================================
  112. ##### NAND Initialization and de-initialization functions #####
  113. ==============================================================================
  114. [..]
  115. This section provides functions allowing to initialize/de-initialize
  116. the NAND memory
  117. @endverbatim
  118. * @{
  119. */
  120. /**
  121. * @brief Perform NAND memory Initialization sequence
  122. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  123. * the configuration information for NAND module.
  124. * @param ComSpace_Timing pointer to Common space timing structure
  125. * @param AttSpace_Timing pointer to Attribute space timing structure
  126. * @retval HAL status
  127. */
  128. HAL_StatusTypeDef HAL_NAND_Init(NAND_HandleTypeDef *hnand, FMC_NAND_PCC_TimingTypeDef *ComSpace_Timing, FMC_NAND_PCC_TimingTypeDef *AttSpace_Timing)
  129. {
  130. /* Check the NAND handle state */
  131. if(hnand == NULL)
  132. {
  133. return HAL_ERROR;
  134. }
  135. if(hnand->State == HAL_NAND_STATE_RESET)
  136. {
  137. /* Allocate lock resource and initialize it */
  138. hnand->Lock = HAL_UNLOCKED;
  139. /* Initialize the low level hardware (MSP) */
  140. HAL_NAND_MspInit(hnand);
  141. }
  142. /* Initialize NAND control Interface */
  143. FMC_NAND_Init(hnand->Instance, &(hnand->Init));
  144. /* Initialize NAND common space timing Interface */
  145. FMC_NAND_CommonSpace_Timing_Init(hnand->Instance, ComSpace_Timing, hnand->Init.NandBank);
  146. /* Initialize NAND attribute space timing Interface */
  147. FMC_NAND_AttributeSpace_Timing_Init(hnand->Instance, AttSpace_Timing, hnand->Init.NandBank);
  148. /* Enable the NAND device */
  149. __FMC_NAND_ENABLE(hnand->Instance, hnand->Init.NandBank);
  150. /* Update the NAND controller state */
  151. hnand->State = HAL_NAND_STATE_READY;
  152. return HAL_OK;
  153. }
  154. /**
  155. * @brief Perform NAND memory De-Initialization sequence
  156. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  157. * the configuration information for NAND module.
  158. * @retval HAL status
  159. */
  160. HAL_StatusTypeDef HAL_NAND_DeInit(NAND_HandleTypeDef *hnand)
  161. {
  162. /* Initialize the low level hardware (MSP) */
  163. HAL_NAND_MspDeInit(hnand);
  164. /* Configure the NAND registers with their reset values */
  165. FMC_NAND_DeInit(hnand->Instance, hnand->Init.NandBank);
  166. /* Reset the NAND controller state */
  167. hnand->State = HAL_NAND_STATE_RESET;
  168. /* Release Lock */
  169. __HAL_UNLOCK(hnand);
  170. return HAL_OK;
  171. }
  172. /**
  173. * @brief NAND MSP Init
  174. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  175. * the configuration information for NAND module.
  176. * @retval None
  177. */
  178. __weak void HAL_NAND_MspInit(NAND_HandleTypeDef *hnand)
  179. {
  180. /* Prevent unused argument(s) compilation warning */
  181. UNUSED(hnand);
  182. /* NOTE : This function Should not be modified, when the callback is needed,
  183. the HAL_NAND_MspInit could be implemented in the user file
  184. */
  185. }
  186. /**
  187. * @brief NAND MSP DeInit
  188. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  189. * the configuration information for NAND module.
  190. * @retval None
  191. */
  192. __weak void HAL_NAND_MspDeInit(NAND_HandleTypeDef *hnand)
  193. {
  194. /* Prevent unused argument(s) compilation warning */
  195. UNUSED(hnand);
  196. /* NOTE : This function Should not be modified, when the callback is needed,
  197. the HAL_NAND_MspDeInit could be implemented in the user file
  198. */
  199. }
  200. /**
  201. * @brief This function handles NAND device interrupt request.
  202. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  203. * the configuration information for NAND module.
  204. * @retval HAL status
  205. */
  206. void HAL_NAND_IRQHandler(NAND_HandleTypeDef *hnand)
  207. {
  208. /* Check NAND interrupt Rising edge flag */
  209. if(__FMC_NAND_GET_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_RISING_EDGE))
  210. {
  211. /* NAND interrupt callback*/
  212. HAL_NAND_ITCallback(hnand);
  213. /* Clear NAND interrupt Rising edge pending bit */
  214. __FMC_NAND_CLEAR_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_RISING_EDGE);
  215. }
  216. /* Check NAND interrupt Level flag */
  217. if(__FMC_NAND_GET_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_LEVEL))
  218. {
  219. /* NAND interrupt callback*/
  220. HAL_NAND_ITCallback(hnand);
  221. /* Clear NAND interrupt Level pending bit */
  222. __FMC_NAND_CLEAR_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_LEVEL);
  223. }
  224. /* Check NAND interrupt Falling edge flag */
  225. if(__FMC_NAND_GET_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_FALLING_EDGE))
  226. {
  227. /* NAND interrupt callback*/
  228. HAL_NAND_ITCallback(hnand);
  229. /* Clear NAND interrupt Falling edge pending bit */
  230. __FMC_NAND_CLEAR_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_FALLING_EDGE);
  231. }
  232. /* Check NAND interrupt FIFO empty flag */
  233. if(__FMC_NAND_GET_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_FEMPT))
  234. {
  235. /* NAND interrupt callback*/
  236. HAL_NAND_ITCallback(hnand);
  237. /* Clear NAND interrupt FIFO empty pending bit */
  238. __FMC_NAND_CLEAR_FLAG(hnand->Instance, hnand->Init.NandBank, FMC_FLAG_FEMPT);
  239. }
  240. }
  241. /**
  242. * @brief NAND interrupt feature callback
  243. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  244. * the configuration information for NAND module.
  245. * @retval None
  246. */
  247. __weak void HAL_NAND_ITCallback(NAND_HandleTypeDef *hnand)
  248. {
  249. /* Prevent unused argument(s) compilation warning */
  250. UNUSED(hnand);
  251. /* NOTE : This function Should not be modified, when the callback is needed,
  252. the HAL_NAND_ITCallback could be implemented in the user file
  253. */
  254. }
  255. /**
  256. * @}
  257. */
  258. /** @defgroup NAND_Exported_Functions_Group2 Input and Output functions
  259. * @brief Input Output and memory control functions
  260. *
  261. @verbatim
  262. ==============================================================================
  263. ##### NAND Input and Output functions #####
  264. ==============================================================================
  265. [..]
  266. This section provides functions allowing to use and control the NAND
  267. memory
  268. @endverbatim
  269. * @{
  270. */
  271. /**
  272. * @brief Read the NAND memory electronic signature
  273. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  274. * the configuration information for NAND module.
  275. * @param pNAND_ID NAND ID structure
  276. * @retval HAL status
  277. */
  278. HAL_StatusTypeDef HAL_NAND_Read_ID(NAND_HandleTypeDef *hnand, NAND_IDTypeDef *pNAND_ID)
  279. {
  280. __IO uint32_t data = 0U;
  281. __IO uint32_t data1 = 0U;
  282. uint32_t deviceaddress = 0U;
  283. /* Process Locked */
  284. __HAL_LOCK(hnand);
  285. /* Check the NAND controller state */
  286. if(hnand->State == HAL_NAND_STATE_BUSY)
  287. {
  288. return HAL_BUSY;
  289. }
  290. /* Identify the device address */
  291. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  292. {
  293. deviceaddress = NAND_DEVICE1;
  294. }
  295. else
  296. {
  297. deviceaddress = NAND_DEVICE2;
  298. }
  299. /* Update the NAND controller state */
  300. hnand->State = HAL_NAND_STATE_BUSY;
  301. /* Send Read ID command sequence */
  302. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_READID;
  303. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  304. /* Read the electronic signature from NAND flash */
  305. if (hnand->Init.MemoryDataWidth == FMC_NAND_PCC_MEM_BUS_WIDTH_8)
  306. {
  307. data = *(__IO uint32_t *)deviceaddress;
  308. /* Return the data read */
  309. pNAND_ID->Maker_Id = ADDR_1ST_CYCLE(data);
  310. pNAND_ID->Device_Id = ADDR_2ND_CYCLE(data);
  311. pNAND_ID->Third_Id = ADDR_3RD_CYCLE(data);
  312. pNAND_ID->Fourth_Id = ADDR_4TH_CYCLE(data);
  313. }
  314. else
  315. {
  316. data = *(__IO uint32_t *)deviceaddress;
  317. data1 = *((__IO uint32_t *)deviceaddress + 4U);
  318. /* Return the data read */
  319. pNAND_ID->Maker_Id = ADDR_1ST_CYCLE(data);
  320. pNAND_ID->Device_Id = ADDR_3RD_CYCLE(data);
  321. pNAND_ID->Third_Id = ADDR_1ST_CYCLE(data1);
  322. pNAND_ID->Fourth_Id = ADDR_3RD_CYCLE(data1);
  323. }
  324. /* Update the NAND controller state */
  325. hnand->State = HAL_NAND_STATE_READY;
  326. /* Process unlocked */
  327. __HAL_UNLOCK(hnand);
  328. return HAL_OK;
  329. }
  330. /**
  331. * @brief NAND memory reset
  332. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  333. * the configuration information for NAND module.
  334. * @retval HAL status
  335. */
  336. HAL_StatusTypeDef HAL_NAND_Reset(NAND_HandleTypeDef *hnand)
  337. {
  338. uint32_t deviceaddress = 0U;
  339. /* Process Locked */
  340. __HAL_LOCK(hnand);
  341. /* Check the NAND controller state */
  342. if(hnand->State == HAL_NAND_STATE_BUSY)
  343. {
  344. return HAL_BUSY;
  345. }
  346. /* Identify the device address */
  347. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  348. {
  349. deviceaddress = NAND_DEVICE1;
  350. }
  351. else
  352. {
  353. deviceaddress = NAND_DEVICE2;
  354. }
  355. /* Update the NAND controller state */
  356. hnand->State = HAL_NAND_STATE_BUSY;
  357. /* Send NAND reset command */
  358. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = 0xFF;
  359. /* Update the NAND controller state */
  360. hnand->State = HAL_NAND_STATE_READY;
  361. /* Process unlocked */
  362. __HAL_UNLOCK(hnand);
  363. return HAL_OK;
  364. }
  365. /**
  366. * @brief Configure the device: Enter the physical parameters of the device
  367. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  368. * the configuration information for NAND module.
  369. * @param pDeviceConfig pointer to NAND_DeviceConfigTypeDef structure
  370. * @retval HAL status
  371. */
  372. HAL_StatusTypeDef HAL_NAND_ConfigDevice(NAND_HandleTypeDef *hnand, NAND_DeviceConfigTypeDef *pDeviceConfig)
  373. {
  374. hnand->Config.PageSize = pDeviceConfig->PageSize;
  375. hnand->Config.SpareAreaSize = pDeviceConfig->SpareAreaSize;
  376. hnand->Config.BlockSize = pDeviceConfig->BlockSize;
  377. hnand->Config.BlockNbr = pDeviceConfig->BlockNbr;
  378. hnand->Config.PlaneSize = pDeviceConfig->PlaneSize;
  379. hnand->Config.PlaneNbr = pDeviceConfig->PlaneNbr;
  380. hnand->Config.ExtraCommandEnable = pDeviceConfig->ExtraCommandEnable;
  381. return HAL_OK;
  382. }
  383. /**
  384. * @brief Read Page(s) from NAND memory block (8-bits addressing)
  385. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  386. * the configuration information for NAND module.
  387. * @param pAddress pointer to NAND address structure
  388. * @param pBuffer pointer to destination read buffer
  389. * @param NumPageToRead number of pages to read from block
  390. * @retval HAL status
  391. */
  392. HAL_StatusTypeDef HAL_NAND_Read_Page_8b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint8_t *pBuffer, uint32_t NumPageToRead)
  393. {
  394. __IO uint32_t index = 0U;
  395. uint32_t tickstart = 0U;
  396. uint32_t deviceaddress = 0U, size = 0U, numPagesRead = 0U, nandaddress = 0U;
  397. /* Process Locked */
  398. __HAL_LOCK(hnand);
  399. /* Check the NAND controller state */
  400. if(hnand->State == HAL_NAND_STATE_BUSY)
  401. {
  402. return HAL_BUSY;
  403. }
  404. /* Identify the device address */
  405. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  406. {
  407. deviceaddress = NAND_DEVICE1;
  408. }
  409. else
  410. {
  411. deviceaddress = NAND_DEVICE2;
  412. }
  413. /* Update the NAND controller state */
  414. hnand->State = HAL_NAND_STATE_BUSY;
  415. /* NAND raw address calculation */
  416. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  417. /* Page(s) read loop */
  418. while((NumPageToRead != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  419. {
  420. /* update the buffer size */
  421. size = (hnand->Config.PageSize) + ((hnand->Config.PageSize) * numPagesRead);
  422. /* Send read page command sequence */
  423. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  424. /* Cards with page size <= 512 bytes */
  425. if((hnand->Config.PageSize) <= 512U)
  426. {
  427. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  428. {
  429. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  430. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  431. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  432. }
  433. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  434. {
  435. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  436. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  437. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  438. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  439. }
  440. }
  441. else /* (hnand->Config.PageSize) > 512 */
  442. {
  443. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  444. {
  445. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  446. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  447. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  448. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  449. }
  450. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  451. {
  452. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  453. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  454. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  455. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  456. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  457. }
  458. }
  459. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_TRUE1;
  460. /* Check if an extra command is needed for reading pages */
  461. if(hnand->Config.ExtraCommandEnable == ENABLE)
  462. {
  463. /* Get tick */
  464. tickstart = HAL_GetTick();
  465. /* Read status until NAND is ready */
  466. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  467. {
  468. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  469. {
  470. return HAL_TIMEOUT;
  471. }
  472. }
  473. /* Go back to read mode */
  474. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = ((uint8_t)0x00);
  475. __DSB();
  476. }
  477. /* Get Data into Buffer */
  478. for(; index < size; index++)
  479. {
  480. *(uint8_t *)pBuffer++ = *(uint8_t *)deviceaddress;
  481. }
  482. /* Increment read pages number */
  483. numPagesRead++;
  484. /* Decrement pages to read */
  485. NumPageToRead--;
  486. /* Increment the NAND address */
  487. nandaddress = (uint32_t)(nandaddress + 1U);
  488. }
  489. /* Update the NAND controller state */
  490. hnand->State = HAL_NAND_STATE_READY;
  491. /* Process unlocked */
  492. __HAL_UNLOCK(hnand);
  493. return HAL_OK;
  494. }
  495. /**
  496. * @brief Read Page(s) from NAND memory block (16-bits addressing)
  497. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  498. * the configuration information for NAND module.
  499. * @param pAddress pointer to NAND address structure
  500. * @param pBuffer pointer to destination read buffer. pBuffer should be 16bits aligned
  501. * @param NumPageToRead number of pages to read from block
  502. * @retval HAL status
  503. */
  504. HAL_StatusTypeDef HAL_NAND_Read_Page_16b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint16_t *pBuffer, uint32_t NumPageToRead)
  505. {
  506. __IO uint32_t index = 0U;
  507. uint32_t tickstart = 0U;
  508. uint32_t deviceaddress = 0U, size = 0U, numPagesRead = 0U, nandaddress = 0U;
  509. /* Process Locked */
  510. __HAL_LOCK(hnand);
  511. /* Check the NAND controller state */
  512. if(hnand->State == HAL_NAND_STATE_BUSY)
  513. {
  514. return HAL_BUSY;
  515. }
  516. /* Identify the device address */
  517. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  518. {
  519. deviceaddress = NAND_DEVICE1;
  520. }
  521. else
  522. {
  523. deviceaddress = NAND_DEVICE2;
  524. }
  525. /* Update the NAND controller state */
  526. hnand->State = HAL_NAND_STATE_BUSY;
  527. /* NAND raw address calculation */
  528. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  529. /* Page(s) read loop */
  530. while((NumPageToRead != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  531. {
  532. /* update the buffer size */
  533. size = (hnand->Config.PageSize) + ((hnand->Config.PageSize) * numPagesRead);
  534. /* Send read page command sequence */
  535. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  536. __DSB();
  537. /* Cards with page size <= 512 bytes */
  538. if((hnand->Config.PageSize) <= 512U)
  539. {
  540. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  541. {
  542. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  543. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  544. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  545. }
  546. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  547. {
  548. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  549. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  550. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  551. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  552. }
  553. }
  554. else /* (hnand->Config.PageSize) > 512 */
  555. {
  556. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  557. {
  558. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  559. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  560. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  561. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  562. }
  563. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  564. {
  565. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  566. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  567. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  568. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  569. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  570. }
  571. }
  572. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_TRUE1;
  573. if(hnand->Config.ExtraCommandEnable == ENABLE)
  574. {
  575. /* Get tick */
  576. tickstart = HAL_GetTick();
  577. /* Read status until NAND is ready */
  578. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  579. {
  580. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  581. {
  582. return HAL_TIMEOUT;
  583. }
  584. }
  585. /* Go back to read mode */
  586. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = ((uint8_t)0x00);
  587. }
  588. /* Get Data into Buffer */
  589. for(; index < size; index++)
  590. {
  591. *(uint16_t *)pBuffer++ = *(uint16_t *)deviceaddress;
  592. }
  593. /* Increment read pages number */
  594. numPagesRead++;
  595. /* Decrement pages to read */
  596. NumPageToRead--;
  597. /* Increment the NAND address */
  598. nandaddress = (uint32_t)(nandaddress + 1U);
  599. }
  600. /* Update the NAND controller state */
  601. hnand->State = HAL_NAND_STATE_READY;
  602. /* Process unlocked */
  603. __HAL_UNLOCK(hnand);
  604. return HAL_OK;
  605. }
  606. /**
  607. * @brief Write Page(s) to NAND memory block (8-bits addressing)
  608. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  609. * the configuration information for NAND module.
  610. * @param pAddress pointer to NAND address structure
  611. * @param pBuffer pointer to source buffer to write
  612. * @param NumPageToWrite : number of pages to write to block
  613. * @retval HAL status
  614. */
  615. HAL_StatusTypeDef HAL_NAND_Write_Page_8b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint8_t *pBuffer, uint32_t NumPageToWrite)
  616. {
  617. __IO uint32_t index = 0U;
  618. uint32_t tickstart = 0U;
  619. uint32_t deviceaddress = 0U, size = 0U, numPagesWritten = 0U, nandaddress = 0U;
  620. /* Process Locked */
  621. __HAL_LOCK(hnand);
  622. /* Check the NAND controller state */
  623. if(hnand->State == HAL_NAND_STATE_BUSY)
  624. {
  625. return HAL_BUSY;
  626. }
  627. /* Identify the device address */
  628. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  629. {
  630. deviceaddress = NAND_DEVICE1;
  631. }
  632. else
  633. {
  634. deviceaddress = NAND_DEVICE2;
  635. }
  636. /* Update the NAND controller state */
  637. hnand->State = HAL_NAND_STATE_BUSY;
  638. /* NAND raw address calculation */
  639. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  640. /* Page(s) write loop */
  641. while((NumPageToWrite != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  642. {
  643. /* update the buffer size */
  644. size = hnand->Config.PageSize + ((hnand->Config.PageSize) * numPagesWritten);
  645. /* Send write page command sequence */
  646. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  647. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  648. /* Cards with page size <= 512 bytes */
  649. if((hnand->Config.PageSize) <= 512U)
  650. {
  651. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  652. {
  653. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  654. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  655. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  656. }
  657. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  658. {
  659. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  660. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  661. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  662. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  663. }
  664. }
  665. else /* (hnand->Config.PageSize) > 512 */
  666. {
  667. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  668. {
  669. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  670. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  671. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  672. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  673. }
  674. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  675. {
  676. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  677. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  678. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  679. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  680. __DSB();
  681. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  682. __DSB();
  683. }
  684. }
  685. /* Write data to memory */
  686. for(; index < size; index++)
  687. {
  688. *(__IO uint8_t *)deviceaddress = *(uint8_t *)pBuffer++;
  689. }
  690. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE_TRUE1;
  691. /* Read status until NAND is ready */
  692. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  693. {
  694. /* Get tick */
  695. tickstart = HAL_GetTick();
  696. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  697. {
  698. return HAL_TIMEOUT;
  699. }
  700. }
  701. /* Increment written pages number */
  702. numPagesWritten++;
  703. /* Decrement pages to write */
  704. NumPageToWrite--;
  705. /* Increment the NAND address */
  706. nandaddress = (uint32_t)(nandaddress + 1U);
  707. }
  708. /* Update the NAND controller state */
  709. hnand->State = HAL_NAND_STATE_READY;
  710. /* Process unlocked */
  711. __HAL_UNLOCK(hnand);
  712. return HAL_OK;
  713. }
  714. /**
  715. * @brief Write Page(s) to NAND memory block (16-bits addressing)
  716. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  717. * the configuration information for NAND module.
  718. * @param pAddress pointer to NAND address structure
  719. * @param pBuffer pointer to source buffer to write. pBuffer should be 16bits aligned
  720. * @param NumPageToWrite : number of pages to write to block
  721. * @retval HAL status
  722. */
  723. HAL_StatusTypeDef HAL_NAND_Write_Page_16b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint16_t *pBuffer, uint32_t NumPageToWrite)
  724. {
  725. __IO uint32_t index = 0U;
  726. uint32_t tickstart = 0U;
  727. uint32_t deviceaddress = 0U, size = 0U, numPagesWritten = 0U, nandaddress = 0U;
  728. /* Process Locked */
  729. __HAL_LOCK(hnand);
  730. /* Check the NAND controller state */
  731. if(hnand->State == HAL_NAND_STATE_BUSY)
  732. {
  733. return HAL_BUSY;
  734. }
  735. /* Identify the device address */
  736. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  737. {
  738. deviceaddress = NAND_DEVICE1;
  739. }
  740. else
  741. {
  742. deviceaddress = NAND_DEVICE2;
  743. }
  744. /* Update the NAND controller state */
  745. hnand->State = HAL_NAND_STATE_BUSY;
  746. /* NAND raw address calculation */
  747. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  748. /* Page(s) write loop */
  749. while((NumPageToWrite != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  750. {
  751. /* update the buffer size */
  752. size = (hnand->Config.PageSize) + ((hnand->Config.PageSize) * numPagesWritten);
  753. /* Send write page command sequence */
  754. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  755. __DSB();
  756. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  757. __DSB();
  758. /* Cards with page size <= 512 bytes */
  759. if((hnand->Config.PageSize) <= 512U)
  760. {
  761. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  762. {
  763. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  764. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  765. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  766. }
  767. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  768. {
  769. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  770. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  771. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  772. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  773. }
  774. }
  775. else /* (hnand->Config.PageSize) > 512 */
  776. {
  777. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  778. {
  779. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  780. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  781. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  782. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  783. }
  784. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  785. {
  786. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  787. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  788. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  789. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  790. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  791. }
  792. }
  793. /* Write data to memory */
  794. for(; index < size; index++)
  795. {
  796. *(__IO uint16_t *)deviceaddress = *(uint16_t *)pBuffer++;
  797. }
  798. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE_TRUE1;
  799. /* Read status until NAND is ready */
  800. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  801. {
  802. /* Get tick */
  803. tickstart = HAL_GetTick();
  804. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  805. {
  806. return HAL_TIMEOUT;
  807. }
  808. }
  809. /* Increment written pages number */
  810. numPagesWritten++;
  811. /* Decrement pages to write */
  812. NumPageToWrite--;
  813. /* Increment the NAND address */
  814. nandaddress = (uint32_t)(nandaddress + 1U);
  815. }
  816. /* Update the NAND controller state */
  817. hnand->State = HAL_NAND_STATE_READY;
  818. /* Process unlocked */
  819. __HAL_UNLOCK(hnand);
  820. return HAL_OK;
  821. }
  822. /**
  823. * @brief Read Spare area(s) from NAND memory
  824. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  825. * the configuration information for NAND module.
  826. * @param pAddress pointer to NAND address structure
  827. * @param pBuffer pointer to source buffer to write
  828. * @param NumSpareAreaToRead Number of spare area to read
  829. * @retval HAL status
  830. */
  831. HAL_StatusTypeDef HAL_NAND_Read_SpareArea_8b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint8_t *pBuffer, uint32_t NumSpareAreaToRead)
  832. {
  833. __IO uint32_t index = 0U;
  834. uint32_t tickstart = 0U;
  835. uint32_t deviceaddress = 0U, size = 0U, numSpareAreaRead = 0U, nandaddress = 0U, columnaddress = 0U;
  836. /* Process Locked */
  837. __HAL_LOCK(hnand);
  838. /* Check the NAND controller state */
  839. if(hnand->State == HAL_NAND_STATE_BUSY)
  840. {
  841. return HAL_BUSY;
  842. }
  843. /* Identify the device address */
  844. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  845. {
  846. deviceaddress = NAND_DEVICE1;
  847. }
  848. else
  849. {
  850. deviceaddress = NAND_DEVICE2;
  851. }
  852. /* Update the NAND controller state */
  853. hnand->State = HAL_NAND_STATE_BUSY;
  854. /* NAND raw address calculation */
  855. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  856. /* Column in page address */
  857. columnaddress = COLUMN_ADDRESS(hnand);
  858. /* Spare area(s) read loop */
  859. while((NumSpareAreaToRead != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  860. {
  861. /* update the buffer size */
  862. size = (hnand->Config.SpareAreaSize) + ((hnand->Config.SpareAreaSize) * numSpareAreaRead);
  863. /* Cards with page size <= 512 bytes */
  864. if((hnand->Config.PageSize) <= 512U)
  865. {
  866. /* Send read spare area command sequence */
  867. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_C;
  868. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  869. {
  870. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  871. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  872. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  873. }
  874. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  875. {
  876. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  877. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  878. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  879. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  880. }
  881. }
  882. else /* (hnand->Config.PageSize) > 512 */
  883. {
  884. /* Send read spare area command sequence */
  885. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  886. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  887. {
  888. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  889. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  890. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  891. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  892. }
  893. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  894. {
  895. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  896. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  897. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  898. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  899. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  900. }
  901. }
  902. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_TRUE1;
  903. if(hnand->Config.ExtraCommandEnable == ENABLE)
  904. {
  905. /* Get tick */
  906. tickstart = HAL_GetTick();
  907. /* Read status until NAND is ready */
  908. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  909. {
  910. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  911. {
  912. return HAL_TIMEOUT;
  913. }
  914. }
  915. /* Go back to read mode */
  916. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = ((uint8_t)0x00);
  917. }
  918. /* Get Data into Buffer */
  919. for(; index < size; index++)
  920. {
  921. *(uint8_t *)pBuffer++ = *(uint8_t *)deviceaddress;
  922. }
  923. /* Increment read spare areas number */
  924. numSpareAreaRead++;
  925. /* Decrement spare areas to read */
  926. NumSpareAreaToRead--;
  927. /* Increment the NAND address */
  928. nandaddress = (uint32_t)(nandaddress + 1U);
  929. }
  930. /* Update the NAND controller state */
  931. hnand->State = HAL_NAND_STATE_READY;
  932. /* Process unlocked */
  933. __HAL_UNLOCK(hnand);
  934. return HAL_OK;
  935. }
  936. /**
  937. * @brief Read Spare area(s) from NAND memory (16-bits addressing)
  938. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  939. * the configuration information for NAND module.
  940. * @param pAddress pointer to NAND address structure
  941. * @param pBuffer pointer to source buffer to write. pBuffer should be 16bits aligned.
  942. * @param NumSpareAreaToRead Number of spare area to read
  943. * @retval HAL status
  944. */
  945. HAL_StatusTypeDef HAL_NAND_Read_SpareArea_16b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint16_t *pBuffer, uint32_t NumSpareAreaToRead)
  946. {
  947. __IO uint32_t index = 0U;
  948. uint32_t tickstart = 0U;
  949. uint32_t deviceaddress = 0U, size = 0U, numSpareAreaRead = 0U, nandaddress = 0U, columnaddress = 0U;
  950. /* Process Locked */
  951. __HAL_LOCK(hnand);
  952. /* Check the NAND controller state */
  953. if(hnand->State == HAL_NAND_STATE_BUSY)
  954. {
  955. return HAL_BUSY;
  956. }
  957. /* Identify the device address */
  958. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  959. {
  960. deviceaddress = NAND_DEVICE1;
  961. }
  962. else
  963. {
  964. deviceaddress = NAND_DEVICE2;
  965. }
  966. /* Update the NAND controller state */
  967. hnand->State = HAL_NAND_STATE_BUSY;
  968. /* NAND raw address calculation */
  969. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  970. /* Column in page address */
  971. columnaddress = (uint32_t)(COLUMN_ADDRESS(hnand) * 2U);
  972. /* Spare area(s) read loop */
  973. while((NumSpareAreaToRead != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  974. {
  975. /* update the buffer size */
  976. size = (hnand->Config.SpareAreaSize) + ((hnand->Config.SpareAreaSize) * numSpareAreaRead);
  977. /* Cards with page size <= 512 bytes */
  978. if((hnand->Config.PageSize) <= 512U)
  979. {
  980. /* Send read spare area command sequence */
  981. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_C;
  982. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  983. {
  984. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  985. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  986. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  987. }
  988. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  989. {
  990. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  991. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  992. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  993. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  994. }
  995. }
  996. else /* (hnand->Config.PageSize) > 512 */
  997. {
  998. /* Send read spare area command sequence */
  999. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  1000. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  1001. {
  1002. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1003. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1004. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1005. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1006. }
  1007. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  1008. {
  1009. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1010. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1011. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1012. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1013. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  1014. }
  1015. }
  1016. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_TRUE1;
  1017. if(hnand->Config.ExtraCommandEnable == ENABLE)
  1018. {
  1019. /* Get tick */
  1020. tickstart = HAL_GetTick();
  1021. /* Read status until NAND is ready */
  1022. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  1023. {
  1024. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  1025. {
  1026. return HAL_TIMEOUT;
  1027. }
  1028. }
  1029. /* Go back to read mode */
  1030. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = ((uint8_t)0x00);
  1031. }
  1032. /* Get Data into Buffer */
  1033. for(; index < size; index++)
  1034. {
  1035. *(uint16_t *)pBuffer++ = *(uint16_t *)deviceaddress;
  1036. }
  1037. /* Increment read spare areas number */
  1038. numSpareAreaRead++;
  1039. /* Decrement spare areas to read */
  1040. NumSpareAreaToRead--;
  1041. /* Increment the NAND address */
  1042. nandaddress = (uint32_t)(nandaddress + 1U);
  1043. }
  1044. /* Update the NAND controller state */
  1045. hnand->State = HAL_NAND_STATE_READY;
  1046. /* Process unlocked */
  1047. __HAL_UNLOCK(hnand);
  1048. return HAL_OK;
  1049. }
  1050. /**
  1051. * @brief Write Spare area(s) to NAND memory
  1052. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1053. * the configuration information for NAND module.
  1054. * @param pAddress pointer to NAND address structure
  1055. * @param pBuffer pointer to source buffer to write
  1056. * @param NumSpareAreaTowrite : number of spare areas to write to block
  1057. * @retval HAL status
  1058. */
  1059. HAL_StatusTypeDef HAL_NAND_Write_SpareArea_8b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint8_t *pBuffer, uint32_t NumSpareAreaTowrite)
  1060. {
  1061. __IO uint32_t index = 0U;
  1062. uint32_t tickstart = 0U;
  1063. uint32_t deviceaddress = 0U, size = 0U, numSpareAreaWritten = 0U, nandaddress = 0U, columnaddress = 0U;
  1064. /* Process Locked */
  1065. __HAL_LOCK(hnand);
  1066. /* Check the NAND controller state */
  1067. if(hnand->State == HAL_NAND_STATE_BUSY)
  1068. {
  1069. return HAL_BUSY;
  1070. }
  1071. /* Identify the device address */
  1072. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  1073. {
  1074. deviceaddress = NAND_DEVICE1;
  1075. }
  1076. else
  1077. {
  1078. deviceaddress = NAND_DEVICE2;
  1079. }
  1080. /* Update the FMC_NAND controller state */
  1081. hnand->State = HAL_NAND_STATE_BUSY;
  1082. /* Page address calculation */
  1083. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  1084. /* Column in page address */
  1085. columnaddress = COLUMN_ADDRESS(hnand);
  1086. /* Spare area(s) write loop */
  1087. while((NumSpareAreaTowrite != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  1088. {
  1089. /* update the buffer size */
  1090. size = (hnand->Config.SpareAreaSize) + ((hnand->Config.SpareAreaSize) * numSpareAreaWritten);
  1091. /* Cards with page size <= 512 bytes */
  1092. if((hnand->Config.PageSize) <= 512U)
  1093. {
  1094. /* Send write Spare area command sequence */
  1095. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_C;
  1096. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  1097. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  1098. {
  1099. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  1100. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1101. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1102. }
  1103. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  1104. {
  1105. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  1106. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1107. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1108. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  1109. }
  1110. }
  1111. else /* (hnand->Config.PageSize) > 512 */
  1112. {
  1113. /* Send write Spare area command sequence */
  1114. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  1115. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  1116. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  1117. {
  1118. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1119. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1120. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1121. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1122. }
  1123. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  1124. {
  1125. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1126. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1127. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1128. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1129. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  1130. }
  1131. }
  1132. /* Write data to memory */
  1133. for(; index < size; index++)
  1134. {
  1135. *(__IO uint8_t *)deviceaddress = *(uint8_t *)pBuffer++;
  1136. }
  1137. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE_TRUE1;
  1138. /* Get tick */
  1139. tickstart = HAL_GetTick();
  1140. /* Read status until NAND is ready */
  1141. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  1142. {
  1143. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  1144. {
  1145. return HAL_TIMEOUT;
  1146. }
  1147. }
  1148. /* Increment written spare areas number */
  1149. numSpareAreaWritten++;
  1150. /* Decrement spare areas to write */
  1151. NumSpareAreaTowrite--;
  1152. /* Increment the NAND address */
  1153. nandaddress = (uint32_t)(nandaddress + 1U);
  1154. }
  1155. /* Update the NAND controller state */
  1156. hnand->State = HAL_NAND_STATE_READY;
  1157. /* Process unlocked */
  1158. __HAL_UNLOCK(hnand);
  1159. return HAL_OK;
  1160. }
  1161. /**
  1162. * @brief Write Spare area(s) to NAND memory (16-bits addressing)
  1163. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1164. * the configuration information for NAND module.
  1165. * @param pAddress pointer to NAND address structure
  1166. * @param pBuffer pointer to source buffer to write. pBuffer should be 16bits aligned.
  1167. * @param NumSpareAreaTowrite : number of spare areas to write to block
  1168. * @retval HAL status
  1169. */
  1170. HAL_StatusTypeDef HAL_NAND_Write_SpareArea_16b(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress, uint16_t *pBuffer, uint32_t NumSpareAreaTowrite)
  1171. {
  1172. __IO uint32_t index = 0U;
  1173. uint32_t tickstart = 0U;
  1174. uint32_t deviceaddress = 0U, size = 0U, numSpareAreaWritten = 0U, nandaddress = 0U, columnaddress = 0U;
  1175. /* Process Locked */
  1176. __HAL_LOCK(hnand);
  1177. /* Check the NAND controller state */
  1178. if(hnand->State == HAL_NAND_STATE_BUSY)
  1179. {
  1180. return HAL_BUSY;
  1181. }
  1182. /* Identify the device address */
  1183. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  1184. {
  1185. deviceaddress = NAND_DEVICE1;
  1186. }
  1187. else
  1188. {
  1189. deviceaddress = NAND_DEVICE2;
  1190. }
  1191. /* Update the FMC_NAND controller state */
  1192. hnand->State = HAL_NAND_STATE_BUSY;
  1193. /* NAND raw address calculation */
  1194. nandaddress = ARRAY_ADDRESS(pAddress, hnand);
  1195. /* Column in page address */
  1196. columnaddress = (uint32_t)(COLUMN_ADDRESS(hnand) * 2U);
  1197. /* Spare area(s) write loop */
  1198. while((NumSpareAreaTowrite != 0U) && (nandaddress < ((hnand->Config.BlockSize) * (hnand->Config.BlockNbr))))
  1199. {
  1200. /* update the buffer size */
  1201. size = (hnand->Config.SpareAreaSize) + ((hnand->Config.SpareAreaSize) * numSpareAreaWritten);
  1202. /* Cards with page size <= 512 bytes */
  1203. if((hnand->Config.PageSize) <= 512U)
  1204. {
  1205. /* Send write Spare area command sequence */
  1206. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_C;
  1207. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  1208. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  1209. {
  1210. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  1211. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1212. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1213. }
  1214. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  1215. {
  1216. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = 0x00;
  1217. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1218. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1219. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  1220. }
  1221. }
  1222. else /* (hnand->Config.PageSize) > 512 */
  1223. {
  1224. /* Send write Spare area command sequence */
  1225. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_AREA_A;
  1226. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE0;
  1227. if (((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) <= 65535U)
  1228. {
  1229. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1230. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1231. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1232. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1233. }
  1234. else /* ((hnand->Config.BlockSize)*(hnand->Config.BlockNbr)) > 65535 */
  1235. {
  1236. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_1ST_CYCLE(columnaddress);
  1237. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = COLUMN_2ND_CYCLE(columnaddress);
  1238. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(nandaddress);
  1239. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(nandaddress);
  1240. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(nandaddress);
  1241. }
  1242. }
  1243. /* Write data to memory */
  1244. for(; index < size; index++)
  1245. {
  1246. *(__IO uint16_t *)deviceaddress = *(uint16_t *)pBuffer++;
  1247. }
  1248. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_WRITE_TRUE1;
  1249. /* Read status until NAND is ready */
  1250. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  1251. {
  1252. /* Get tick */
  1253. tickstart = HAL_GetTick();
  1254. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  1255. {
  1256. return HAL_TIMEOUT;
  1257. }
  1258. }
  1259. /* Increment written spare areas number */
  1260. numSpareAreaWritten++;
  1261. /* Decrement spare areas to write */
  1262. NumSpareAreaTowrite--;
  1263. /* Increment the NAND address */
  1264. nandaddress = (uint32_t)(nandaddress + 1U);
  1265. }
  1266. /* Update the NAND controller state */
  1267. hnand->State = HAL_NAND_STATE_READY;
  1268. /* Process unlocked */
  1269. __HAL_UNLOCK(hnand);
  1270. return HAL_OK;
  1271. }
  1272. /**
  1273. * @brief NAND memory Block erase
  1274. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1275. * the configuration information for NAND module.
  1276. * @param pAddress pointer to NAND address structure
  1277. * @retval HAL status
  1278. */
  1279. HAL_StatusTypeDef HAL_NAND_Erase_Block(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress)
  1280. {
  1281. uint32_t deviceaddress = 0U;
  1282. uint32_t tickstart = 0U;
  1283. /* Process Locked */
  1284. __HAL_LOCK(hnand);
  1285. /* Check the NAND controller state */
  1286. if(hnand->State == HAL_NAND_STATE_BUSY)
  1287. {
  1288. return HAL_BUSY;
  1289. }
  1290. /* Identify the device address */
  1291. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  1292. {
  1293. deviceaddress = NAND_DEVICE1;
  1294. }
  1295. else
  1296. {
  1297. deviceaddress = NAND_DEVICE2;
  1298. }
  1299. /* Update the NAND controller state */
  1300. hnand->State = HAL_NAND_STATE_BUSY;
  1301. /* Send Erase block command sequence */
  1302. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_ERASE0;
  1303. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_1ST_CYCLE(ARRAY_ADDRESS(pAddress, hnand));
  1304. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_2ND_CYCLE(ARRAY_ADDRESS(pAddress, hnand));
  1305. *(__IO uint8_t *)((uint32_t)(deviceaddress | ADDR_AREA)) = ADDR_3RD_CYCLE(ARRAY_ADDRESS(pAddress, hnand));
  1306. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_ERASE1;
  1307. /* Update the NAND controller state */
  1308. hnand->State = HAL_NAND_STATE_READY;
  1309. /* Get tick */
  1310. tickstart = HAL_GetTick();
  1311. /* Read status until NAND is ready */
  1312. while(HAL_NAND_Read_Status(hnand) != NAND_READY)
  1313. {
  1314. if((HAL_GetTick() - tickstart ) > NAND_WRITE_TIMEOUT)
  1315. {
  1316. /* Process unlocked */
  1317. __HAL_UNLOCK(hnand);
  1318. return HAL_TIMEOUT;
  1319. }
  1320. }
  1321. /* Process unlocked */
  1322. __HAL_UNLOCK(hnand);
  1323. return HAL_OK;
  1324. }
  1325. /**
  1326. * @brief NAND memory read status
  1327. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1328. * the configuration information for NAND module.
  1329. * @retval NAND status
  1330. */
  1331. uint32_t HAL_NAND_Read_Status(NAND_HandleTypeDef *hnand)
  1332. {
  1333. uint32_t data = 0U;
  1334. uint32_t deviceaddress = 0U;
  1335. /* Identify the device address */
  1336. if(hnand->Init.NandBank == FMC_NAND_BANK2)
  1337. {
  1338. deviceaddress = NAND_DEVICE1;
  1339. }
  1340. else
  1341. {
  1342. deviceaddress = NAND_DEVICE2;
  1343. }
  1344. /* Send Read status operation command */
  1345. *(__IO uint8_t *)((uint32_t)(deviceaddress | CMD_AREA)) = NAND_CMD_STATUS;
  1346. /* Read status register data */
  1347. data = *(__IO uint8_t *)deviceaddress;
  1348. /* Return the status */
  1349. if((data & NAND_ERROR) == NAND_ERROR)
  1350. {
  1351. return NAND_ERROR;
  1352. }
  1353. else if((data & NAND_READY) == NAND_READY)
  1354. {
  1355. return NAND_READY;
  1356. }
  1357. return NAND_BUSY;
  1358. }
  1359. /**
  1360. * @brief Increment the NAND memory address
  1361. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1362. * the configuration information for NAND module.
  1363. * @param pAddress pointer to NAND address structure
  1364. * @retval The new status of the increment address operation. It can be:
  1365. * - NAND_VALID_ADDRESS: When the new address is valid address
  1366. * - NAND_INVALID_ADDRESS: When the new address is invalid address
  1367. */
  1368. uint32_t HAL_NAND_Address_Inc(NAND_HandleTypeDef *hnand, NAND_AddressTypeDef *pAddress)
  1369. {
  1370. uint32_t status = NAND_VALID_ADDRESS;
  1371. /* Increment page address */
  1372. pAddress->Page++;
  1373. /* Check NAND address is valid */
  1374. if(pAddress->Page == hnand->Config.BlockSize)
  1375. {
  1376. pAddress->Page = 0U;
  1377. pAddress->Block++;
  1378. if(pAddress->Block == hnand->Config.PlaneSize)
  1379. {
  1380. pAddress->Block = 0U;
  1381. pAddress->Plane++;
  1382. if(pAddress->Plane == (hnand->Config.PlaneNbr))
  1383. {
  1384. status = NAND_INVALID_ADDRESS;
  1385. }
  1386. }
  1387. }
  1388. return (status);
  1389. }
  1390. /**
  1391. * @}
  1392. */
  1393. /** @defgroup NAND_Exported_Functions_Group3 Peripheral Control functions
  1394. * @brief management functions
  1395. *
  1396. @verbatim
  1397. ==============================================================================
  1398. ##### NAND Control functions #####
  1399. ==============================================================================
  1400. [..]
  1401. This subsection provides a set of functions allowing to control dynamically
  1402. the NAND interface.
  1403. @endverbatim
  1404. * @{
  1405. */
  1406. /**
  1407. * @brief Enables dynamically NAND ECC feature.
  1408. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1409. * the configuration information for NAND module.
  1410. * @retval HAL status
  1411. */
  1412. HAL_StatusTypeDef HAL_NAND_ECC_Enable(NAND_HandleTypeDef *hnand)
  1413. {
  1414. /* Check the NAND controller state */
  1415. if(hnand->State == HAL_NAND_STATE_BUSY)
  1416. {
  1417. return HAL_BUSY;
  1418. }
  1419. /* Update the NAND state */
  1420. hnand->State = HAL_NAND_STATE_BUSY;
  1421. /* Enable ECC feature */
  1422. FMC_NAND_ECC_Enable(hnand->Instance, hnand->Init.NandBank);
  1423. /* Update the NAND state */
  1424. hnand->State = HAL_NAND_STATE_READY;
  1425. return HAL_OK;
  1426. }
  1427. /**
  1428. * @brief Disables dynamically FMC_NAND ECC feature.
  1429. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1430. * the configuration information for NAND module.
  1431. * @retval HAL status
  1432. */
  1433. HAL_StatusTypeDef HAL_NAND_ECC_Disable(NAND_HandleTypeDef *hnand)
  1434. {
  1435. /* Check the NAND controller state */
  1436. if(hnand->State == HAL_NAND_STATE_BUSY)
  1437. {
  1438. return HAL_BUSY;
  1439. }
  1440. /* Update the NAND state */
  1441. hnand->State = HAL_NAND_STATE_BUSY;
  1442. /* Disable ECC feature */
  1443. FMC_NAND_ECC_Disable(hnand->Instance, hnand->Init.NandBank);
  1444. /* Update the NAND state */
  1445. hnand->State = HAL_NAND_STATE_READY;
  1446. return HAL_OK;
  1447. }
  1448. /**
  1449. * @brief Disables dynamically NAND ECC feature.
  1450. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1451. * the configuration information for NAND module.
  1452. * @param ECCval pointer to ECC value
  1453. * @param Timeout maximum timeout to wait
  1454. * @retval HAL status
  1455. */
  1456. HAL_StatusTypeDef HAL_NAND_GetECC(NAND_HandleTypeDef *hnand, uint32_t *ECCval, uint32_t Timeout)
  1457. {
  1458. HAL_StatusTypeDef status = HAL_OK;
  1459. /* Check the NAND controller state */
  1460. if(hnand->State == HAL_NAND_STATE_BUSY)
  1461. {
  1462. return HAL_BUSY;
  1463. }
  1464. /* Update the NAND state */
  1465. hnand->State = HAL_NAND_STATE_BUSY;
  1466. /* Get NAND ECC value */
  1467. status = FMC_NAND_GetECC(hnand->Instance, ECCval, hnand->Init.NandBank, Timeout);
  1468. /* Update the NAND state */
  1469. hnand->State = HAL_NAND_STATE_READY;
  1470. return status;
  1471. }
  1472. /**
  1473. * @}
  1474. */
  1475. /** @defgroup NAND_Exported_Functions_Group4 Peripheral State functions
  1476. * @brief Peripheral State functions
  1477. *
  1478. @verbatim
  1479. ==============================================================================
  1480. ##### NAND State functions #####
  1481. ==============================================================================
  1482. [..]
  1483. This subsection permits to get in run-time the status of the NAND controller
  1484. and the data flow.
  1485. @endverbatim
  1486. * @{
  1487. */
  1488. /**
  1489. * @brief return the NAND state
  1490. * @param hnand pointer to a NAND_HandleTypeDef structure that contains
  1491. * the configuration information for NAND module.
  1492. * @retval HAL state
  1493. */
  1494. HAL_NAND_StateTypeDef HAL_NAND_GetState(NAND_HandleTypeDef *hnand)
  1495. {
  1496. return hnand->State;
  1497. }
  1498. /**
  1499. * @}
  1500. */
  1501. /**
  1502. * @}
  1503. */
  1504. /**
  1505. * @}
  1506. */
  1507. #endif /* HAL_NAND_MODULE_ENABLED */
  1508. /**
  1509. * @}
  1510. */
  1511. #endif /* STM32F302xE || STM32F303xE || STM32F398xx */
  1512. /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/