STM32Cube BSP FW for STM32F769I-Discovery

Dependents:   mbed-os-example-blinky-5 DISCO-F769NI_TOUCHSCREEN_demo_custom_1 Datarecorder2 DISCO-F769NI_TOUCHSCREEN_demo ... more

Committer:
Jerome Coutant
Date:
Fri Feb 10 13:08:21 2017 +0100
Revision:
0:c0f3bbab73d2
Child:
1:3e58f8a39705
STM32Cube_FW_F7_V1.5.1 BSP STM32F769I-Discovery

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Jerome Coutant 0:c0f3bbab73d2 1 /**
Jerome Coutant 0:c0f3bbab73d2 2 ******************************************************************************
Jerome Coutant 0:c0f3bbab73d2 3 * @file stm32f769i_discovery_qspi.c
Jerome Coutant 0:c0f3bbab73d2 4 * @author MCD Application Team
Jerome Coutant 0:c0f3bbab73d2 5 * @version V1.1.0
Jerome Coutant 0:c0f3bbab73d2 6 * @date 29-August-2016
Jerome Coutant 0:c0f3bbab73d2 7 * @brief This file includes a standard driver for the MX25L512 QSPI
Jerome Coutant 0:c0f3bbab73d2 8 * memory mounted on STM32F769I-Discovery board.
Jerome Coutant 0:c0f3bbab73d2 9 @verbatim
Jerome Coutant 0:c0f3bbab73d2 10 ==============================================================================
Jerome Coutant 0:c0f3bbab73d2 11 ##### How to use this driver #####
Jerome Coutant 0:c0f3bbab73d2 12 ==============================================================================
Jerome Coutant 0:c0f3bbab73d2 13 [..]
Jerome Coutant 0:c0f3bbab73d2 14 (#) This driver is used to drive the MX25L512 QSPI external
Jerome Coutant 0:c0f3bbab73d2 15 memory mounted on STM32F769I-Discovery board.
Jerome Coutant 0:c0f3bbab73d2 16
Jerome Coutant 0:c0f3bbab73d2 17 (#) This driver need a specific component driver (MX25L51245G) to be included with.
Jerome Coutant 0:c0f3bbab73d2 18
Jerome Coutant 0:c0f3bbab73d2 19 (#) Initialization steps:
Jerome Coutant 0:c0f3bbab73d2 20 (++) Initialize the QPSI external memory using the BSP_QSPI_Init() function. This
Jerome Coutant 0:c0f3bbab73d2 21 function includes the MSP layer hardware resources initialization and the
Jerome Coutant 0:c0f3bbab73d2 22 QSPI interface with the external memory.
Jerome Coutant 0:c0f3bbab73d2 23
Jerome Coutant 0:c0f3bbab73d2 24 (#) QSPI memory operations
Jerome Coutant 0:c0f3bbab73d2 25 (++) QSPI memory can be accessed with read/write operations once it is
Jerome Coutant 0:c0f3bbab73d2 26 initialized.
Jerome Coutant 0:c0f3bbab73d2 27 Read/write operation can be performed with AHB access using the functions
Jerome Coutant 0:c0f3bbab73d2 28 BSP_QSPI_Read()/BSP_QSPI_Write().
Jerome Coutant 0:c0f3bbab73d2 29 (++) The function BSP_QSPI_GetInfo() returns the configuration of the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 30 (see the QSPI memory data sheet)
Jerome Coutant 0:c0f3bbab73d2 31 (++) Perform erase block operation using the function BSP_QSPI_Erase_Block() and by
Jerome Coutant 0:c0f3bbab73d2 32 specifying the block address. You can perform an erase operation of the whole
Jerome Coutant 0:c0f3bbab73d2 33 chip by calling the function BSP_QSPI_Erase_Chip().
Jerome Coutant 0:c0f3bbab73d2 34 (++) The function BSP_QSPI_GetStatus() returns the current status of the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 35 (see the QSPI memory data sheet)
Jerome Coutant 0:c0f3bbab73d2 36 @endverbatim
Jerome Coutant 0:c0f3bbab73d2 37 ******************************************************************************
Jerome Coutant 0:c0f3bbab73d2 38 * @attention
Jerome Coutant 0:c0f3bbab73d2 39 *
Jerome Coutant 0:c0f3bbab73d2 40 * <h2><center>&copy; COPYRIGHT(c) 2016 STMicroelectronics</center></h2>
Jerome Coutant 0:c0f3bbab73d2 41 *
Jerome Coutant 0:c0f3bbab73d2 42 * Redistribution and use in source and binary forms, with or without modification,
Jerome Coutant 0:c0f3bbab73d2 43 * are permitted provided that the following conditions are met:
Jerome Coutant 0:c0f3bbab73d2 44 * 1. Redistributions of source code must retain the above copyright notice,
Jerome Coutant 0:c0f3bbab73d2 45 * this list of conditions and the following disclaimer.
Jerome Coutant 0:c0f3bbab73d2 46 * 2. Redistributions in binary form must reproduce the above copyright notice,
Jerome Coutant 0:c0f3bbab73d2 47 * this list of conditions and the following disclaimer in the documentation
Jerome Coutant 0:c0f3bbab73d2 48 * and/or other materials provided with the distribution.
Jerome Coutant 0:c0f3bbab73d2 49 * 3. Neither the name of STMicroelectronics nor the names of its contributors
Jerome Coutant 0:c0f3bbab73d2 50 * may be used to endorse or promote products derived from this software
Jerome Coutant 0:c0f3bbab73d2 51 * without specific prior written permission.
Jerome Coutant 0:c0f3bbab73d2 52 *
Jerome Coutant 0:c0f3bbab73d2 53 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
Jerome Coutant 0:c0f3bbab73d2 54 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
Jerome Coutant 0:c0f3bbab73d2 55 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
Jerome Coutant 0:c0f3bbab73d2 56 * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
Jerome Coutant 0:c0f3bbab73d2 57 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
Jerome Coutant 0:c0f3bbab73d2 58 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
Jerome Coutant 0:c0f3bbab73d2 59 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
Jerome Coutant 0:c0f3bbab73d2 60 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
Jerome Coutant 0:c0f3bbab73d2 61 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
Jerome Coutant 0:c0f3bbab73d2 62 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
Jerome Coutant 0:c0f3bbab73d2 63 *
Jerome Coutant 0:c0f3bbab73d2 64 ******************************************************************************
Jerome Coutant 0:c0f3bbab73d2 65 */
Jerome Coutant 0:c0f3bbab73d2 66
Jerome Coutant 0:c0f3bbab73d2 67 /* Includes ------------------------------------------------------------------*/
Jerome Coutant 0:c0f3bbab73d2 68 #include "stm32f769i_discovery_qspi.h"
Jerome Coutant 0:c0f3bbab73d2 69
Jerome Coutant 0:c0f3bbab73d2 70 /** @addtogroup BSP
Jerome Coutant 0:c0f3bbab73d2 71 * @{
Jerome Coutant 0:c0f3bbab73d2 72 */
Jerome Coutant 0:c0f3bbab73d2 73
Jerome Coutant 0:c0f3bbab73d2 74 /** @addtogroup STM32F769I_DISCOVERY
Jerome Coutant 0:c0f3bbab73d2 75 * @{
Jerome Coutant 0:c0f3bbab73d2 76 */
Jerome Coutant 0:c0f3bbab73d2 77
Jerome Coutant 0:c0f3bbab73d2 78 /** @defgroup STM32F769I_DISCOVERY_QSPI STM32F769I-Discovery QSPI
Jerome Coutant 0:c0f3bbab73d2 79 * @{
Jerome Coutant 0:c0f3bbab73d2 80 */
Jerome Coutant 0:c0f3bbab73d2 81
Jerome Coutant 0:c0f3bbab73d2 82
Jerome Coutant 0:c0f3bbab73d2 83 /* Private variables ---------------------------------------------------------*/
Jerome Coutant 0:c0f3bbab73d2 84
Jerome Coutant 0:c0f3bbab73d2 85 /** @defgroup STM32F769I_DISCOVERY_QSPI_Private_Variables STM32F769I_DISCOVERY QSPI Private Variables
Jerome Coutant 0:c0f3bbab73d2 86 * @{
Jerome Coutant 0:c0f3bbab73d2 87 */
Jerome Coutant 0:c0f3bbab73d2 88 QSPI_HandleTypeDef QSPIHandle;
Jerome Coutant 0:c0f3bbab73d2 89
Jerome Coutant 0:c0f3bbab73d2 90 /**
Jerome Coutant 0:c0f3bbab73d2 91 * @}
Jerome Coutant 0:c0f3bbab73d2 92 */
Jerome Coutant 0:c0f3bbab73d2 93
Jerome Coutant 0:c0f3bbab73d2 94
Jerome Coutant 0:c0f3bbab73d2 95
Jerome Coutant 0:c0f3bbab73d2 96 /* Private functions ---------------------------------------------------------*/
Jerome Coutant 0:c0f3bbab73d2 97
Jerome Coutant 0:c0f3bbab73d2 98 /** @defgroup STM32F769I_DISCOVERY_QSPI_Private_Functions STM32F769I_DISCOVERY QSPI Private Functions
Jerome Coutant 0:c0f3bbab73d2 99 * @{
Jerome Coutant 0:c0f3bbab73d2 100 */
Jerome Coutant 0:c0f3bbab73d2 101 static uint8_t QSPI_ResetMemory(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 102 static uint8_t QSPI_EnterFourBytesAddress(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 103 static uint8_t QSPI_DummyCyclesCfg(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 104 static uint8_t QSPI_EnterMemory_QPI(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 105 static uint8_t QSPI_ExitMemory_QPI(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 106 static uint8_t QSPI_OutDrvStrengthCfg(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 107 static uint8_t QSPI_WriteEnable(QSPI_HandleTypeDef *hqspi);
Jerome Coutant 0:c0f3bbab73d2 108 static uint8_t QSPI_AutoPollingMemReady (QSPI_HandleTypeDef *hqspi, uint32_t Timeout);
Jerome Coutant 0:c0f3bbab73d2 109
Jerome Coutant 0:c0f3bbab73d2 110 /**
Jerome Coutant 0:c0f3bbab73d2 111 * @}
Jerome Coutant 0:c0f3bbab73d2 112 */
Jerome Coutant 0:c0f3bbab73d2 113
Jerome Coutant 0:c0f3bbab73d2 114 /** @defgroup STM32F769I_DISCOVERY_QSPI_Exported_Functions STM32F769I_DISCOVERY QSPI Exported Functions
Jerome Coutant 0:c0f3bbab73d2 115 * @{
Jerome Coutant 0:c0f3bbab73d2 116 */
Jerome Coutant 0:c0f3bbab73d2 117
Jerome Coutant 0:c0f3bbab73d2 118 /**
Jerome Coutant 0:c0f3bbab73d2 119 * @brief Initializes the QSPI interface.
Jerome Coutant 0:c0f3bbab73d2 120 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 121 */
Jerome Coutant 0:c0f3bbab73d2 122 uint8_t BSP_QSPI_Init(void)
Jerome Coutant 0:c0f3bbab73d2 123 {
Jerome Coutant 0:c0f3bbab73d2 124 QSPIHandle.Instance = QUADSPI;
Jerome Coutant 0:c0f3bbab73d2 125
Jerome Coutant 0:c0f3bbab73d2 126 /* Call the DeInit function to reset the driver */
Jerome Coutant 0:c0f3bbab73d2 127 if (HAL_QSPI_DeInit(&QSPIHandle) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 128 {
Jerome Coutant 0:c0f3bbab73d2 129 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 130 }
Jerome Coutant 0:c0f3bbab73d2 131
Jerome Coutant 0:c0f3bbab73d2 132 /* System level initialization */
Jerome Coutant 0:c0f3bbab73d2 133 BSP_QSPI_MspInit(&QSPIHandle, NULL);
Jerome Coutant 0:c0f3bbab73d2 134
Jerome Coutant 0:c0f3bbab73d2 135 /* QSPI initialization */
Jerome Coutant 0:c0f3bbab73d2 136 /* QSPI freq = SYSCLK /(1 + ClockPrescaler) = 216 MHz/(1+1) = 108 Mhz */
Jerome Coutant 0:c0f3bbab73d2 137 QSPIHandle.Init.ClockPrescaler = 1; /* QSPI freq = 216 MHz/(1+1) = 108 Mhz */
Jerome Coutant 0:c0f3bbab73d2 138 QSPIHandle.Init.FifoThreshold = 16;
Jerome Coutant 0:c0f3bbab73d2 139 QSPIHandle.Init.SampleShifting = QSPI_SAMPLE_SHIFTING_HALFCYCLE;
Jerome Coutant 0:c0f3bbab73d2 140 QSPIHandle.Init.FlashSize = POSITION_VAL(MX25L512_FLASH_SIZE) - 1;
Jerome Coutant 0:c0f3bbab73d2 141 QSPIHandle.Init.ChipSelectHighTime = QSPI_CS_HIGH_TIME_1_CYCLE;
Jerome Coutant 0:c0f3bbab73d2 142 QSPIHandle.Init.ClockMode = QSPI_CLOCK_MODE_0;
Jerome Coutant 0:c0f3bbab73d2 143 QSPIHandle.Init.FlashID = QSPI_FLASH_ID_1;
Jerome Coutant 0:c0f3bbab73d2 144 QSPIHandle.Init.DualFlash = QSPI_DUALFLASH_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 145
Jerome Coutant 0:c0f3bbab73d2 146 if (HAL_QSPI_Init(&QSPIHandle) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 147 {
Jerome Coutant 0:c0f3bbab73d2 148 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 149 }
Jerome Coutant 0:c0f3bbab73d2 150
Jerome Coutant 0:c0f3bbab73d2 151 /* QSPI memory reset */
Jerome Coutant 0:c0f3bbab73d2 152 if (QSPI_ResetMemory(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 153 {
Jerome Coutant 0:c0f3bbab73d2 154 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 155 }
Jerome Coutant 0:c0f3bbab73d2 156
Jerome Coutant 0:c0f3bbab73d2 157 /* Put QSPI memory in QPI mode */
Jerome Coutant 0:c0f3bbab73d2 158 if( QSPI_EnterMemory_QPI( &QSPIHandle )!=QSPI_OK )
Jerome Coutant 0:c0f3bbab73d2 159 {
Jerome Coutant 0:c0f3bbab73d2 160 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 161 }
Jerome Coutant 0:c0f3bbab73d2 162
Jerome Coutant 0:c0f3bbab73d2 163 /* Set the QSPI memory in 4-bytes address mode */
Jerome Coutant 0:c0f3bbab73d2 164 if (QSPI_EnterFourBytesAddress(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 165 {
Jerome Coutant 0:c0f3bbab73d2 166 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 167 }
Jerome Coutant 0:c0f3bbab73d2 168
Jerome Coutant 0:c0f3bbab73d2 169 /* Configuration of the dummy cycles on QSPI memory side */
Jerome Coutant 0:c0f3bbab73d2 170 if (QSPI_DummyCyclesCfg(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 171 {
Jerome Coutant 0:c0f3bbab73d2 172 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 173 }
Jerome Coutant 0:c0f3bbab73d2 174
Jerome Coutant 0:c0f3bbab73d2 175 /* Configuration of the Output driver strength on memory side */
Jerome Coutant 0:c0f3bbab73d2 176 if( QSPI_OutDrvStrengthCfg( &QSPIHandle ) != QSPI_OK )
Jerome Coutant 0:c0f3bbab73d2 177 {
Jerome Coutant 0:c0f3bbab73d2 178 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 179 }
Jerome Coutant 0:c0f3bbab73d2 180
Jerome Coutant 0:c0f3bbab73d2 181 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 182 }
Jerome Coutant 0:c0f3bbab73d2 183
Jerome Coutant 0:c0f3bbab73d2 184 /**
Jerome Coutant 0:c0f3bbab73d2 185 * @brief De-Initializes the QSPI interface.
Jerome Coutant 0:c0f3bbab73d2 186 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 187 */
Jerome Coutant 0:c0f3bbab73d2 188 uint8_t BSP_QSPI_DeInit(void)
Jerome Coutant 0:c0f3bbab73d2 189 {
Jerome Coutant 0:c0f3bbab73d2 190 QSPIHandle.Instance = QUADSPI;
Jerome Coutant 0:c0f3bbab73d2 191
Jerome Coutant 0:c0f3bbab73d2 192 /* Put QSPI memory in SPI mode */
Jerome Coutant 0:c0f3bbab73d2 193 if( QSPI_ExitMemory_QPI(&QSPIHandle )!=QSPI_OK )
Jerome Coutant 0:c0f3bbab73d2 194 {
Jerome Coutant 0:c0f3bbab73d2 195 return QSPI_NOT_SUPPORTED;
Jerome Coutant 0:c0f3bbab73d2 196 }
Jerome Coutant 0:c0f3bbab73d2 197
Jerome Coutant 0:c0f3bbab73d2 198 /* Call the DeInit function to reset the driver */
Jerome Coutant 0:c0f3bbab73d2 199 if (HAL_QSPI_DeInit(&QSPIHandle) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 200 {
Jerome Coutant 0:c0f3bbab73d2 201 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 202 }
Jerome Coutant 0:c0f3bbab73d2 203
Jerome Coutant 0:c0f3bbab73d2 204 /* System level De-initialization */
Jerome Coutant 0:c0f3bbab73d2 205 BSP_QSPI_MspDeInit(&QSPIHandle, NULL);
Jerome Coutant 0:c0f3bbab73d2 206
Jerome Coutant 0:c0f3bbab73d2 207 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 208 }
Jerome Coutant 0:c0f3bbab73d2 209
Jerome Coutant 0:c0f3bbab73d2 210 /**
Jerome Coutant 0:c0f3bbab73d2 211 * @brief Reads an amount of data from the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 212 * @param pData: Pointer to data to be read
Jerome Coutant 0:c0f3bbab73d2 213 * @param ReadAddr: Read start address
Jerome Coutant 0:c0f3bbab73d2 214 * @param Size: Size of data to read
Jerome Coutant 0:c0f3bbab73d2 215 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 216 */
Jerome Coutant 0:c0f3bbab73d2 217 uint8_t BSP_QSPI_Read(uint8_t* pData, uint32_t ReadAddr, uint32_t Size)
Jerome Coutant 0:c0f3bbab73d2 218 {
Jerome Coutant 0:c0f3bbab73d2 219 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 220
Jerome Coutant 0:c0f3bbab73d2 221 /* Initialize the read command */
Jerome Coutant 0:c0f3bbab73d2 222 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 223 s_command.Instruction = QPI_READ_4_BYTE_ADDR_CMD;
Jerome Coutant 0:c0f3bbab73d2 224 s_command.AddressMode = QSPI_ADDRESS_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 225 s_command.AddressSize = QSPI_ADDRESS_32_BITS;
Jerome Coutant 0:c0f3bbab73d2 226 s_command.Address = ReadAddr;
Jerome Coutant 0:c0f3bbab73d2 227 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 228 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 229 s_command.DummyCycles = MX25L512_DUMMY_CYCLES_READ_QUAD_IO;
Jerome Coutant 0:c0f3bbab73d2 230 s_command.NbData = Size;
Jerome Coutant 0:c0f3bbab73d2 231 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 232 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 233 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 234
Jerome Coutant 0:c0f3bbab73d2 235 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 236 if (HAL_QSPI_Command(&QSPIHandle, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 237 {
Jerome Coutant 0:c0f3bbab73d2 238 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 239 }
Jerome Coutant 0:c0f3bbab73d2 240
Jerome Coutant 0:c0f3bbab73d2 241 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 242 if (HAL_QSPI_Receive(&QSPIHandle, pData, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 243 {
Jerome Coutant 0:c0f3bbab73d2 244 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 245 }
Jerome Coutant 0:c0f3bbab73d2 246
Jerome Coutant 0:c0f3bbab73d2 247 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 248 }
Jerome Coutant 0:c0f3bbab73d2 249
Jerome Coutant 0:c0f3bbab73d2 250 /**
Jerome Coutant 0:c0f3bbab73d2 251 * @brief Writes an amount of data to the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 252 * @param pData: Pointer to data to be written
Jerome Coutant 0:c0f3bbab73d2 253 * @param WriteAddr: Write start address
Jerome Coutant 0:c0f3bbab73d2 254 * @param Size: Size of data to write
Jerome Coutant 0:c0f3bbab73d2 255 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 256 */
Jerome Coutant 0:c0f3bbab73d2 257 uint8_t BSP_QSPI_Write(uint8_t* pData, uint32_t WriteAddr, uint32_t Size)
Jerome Coutant 0:c0f3bbab73d2 258 {
Jerome Coutant 0:c0f3bbab73d2 259 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 260 uint32_t end_addr, current_size, current_addr;
Jerome Coutant 0:c0f3bbab73d2 261
Jerome Coutant 0:c0f3bbab73d2 262 /* Calculation of the size between the write address and the end of the page */
Jerome Coutant 0:c0f3bbab73d2 263 current_addr = 0;
Jerome Coutant 0:c0f3bbab73d2 264
Jerome Coutant 0:c0f3bbab73d2 265 while (current_addr <= WriteAddr)
Jerome Coutant 0:c0f3bbab73d2 266 {
Jerome Coutant 0:c0f3bbab73d2 267 current_addr += MX25L512_PAGE_SIZE;
Jerome Coutant 0:c0f3bbab73d2 268 }
Jerome Coutant 0:c0f3bbab73d2 269 current_size = current_addr - WriteAddr;
Jerome Coutant 0:c0f3bbab73d2 270
Jerome Coutant 0:c0f3bbab73d2 271 /* Check if the size of the data is less than the remaining place in the page */
Jerome Coutant 0:c0f3bbab73d2 272 if (current_size > Size)
Jerome Coutant 0:c0f3bbab73d2 273 {
Jerome Coutant 0:c0f3bbab73d2 274 current_size = Size;
Jerome Coutant 0:c0f3bbab73d2 275 }
Jerome Coutant 0:c0f3bbab73d2 276
Jerome Coutant 0:c0f3bbab73d2 277 /* Initialize the address variables */
Jerome Coutant 0:c0f3bbab73d2 278 current_addr = WriteAddr;
Jerome Coutant 0:c0f3bbab73d2 279 end_addr = WriteAddr + Size;
Jerome Coutant 0:c0f3bbab73d2 280
Jerome Coutant 0:c0f3bbab73d2 281 /* Initialize the program command */
Jerome Coutant 0:c0f3bbab73d2 282 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 283 s_command.Instruction = QPI_PAGE_PROG_4_BYTE_ADDR_CMD;
Jerome Coutant 0:c0f3bbab73d2 284 s_command.AddressMode = QSPI_ADDRESS_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 285 s_command.AddressSize = QSPI_ADDRESS_32_BITS;
Jerome Coutant 0:c0f3bbab73d2 286 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 287 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 288 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 289 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 290 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 291 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 292
Jerome Coutant 0:c0f3bbab73d2 293 /* Perform the write page by page */
Jerome Coutant 0:c0f3bbab73d2 294 do
Jerome Coutant 0:c0f3bbab73d2 295 {
Jerome Coutant 0:c0f3bbab73d2 296 s_command.Address = current_addr;
Jerome Coutant 0:c0f3bbab73d2 297 s_command.NbData = current_size;
Jerome Coutant 0:c0f3bbab73d2 298
Jerome Coutant 0:c0f3bbab73d2 299 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 300 if (QSPI_WriteEnable(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 301 {
Jerome Coutant 0:c0f3bbab73d2 302 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 303 }
Jerome Coutant 0:c0f3bbab73d2 304
Jerome Coutant 0:c0f3bbab73d2 305 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 306 if (HAL_QSPI_Command(&QSPIHandle, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 307 {
Jerome Coutant 0:c0f3bbab73d2 308 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 309 }
Jerome Coutant 0:c0f3bbab73d2 310
Jerome Coutant 0:c0f3bbab73d2 311 /* Transmission of the data */
Jerome Coutant 0:c0f3bbab73d2 312 if (HAL_QSPI_Transmit(&QSPIHandle, pData, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 313 {
Jerome Coutant 0:c0f3bbab73d2 314 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 315 }
Jerome Coutant 0:c0f3bbab73d2 316
Jerome Coutant 0:c0f3bbab73d2 317 /* Configure automatic polling mode to wait for end of program */
Jerome Coutant 0:c0f3bbab73d2 318 if (QSPI_AutoPollingMemReady(&QSPIHandle, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 319 {
Jerome Coutant 0:c0f3bbab73d2 320 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 321 }
Jerome Coutant 0:c0f3bbab73d2 322
Jerome Coutant 0:c0f3bbab73d2 323 /* Update the address and size variables for next page programming */
Jerome Coutant 0:c0f3bbab73d2 324 current_addr += current_size;
Jerome Coutant 0:c0f3bbab73d2 325 pData += current_size;
Jerome Coutant 0:c0f3bbab73d2 326 current_size = ((current_addr + MX25L512_PAGE_SIZE) > end_addr) ? (end_addr - current_addr) : MX25L512_PAGE_SIZE;
Jerome Coutant 0:c0f3bbab73d2 327 } while (current_addr < end_addr);
Jerome Coutant 0:c0f3bbab73d2 328
Jerome Coutant 0:c0f3bbab73d2 329 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 330 }
Jerome Coutant 0:c0f3bbab73d2 331
Jerome Coutant 0:c0f3bbab73d2 332 /**
Jerome Coutant 0:c0f3bbab73d2 333 * @brief Erases the specified block of the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 334 * @param BlockAddress: Block address to erase
Jerome Coutant 0:c0f3bbab73d2 335 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 336 */
Jerome Coutant 0:c0f3bbab73d2 337 uint8_t BSP_QSPI_Erase_Block(uint32_t BlockAddress)
Jerome Coutant 0:c0f3bbab73d2 338 {
Jerome Coutant 0:c0f3bbab73d2 339 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 340
Jerome Coutant 0:c0f3bbab73d2 341 /* Initialize the erase command */
Jerome Coutant 0:c0f3bbab73d2 342 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 343 s_command.Instruction = SUBSECTOR_ERASE_4_BYTE_ADDR_CMD;
Jerome Coutant 0:c0f3bbab73d2 344 s_command.AddressMode = QSPI_ADDRESS_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 345 s_command.AddressSize = QSPI_ADDRESS_32_BITS;
Jerome Coutant 0:c0f3bbab73d2 346 s_command.Address = BlockAddress;
Jerome Coutant 0:c0f3bbab73d2 347 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 348 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 349 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 350 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 351 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 352 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 353
Jerome Coutant 0:c0f3bbab73d2 354 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 355 if (QSPI_WriteEnable(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 356 {
Jerome Coutant 0:c0f3bbab73d2 357 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 358 }
Jerome Coutant 0:c0f3bbab73d2 359
Jerome Coutant 0:c0f3bbab73d2 360 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 361 if (HAL_QSPI_Command(&QSPIHandle, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 362 {
Jerome Coutant 0:c0f3bbab73d2 363 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 364 }
Jerome Coutant 0:c0f3bbab73d2 365
Jerome Coutant 0:c0f3bbab73d2 366 /* Configure automatic polling mode to wait for end of erase */
Jerome Coutant 0:c0f3bbab73d2 367 if (QSPI_AutoPollingMemReady(&QSPIHandle, MX25L512_SUBSECTOR_ERASE_MAX_TIME) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 368 {
Jerome Coutant 0:c0f3bbab73d2 369 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 370 }
Jerome Coutant 0:c0f3bbab73d2 371
Jerome Coutant 0:c0f3bbab73d2 372 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 373 }
Jerome Coutant 0:c0f3bbab73d2 374
Jerome Coutant 0:c0f3bbab73d2 375 /**
Jerome Coutant 0:c0f3bbab73d2 376 * @brief Erases the entire QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 377 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 378 */
Jerome Coutant 0:c0f3bbab73d2 379 uint8_t BSP_QSPI_Erase_Chip(void)
Jerome Coutant 0:c0f3bbab73d2 380 {
Jerome Coutant 0:c0f3bbab73d2 381 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 382
Jerome Coutant 0:c0f3bbab73d2 383 /* Initialize the erase command */
Jerome Coutant 0:c0f3bbab73d2 384 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 385 s_command.Instruction = BULK_ERASE_CMD;
Jerome Coutant 0:c0f3bbab73d2 386 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 387 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 388 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 389 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 390 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 391 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 392 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 393
Jerome Coutant 0:c0f3bbab73d2 394 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 395 if (QSPI_WriteEnable(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 396 {
Jerome Coutant 0:c0f3bbab73d2 397 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 398 }
Jerome Coutant 0:c0f3bbab73d2 399
Jerome Coutant 0:c0f3bbab73d2 400 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 401 if (HAL_QSPI_Command(&QSPIHandle, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 402 {
Jerome Coutant 0:c0f3bbab73d2 403 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 404 }
Jerome Coutant 0:c0f3bbab73d2 405
Jerome Coutant 0:c0f3bbab73d2 406 /* Configure automatic polling mode to wait for end of erase */
Jerome Coutant 0:c0f3bbab73d2 407 if (QSPI_AutoPollingMemReady(&QSPIHandle, MX25L512_BULK_ERASE_MAX_TIME) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 408 {
Jerome Coutant 0:c0f3bbab73d2 409 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 410 }
Jerome Coutant 0:c0f3bbab73d2 411
Jerome Coutant 0:c0f3bbab73d2 412 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 413 }
Jerome Coutant 0:c0f3bbab73d2 414
Jerome Coutant 0:c0f3bbab73d2 415 /**
Jerome Coutant 0:c0f3bbab73d2 416 * @brief Reads current status of the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 417 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 418 */
Jerome Coutant 0:c0f3bbab73d2 419 uint8_t BSP_QSPI_GetStatus(void)
Jerome Coutant 0:c0f3bbab73d2 420 {
Jerome Coutant 0:c0f3bbab73d2 421 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 422 uint8_t reg;
Jerome Coutant 0:c0f3bbab73d2 423
Jerome Coutant 0:c0f3bbab73d2 424 /* Initialize the read flag status register command */
Jerome Coutant 0:c0f3bbab73d2 425 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 426 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 427 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 428 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 429 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 430 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 431 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 432 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 433 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 434 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 435
Jerome Coutant 0:c0f3bbab73d2 436 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 437 if (HAL_QSPI_Command(&QSPIHandle, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 438 {
Jerome Coutant 0:c0f3bbab73d2 439 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 440 }
Jerome Coutant 0:c0f3bbab73d2 441
Jerome Coutant 0:c0f3bbab73d2 442 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 443 if (HAL_QSPI_Receive(&QSPIHandle, &reg, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 444 {
Jerome Coutant 0:c0f3bbab73d2 445 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 446 }
Jerome Coutant 0:c0f3bbab73d2 447
Jerome Coutant 0:c0f3bbab73d2 448 /* Check the value of the register*/
Jerome Coutant 0:c0f3bbab73d2 449 if ((reg & MX25L512_SR_WIP) == 0)
Jerome Coutant 0:c0f3bbab73d2 450 {
Jerome Coutant 0:c0f3bbab73d2 451 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 452 }
Jerome Coutant 0:c0f3bbab73d2 453 else
Jerome Coutant 0:c0f3bbab73d2 454 {
Jerome Coutant 0:c0f3bbab73d2 455 return QSPI_BUSY;
Jerome Coutant 0:c0f3bbab73d2 456 }
Jerome Coutant 0:c0f3bbab73d2 457 }
Jerome Coutant 0:c0f3bbab73d2 458
Jerome Coutant 0:c0f3bbab73d2 459 /**
Jerome Coutant 0:c0f3bbab73d2 460 * @brief Return the configuration of the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 461 * @param pInfo: pointer on the configuration structure
Jerome Coutant 0:c0f3bbab73d2 462 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 463 */
Jerome Coutant 0:c0f3bbab73d2 464 uint8_t BSP_QSPI_GetInfo(QSPI_Info* pInfo)
Jerome Coutant 0:c0f3bbab73d2 465 {
Jerome Coutant 0:c0f3bbab73d2 466 /* Configure the structure with the memory configuration */
Jerome Coutant 0:c0f3bbab73d2 467 pInfo->FlashSize = MX25L512_FLASH_SIZE;
Jerome Coutant 0:c0f3bbab73d2 468 pInfo->EraseSectorSize = MX25L512_SUBSECTOR_SIZE;
Jerome Coutant 0:c0f3bbab73d2 469 pInfo->EraseSectorsNumber = (MX25L512_FLASH_SIZE/MX25L512_SUBSECTOR_SIZE);
Jerome Coutant 0:c0f3bbab73d2 470 pInfo->ProgPageSize = MX25L512_PAGE_SIZE;
Jerome Coutant 0:c0f3bbab73d2 471 pInfo->ProgPagesNumber = (MX25L512_FLASH_SIZE/MX25L512_PAGE_SIZE);
Jerome Coutant 0:c0f3bbab73d2 472
Jerome Coutant 0:c0f3bbab73d2 473 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 474 }
Jerome Coutant 0:c0f3bbab73d2 475
Jerome Coutant 0:c0f3bbab73d2 476 /**
Jerome Coutant 0:c0f3bbab73d2 477 * @brief Configure the QSPI in memory-mapped mode
Jerome Coutant 0:c0f3bbab73d2 478 * @retval QSPI memory status
Jerome Coutant 0:c0f3bbab73d2 479 */
Jerome Coutant 0:c0f3bbab73d2 480 uint8_t BSP_QSPI_EnableMemoryMappedMode(void)
Jerome Coutant 0:c0f3bbab73d2 481 {
Jerome Coutant 0:c0f3bbab73d2 482 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 483 QSPI_MemoryMappedTypeDef s_mem_mapped_cfg;
Jerome Coutant 0:c0f3bbab73d2 484
Jerome Coutant 0:c0f3bbab73d2 485 /* Configure the command for the read instruction */
Jerome Coutant 0:c0f3bbab73d2 486 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 487 s_command.Instruction = QPI_READ_4_BYTE_ADDR_CMD;
Jerome Coutant 0:c0f3bbab73d2 488 s_command.AddressMode = QSPI_ADDRESS_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 489 s_command.AddressSize = QSPI_ADDRESS_32_BITS;
Jerome Coutant 0:c0f3bbab73d2 490 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 491 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 492 s_command.DummyCycles = MX25L512_DUMMY_CYCLES_READ_QUAD_IO;
Jerome Coutant 0:c0f3bbab73d2 493 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 494 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 495 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 496
Jerome Coutant 0:c0f3bbab73d2 497 /* Configure the memory mapped mode */
Jerome Coutant 0:c0f3bbab73d2 498 s_mem_mapped_cfg.TimeOutActivation = QSPI_TIMEOUT_COUNTER_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 499 s_mem_mapped_cfg.TimeOutPeriod = 0;
Jerome Coutant 0:c0f3bbab73d2 500
Jerome Coutant 0:c0f3bbab73d2 501 if (HAL_QSPI_MemoryMapped(&QSPIHandle, &s_command, &s_mem_mapped_cfg) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 502 {
Jerome Coutant 0:c0f3bbab73d2 503 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 504 }
Jerome Coutant 0:c0f3bbab73d2 505
Jerome Coutant 0:c0f3bbab73d2 506 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 507 }
Jerome Coutant 0:c0f3bbab73d2 508
Jerome Coutant 0:c0f3bbab73d2 509 /**
Jerome Coutant 0:c0f3bbab73d2 510 * @}
Jerome Coutant 0:c0f3bbab73d2 511 */
Jerome Coutant 0:c0f3bbab73d2 512
Jerome Coutant 0:c0f3bbab73d2 513 /** @addtogroup STM32F769I_DISCOVERY_QSPI_Private_Functions
Jerome Coutant 0:c0f3bbab73d2 514 * @{
Jerome Coutant 0:c0f3bbab73d2 515 */
Jerome Coutant 0:c0f3bbab73d2 516
Jerome Coutant 0:c0f3bbab73d2 517 /**
Jerome Coutant 0:c0f3bbab73d2 518 * @brief QSPI MSP Initialization
Jerome Coutant 0:c0f3bbab73d2 519 * This function configures the hardware resources used in this example:
Jerome Coutant 0:c0f3bbab73d2 520 * - Peripheral's clock enable
Jerome Coutant 0:c0f3bbab73d2 521 * - Peripheral's GPIO Configuration
Jerome Coutant 0:c0f3bbab73d2 522 * - NVIC configuration for QSPI interrupt
Jerome Coutant 0:c0f3bbab73d2 523 * @retval None
Jerome Coutant 0:c0f3bbab73d2 524 */
Jerome Coutant 0:c0f3bbab73d2 525 __weak void BSP_QSPI_MspInit(QSPI_HandleTypeDef *hqspi, void *Params)
Jerome Coutant 0:c0f3bbab73d2 526 {
Jerome Coutant 0:c0f3bbab73d2 527 GPIO_InitTypeDef gpio_init_structure;
Jerome Coutant 0:c0f3bbab73d2 528
Jerome Coutant 0:c0f3bbab73d2 529 /*##-1- Enable peripherals and GPIO Clocks #################################*/
Jerome Coutant 0:c0f3bbab73d2 530 /* Enable the QuadSPI memory interface clock */
Jerome Coutant 0:c0f3bbab73d2 531 QSPI_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 532 /* Reset the QuadSPI memory interface */
Jerome Coutant 0:c0f3bbab73d2 533 QSPI_FORCE_RESET();
Jerome Coutant 0:c0f3bbab73d2 534 QSPI_RELEASE_RESET();
Jerome Coutant 0:c0f3bbab73d2 535 /* Enable GPIO clocks */
Jerome Coutant 0:c0f3bbab73d2 536 QSPI_CS_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 537 QSPI_CLK_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 538 QSPI_D0_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 539 QSPI_D1_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 540 QSPI_D2_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 541 QSPI_D3_GPIO_CLK_ENABLE();
Jerome Coutant 0:c0f3bbab73d2 542
Jerome Coutant 0:c0f3bbab73d2 543 /*##-2- Configure peripheral GPIO ##########################################*/
Jerome Coutant 0:c0f3bbab73d2 544 /* QSPI CS GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 545 gpio_init_structure.Pin = QSPI_CS_PIN;
Jerome Coutant 0:c0f3bbab73d2 546 gpio_init_structure.Alternate = QSPI_CS_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 547 gpio_init_structure.Mode = GPIO_MODE_AF_PP;
Jerome Coutant 0:c0f3bbab73d2 548 gpio_init_structure.Pull = GPIO_PULLUP;
Jerome Coutant 0:c0f3bbab73d2 549 gpio_init_structure.Speed = GPIO_SPEED_FREQ_HIGH;
Jerome Coutant 0:c0f3bbab73d2 550 HAL_GPIO_Init(QSPI_CS_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 551 /* QSPI CLK GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 552 gpio_init_structure.Pin = QSPI_CLK_PIN;
Jerome Coutant 0:c0f3bbab73d2 553 gpio_init_structure.Alternate = QSPI_CLK_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 554 gpio_init_structure.Pull = GPIO_NOPULL;
Jerome Coutant 0:c0f3bbab73d2 555 HAL_GPIO_Init(QSPI_CLK_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 556 /* QSPI D0 GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 557 gpio_init_structure.Pin = QSPI_D0_PIN;
Jerome Coutant 0:c0f3bbab73d2 558 gpio_init_structure.Alternate = QSPI_D0_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 559 HAL_GPIO_Init(QSPI_D0_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 560 /* QSPI D1 GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 561 gpio_init_structure.Pin = QSPI_D1_PIN;
Jerome Coutant 0:c0f3bbab73d2 562 gpio_init_structure.Alternate = QSPI_D1_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 563 HAL_GPIO_Init(QSPI_D1_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 564 /* QSPI D2 GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 565 gpio_init_structure.Pin = QSPI_D2_PIN;
Jerome Coutant 0:c0f3bbab73d2 566 gpio_init_structure.Alternate = QSPI_D2_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 567 HAL_GPIO_Init(QSPI_D2_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 568 /* QSPI D3 GPIO pin configuration */
Jerome Coutant 0:c0f3bbab73d2 569 gpio_init_structure.Pin = QSPI_D3_PIN;
Jerome Coutant 0:c0f3bbab73d2 570 gpio_init_structure.Alternate = QSPI_D3_PIN_AF;
Jerome Coutant 0:c0f3bbab73d2 571 HAL_GPIO_Init(QSPI_D3_GPIO_PORT, &gpio_init_structure);
Jerome Coutant 0:c0f3bbab73d2 572
Jerome Coutant 0:c0f3bbab73d2 573 /*##-3- Configure the NVIC for QSPI #########################################*/
Jerome Coutant 0:c0f3bbab73d2 574 /* NVIC configuration for QSPI interrupt */
Jerome Coutant 0:c0f3bbab73d2 575 HAL_NVIC_SetPriority(QUADSPI_IRQn, 0x0F, 0);
Jerome Coutant 0:c0f3bbab73d2 576 HAL_NVIC_EnableIRQ(QUADSPI_IRQn);
Jerome Coutant 0:c0f3bbab73d2 577 }
Jerome Coutant 0:c0f3bbab73d2 578
Jerome Coutant 0:c0f3bbab73d2 579 /**
Jerome Coutant 0:c0f3bbab73d2 580 * @brief QSPI MSP De-Initialization
Jerome Coutant 0:c0f3bbab73d2 581 * This function frees the hardware resources used in this example:
Jerome Coutant 0:c0f3bbab73d2 582 * - Disable the Peripheral's clock
Jerome Coutant 0:c0f3bbab73d2 583 * - Revert GPIO and NVIC configuration to their default state
Jerome Coutant 0:c0f3bbab73d2 584 * @retval None
Jerome Coutant 0:c0f3bbab73d2 585 */
Jerome Coutant 0:c0f3bbab73d2 586 __weak void BSP_QSPI_MspDeInit(QSPI_HandleTypeDef *hqspi, void *Params)
Jerome Coutant 0:c0f3bbab73d2 587 {
Jerome Coutant 0:c0f3bbab73d2 588 /*##-1- Disable the NVIC for QSPI ###########################################*/
Jerome Coutant 0:c0f3bbab73d2 589 HAL_NVIC_DisableIRQ(QUADSPI_IRQn);
Jerome Coutant 0:c0f3bbab73d2 590
Jerome Coutant 0:c0f3bbab73d2 591 /*##-2- Disable peripherals and GPIO Clocks ################################*/
Jerome Coutant 0:c0f3bbab73d2 592 /* De-Configure QSPI pins */
Jerome Coutant 0:c0f3bbab73d2 593 HAL_GPIO_DeInit(QSPI_CS_GPIO_PORT, QSPI_CS_PIN);
Jerome Coutant 0:c0f3bbab73d2 594 HAL_GPIO_DeInit(QSPI_CLK_GPIO_PORT, QSPI_CLK_PIN);
Jerome Coutant 0:c0f3bbab73d2 595 HAL_GPIO_DeInit(QSPI_D0_GPIO_PORT, QSPI_D0_PIN);
Jerome Coutant 0:c0f3bbab73d2 596 HAL_GPIO_DeInit(QSPI_D1_GPIO_PORT, QSPI_D1_PIN);
Jerome Coutant 0:c0f3bbab73d2 597 HAL_GPIO_DeInit(QSPI_D2_GPIO_PORT, QSPI_D2_PIN);
Jerome Coutant 0:c0f3bbab73d2 598 HAL_GPIO_DeInit(QSPI_D3_GPIO_PORT, QSPI_D3_PIN);
Jerome Coutant 0:c0f3bbab73d2 599
Jerome Coutant 0:c0f3bbab73d2 600 /*##-3- Reset peripherals ##################################################*/
Jerome Coutant 0:c0f3bbab73d2 601 /* Reset the QuadSPI memory interface */
Jerome Coutant 0:c0f3bbab73d2 602 QSPI_FORCE_RESET();
Jerome Coutant 0:c0f3bbab73d2 603 QSPI_RELEASE_RESET();
Jerome Coutant 0:c0f3bbab73d2 604
Jerome Coutant 0:c0f3bbab73d2 605 /* Disable the QuadSPI memory interface clock */
Jerome Coutant 0:c0f3bbab73d2 606 QSPI_CLK_DISABLE();
Jerome Coutant 0:c0f3bbab73d2 607 }
Jerome Coutant 0:c0f3bbab73d2 608
Jerome Coutant 0:c0f3bbab73d2 609 /**
Jerome Coutant 0:c0f3bbab73d2 610 * @brief This function reset the QSPI memory.
Jerome Coutant 0:c0f3bbab73d2 611 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 612 * @retval None
Jerome Coutant 0:c0f3bbab73d2 613 */
Jerome Coutant 0:c0f3bbab73d2 614 static uint8_t QSPI_ResetMemory(QSPI_HandleTypeDef *hqspi)
Jerome Coutant 0:c0f3bbab73d2 615 {
Jerome Coutant 0:c0f3bbab73d2 616 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 617 QSPI_AutoPollingTypeDef s_config;
Jerome Coutant 0:c0f3bbab73d2 618 uint8_t reg;
Jerome Coutant 0:c0f3bbab73d2 619
Jerome Coutant 0:c0f3bbab73d2 620 /* Send command RESET command in QPI mode (QUAD I/Os) */
Jerome Coutant 0:c0f3bbab73d2 621 /* Initialize the reset enable command */
Jerome Coutant 0:c0f3bbab73d2 622 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 623 s_command.Instruction = RESET_ENABLE_CMD;
Jerome Coutant 0:c0f3bbab73d2 624 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 625 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 626 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 627 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 628 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 629 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 630 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 631 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 632 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 633 {
Jerome Coutant 0:c0f3bbab73d2 634 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 635 }
Jerome Coutant 0:c0f3bbab73d2 636 /* Send the reset memory command */
Jerome Coutant 0:c0f3bbab73d2 637 s_command.Instruction = RESET_MEMORY_CMD;
Jerome Coutant 0:c0f3bbab73d2 638 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 639 {
Jerome Coutant 0:c0f3bbab73d2 640 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 641 }
Jerome Coutant 0:c0f3bbab73d2 642
Jerome Coutant 0:c0f3bbab73d2 643 /* Send command RESET command in SPI mode */
Jerome Coutant 0:c0f3bbab73d2 644 /* Initialize the reset enable command */
Jerome Coutant 0:c0f3bbab73d2 645 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 646 s_command.Instruction = RESET_ENABLE_CMD;
Jerome Coutant 0:c0f3bbab73d2 647 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 648 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 649 {
Jerome Coutant 0:c0f3bbab73d2 650 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 651 }
Jerome Coutant 0:c0f3bbab73d2 652 /* Send the reset memory command */
Jerome Coutant 0:c0f3bbab73d2 653 s_command.Instruction = RESET_MEMORY_CMD;
Jerome Coutant 0:c0f3bbab73d2 654 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 655 {
Jerome Coutant 0:c0f3bbab73d2 656 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 657 }
Jerome Coutant 0:c0f3bbab73d2 658
Jerome Coutant 0:c0f3bbab73d2 659 /* After reset CMD, 1000ms requested if QSPI memory SWReset occured during full chip erase operation */
Jerome Coutant 0:c0f3bbab73d2 660 HAL_Delay( 1000 );
Jerome Coutant 0:c0f3bbab73d2 661
Jerome Coutant 0:c0f3bbab73d2 662 /* Configure automatic polling mode to wait the WIP bit=0 */
Jerome Coutant 0:c0f3bbab73d2 663 s_config.Match = 0;
Jerome Coutant 0:c0f3bbab73d2 664 s_config.Mask = MX25L512_SR_WIP;
Jerome Coutant 0:c0f3bbab73d2 665 s_config.MatchMode = QSPI_MATCH_MODE_AND;
Jerome Coutant 0:c0f3bbab73d2 666 s_config.StatusBytesSize = 1;
Jerome Coutant 0:c0f3bbab73d2 667 s_config.Interval = 0x10;
Jerome Coutant 0:c0f3bbab73d2 668 s_config.AutomaticStop = QSPI_AUTOMATIC_STOP_ENABLE;
Jerome Coutant 0:c0f3bbab73d2 669
Jerome Coutant 0:c0f3bbab73d2 670 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 671 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 672 s_command.DataMode = QSPI_DATA_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 673
Jerome Coutant 0:c0f3bbab73d2 674 if (HAL_QSPI_AutoPolling(hqspi, &s_command, &s_config, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 675 {
Jerome Coutant 0:c0f3bbab73d2 676 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 677 }
Jerome Coutant 0:c0f3bbab73d2 678
Jerome Coutant 0:c0f3bbab73d2 679 /* Initialize the reading of status register */
Jerome Coutant 0:c0f3bbab73d2 680 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 681 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 682 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 683 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 684 s_command.DataMode = QSPI_DATA_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 685 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 686 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 687 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 688 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 689 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 690
Jerome Coutant 0:c0f3bbab73d2 691 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 692 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 693 {
Jerome Coutant 0:c0f3bbab73d2 694 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 695 }
Jerome Coutant 0:c0f3bbab73d2 696
Jerome Coutant 0:c0f3bbab73d2 697 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 698 if (HAL_QSPI_Receive(hqspi, &reg, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 699 {
Jerome Coutant 0:c0f3bbab73d2 700 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 701 }
Jerome Coutant 0:c0f3bbab73d2 702
Jerome Coutant 0:c0f3bbab73d2 703 /* Enable write operations, command in 1 bit */
Jerome Coutant 0:c0f3bbab73d2 704 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 705 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 706 s_command.Instruction = WRITE_ENABLE_CMD;
Jerome Coutant 0:c0f3bbab73d2 707 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 708 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 709 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 710 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 711 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 712 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 713 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 714
Jerome Coutant 0:c0f3bbab73d2 715 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 716 {
Jerome Coutant 0:c0f3bbab73d2 717 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 718 }
Jerome Coutant 0:c0f3bbab73d2 719
Jerome Coutant 0:c0f3bbab73d2 720 /* Configure automatic polling mode to wait for write enabling */
Jerome Coutant 0:c0f3bbab73d2 721 s_config.Match = MX25L512_SR_WREN;
Jerome Coutant 0:c0f3bbab73d2 722 s_config.Mask = MX25L512_SR_WREN;
Jerome Coutant 0:c0f3bbab73d2 723 s_config.MatchMode = QSPI_MATCH_MODE_AND;
Jerome Coutant 0:c0f3bbab73d2 724 s_config.StatusBytesSize = 1;
Jerome Coutant 0:c0f3bbab73d2 725 s_config.Interval = 0x10;
Jerome Coutant 0:c0f3bbab73d2 726 s_config.AutomaticStop = QSPI_AUTOMATIC_STOP_ENABLE;
Jerome Coutant 0:c0f3bbab73d2 727
Jerome Coutant 0:c0f3bbab73d2 728 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 729 s_command.DataMode = QSPI_DATA_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 730
Jerome Coutant 0:c0f3bbab73d2 731 if (HAL_QSPI_AutoPolling(hqspi, &s_command, &s_config, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 732 {
Jerome Coutant 0:c0f3bbab73d2 733 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 734 }
Jerome Coutant 0:c0f3bbab73d2 735
Jerome Coutant 0:c0f3bbab73d2 736 /* Update the configuration register with new dummy cycles */
Jerome Coutant 0:c0f3bbab73d2 737 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 738 s_command.Instruction = WRITE_STATUS_CFG_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 739 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 740 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 741 s_command.DataMode = QSPI_DATA_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 742 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 743 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 744 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 745 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 746 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 747
Jerome Coutant 0:c0f3bbab73d2 748 /* Enable the Quad IO on the QSPI memory (Non-volatile bit) */
Jerome Coutant 0:c0f3bbab73d2 749 reg |= MX25L512_SR_QUADEN;
Jerome Coutant 0:c0f3bbab73d2 750
Jerome Coutant 0:c0f3bbab73d2 751 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 752 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 753 {
Jerome Coutant 0:c0f3bbab73d2 754 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 755 }
Jerome Coutant 0:c0f3bbab73d2 756
Jerome Coutant 0:c0f3bbab73d2 757 /* Transmission of the data */
Jerome Coutant 0:c0f3bbab73d2 758 if (HAL_QSPI_Transmit(hqspi, &reg, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 759 {
Jerome Coutant 0:c0f3bbab73d2 760 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 761 }
Jerome Coutant 0:c0f3bbab73d2 762
Jerome Coutant 0:c0f3bbab73d2 763 /* 40ms Write Status/Configuration Register Cycle Time */
Jerome Coutant 0:c0f3bbab73d2 764 HAL_Delay( 40 );
Jerome Coutant 0:c0f3bbab73d2 765
Jerome Coutant 0:c0f3bbab73d2 766 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 767 }
Jerome Coutant 0:c0f3bbab73d2 768
Jerome Coutant 0:c0f3bbab73d2 769 /**
Jerome Coutant 0:c0f3bbab73d2 770 * @brief This function set the QSPI memory in 4-byte address mode
Jerome Coutant 0:c0f3bbab73d2 771 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 772 * @retval None
Jerome Coutant 0:c0f3bbab73d2 773 */
Jerome Coutant 0:c0f3bbab73d2 774 static uint8_t QSPI_EnterFourBytesAddress(QSPI_HandleTypeDef *hqspi)
Jerome Coutant 0:c0f3bbab73d2 775 {
Jerome Coutant 0:c0f3bbab73d2 776 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 777
Jerome Coutant 0:c0f3bbab73d2 778 /* Initialize the command */
Jerome Coutant 0:c0f3bbab73d2 779 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 780 s_command.Instruction = ENTER_4_BYTE_ADDR_MODE_CMD;
Jerome Coutant 0:c0f3bbab73d2 781 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 782 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 783 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 784 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 785 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 786 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 787 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 788
Jerome Coutant 0:c0f3bbab73d2 789 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 790 if (QSPI_WriteEnable(hqspi) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 791 {
Jerome Coutant 0:c0f3bbab73d2 792 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 793 }
Jerome Coutant 0:c0f3bbab73d2 794
Jerome Coutant 0:c0f3bbab73d2 795 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 796 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 797 {
Jerome Coutant 0:c0f3bbab73d2 798 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 799 }
Jerome Coutant 0:c0f3bbab73d2 800
Jerome Coutant 0:c0f3bbab73d2 801 /* Configure automatic polling mode to wait the memory is ready */
Jerome Coutant 0:c0f3bbab73d2 802 if (QSPI_AutoPollingMemReady(hqspi, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 803 {
Jerome Coutant 0:c0f3bbab73d2 804 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 805 }
Jerome Coutant 0:c0f3bbab73d2 806
Jerome Coutant 0:c0f3bbab73d2 807 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 808 }
Jerome Coutant 0:c0f3bbab73d2 809
Jerome Coutant 0:c0f3bbab73d2 810 /**
Jerome Coutant 0:c0f3bbab73d2 811 * @brief This function configure the dummy cycles on memory side.
Jerome Coutant 0:c0f3bbab73d2 812 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 813 * @retval None
Jerome Coutant 0:c0f3bbab73d2 814 */
Jerome Coutant 0:c0f3bbab73d2 815 static uint8_t QSPI_DummyCyclesCfg(QSPI_HandleTypeDef *hqspi)
Jerome Coutant 0:c0f3bbab73d2 816 {
Jerome Coutant 0:c0f3bbab73d2 817 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 818 uint8_t reg[2];
Jerome Coutant 0:c0f3bbab73d2 819
Jerome Coutant 0:c0f3bbab73d2 820 /* Initialize the reading of status register */
Jerome Coutant 0:c0f3bbab73d2 821 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 822 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 823 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 824 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 825 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 826 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 827 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 828 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 829 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 830 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 831
Jerome Coutant 0:c0f3bbab73d2 832 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 833 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 834 {
Jerome Coutant 0:c0f3bbab73d2 835 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 836 }
Jerome Coutant 0:c0f3bbab73d2 837
Jerome Coutant 0:c0f3bbab73d2 838 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 839 if (HAL_QSPI_Receive(hqspi, &(reg[0]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 840 {
Jerome Coutant 0:c0f3bbab73d2 841 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 842 }
Jerome Coutant 0:c0f3bbab73d2 843
Jerome Coutant 0:c0f3bbab73d2 844 /* Initialize the reading of configuration register */
Jerome Coutant 0:c0f3bbab73d2 845 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 846 s_command.Instruction = READ_CFG_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 847 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 848 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 849 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 850 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 851 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 852 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 853 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 854 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 855
Jerome Coutant 0:c0f3bbab73d2 856 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 857 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 858 {
Jerome Coutant 0:c0f3bbab73d2 859 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 860 }
Jerome Coutant 0:c0f3bbab73d2 861
Jerome Coutant 0:c0f3bbab73d2 862 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 863 if (HAL_QSPI_Receive(hqspi, &(reg[1]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 864 {
Jerome Coutant 0:c0f3bbab73d2 865 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 866 }
Jerome Coutant 0:c0f3bbab73d2 867
Jerome Coutant 0:c0f3bbab73d2 868 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 869 if (QSPI_WriteEnable(hqspi) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 870 {
Jerome Coutant 0:c0f3bbab73d2 871 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 872 }
Jerome Coutant 0:c0f3bbab73d2 873
Jerome Coutant 0:c0f3bbab73d2 874 /* Update the configuration register with new dummy cycles */
Jerome Coutant 0:c0f3bbab73d2 875 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 876 s_command.Instruction = WRITE_STATUS_CFG_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 877 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 878 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 879 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 880 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 881 s_command.NbData = 2;
Jerome Coutant 0:c0f3bbab73d2 882 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 883 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 884 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 885
Jerome Coutant 0:c0f3bbab73d2 886 /* MX25L512_DUMMY_CYCLES_READ_QUAD = 3 for 10 cycles in QPI mode */
Jerome Coutant 0:c0f3bbab73d2 887 MODIFY_REG( reg[1], MX25L512_CR_NB_DUMMY, (MX25L512_DUMMY_CYCLES_READ_QUAD << POSITION_VAL(MX25L512_CR_NB_DUMMY)));
Jerome Coutant 0:c0f3bbab73d2 888
Jerome Coutant 0:c0f3bbab73d2 889 /* Configure the write volatile configuration register command */
Jerome Coutant 0:c0f3bbab73d2 890 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 891 {
Jerome Coutant 0:c0f3bbab73d2 892 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 893 }
Jerome Coutant 0:c0f3bbab73d2 894
Jerome Coutant 0:c0f3bbab73d2 895 /* Transmission of the data */
Jerome Coutant 0:c0f3bbab73d2 896 if (HAL_QSPI_Transmit(hqspi, &(reg[0]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 897 {
Jerome Coutant 0:c0f3bbab73d2 898 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 899 }
Jerome Coutant 0:c0f3bbab73d2 900
Jerome Coutant 0:c0f3bbab73d2 901 /* 40ms Write Status/Configuration Register Cycle Time */
Jerome Coutant 0:c0f3bbab73d2 902 HAL_Delay( 40 );
Jerome Coutant 0:c0f3bbab73d2 903
Jerome Coutant 0:c0f3bbab73d2 904 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 905 }
Jerome Coutant 0:c0f3bbab73d2 906
Jerome Coutant 0:c0f3bbab73d2 907 /**
Jerome Coutant 0:c0f3bbab73d2 908 * @brief This function put QSPI memory in QPI mode (quad I/O).
Jerome Coutant 0:c0f3bbab73d2 909 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 910 * @retval None
Jerome Coutant 0:c0f3bbab73d2 911 */
Jerome Coutant 0:c0f3bbab73d2 912 static uint8_t QSPI_EnterMemory_QPI( QSPI_HandleTypeDef *hqspi )
Jerome Coutant 0:c0f3bbab73d2 913 {
Jerome Coutant 0:c0f3bbab73d2 914 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 915 QSPI_AutoPollingTypeDef s_config;
Jerome Coutant 0:c0f3bbab73d2 916
Jerome Coutant 0:c0f3bbab73d2 917 /* Initialize the QPI enable command */
Jerome Coutant 0:c0f3bbab73d2 918 /* QSPI memory is supported to be in SPI mode, so CMD on 1 LINE */
Jerome Coutant 0:c0f3bbab73d2 919 s_command.InstructionMode = QSPI_INSTRUCTION_1_LINE;
Jerome Coutant 0:c0f3bbab73d2 920 s_command.Instruction = ENTER_QUAD_CMD;
Jerome Coutant 0:c0f3bbab73d2 921 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 922 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 923 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 924 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 925 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 926 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 927 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 928
Jerome Coutant 0:c0f3bbab73d2 929 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 930 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 931 {
Jerome Coutant 0:c0f3bbab73d2 932 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 933 }
Jerome Coutant 0:c0f3bbab73d2 934
Jerome Coutant 0:c0f3bbab73d2 935 /* Configure automatic polling mode to wait the QUADEN bit=1 and WIP bit=0 */
Jerome Coutant 0:c0f3bbab73d2 936 s_config.Match = MX25L512_SR_QUADEN;
Jerome Coutant 0:c0f3bbab73d2 937 s_config.Mask = MX25L512_SR_QUADEN|MX25L512_SR_WIP;
Jerome Coutant 0:c0f3bbab73d2 938 s_config.MatchMode = QSPI_MATCH_MODE_AND;
Jerome Coutant 0:c0f3bbab73d2 939 s_config.StatusBytesSize = 1;
Jerome Coutant 0:c0f3bbab73d2 940 s_config.Interval = 0x10;
Jerome Coutant 0:c0f3bbab73d2 941 s_config.AutomaticStop = QSPI_AUTOMATIC_STOP_ENABLE;
Jerome Coutant 0:c0f3bbab73d2 942
Jerome Coutant 0:c0f3bbab73d2 943 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 944 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 945 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 946
Jerome Coutant 0:c0f3bbab73d2 947 if (HAL_QSPI_AutoPolling(hqspi, &s_command, &s_config, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 948 {
Jerome Coutant 0:c0f3bbab73d2 949 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 950 }
Jerome Coutant 0:c0f3bbab73d2 951
Jerome Coutant 0:c0f3bbab73d2 952 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 953 }
Jerome Coutant 0:c0f3bbab73d2 954
Jerome Coutant 0:c0f3bbab73d2 955 /**
Jerome Coutant 0:c0f3bbab73d2 956 * @brief This function put QSPI memory in SPI mode.
Jerome Coutant 0:c0f3bbab73d2 957 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 958 * @retval None
Jerome Coutant 0:c0f3bbab73d2 959 */
Jerome Coutant 0:c0f3bbab73d2 960 static uint8_t QSPI_ExitMemory_QPI( QSPI_HandleTypeDef *hqspi)
Jerome Coutant 0:c0f3bbab73d2 961 {
Jerome Coutant 0:c0f3bbab73d2 962 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 963
Jerome Coutant 0:c0f3bbab73d2 964 /* Initialize the QPI enable command */
Jerome Coutant 0:c0f3bbab73d2 965 /* QSPI memory is supported to be in QPI mode, so CMD on 4 LINES */
Jerome Coutant 0:c0f3bbab73d2 966 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 967 s_command.Instruction = EXIT_QUAD_CMD;
Jerome Coutant 0:c0f3bbab73d2 968 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 969 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 970 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 971 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 972 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 973 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 974 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 975
Jerome Coutant 0:c0f3bbab73d2 976 /* Send the command */
Jerome Coutant 0:c0f3bbab73d2 977 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 978 {
Jerome Coutant 0:c0f3bbab73d2 979 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 980 }
Jerome Coutant 0:c0f3bbab73d2 981
Jerome Coutant 0:c0f3bbab73d2 982 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 983 }
Jerome Coutant 0:c0f3bbab73d2 984
Jerome Coutant 0:c0f3bbab73d2 985 /**
Jerome Coutant 0:c0f3bbab73d2 986 * @brief This function configure the Output driver strength on memory side.
Jerome Coutant 0:c0f3bbab73d2 987 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 988 * @retval None
Jerome Coutant 0:c0f3bbab73d2 989 */
Jerome Coutant 0:c0f3bbab73d2 990 static uint8_t QSPI_OutDrvStrengthCfg( QSPI_HandleTypeDef *hqspi )
Jerome Coutant 0:c0f3bbab73d2 991 {
Jerome Coutant 0:c0f3bbab73d2 992 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 993 uint8_t reg[2];
Jerome Coutant 0:c0f3bbab73d2 994
Jerome Coutant 0:c0f3bbab73d2 995 /* Initialize the reading of status register */
Jerome Coutant 0:c0f3bbab73d2 996 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 997 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 998 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 999 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 1000 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1001 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 1002 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 1003 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 1004 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 1005 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 1006
Jerome Coutant 0:c0f3bbab73d2 1007 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 1008 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1009 {
Jerome Coutant 0:c0f3bbab73d2 1010 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1011 }
Jerome Coutant 0:c0f3bbab73d2 1012
Jerome Coutant 0:c0f3bbab73d2 1013 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 1014 if (HAL_QSPI_Receive(hqspi, &(reg[0]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1015 {
Jerome Coutant 0:c0f3bbab73d2 1016 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1017 }
Jerome Coutant 0:c0f3bbab73d2 1018
Jerome Coutant 0:c0f3bbab73d2 1019 /* Initialize the reading of configuration register */
Jerome Coutant 0:c0f3bbab73d2 1020 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1021 s_command.Instruction = READ_CFG_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 1022 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 1023 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 1024 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1025 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 1026 s_command.NbData = 1;
Jerome Coutant 0:c0f3bbab73d2 1027 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 1028 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 1029 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 1030
Jerome Coutant 0:c0f3bbab73d2 1031 /* Configure the command */
Jerome Coutant 0:c0f3bbab73d2 1032 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1033 {
Jerome Coutant 0:c0f3bbab73d2 1034 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1035 }
Jerome Coutant 0:c0f3bbab73d2 1036
Jerome Coutant 0:c0f3bbab73d2 1037 /* Reception of the data */
Jerome Coutant 0:c0f3bbab73d2 1038 if (HAL_QSPI_Receive(hqspi, &(reg[1]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1039 {
Jerome Coutant 0:c0f3bbab73d2 1040 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1041 }
Jerome Coutant 0:c0f3bbab73d2 1042
Jerome Coutant 0:c0f3bbab73d2 1043 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 1044 if (QSPI_WriteEnable(&QSPIHandle) != QSPI_OK)
Jerome Coutant 0:c0f3bbab73d2 1045 {
Jerome Coutant 0:c0f3bbab73d2 1046 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1047 }
Jerome Coutant 0:c0f3bbab73d2 1048
Jerome Coutant 0:c0f3bbab73d2 1049 /* Update the configuration register with new output driver strength */
Jerome Coutant 0:c0f3bbab73d2 1050 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1051 s_command.Instruction = WRITE_STATUS_CFG_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 1052 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 1053 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 1054 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1055 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 1056 s_command.NbData = 2;
Jerome Coutant 0:c0f3bbab73d2 1057 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 1058 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 1059 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 1060
Jerome Coutant 0:c0f3bbab73d2 1061 /* Set Output Strength of the QSPI memory 15 ohms */
Jerome Coutant 0:c0f3bbab73d2 1062 MODIFY_REG( reg[1], MX25L512_CR_ODS, (MX25L512_CR_ODS_15 << POSITION_VAL(MX25L512_CR_ODS)));
Jerome Coutant 0:c0f3bbab73d2 1063
Jerome Coutant 0:c0f3bbab73d2 1064 /* Configure the write volatile configuration register command */
Jerome Coutant 0:c0f3bbab73d2 1065 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1066 {
Jerome Coutant 0:c0f3bbab73d2 1067 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1068 }
Jerome Coutant 0:c0f3bbab73d2 1069
Jerome Coutant 0:c0f3bbab73d2 1070 /* Transmission of the data */
Jerome Coutant 0:c0f3bbab73d2 1071 if (HAL_QSPI_Transmit(hqspi, &(reg[0]), HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1072 {
Jerome Coutant 0:c0f3bbab73d2 1073 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1074 }
Jerome Coutant 0:c0f3bbab73d2 1075
Jerome Coutant 0:c0f3bbab73d2 1076 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 1077 }
Jerome Coutant 0:c0f3bbab73d2 1078
Jerome Coutant 0:c0f3bbab73d2 1079 /**
Jerome Coutant 0:c0f3bbab73d2 1080 * @brief This function send a Write Enable and wait it is effective.
Jerome Coutant 0:c0f3bbab73d2 1081 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 1082 * @retval None
Jerome Coutant 0:c0f3bbab73d2 1083 */
Jerome Coutant 0:c0f3bbab73d2 1084 static uint8_t QSPI_WriteEnable(QSPI_HandleTypeDef *hqspi)
Jerome Coutant 0:c0f3bbab73d2 1085 {
Jerome Coutant 0:c0f3bbab73d2 1086 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 1087 QSPI_AutoPollingTypeDef s_config;
Jerome Coutant 0:c0f3bbab73d2 1088
Jerome Coutant 0:c0f3bbab73d2 1089 /* Enable write operations */
Jerome Coutant 0:c0f3bbab73d2 1090 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1091 s_command.Instruction = WRITE_ENABLE_CMD;
Jerome Coutant 0:c0f3bbab73d2 1092 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 1093 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 1094 s_command.DataMode = QSPI_DATA_NONE;
Jerome Coutant 0:c0f3bbab73d2 1095 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 1096 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 1097 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 1098 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 1099
Jerome Coutant 0:c0f3bbab73d2 1100 if (HAL_QSPI_Command(hqspi, &s_command, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1101 {
Jerome Coutant 0:c0f3bbab73d2 1102 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1103 }
Jerome Coutant 0:c0f3bbab73d2 1104
Jerome Coutant 0:c0f3bbab73d2 1105 /* Configure automatic polling mode to wait for write enabling */
Jerome Coutant 0:c0f3bbab73d2 1106 s_config.Match = MX25L512_SR_WREN;
Jerome Coutant 0:c0f3bbab73d2 1107 s_config.Mask = MX25L512_SR_WREN;
Jerome Coutant 0:c0f3bbab73d2 1108 s_config.MatchMode = QSPI_MATCH_MODE_AND;
Jerome Coutant 0:c0f3bbab73d2 1109 s_config.StatusBytesSize = 1;
Jerome Coutant 0:c0f3bbab73d2 1110 s_config.Interval = 0x10;
Jerome Coutant 0:c0f3bbab73d2 1111 s_config.AutomaticStop = QSPI_AUTOMATIC_STOP_ENABLE;
Jerome Coutant 0:c0f3bbab73d2 1112
Jerome Coutant 0:c0f3bbab73d2 1113 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 1114 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1115
Jerome Coutant 0:c0f3bbab73d2 1116 if (HAL_QSPI_AutoPolling(hqspi, &s_command, &s_config, HAL_QPSI_TIMEOUT_DEFAULT_VALUE) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1117 {
Jerome Coutant 0:c0f3bbab73d2 1118 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1119 }
Jerome Coutant 0:c0f3bbab73d2 1120
Jerome Coutant 0:c0f3bbab73d2 1121 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 1122 }
Jerome Coutant 0:c0f3bbab73d2 1123
Jerome Coutant 0:c0f3bbab73d2 1124 /**
Jerome Coutant 0:c0f3bbab73d2 1125 * @brief This function read the SR of the memory and wait the EOP.
Jerome Coutant 0:c0f3bbab73d2 1126 * @param hqspi: QSPI handle
Jerome Coutant 0:c0f3bbab73d2 1127 * @param Timeout
Jerome Coutant 0:c0f3bbab73d2 1128 * @retval None
Jerome Coutant 0:c0f3bbab73d2 1129 */
Jerome Coutant 0:c0f3bbab73d2 1130 static uint8_t QSPI_AutoPollingMemReady(QSPI_HandleTypeDef *hqspi, uint32_t Timeout)
Jerome Coutant 0:c0f3bbab73d2 1131 {
Jerome Coutant 0:c0f3bbab73d2 1132 QSPI_CommandTypeDef s_command;
Jerome Coutant 0:c0f3bbab73d2 1133 QSPI_AutoPollingTypeDef s_config;
Jerome Coutant 0:c0f3bbab73d2 1134
Jerome Coutant 0:c0f3bbab73d2 1135 /* Configure automatic polling mode to wait for memory ready */
Jerome Coutant 0:c0f3bbab73d2 1136 s_command.InstructionMode = QSPI_INSTRUCTION_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1137 s_command.Instruction = READ_STATUS_REG_CMD;
Jerome Coutant 0:c0f3bbab73d2 1138 s_command.AddressMode = QSPI_ADDRESS_NONE;
Jerome Coutant 0:c0f3bbab73d2 1139 s_command.AlternateByteMode = QSPI_ALTERNATE_BYTES_NONE;
Jerome Coutant 0:c0f3bbab73d2 1140 s_command.DataMode = QSPI_DATA_4_LINES;
Jerome Coutant 0:c0f3bbab73d2 1141 s_command.DummyCycles = 0;
Jerome Coutant 0:c0f3bbab73d2 1142 s_command.DdrMode = QSPI_DDR_MODE_DISABLE;
Jerome Coutant 0:c0f3bbab73d2 1143 s_command.DdrHoldHalfCycle = QSPI_DDR_HHC_ANALOG_DELAY;
Jerome Coutant 0:c0f3bbab73d2 1144 s_command.SIOOMode = QSPI_SIOO_INST_EVERY_CMD;
Jerome Coutant 0:c0f3bbab73d2 1145
Jerome Coutant 0:c0f3bbab73d2 1146 s_config.Match = 0;
Jerome Coutant 0:c0f3bbab73d2 1147 s_config.Mask = MX25L512_SR_WIP;
Jerome Coutant 0:c0f3bbab73d2 1148 s_config.MatchMode = QSPI_MATCH_MODE_AND;
Jerome Coutant 0:c0f3bbab73d2 1149 s_config.StatusBytesSize = 1;
Jerome Coutant 0:c0f3bbab73d2 1150 s_config.Interval = 0x10;
Jerome Coutant 0:c0f3bbab73d2 1151 s_config.AutomaticStop = QSPI_AUTOMATIC_STOP_ENABLE;
Jerome Coutant 0:c0f3bbab73d2 1152
Jerome Coutant 0:c0f3bbab73d2 1153 if (HAL_QSPI_AutoPolling(hqspi, &s_command, &s_config, Timeout) != HAL_OK)
Jerome Coutant 0:c0f3bbab73d2 1154 {
Jerome Coutant 0:c0f3bbab73d2 1155 return QSPI_ERROR;
Jerome Coutant 0:c0f3bbab73d2 1156 }
Jerome Coutant 0:c0f3bbab73d2 1157
Jerome Coutant 0:c0f3bbab73d2 1158 return QSPI_OK;
Jerome Coutant 0:c0f3bbab73d2 1159 }
Jerome Coutant 0:c0f3bbab73d2 1160 /**
Jerome Coutant 0:c0f3bbab73d2 1161 * @}
Jerome Coutant 0:c0f3bbab73d2 1162 */
Jerome Coutant 0:c0f3bbab73d2 1163
Jerome Coutant 0:c0f3bbab73d2 1164 /**
Jerome Coutant 0:c0f3bbab73d2 1165 * @}
Jerome Coutant 0:c0f3bbab73d2 1166 */
Jerome Coutant 0:c0f3bbab73d2 1167
Jerome Coutant 0:c0f3bbab73d2 1168 /**
Jerome Coutant 0:c0f3bbab73d2 1169 * @}
Jerome Coutant 0:c0f3bbab73d2 1170 */
Jerome Coutant 0:c0f3bbab73d2 1171
Jerome Coutant 0:c0f3bbab73d2 1172 /**
Jerome Coutant 0:c0f3bbab73d2 1173 * @}
Jerome Coutant 0:c0f3bbab73d2 1174 */
Jerome Coutant 0:c0f3bbab73d2 1175
Jerome Coutant 0:c0f3bbab73d2 1176 /************************ (C) COPYRIGHT STMicroelectronics *****END OF FILE****/