STM32769I_EVAL BSP User Manual: stm32f769i_eval_sdram.c Source File

STM32769I_EVAL BSP

stm32f769i_eval_sdram.c
Go to the documentation of this file.
00001 /**
00002   ******************************************************************************
00003   * @file    stm32f769i_eval_sdram.c
00004   * @author  MCD Application Team
00005   * @version V2.0.1
00006   * @date    06-April-2017
00007   * @brief   This file includes the SDRAM driver for the MT48LC4M32B2B5-7 memory 
00008   *          device mounted on STM32F769I-EVAL evaluation boards.
00009   @verbatim
00010   How To use this driver:
00011   -----------------------
00012    - This driver is used to drive the MT48LC4M32B2B5-7 SDRAM external memory mounted
00013      on STM32F769I-EVAL evaluation board.
00014    - This driver does not need a specific component driver for the SDRAM device
00015      to be included with.
00016 
00017   Driver description:
00018   ------------------
00019   + Initialization steps:
00020      o Initialize the SDRAM external memory using the BSP_SDRAM_Init() function. This 
00021        function includes the MSP layer hardware resources initialization and the
00022        FMC controller configuration to interface with the external SDRAM memory.
00023      o It contains the SDRAM initialization sequence to program the SDRAM external 
00024        device using the function BSP_SDRAM_Initialization_sequence(). Note that this 
00025        sequence is standard for all SDRAM devices, but can include some differences
00026        from a device to another. If it is the case, the right sequence should be 
00027        implemented separately.
00028   
00029   + SDRAM read/write operations
00030      o SDRAM external memory can be accessed with read/write operations once it is
00031        initialized.
00032        Read/write operation can be performed with AHB access using the functions
00033        BSP_SDRAM_ReadData()/BSP_SDRAM_WriteData(), or by DMA transfer using the functions
00034        BSP_SDRAM_ReadData_DMA()/BSP_SDRAM_WriteData_DMA().
00035      o The AHB access is performed with 32-bit width transaction, the DMA transfer
00036        configuration is fixed at single (no burst) word transfer (see the 
00037        SDRAM_MspInit() static function).
00038      o User can implement his own functions for read/write access with his desired 
00039        configurations.
00040      o If interrupt mode is used for DMA transfer, the function BSP_SDRAM_DMA_IRQHandler()
00041        is called in IRQ handler file, to serve the generated interrupt once the DMA 
00042        transfer is complete.
00043      o You can send a command to the SDRAM device in runtime using the function 
00044        BSP_SDRAM_Sendcmd(), and giving the desired command as parameter chosen between 
00045        the predefined commands of the "FMC_SDRAM_CommandTypeDef" structure. 
00046   @endverbatim
00047   ******************************************************************************
00048   * @attention
00049   *
00050   * <h2><center>&copy; COPYRIGHT(c) 2017 STMicroelectronics</center></h2>
00051   *
00052   * Redistribution and use in source and binary forms, with or without modification,
00053   * are permitted provided that the following conditions are met:
00054   *   1. Redistributions of source code must retain the above copyright notice,
00055   *      this list of conditions and the following disclaimer.
00056   *   2. Redistributions in binary form must reproduce the above copyright notice,
00057   *      this list of conditions and the following disclaimer in the documentation
00058   *      and/or other materials provided with the distribution.
00059   *   3. Neither the name of STMicroelectronics nor the names of its contributors
00060   *      may be used to endorse or promote products derived from this software
00061   *      without specific prior written permission.
00062   *
00063   * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
00064   * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00065   * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
00066   * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
00067   * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
00068   * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
00069   * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
00070   * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
00071   * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
00072   * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00073   *
00074   ******************************************************************************
00075   */
00076 
00077 /* Dependencies
00078 - stm32f7xx_hal_sdram.c
00079 - stm32f7xx_ll_fmc.c
00080 - stm32f7xx_hal_dma.c  
00081 - stm32f7xx_hal_gpio.c
00082 - stm32f7xx_hal_cortex.c
00083 - stm32f7xx_hal_rcc_ex.h
00084 EndDependencies */ 
00085 
00086 /* Includes ------------------------------------------------------------------*/
00087 #include "stm32f769i_eval_sdram.h"
00088 
00089 /** @addtogroup BSP
00090   * @{
00091   */
00092 
00093 /** @addtogroup STM32F769I_EVAL
00094   * @{
00095   */ 
00096   
00097 /** @defgroup STM32F769I_EVAL_SDRAM STM32F769I_EVAL SDRAM
00098   * @{
00099   */ 
00100 
00101 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Types_Definitions SDRAM Private Types Definitions
00102   * @{
00103   */ 
00104 /**
00105   * @}
00106   */
00107 
00108 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Defines SDRAM Private Defines
00109   * @{
00110   */
00111 /**
00112   * @}
00113   */
00114 
00115 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Macros SDRAM Private Macros
00116   * @{
00117   */  
00118 /**
00119   * @}
00120   */
00121 
00122 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Variables SDRAM Private Variables
00123   * @{
00124   */       
00125 SDRAM_HandleTypeDef sdramHandle;
00126 static FMC_SDRAM_TimingTypeDef Timing;
00127 static FMC_SDRAM_CommandTypeDef Command;
00128 /**
00129   * @}
00130   */ 
00131 
00132 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Functions_Prototypes SDRAM Private Functions Prototypes
00133   * @{
00134   */ 
00135 /**
00136   * @}
00137   */
00138     
00139 /** @defgroup STM32F769I_EVAL_SDRAM_Private_Functions SDRAM Private Functions
00140   * @{
00141   */ 
00142 
00143 /**
00144   * @brief  Initializes the SDRAM device.
00145   * @retval SDRAM status
00146   */
00147 uint8_t BSP_SDRAM_Init(void)
00148 { 
00149   static uint8_t sdramstatus = SDRAM_ERROR;
00150   /* SDRAM device configuration */
00151   sdramHandle.Instance = FMC_SDRAM_DEVICE;
00152     
00153   /* Timing configuration for 100Mhz as SDRAM clock frequency (System clock is up to 200Mhz) */
00154   Timing.LoadToActiveDelay    = 2;
00155   Timing.ExitSelfRefreshDelay = 7;
00156   Timing.SelfRefreshTime      = 4;
00157   Timing.RowCycleDelay        = 7;
00158   Timing.WriteRecoveryTime    = 2;
00159   Timing.RPDelay              = 2;
00160   Timing.RCDDelay             = 2;
00161   
00162   sdramHandle.Init.SDBank             = FMC_SDRAM_BANK1;
00163   sdramHandle.Init.ColumnBitsNumber   = FMC_SDRAM_COLUMN_BITS_NUM_9;
00164   sdramHandle.Init.RowBitsNumber      = FMC_SDRAM_ROW_BITS_NUM_12;
00165   sdramHandle.Init.MemoryDataWidth    = SDRAM_MEMORY_WIDTH;
00166   sdramHandle.Init.InternalBankNumber = FMC_SDRAM_INTERN_BANKS_NUM_4;
00167   sdramHandle.Init.CASLatency         = FMC_SDRAM_CAS_LATENCY_3;
00168   sdramHandle.Init.WriteProtection    = FMC_SDRAM_WRITE_PROTECTION_DISABLE;
00169   sdramHandle.Init.SDClockPeriod      = SDCLOCK_PERIOD;
00170   sdramHandle.Init.ReadBurst          = FMC_SDRAM_RBURST_ENABLE;
00171   sdramHandle.Init.ReadPipeDelay      = FMC_SDRAM_RPIPE_DELAY_0;
00172   
00173   /* SDRAM controller initialization */
00174 
00175   BSP_SDRAM_MspInit(&sdramHandle, NULL); /* __weak function can be rewritten by the application */
00176 
00177   if(HAL_SDRAM_Init(&sdramHandle, &Timing) != HAL_OK)
00178   {
00179     sdramstatus = SDRAM_ERROR;
00180   }
00181   else
00182   {
00183     sdramstatus = SDRAM_OK;
00184   }
00185   
00186   /* SDRAM initialization sequence */
00187   BSP_SDRAM_Initialization_sequence(REFRESH_COUNT);
00188   
00189   return sdramstatus;
00190 }
00191 
00192 /**
00193   * @brief  DeInitializes the SDRAM device.
00194   * @retval SDRAM status
00195   */
00196 uint8_t BSP_SDRAM_DeInit(void)
00197 { 
00198   static uint8_t sdramstatus = SDRAM_ERROR;
00199   /* SDRAM device de-initialization */
00200   sdramHandle.Instance = FMC_SDRAM_DEVICE;
00201 
00202   if(HAL_SDRAM_DeInit(&sdramHandle) != HAL_OK)
00203   {
00204     sdramstatus = SDRAM_ERROR;
00205   }
00206   else
00207   {
00208     sdramstatus = SDRAM_OK;
00209   }
00210   
00211   /* SDRAM controller de-initialization */
00212   BSP_SDRAM_MspDeInit(&sdramHandle, NULL);
00213   
00214   return sdramstatus;
00215 }
00216 
00217 /**
00218   * @brief  Programs the SDRAM device.
00219   * @param  RefreshCount: SDRAM refresh counter value 
00220   * @retval None
00221   */
00222 void BSP_SDRAM_Initialization_sequence(uint32_t RefreshCount)
00223 {
00224   __IO uint32_t tmpmrd = 0;
00225   
00226   /* Step 1: Configure a clock configuration enable command */
00227   Command.CommandMode            = FMC_SDRAM_CMD_CLK_ENABLE;
00228   Command.CommandTarget          = FMC_SDRAM_CMD_TARGET_BANK1;
00229   Command.AutoRefreshNumber      = 1;
00230   Command.ModeRegisterDefinition = 0;
00231 
00232   /* Send the command */
00233   HAL_SDRAM_SendCommand(&sdramHandle, &Command, SDRAM_TIMEOUT);
00234 
00235   /* Step 2: Insert 100 us minimum delay */ 
00236   /* Inserted delay is equal to 1 ms due to systick time base unit (ms) */
00237   HAL_Delay(1);
00238     
00239   /* Step 3: Configure a PALL (precharge all) command */ 
00240   Command.CommandMode            = FMC_SDRAM_CMD_PALL;
00241   Command.CommandTarget          = FMC_SDRAM_CMD_TARGET_BANK1;
00242   Command.AutoRefreshNumber      = 1;
00243   Command.ModeRegisterDefinition = 0;
00244 
00245   /* Send the command */
00246   HAL_SDRAM_SendCommand(&sdramHandle, &Command, SDRAM_TIMEOUT);  
00247   
00248   /* Step 4: Configure an Auto Refresh command */ 
00249   Command.CommandMode            = FMC_SDRAM_CMD_AUTOREFRESH_MODE;
00250   Command.CommandTarget          = FMC_SDRAM_CMD_TARGET_BANK1;
00251   Command.AutoRefreshNumber      = 8;
00252   Command.ModeRegisterDefinition = 0;
00253 
00254   /* Send the command */
00255   HAL_SDRAM_SendCommand(&sdramHandle, &Command, SDRAM_TIMEOUT);
00256   
00257   /* Step 5: Program the external memory mode register */
00258   tmpmrd = (uint32_t)SDRAM_MODEREG_BURST_LENGTH_1          |\
00259                      SDRAM_MODEREG_BURST_TYPE_SEQUENTIAL   |\
00260                      SDRAM_MODEREG_CAS_LATENCY_3           |\
00261                      SDRAM_MODEREG_OPERATING_MODE_STANDARD |\
00262                      SDRAM_MODEREG_WRITEBURST_MODE_SINGLE;
00263   
00264   Command.CommandMode            = FMC_SDRAM_CMD_LOAD_MODE;
00265   Command.CommandTarget          = FMC_SDRAM_CMD_TARGET_BANK1;
00266   Command.AutoRefreshNumber      = 1;
00267   Command.ModeRegisterDefinition = tmpmrd;
00268 
00269   /* Send the command */
00270   HAL_SDRAM_SendCommand(&sdramHandle, &Command, SDRAM_TIMEOUT);
00271   
00272   /* Step 6: Set the refresh rate counter */
00273   /* Set the device refresh rate */
00274   HAL_SDRAM_ProgramRefreshRate(&sdramHandle, RefreshCount); 
00275 }
00276 
00277 /**
00278   * @brief  Reads an amount of data from the SDRAM memory in polling mode.
00279   * @param  uwStartAddress: Read start address
00280   * @param  pData: Pointer to data to be read  
00281   * @param  uwDataSize: Size of read data from the memory
00282   * @retval SDRAM status
00283   */
00284 uint8_t BSP_SDRAM_ReadData(uint32_t uwStartAddress, uint32_t *pData, uint32_t uwDataSize)
00285 {
00286   if(HAL_SDRAM_Read_32b(&sdramHandle, (uint32_t *)uwStartAddress, pData, uwDataSize) != HAL_OK)
00287   {
00288     return SDRAM_ERROR;
00289   }
00290   else
00291   {
00292     return SDRAM_OK;
00293   } 
00294 }
00295 
00296 /**
00297   * @brief  Reads an amount of data from the SDRAM memory in DMA mode.
00298   * @param  uwStartAddress: Read start address
00299   * @param  pData: Pointer to data to be read  
00300   * @param  uwDataSize: Size of read data from the memory
00301   * @retval SDRAM status
00302   */
00303 uint8_t BSP_SDRAM_ReadData_DMA(uint32_t uwStartAddress, uint32_t *pData, uint32_t uwDataSize)
00304 {
00305   if(HAL_SDRAM_Read_DMA(&sdramHandle, (uint32_t *)uwStartAddress, pData, uwDataSize) != HAL_OK)
00306   {
00307     return SDRAM_ERROR;
00308   }
00309   else
00310   {
00311     return SDRAM_OK;
00312   }     
00313 }
00314 
00315 /**
00316   * @brief  Writes an amount of data to the SDRAM memory in polling mode.
00317   * @param  uwStartAddress: Write start address
00318   * @param  pData: Pointer to data to be written  
00319   * @param  uwDataSize: Size of written data from the memory
00320   * @retval SDRAM status
00321   */
00322 uint8_t BSP_SDRAM_WriteData(uint32_t uwStartAddress, uint32_t *pData, uint32_t uwDataSize) 
00323 {
00324   if(HAL_SDRAM_Write_32b(&sdramHandle, (uint32_t *)uwStartAddress, pData, uwDataSize) != HAL_OK)
00325   {
00326     return SDRAM_ERROR;
00327   }
00328   else
00329   {
00330     return SDRAM_OK;
00331   }
00332 }
00333 
00334 /**
00335   * @brief  Writes an amount of data to the SDRAM memory in DMA mode.
00336   * @param  uwStartAddress: Write start address
00337   * @param  pData: Pointer to data to be written  
00338   * @param  uwDataSize: Size of written data from the memory
00339   * @retval SDRAM status
00340   */
00341 uint8_t BSP_SDRAM_WriteData_DMA(uint32_t uwStartAddress, uint32_t *pData, uint32_t uwDataSize) 
00342 {
00343   if(HAL_SDRAM_Write_DMA(&sdramHandle, (uint32_t *)uwStartAddress, pData, uwDataSize) != HAL_OK)
00344   {
00345     return SDRAM_ERROR;
00346   }
00347   else
00348   {
00349     return SDRAM_OK;
00350   } 
00351 }
00352 
00353 /**
00354   * @brief  Sends command to the SDRAM bank.
00355   * @param  SdramCmd: Pointer to SDRAM command structure 
00356   * @retval SDRAM status
00357   */  
00358 uint8_t BSP_SDRAM_Sendcmd(FMC_SDRAM_CommandTypeDef *SdramCmd)
00359 {
00360   if(HAL_SDRAM_SendCommand(&sdramHandle, SdramCmd, SDRAM_TIMEOUT) != HAL_OK)
00361   {
00362     return SDRAM_ERROR;
00363   }
00364   else
00365   {
00366     return SDRAM_OK;
00367   }
00368 }
00369 
00370 /**
00371   * @brief  Initializes SDRAM MSP.
00372   * @param  hsdram: SDRAM handle
00373   * @param  Params  
00374   * @retval None
00375   */
00376 __weak void BSP_SDRAM_MspInit(SDRAM_HandleTypeDef  *hsdram, void *Params)
00377 {  
00378   static DMA_HandleTypeDef dma_handle;
00379   GPIO_InitTypeDef gpio_init_structure;
00380   
00381   /* Enable FMC clock */
00382   __HAL_RCC_FMC_CLK_ENABLE();
00383   
00384   /* Enable chosen DMAx clock */
00385   __DMAx_CLK_ENABLE();
00386 
00387   /* Enable GPIOs clock */
00388   __HAL_RCC_GPIOD_CLK_ENABLE();
00389   __HAL_RCC_GPIOE_CLK_ENABLE();
00390   __HAL_RCC_GPIOF_CLK_ENABLE();
00391   __HAL_RCC_GPIOG_CLK_ENABLE();
00392   __HAL_RCC_GPIOH_CLK_ENABLE();
00393   __HAL_RCC_GPIOI_CLK_ENABLE();
00394   
00395   /* Common GPIO configuration */
00396   gpio_init_structure.Mode      = GPIO_MODE_AF_PP;
00397   gpio_init_structure.Pull      = GPIO_PULLUP;
00398   gpio_init_structure.Speed     = GPIO_SPEED_FREQ_VERY_HIGH;
00399   gpio_init_structure.Alternate = GPIO_AF12_FMC;
00400   
00401   /* GPIOD configuration */
00402   gpio_init_structure.Pin   = GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_8| GPIO_PIN_9 | GPIO_PIN_10 |\
00403                               GPIO_PIN_14 | GPIO_PIN_15;
00404  
00405    
00406   HAL_GPIO_Init(GPIOD, &gpio_init_structure);
00407 
00408   /* GPIOE configuration */  
00409   gpio_init_structure.Pin   = GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_7| GPIO_PIN_8 | GPIO_PIN_9 |\
00410                               GPIO_PIN_10 | GPIO_PIN_11 | GPIO_PIN_12 | GPIO_PIN_13 | GPIO_PIN_14 |\
00411                               GPIO_PIN_15;
00412       
00413   HAL_GPIO_Init(GPIOE, &gpio_init_structure);
00414   
00415   /* GPIOF configuration */  
00416   gpio_init_structure.Pin   = GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_2| GPIO_PIN_3 | GPIO_PIN_4 |\
00417                               GPIO_PIN_5 | GPIO_PIN_11 | GPIO_PIN_12 | GPIO_PIN_13 | GPIO_PIN_14 |\
00418                               GPIO_PIN_15;
00419     
00420   HAL_GPIO_Init(GPIOF, &gpio_init_structure);
00421   
00422   /* GPIOG configuration */  
00423   gpio_init_structure.Pin   = GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_4| GPIO_PIN_5 | GPIO_PIN_8 |\
00424                               GPIO_PIN_15;
00425   HAL_GPIO_Init(GPIOG, &gpio_init_structure);
00426 
00427   /* GPIOH configuration */  
00428   gpio_init_structure.Pin   = GPIO_PIN_2 | GPIO_PIN_3 | GPIO_PIN_5 | GPIO_PIN_8 | GPIO_PIN_9 |\
00429                               GPIO_PIN_10 | GPIO_PIN_11 | GPIO_PIN_12 | GPIO_PIN_13 | GPIO_PIN_14 |\
00430                               GPIO_PIN_15;
00431   HAL_GPIO_Init(GPIOH, &gpio_init_structure); 
00432   
00433   /* GPIOI configuration */  
00434   gpio_init_structure.Pin   = GPIO_PIN_0 | GPIO_PIN_1 | GPIO_PIN_2 | GPIO_PIN_3 | GPIO_PIN_4 |\
00435                               GPIO_PIN_5 | GPIO_PIN_6 | GPIO_PIN_7 | GPIO_PIN_9 | GPIO_PIN_10;
00436   HAL_GPIO_Init(GPIOI, &gpio_init_structure);  
00437   
00438   /* Configure common DMA parameters */
00439   dma_handle.Init.Channel             = SDRAM_DMAx_CHANNEL;
00440   dma_handle.Init.Direction           = DMA_MEMORY_TO_MEMORY;
00441   dma_handle.Init.PeriphInc           = DMA_PINC_ENABLE;
00442   dma_handle.Init.MemInc              = DMA_MINC_ENABLE;
00443   dma_handle.Init.PeriphDataAlignment = DMA_PDATAALIGN_WORD;
00444   dma_handle.Init.MemDataAlignment    = DMA_MDATAALIGN_WORD;
00445   dma_handle.Init.Mode                = DMA_NORMAL;
00446   dma_handle.Init.Priority            = DMA_PRIORITY_HIGH;
00447   dma_handle.Init.FIFOMode            = DMA_FIFOMODE_DISABLE;         
00448   dma_handle.Init.FIFOThreshold       = DMA_FIFO_THRESHOLD_FULL;
00449   dma_handle.Init.MemBurst            = DMA_MBURST_SINGLE;
00450   dma_handle.Init.PeriphBurst         = DMA_PBURST_SINGLE; 
00451   
00452   dma_handle.Instance = SDRAM_DMAx_STREAM;
00453   
00454    /* Associate the DMA handle */
00455   __HAL_LINKDMA(hsdram, hdma, dma_handle);
00456   
00457   /* Deinitialize the stream for new transfer */
00458   HAL_DMA_DeInit(&dma_handle);
00459   
00460   /* Configure the DMA stream */
00461   HAL_DMA_Init(&dma_handle); 
00462   
00463   /* NVIC configuration for DMA transfer complete interrupt */
00464   HAL_NVIC_SetPriority(SDRAM_DMAx_IRQn, 0x0F, 0);
00465   HAL_NVIC_EnableIRQ(SDRAM_DMAx_IRQn);
00466 }
00467 
00468 /**
00469   * @brief  DeInitializes SDRAM MSP.
00470   * @param  hsdram: SDRAM handle
00471   * @param  Params   
00472   * @retval None
00473   */
00474 __weak void BSP_SDRAM_MspDeInit(SDRAM_HandleTypeDef  *hsdram, void *Params)
00475 {  
00476     static DMA_HandleTypeDef dma_handle;
00477   
00478     /* Disable NVIC configuration for DMA interrupt */
00479     HAL_NVIC_DisableIRQ(SDRAM_DMAx_IRQn);
00480 
00481     /* Deinitialize the stream for new transfer */
00482     dma_handle.Instance = SDRAM_DMAx_STREAM;
00483     HAL_DMA_DeInit(&dma_handle);
00484 
00485     /* GPIO pins clock, FMC clock and DMA clock can be shut down in the applications
00486        by surcharging this __weak function */ 
00487 }
00488 
00489 /**
00490   * @}
00491   */  
00492   
00493 /**
00494   * @}
00495   */ 
00496   
00497 /**
00498   * @}
00499   */ 
00500   
00501 /**
00502   * @}
00503   */ 
00504 
00505 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/
Generated on Thu May 25 2017 11:03:11 for STM32769I_EVAL BSP User Manual by   doxygen 1.7.6.1