1 /*
2  * Copyright 2017-2020 NXP
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  */
7 
8 #include "fsl_romapi.h"
9 
10 /*******************************************************************************
11  * Definitions
12  ******************************************************************************/
13 
14 /* Component ID definition, used by tools. */
15 #ifndef FSL_COMPONENT_ID
16 #define FSL_COMPONENT_ID "driver.romapi"
17 #endif
18 
19 /*******************************************************************************
20  * Prototypes
21  ******************************************************************************/
22 
23 /*!
24  * @brief Interface for the ROM FLEXSPI NOR flash driver.
25  */
26 typedef struct
27 {
28     uint32_t version;
29     status_t (*init)(uint32_t instance, flexspi_nor_config_t *config);
30     status_t (*program)(uint32_t instance, flexspi_nor_config_t *config, uint32_t dst_addr, const uint32_t *src);
31     status_t (*erase_all)(uint32_t instance, flexspi_nor_config_t *config);
32     status_t (*erase)(uint32_t instance, flexspi_nor_config_t *config, uint32_t start, uint32_t lengthInBytes);
33     status_t (*read)(
34         uint32_t instance, flexspi_nor_config_t *config, uint32_t *dst, uint32_t addr, uint32_t lengthInBytes);
35     void (*clear_cache)(uint32_t instance);
36     status_t (*xfer)(uint32_t instance, flexspi_xfer_t *xfer);
37     status_t (*update_lut)(uint32_t instance, uint32_t seqIndex, const uint32_t *lutBase, uint32_t seqNumber);
38     status_t (*get_config)(uint32_t instance, flexspi_nor_config_t *config, serial_nor_config_option_t *option);
39 } flexspi_nor_driver_interface_t;
40 
41 /*!
42  * @brief Root of the bootloader api tree.
43  *
44  * An instance of this struct resides in read-only memory in the bootloader. It
45  * provides a user application access to APIs exported by the bootloader.
46  *
47  * @note The order of existing fields must not be changed.
48  */
49 typedef struct
50 {
51     const uint32_t version;                                 /*!< Bootloader version number */
52     const char *copyright;                                  /*!< Bootloader Copyright */
53     void (*runBootloader)(void *arg);                       /*!< Function to start the bootloader executing */
54     const uint32_t *reserved0;                              /*!< Reserved */
55     const flexspi_nor_driver_interface_t *flexSpiNorDriver; /*!< FlexSPI NOR Flash API */
56     const uint32_t *reserved1[5];                           /*!< Reserved */
57 } bootloader_api_entry_t;
58 
59 /*******************************************************************************
60  * Variables
61  ******************************************************************************/
62 
63 #define g_bootloaderTree ((bootloader_api_entry_t *)*(uint32_t *)0x0020001cU)
64 
65 /*******************************************************************************
66  * Codes
67  ******************************************************************************/
68 
69 /*******************************************************************************
70  * ROM FLEXSPI NOR driver
71  ******************************************************************************/
72 #if defined(FSL_FEATURE_BOOT_ROM_HAS_ROMAPI) && FSL_FEATURE_BOOT_ROM_HAS_ROMAPI
73 
74 #if defined(FSL_ROM_HAS_RUNBOOTLOADER_API) && FSL_ROM_HAS_RUNBOOTLOADER_API
75 /*!
76  * @brief Enter Bootloader.
77  *
78  * @param arg A pointer to the storage for the bootloader param.
79  *        refer to System Boot Chapter in device reference manual for details.
80  */
ROM_RunBootloader(void * arg)81 void ROM_RunBootloader(void *arg)
82 {
83     g_bootloaderTree->runBootloader(arg);
84 }
85 #endif /* FSL_ROM_HAS_RUNBOOTLOADER_API */
86 
87 /*!
88  * @brief Initialize Serial NOR devices via FLEXSPI.
89  *
90  * @param instance storage the instance of FLEXSPI.
91  * @param config A pointer to the storage for the driver runtime state.
92  */
ROM_FLEXSPI_NorFlash_Init(uint32_t instance,flexspi_nor_config_t * config)93 status_t ROM_FLEXSPI_NorFlash_Init(uint32_t instance, flexspi_nor_config_t *config)
94 {
95     return g_bootloaderTree->flexSpiNorDriver->init(instance, config);
96 }
97 
98 /*!
99  * @brief Program data to Serial NOR via FLEXSPI.
100  *
101  * @param instance storage the instance of FLEXSPI.
102  * @param config  A pointer to the storage for the driver runtime state.
103  * @param dstAddr A pointer to the desired flash memory to be programmed.
104  * @param src A pointer to the source buffer of data that is to be programmed
105  *            into the NOR flash.
106  */
ROM_FLEXSPI_NorFlash_ProgramPage(uint32_t instance,flexspi_nor_config_t * config,uint32_t dstAddr,const uint32_t * src)107 status_t ROM_FLEXSPI_NorFlash_ProgramPage(uint32_t instance,
108                                           flexspi_nor_config_t *config,
109                                           uint32_t dstAddr,
110                                           const uint32_t *src)
111 {
112     return g_bootloaderTree->flexSpiNorDriver->program(instance, config, dstAddr, src);
113 }
114 
115 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ
116 /*!
117  * @brief Read data from Serial NOR
118  *
119  * @param instance storage the instance of FLEXSPI.
120  * @param config  A pointer to the storage for the driver runtime state.
121  * @param dst     A pointer to the dest buffer of data that is to be read from the NOR flash.
122  * @param lengthInBytes The length, given in bytes to be read.
123  */
ROM_FLEXSPI_NorFlash_Read(uint32_t instance,flexspi_nor_config_t * config,uint32_t * dst,uint32_t start,uint32_t lengthInBytes)124 status_t ROM_FLEXSPI_NorFlash_Read(
125     uint32_t instance, flexspi_nor_config_t *config, uint32_t *dst, uint32_t start, uint32_t lengthInBytes)
126 {
127     return g_bootloaderTree->flexSpiNorDriver->read(instance, config, dst, start, lengthInBytes);
128 }
129 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ */
130 
131 /*!
132  * @brief Erase Flash Region specified by address and length.
133  *
134  * @param instance storage the index of FLEXSPI.
135  * @param config A pointer to the storage for the driver runtime state.
136  * @param start The start address of the desired NOR flash memory to be erased.
137  * @param length The length, given in bytes to be erased.
138  */
ROM_FLEXSPI_NorFlash_Erase(uint32_t instance,flexspi_nor_config_t * config,uint32_t start,uint32_t length)139 status_t ROM_FLEXSPI_NorFlash_Erase(uint32_t instance, flexspi_nor_config_t *config, uint32_t start, uint32_t length)
140 {
141     return g_bootloaderTree->flexSpiNorDriver->erase(instance, config, start, length);
142 }
143 
144 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL
145 /*! @brief Erase all the Serial NOR devices connected on FLEXSPI. */
ROM_FLEXSPI_NorFlash_EraseAll(uint32_t instance,flexspi_nor_config_t * config)146 status_t ROM_FLEXSPI_NorFlash_EraseAll(uint32_t instance, flexspi_nor_config_t *config)
147 {
148     return g_bootloaderTree->flexSpiNorDriver->erase_all(instance, config);
149 }
150 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL */
151 
152 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER
153 /*! @brief FLEXSPI command */
ROM_FLEXSPI_NorFlash_CommandXfer(uint32_t instance,flexspi_xfer_t * xfer)154 status_t ROM_FLEXSPI_NorFlash_CommandXfer(uint32_t instance, flexspi_xfer_t *xfer)
155 {
156     return g_bootloaderTree->flexSpiNorDriver->xfer(instance, xfer);
157 }
158 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER */
159 
160 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT
161 /*! @brief Configure FLEXSPI Lookup table. */
ROM_FLEXSPI_NorFlash_UpdateLut(uint32_t instance,uint32_t seqIndex,const uint32_t * lutBase,uint32_t seqNumber)162 status_t ROM_FLEXSPI_NorFlash_UpdateLut(uint32_t instance,
163                                         uint32_t seqIndex,
164                                         const uint32_t *lutBase,
165                                         uint32_t seqNumber)
166 {
167     return g_bootloaderTree->flexSpiNorDriver->update_lut(instance, seqIndex, lutBase, seqNumber);
168 }
169 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT */
170 
171 /*! @brief Software reset for the FLEXSPI logic. */
ROM_FLEXSPI_NorFlash_ClearCache(uint32_t instance)172 void ROM_FLEXSPI_NorFlash_ClearCache(uint32_t instance)
173 {
174     g_bootloaderTree->flexSpiNorDriver->clear_cache(instance);
175 }
176 
177 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG
178 /*! @brief Get FLEXSPI NOR Configuration Block based on specified option. */
ROM_FLEXSPI_NorFlash_GetConfig(uint32_t instance,flexspi_nor_config_t * config,serial_nor_config_option_t * option)179 status_t ROM_FLEXSPI_NorFlash_GetConfig(uint32_t instance,
180                                         flexspi_nor_config_t *config,
181                                         serial_nor_config_option_t *option)
182 {
183     status_t status = g_bootloaderTree->flexSpiNorDriver->get_config(instance, config, option);
184     if (status == kStatus_Success)
185     {
186         if (config->memConfig.readSampleClkSrc == (uint8_t)kFLEXSPIReadSampleClk_LoopbackInternally)
187         {
188             config->memConfig.readSampleClkSrc = (uint8_t)kFLEXSPIReadSampleClk_LoopbackFromDqsPad;
189         }
190     }
191 
192     return status;
193 }
194 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG */
195 
196 #endif /* FSL_FEATURE_BOOT_ROM_HAS_ROMAPI */
197