1 /*
2  * Copyright 2017-2021 NXP
3  * All rights reserved.
4  *
5  * SPDX-License-Identifier: BSD-3-Clause
6  */
7 
8 #ifndef _FSL_ROMAPI_H_
9 #define _FSL_ROMAPI_H_
10 
11 #include "fsl_common.h"
12 
13 /*!
14  * @addtogroup romapi
15  * @{
16  */
17 
18 /*! @brief ROM API version 1.1.1. */
19 #define FSL_ROM_ROMAPI_VERSION (MAKE_VERSION(1U, 1U, 1U))
20 /*! @brief ROM FLEXSPI NOR driver version 1.7.0. */
21 #define FSL_ROM_FLEXSPINOR_DRIVER_VERSION (MAKE_VERSION(1U, 7U, 0U))
22 
23 /*!
24  * @name Common ROMAPI features info defines
25  * @{
26  */
27 /*! @brief ROM has FLEXSPI NOR API. */
28 #define FSL_ROM_HAS_FLEXSPINOR_API (1)
29 /*! @brief ROM has run bootloader API. */
30 #define FSL_ROM_HAS_RUNBOOTLOADER_API (1)
31 /*! @brief ROM has FLEXSPI NOR get config API. */
32 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG (1)
33 /*! @brief ROM has flash init API. */
34 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_FLASH_INIT (1)
35 /*! @brief ROM has erase API. */
36 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE (1)
37 /*! @brief ROM has erase sector API. */
38 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_SECTOR (1)
39 /*! @brief ROM has erase block API. */
40 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_BLOCK (1)
41 /*! @brief ROM has erase all API. */
42 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL (1)
43 /*! @brief ROM has read API. */
44 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ (1)
45 /*! @brief ROM has update lut API. */
46 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT (1)
47 /*! @brief ROM has FLEXSPI command API. */
48 #define FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER (1)
49 
50 /*@}*/
51 
52 #define kROM_StatusGroup_FLEXSPINOR 201U /*!< ROM FLEXSPI NOR status group number.*/
53 
54 #define FSL_ROM_FLEXSPI_LUT_SEQ(cmd0, pad0, op0, cmd1, pad1, op1)                                                      \
55     (FLEXSPI_LUT_OPERAND0(op0) | FLEXSPI_LUT_NUM_PADS0(pad0) | FLEXSPI_LUT_OPCODE0(cmd0) | FLEXSPI_LUT_OPERAND1(op1) | \
56      FLEXSPI_LUT_NUM_PADS1(pad1) | FLEXSPI_LUT_OPCODE1(cmd1))
57 
58 /*! @brief Generate bit mask */
59 #define FSL_ROM_FLEXSPI_BITMASK(bit_offset) (1U << (bit_offset))
60 
61 /*! @brief FLEXSPI memory config block related definitions */
62 #define FLEXSPI_CFG_BLK_TAG     (0x42464346UL) /*!< ascii "FCFB" Big Endian */
63 #define FLEXSPI_CFG_BLK_VERSION (0x56010400UL) /*!< V1.4.0 */
64 
65 #define CMD_SDR        0x01U
66 #define CMD_DDR        0x21U
67 #define RADDR_SDR      0x02U
68 #define RADDR_DDR      0x22U
69 #define CADDR_SDR      0x03U
70 #define CADDR_DDR      0x23U
71 #define MODE1_SDR      0x04U
72 #define MODE1_DDR      0x24U
73 #define MODE2_SDR      0x05U
74 #define MODE2_DDR      0x25U
75 #define MODE4_SDR      0x06U
76 #define MODE4_DDR      0x26U
77 #define MODE8_SDR      0x07U
78 #define MODE8_DDR      0x27U
79 #define WRITE_SDR      0x08U
80 #define WRITE_DDR      0x28U
81 #define READ_SDR       0x09U
82 #define READ_DDR       0x29U
83 #define LEARN_SDR      0x0AU
84 #define LEARN_DDR      0x2AU
85 #define DATSZ_SDR      0x0BU
86 #define DATSZ_DDR      0x2BU
87 #define DUMMY_SDR      0x0CU
88 #define DUMMY_DDR      0x2CU
89 #define DUMMY_RWDS_SDR 0x0DU
90 #define DUMMY_RWDS_DDR 0x2DU
91 #define JMP_ON_CS      0x1FU
92 #define STOP           0U
93 
94 #define FLEXSPI_1PAD 0U
95 #define FLEXSPI_2PAD 1U
96 #define FLEXSPI_4PAD 2U
97 #define FLEXSPI_8PAD 3U
98 
99 /*!
100  * NOR LUT sequence index used for default LUT assignment.
101  *
102  * @note It will take effect if the lut sequences are not customized.
103  */
104 #define NOR_CMD_LUT_SEQ_IDX_READ       0U /*!< READ LUT sequence id in lookupTable stored in config block */
105 #define NOR_CMD_LUT_SEQ_IDX_READSTATUS 1U /*!< Read Status LUT sequence id in lookupTable stored in config block */
106 #define NOR_CMD_LUT_SEQ_IDX_READSTATUS_XPI \
107     2U /*!< Read status DPI/QPI/OPI sequence id in lookupTable stored in config block */
108 #define NOR_CMD_LUT_SEQ_IDX_WRITEENABLE 3U /*!< Write Enable sequence id in lookupTable stored in config block */
109 #define NOR_CMD_LUT_SEQ_IDX_WRITEENABLE_XPI \
110     4U /*!< Write Enable DPI/QPI/OPI sequence id in lookupTable stored in config block */
111 #define NOR_CMD_LUT_SEQ_IDX_ERASESECTOR 5U /*!< Erase Sector sequence id in lookupTable stored in config block */
112 #define NOR_CMD_LUT_SEQ_IDX_READID      7U
113 #define NOR_CMD_LUT_SEQ_IDX_ERASEBLOCK  8U  /*!< Erase Block sequence id in lookupTable stored in config block */
114 #define NOR_CMD_LUT_SEQ_IDX_PAGEPROGRAM 9U  /*!< Program sequence id in lookupTable stored in config block */
115 #define NOR_CMD_LUT_SEQ_IDX_CHIPERASE   11U /*!< Chip Erase sequence in lookupTable id stored in config block */
116 #define NOR_CMD_LUT_SEQ_IDX_READ_SFDP   13U /*!< Read SFDP sequence in lookupTable id stored in config block */
117 #define NOR_CMD_LUT_SEQ_IDX_RESTORE_NOCMD \
118     14U /*!< Restore 0-4-4/0-8-8 mode sequence id in lookupTable stored in config block */
119 #define NOR_CMD_LUT_SEQ_IDX_EXIT_NOCMD \
120     15U /*!< Exit 0-4-4/0-8-8 mode sequence id in lookupTable stored in config block */
121 
122 /*!
123  * @name Configuration Option
124  * @{
125  */
126 /*! @brief Serial NOR Configuration Option. */
127 typedef struct _serial_nor_config_option
128 {
129     union
130     {
131         struct
132         {
133             uint32_t max_freq : 4;          /*!< Maximum supported Frequency */
134             uint32_t misc_mode : 4;         /*!< miscellaneous mode */
135             uint32_t quad_mode_setting : 4; /*!< Quad mode setting */
136             uint32_t cmd_pads : 4;          /*!< Command pads */
137             uint32_t query_pads : 4;        /*!< SFDP read pads */
138             uint32_t device_type : 4;       /*!< Device type */
139             uint32_t option_size : 4;       /*!< Option size, in terms of uint32_t, size = (option_size + 1) * 4 */
140             uint32_t tag : 4;               /*!< Tag, must be 0x0C */
141         } B;
142         uint32_t U;
143     } option0;
144 
145     union
146     {
147         struct
148         {
149             uint32_t dummy_cycles : 8;     /*!< Dummy cycles before read */
150             uint32_t status_override : 8;  /*!< Override status register value during device mode configuration */
151             uint32_t pinmux_group : 4;     /*!< The pinmux group selection */
152             uint32_t dqs_pinmux_group : 4; /*!< The DQS Pinmux Group Selection */
153             uint32_t drive_strength : 4;   /*!< The Drive Strength of FlexSPI Pads */
154             uint32_t flash_connection : 4; /*!< Flash connection option: 0 - Single Flash connected to port A, 1 -
155                                                 Parallel mode, 2 - Single Flash connected to Port B */
156         } B;
157         uint32_t U;
158     } option1;
159 
160 } serial_nor_config_option_t;
161 
162 /*@}*/
163 
164 /*!
165  * @name Support for init FLEXSPI NOR configuration
166  * @{
167  */
168 /*! @brief Flash Pad Definitions */
169 enum
170 {
171     kSerialFlash_1Pad  = 1U, /*!< 1-wire communication */
172     kSerialFlash_2Pads = 2U, /*!< 2-wire communication */
173     kSerialFlash_4Pads = 4U, /*!< 4-wire communication */
174     kSerialFlash_8Pads = 8U, /*!< 8-wire communication */
175 };
176 
177 /*! @brief FLEXSPI clock configuration type */
178 enum
179 {
180     kFLEXSPIClk_SDR, /*!< Clock configure for SDR mode */
181     kFLEXSPIClk_DDR, /*!< Clock configure for DDR mode */
182 };
183 
184 /*! @brief FLEXSPI Read Sample Clock Source definition */
185 enum _flexspi_read_sample_clk
186 {
187     kFLEXSPIReadSampleClk_LoopbackInternally = 0U, /*!< FLEXSPI Read Sample Clock Source from the Internal loopback */
188     kFLEXSPIReadSampleClk_LoopbackFromDqsPad = 1U, /*!< FLEXSPI Read Sample Clock Source from the Dqs Pad loopback */
189     kFLEXSPIReadSampleClk_LoopbackFromSckPad = 2U, /*!< FLEXSPI Read Sample Clock Source from the Sck Pad loopback */
190     kFLEXSPIReadSampleClk_ExternalInputFromDqsPad = 3U, /*!< FLEXSPI Read Sample Clock Source from the External Input
191                                                              by the Dqs Pad */
192 };
193 
194 /*! @brief Flash Type Definition */
195 enum
196 {
197     kFLEXSPIDeviceType_SerialNOR = 1U, /*!< Flash device is Serial NOR */
198 };
199 
200 /*! @brief Flash Configuration Command Type */
201 enum
202 {
203     kDeviceConfigCmdType_Generic,    /*!< Generic command, for example: configure dummy cycles, drive strength, etc. */
204     kDeviceConfigCmdType_QuadEnable, /*!< Quad Enable command */
205     kDeviceConfigCmdType_Spi2Xpi,    /*!< Switch from SPI to DPI/QPI/OPI mode */
206     kDeviceConfigCmdType_Xpi2Spi,    /*!< Switch from DPI/QPI/OPI to SPI mode */
207     kDeviceConfigCmdType_Spi2NoCmd,  /*!< Switch to 0-4-4/0-8-8 mode */
208     kDeviceConfigCmdType_Reset,      /*!< Reset device command */
209 };
210 
211 /*! @brief Definitions for FLEXSPI Serial Clock Frequency */
212 enum _flexspi_serial_clk_freq
213 {
214     kFLEXSPISerialClk_NoChange = 0U, /*!< FlexSPI serial clock no changed */
215     kFLEXSPISerialClk_30MHz    = 1U, /*!< FlexSPI serial clock 30MHz */
216     kFLEXSPISerialClk_50MHz    = 2U, /*!< FlexSPI serial clock 50MHz */
217     kFLEXSPISerialClk_60MHz    = 3U, /*!< FlexSPI serial clock 60MHz */
218     kFLEXSPISerialClk_75MHz    = 4U, /*!< FlexSPI serial clock 75MHz */
219     kFLEXSPISerialClk_80MHz    = 5U, /*!< FlexSPI serial clock 80MHz */
220     kFLEXSPISerialClk_100MHz   = 6U, /*!< FlexSPI serial clock 100MHz */
221     kFLEXSPISerialClk_133MHz   = 7U, /*!< FlexSPI serial clock 133MHz */
222     kFLEXSPISerialClk_166MHz   = 8U, /*!< FlexSPI serial clock 166MHz */
223 };
224 
225 /*! @brief Misc feature bit definitions */
226 enum
227 {
228     kFLEXSPIMiscOffset_DiffClkEnable            = 0U, /*!< Bit for Differential clock enable */
229     kFLEXSPIMiscOffset_Ck2Enable                = 1U, /*!< Bit for CK2 enable */
230     kFLEXSPIMiscOffset_ParallelEnable           = 2U, /*!< Bit for Parallel mode enable */
231     kFLEXSPIMiscOffset_WordAddressableEnable    = 3U, /*!< Bit for Word Addressable enable */
232     kFLEXSPIMiscOffset_SafeConfigFreqEnable     = 4U, /*!< Bit for Safe Configuration Frequency enable */
233     kFLEXSPIMiscOffset_PadSettingOverrideEnable = 5U, /*!< Bit for Pad setting override enable */
234     kFLEXSPIMiscOffset_DdrModeEnable            = 6U, /*!< Bit for DDR clock configuration indication. */
235     kFLEXSPIMiscOffset_UseValidTimeForAllFreq   = 7U, /*!< Bit for DLLCR settings under all modes */
236 };
237 
238 /*@}*/
239 
240 /*! @brief Manufacturer ID */
241 enum
242 {
243     kSerialFlash_ISSI_ManufacturerID    = 0x9DU, /*!< Manufacturer ID of the ISSI serial flash */
244     kSerialFlash_Adesto_ManufacturerID  = 0x1F,  /*!< Manufacturer ID of the Adesto Technologies serial flash*/
245     kSerialFlash_Winbond_ManufacturerID = 0xEFU, /*!< Manufacturer ID of the Winbond serial flash */
246     kSerialFlash_Cypress_ManufacturerID = 0x01U, /*!< Manufacturer ID for Cypress */
247 };
248 
249 /*! @brief ROM FLEXSPI NOR flash status */
250 enum _flexspi_nor_status
251 {
252     kStatus_ROM_FLEXSPI_SequenceExecutionTimeout =
253         MAKE_STATUS(kStatusGroup_FLEXSPI, 0), /*!< Status for Sequence Execution timeout */
254     kStatus_ROM_FLEXSPI_InvalidSequence = MAKE_STATUS(kStatusGroup_FLEXSPI, 1), /*!< Status for Invalid Sequence */
255     kStatus_ROM_FLEXSPI_DeviceTimeout   = MAKE_STATUS(kStatusGroup_FLEXSPI, 2), /*!< Status for Device timeout */
256     kStatus_ROM_FLEXSPINOR_SFDP_NotFound =
257         MAKE_STATUS(kROM_StatusGroup_FLEXSPINOR, 7), /*!< Status for SFDP read failure */
258     kStatus_ROM_FLEXSPINOR_Flash_NotFound =
259         MAKE_STATUS(kROM_StatusGroup_FLEXSPINOR, 9), /*!< Status for Flash detection failure */
260     kStatus_FLEXSPINOR_DTRRead_DummyProbeFailed =
261         MAKE_STATUS(kROM_StatusGroup_FLEXSPINOR, 10), /*!< Status for DDR Read dummy probe failure */
262 };
263 
264 /*!
265  * @name FLEXSPI NOR Configuration
266  * @{
267  */
268 
269 /*! @brief FLEXSPI LUT Sequence structure */
270 typedef struct _flexspi_lut_seq
271 {
272     uint8_t seqNum; /*!< Sequence Number, valid number: 1-16 */
273     uint8_t seqId;  /*!< Sequence Index, valid number: 0-15 */
274     uint16_t reserved;
275 } flexspi_lut_seq_t;
276 
277 /*! @brief FLEXSPI DLL time */
278 typedef struct
279 {
280     uint8_t time_100ps;  /*!< Data valid time, in terms of 100ps */
281     uint8_t delay_cells; /*!< Data valid time, in terms of delay cells */
282 } flexspi_dll_time_t;
283 
284 /*! @brief FLEXSPI Memory Configuration Block */
285 typedef struct _flexspi_mem_config
286 {
287     uint32_t tag;       /*!< [0x000-0x003] Tag, fixed value 0x42464346UL */
288     uint32_t version;   /*!< [0x004-0x007] Version,[31:24] -'V', [23:16] - Major, [15:8] - Minor, [7:0] - bugfix */
289     uint32_t reserved0; /*!< [0x008-0x00b] Reserved for future use */
290     uint8_t readSampleClkSrc;    /*!< [0x00c-0x00c] Read Sample Clock Source, valid value: 0/1/3 */
291     uint8_t csHoldTime;          /*!< [0x00d-0x00d] Data hold time, default value: 3 */
292     uint8_t csSetupTime;         /*!< [0x00e-0x00e] Date setup time, default value: 3 */
293     uint8_t columnAddressWidth;  /*!< [0x00f-0x00f] Column Address with, for HyperBus protocol, it is fixed to 3, For
294                                                     Serial NAND, need to refer to datasheet */
295     uint8_t deviceModeCfgEnable; /*!< [0x010-0x010] Device Mode Configure enable flag, 1 - Enable, 0 - Disable */
296     uint8_t deviceModeType; /*!< [0x011-0x011] Specify the configuration command type:Quad Enable, DPI/QPI/OPI switch,
297                                                Generic configuration, etc. */
298     uint16_t waitTimeCfgCommands;    /*!< [0x012-0x013] Wait time for all configuration commands, unit: 100us, Used for
299                                                         DPI/QPI/OPI switch or reset command */
300     flexspi_lut_seq_t deviceModeSeq; /*!< [0x014-0x017] Device mode sequence info, [7:0] - LUT sequence id, [15:8] - LUt
301                                                         sequence number, [31:16] Reserved */
302     uint32_t deviceModeArg;          /*!< [0x018-0x01b] Argument/Parameter for device configuration */
303     uint8_t configCmdEnable;         /*!< [0x01c-0x01c] Configure command Enable Flag, 1 - Enable, 0 - Disable */
304     uint8_t configModeType[3];       /*!< [0x01d-0x01f] Configure Mode Type, similar as deviceModeTpe */
305     flexspi_lut_seq_t
306         configCmdSeqs[3]; /*!< [0x020-0x02b] Sequence info for Device Configuration command, similar as deviceModeSeq */
307     uint32_t reserved1;   /*!< [0x02c-0x02f] Reserved for future use */
308     uint32_t configCmdArgs[3];     /*!< [0x030-0x03b] Arguments/Parameters for device Configuration commands */
309     uint32_t reserved2;            /*!< [0x03c-0x03f] Reserved for future use */
310     uint32_t controllerMiscOption; /*!< [0x040-0x043] Controller Misc Options, see Misc feature bit definitions for more
311                                       details */
312     uint8_t deviceType;            /*!< [0x044-0x044] Device Type:  See Flash Type Definition for more details */
313     uint8_t sflashPadType; /*!< [0x045-0x045] Serial Flash Pad Type: 1 - Single, 2 - Dual, 4 - Quad, 8 - Octal */
314     uint8_t serialClkFreq; /*!< [0x046-0x046] Serial Flash Frequency, device specific definitions. See System Boot
315                                               Chapter for more details */
316     uint8_t
317         lutCustomSeqEnable; /*!< [0x047-0x047] LUT customization Enable, it is required if the program/erase cannot
318                                               be done using 1 LUT sequence, currently, only applicable to HyperFLASH */
319     uint32_t reserved3[2];  /*!< [0x048-0x04f] Reserved for future use */
320     uint32_t sflashA1Size;  /*!< [0x050-0x053] Size of Flash connected to A1 */
321     uint32_t sflashA2Size;  /*!< [0x054-0x057] Size of Flash connected to A2 */
322     uint32_t sflashB1Size;  /*!< [0x058-0x05b] Size of Flash connected to B1 */
323     uint32_t sflashB2Size;  /*!< [0x05c-0x05f] Size of Flash connected to B2 */
324     uint32_t csPadSettingOverride;       /*!< [0x060-0x063] CS pad setting override value */
325     uint32_t sclkPadSettingOverride;     /*!< [0x064-0x067] SCK pad setting override value */
326     uint32_t dataPadSettingOverride;     /*!< [0x068-0x06b] data pad setting override value */
327     uint32_t dqsPadSettingOverride;      /*!< [0x06c-0x06f] DQS pad setting override value */
328     uint32_t timeoutInMs;                /*!< [0x070-0x073] Timeout threshold for read status command */
329     uint32_t commandInterval;            /*!< [0x074-0x077] CS deselect interval between two commands */
330     flexspi_dll_time_t dataValidTime[2]; /*!< [0x078-0x07b] CLK edge to data valid time for PORT A and PORT B */
331     uint16_t busyOffset;                 /*!< [0x07c-0x07d] Busy offset, valid value: 0-31 */
332     uint16_t busyBitPolarity; /*!< [0x07e-0x07f] Busy flag polarity, 0 - busy flag is 1 when flash device is busy, 1 -
333                                                  busy flag is 0 when flash device is busy */
334     uint32_t lookupTable[64]; /*!< [0x080-0x17f] Lookup table holds Flash command sequences */
335     flexspi_lut_seq_t lutCustomSeq[12]; /*!< [0x180-0x1af] Customizable LUT Sequences */
336     uint32_t reserved4[4];              /*!< [0x1b0-0x1bf] Reserved for future use */
337 } flexspi_mem_config_t;
338 
339 /*! @brief  Serial NOR configuration block */
340 typedef struct _flexspi_nor_config
341 {
342     flexspi_mem_config_t memConfig; /*!< Common memory configuration info via FLEXSPI */
343     uint32_t pageSize;              /*!< Page size of Serial NOR */
344     uint32_t sectorSize;            /*!< Sector size of Serial NOR */
345     uint8_t ipcmdSerialClkFreq;     /*!< Clock frequency for IP command */
346     uint8_t isUniformBlockSize;     /*!< Sector/Block size is the same */
347     uint8_t isDataOrderSwapped;     /*!< Data order (D0, D1, D2, D3) is swapped (D1,D0, D3, D2) */
348     uint8_t reserved0[1];           /*!< Reserved for future use */
349     uint8_t serialNorType;          /*!< Serial NOR Flash type: 0/1/2/3 */
350     uint8_t needExitNoCmdMode;      /*!< Need to exit NoCmd mode before other IP command */
351     uint8_t halfClkForNonReadCmd;   /*!< Half the Serial Clock for non-read command: true/false */
352     uint8_t needRestoreNoCmdMode;   /*!< Need to Restore NoCmd mode after IP command execution */
353     uint32_t blockSize;             /*!< Block size */
354     uint32_t reserve2[11];          /*!< Reserved for future use */
355 } flexspi_nor_config_t;
356 
357 /*@}*/
358 
359 /*! @brief FLEXSPI Operation Context */
360 typedef enum _flexspi_operation
361 {
362     kFLEXSPIOperation_Command,  /*!< FLEXSPI operation: Only command, both TX and RX buffer are ignored. */
363     kFLEXSPIOperation_Config,   /*!< FLEXSPI operation: Configure device mode, the TX FIFO size is fixed in LUT. */
364     kFLEXSPIOperation_Write,    /*!< FLEXSPI operation: Write, only TX buffer is effective */
365     kFLEXSPIOperation_Read,     /*!< FLEXSPI operation: Read, only Rx Buffer is effective. */
366 } flexspi_operation_t;
367 
368 #define kFLEXSPIOperation_End   kFLEXSPIOperation_Read
369 
370 /*! @brief FLEXSPI Transfer Context */
371 typedef struct _flexspi_xfer
372 {
373     flexspi_operation_t operation; /*!< FLEXSPI operation */
374     uint32_t baseAddress;          /*!< FLEXSPI operation base address */
375     uint32_t seqId;                /*!< Sequence Id */
376     uint32_t seqNum;               /*!< Sequence Number */
377     bool isParallelModeEnable;     /*!< Is a parallel transfer */
378     uint32_t *txBuffer;            /*!< Tx buffer */
379     uint32_t txSize;               /*!< Tx size in bytes */
380     uint32_t *rxBuffer;            /*!< Rx buffer */
381     uint32_t rxSize;               /*!< Rx size in bytes */
382 } flexspi_xfer_t;
383 
384 /*! @brief convert the type for MISRA */
385 #define MISRA_CAST(to_type, to_var, from_type, from_var)      \
386     do                                                        \
387     {                                                         \
388         union                                                 \
389         {                                                     \
390             to_type to_var_tmp;                               \
391             from_type from_var_tmp;                           \
392         } type_converter_var = {.from_var_tmp = (from_var)};  \
393         (to_var)             = type_converter_var.to_var_tmp; \
394     } while (false)
395 
396 #ifdef __cplusplus
397 extern "C" {
398 #endif
399 
400 #if defined(FSL_FEATURE_BOOT_ROM_HAS_ROMAPI) && FSL_FEATURE_BOOT_ROM_HAS_ROMAPI
401 
402 /*!
403  * @brief ROM API init
404  *
405  * Get the bootloader api entry address.
406  */
407 void ROM_API_Init(void);
408 
409 /*!
410  * @name Enter Bootloader
411  * @{
412  */
413 
414 #if defined(FSL_ROM_HAS_RUNBOOTLOADER_API) && FSL_ROM_HAS_RUNBOOTLOADER_API
415 /*!
416  * @brief Enter Bootloader.
417  *
418  * @param arg A pointer to the storage for the bootloader param.
419  *        refer to System Boot Chapter in device reference manual for details.
420  */
421 void ROM_RunBootloader(void *arg);
422 #endif /* FSL_ROM_HAS_RUNBOOTLOADER_API */
423 
424 /*@}*/
425 
426 /*!
427  * @name GetConfig
428  * @{
429  */
430 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG
431 /*!
432  * @brief Get FLEXSPI NOR Configuration Block based on specified option.
433  *
434  * @param instance storage the instance of FLEXSPI.
435  * @param config A pointer to the storage for the driver runtime state.
436  * @param option A pointer to the storage Serial NOR Configuration Option Context.
437  *
438  * @retval kStatus_Success Api was executed successfully.
439  * @retval kStatus_InvalidArgument A invalid argument is provided.
440  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
441  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
442  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
443  */
444 status_t ROM_FLEXSPI_NorFlash_GetConfig(uint32_t instance,
445                                         flexspi_nor_config_t *config,
446                                         serial_nor_config_option_t *option);
447 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_GET_CONFIG */
448 
449 /*!
450  * @name Initialization
451  * @{
452  */
453 
454 /*!
455  * @brief Initialize Serial NOR devices via FLEXSPI
456  *
457  * This function checks and initializes the FLEXSPI module for the other FLEXSPI APIs.
458  *
459  * @param instance storage the instance of FLEXSPI.
460  * @param config A pointer to the storage for the driver runtime state.
461  *
462  * @retval kStatus_Success Api was executed successfully.
463  * @retval kStatus_InvalidArgument A invalid argument is provided.
464  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
465  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
466  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
467  */
468 status_t ROM_FLEXSPI_NorFlash_Init(uint32_t instance, flexspi_nor_config_t *config);
469 
470 /*@}*/
471 
472 /*!
473  * @name Programming
474  * @{
475  */
476 
477 /*!
478  * @brief Program data to Serial NOR via FLEXSPI.
479  *
480  * This function programs the NOR flash memory with the dest address for a given
481  * flash area as determined by the dst address and the length.
482  *
483  * @param instance storage the instance of FLEXSPI.
484  * @param config  A pointer to the storage for the driver runtime state.
485  * @param dst_addr A pointer to the desired flash memory to be programmed.
486  *                @note It is recommended that use page aligned access;
487  *                If the dst_addr is not aligned to page, the driver automatically
488  *                aligns address down with the page address.
489  * @param src A pointer to the source buffer of data that is to be programmed
490  *            into the NOR flash.
491  *
492  * @retval kStatus_Success Api was executed successfully.
493  * @retval kStatus_InvalidArgument A invalid argument is provided.
494  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
495  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
496  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
497  */
498 status_t ROM_FLEXSPI_NorFlash_ProgramPage(uint32_t instance,
499                                           flexspi_nor_config_t *config,
500                                           uint32_t dst_addr,
501                                           const uint32_t *src);
502 
503 /*@}*/
504 
505 /*!
506  * @name Reading
507  * @{
508  */
509 
510 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ
511 /*!
512  * @brief Read data from Serial NOR via FLEXSPI.
513  *
514  * This function read the NOR flash memory with the start address for a given
515  * flash area as determined by the dst address and the length.
516  *
517  * @param instance storage the instance of FLEXSPI.
518  * @param config  A pointer to the storage for the driver runtime state.
519  * @param dst     A pointer to the dest buffer of data that is to be read from the NOR flash.
520  *                @note It is recommended that use page aligned access;
521  *                If the dstAddr is not aligned to page, the driver automatically
522  *                aligns address down with the page address.
523  * @param start   The start address of the desired NOR flash memory to be read.
524  * @param lengthInBytes The length, given in bytes to be read.
525  *
526  * @retval kStatus_Success Api was executed successfully.
527  * @retval kStatus_InvalidArgument A invalid argument is provided.
528  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
529  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
530  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
531  */
532 status_t ROM_FLEXSPI_NorFlash_Read(
533     uint32_t instance, flexspi_nor_config_t *config, uint32_t *dst, uint32_t start, uint32_t lengthInBytes);
534 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_READ */
535 
536 /*@}*/
537 
538 /*!
539  * @name Erasing
540  * @{
541  */
542 
543 /*!
544  * @brief Erase Flash Region specified by address and length
545  *
546  * This function erases the appropriate number of flash sectors based on the
547  * desired start address and length.
548  *
549  * @param instance storage the index of FLEXSPI.
550  * @param config A pointer to the storage for the driver runtime state.
551  * @param start The start address of the desired NOR flash memory to be erased.
552  *              @note It is recommended that use sector-aligned access nor device;
553  *              If dstAddr is not aligned with the sector,the driver automatically
554  *              aligns address down with the sector address.
555  * @param length The length, given in bytes to be erased.
556  *              @note It is recommended that use sector-aligned access nor device;
557  *              If length is not aligned with the sector,the driver automatically
558  *              aligns up with the sector.
559  * @retval kStatus_Success Api was executed successfully.
560  * @retval kStatus_InvalidArgument A invalid argument is provided.
561  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
562  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
563  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
564  */
565 status_t ROM_FLEXSPI_NorFlash_Erase(uint32_t instance, flexspi_nor_config_t *config, uint32_t start, uint32_t length);
566 
567 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_SECTOR) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_SECTOR
568 /*!
569  * @brief Erase one sector specified by address
570  *
571  * This function erases one of NOR flash sectors based on the desired address.
572  *
573  * @param instance storage the index of FLEXSPI.
574  * @param config A pointer to the storage for the driver runtime state.
575  * @param start The start address of the desired NOR flash memory to be erased.
576  *                @note It is recommended that use sector-aligned access nor device;
577  *                If dstAddr is not aligned with the sector, the driver automatically
578  *                aligns address down with the sector address.
579  *
580  * @retval kStatus_Success Api was executed successfully.
581  * @retval kStatus_InvalidArgument A invalid argument is provided.
582  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
583  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
584  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
585  */
586 status_t ROM_FLEXSPI_NorFlash_EraseSector(uint32_t instance, flexspi_nor_config_t *config, uint32_t start);
587 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_SECTOR */
588 
589 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_BLOCK) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_BLOCK
590 /*!
591  * @brief Erase one block specified by address
592  *
593  * This function erases one block of NOR flash based on the desired address.
594  *
595  * @param instance storage the index of FLEXSPI.
596  * @param config A pointer to the storage for the driver runtime state.
597  * @param start The start address of the desired NOR flash memory to be erased.
598  *              @note It is recommended that use block-aligned access nor device;
599  *              If dstAddr is not aligned with the block, the driver automatically
600  *              aligns address down with the block address.
601  *
602  * @retval kStatus_Success Api was executed successfully.
603  * @retval kStatus_InvalidArgument A invalid argument is provided.
604  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
605  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
606  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
607  */
608 status_t ROM_FLEXSPI_NorFlash_EraseBlock(uint32_t instance, flexspi_nor_config_t *config, uint32_t start);
609 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_BLOCK */
610 
611 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL
612 /*!
613  * @brief Erase all the Serial NOR devices connected on FLEXSPI.
614  *
615  * @param instance storage the instance of FLEXSPI.
616  * @param config A pointer to the storage for the driver runtime state.
617  *
618  * @retval kStatus_Success Api was executed successfully.
619  * @retval kStatus_InvalidArgument A invalid argument is provided.
620  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
621  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
622  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout the device timeout
623  */
624 status_t ROM_FLEXSPI_NorFlash_EraseAll(uint32_t instance, flexspi_nor_config_t *config);
625 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_ERASE_ALL */
626 
627 /*@}*/
628 
629 /*!
630  * @name Command
631  * @{
632  */
633 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER
634 /*!
635  * @brief FLEXSPI command
636  *
637  * This function is used to perform the command write sequence to the NOR device.
638  *
639  * @param instance storage the index of FLEXSPI.
640  * @param xfer A pointer to the storage FLEXSPI Transfer Context.
641  *
642  * @retval kStatus_Success Api was executed successfully.
643  * @retval kStatus_InvalidArgument A invalid argument is provided.
644  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
645  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
646  */
647 status_t ROM_FLEXSPI_NorFlash_CommandXfer(uint32_t instance, flexspi_xfer_t *xfer);
648 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_CMD_XFER */
649 /*@}*/
650 
651 /*!
652  * @name UpdateLut
653  * @{
654  */
655 #if defined(FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT) && FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT
656 /*!
657  * @brief Configure FLEXSPI Lookup table
658  *
659  * @param instance storage the index of FLEXSPI.
660  * @param seqIndex storage the sequence Id.
661  * @param lutBase A pointer to the look-up-table for command sequences.
662  * @param seqNumber storage sequence number.
663  *
664  * @retval kStatus_Success Api was executed successfully.
665  * @retval kStatus_InvalidArgument A invalid argument is provided.
666  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
667  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
668  */
669 status_t ROM_FLEXSPI_NorFlash_UpdateLut(uint32_t instance,
670                                         uint32_t seqIndex,
671                                         const uint32_t *lutBase,
672                                         uint32_t seqNumber);
673 #endif /* FSL_ROM_FLEXSPINOR_API_HAS_FEATURE_UPDATE_LUT */
674 
675 /*@}*/
676 
677 /*!
678  * @name Device status
679  * @{
680  */
681 /*!
682  * @brief Wait until device is idle.
683  *
684  * @param instance  Indicates the index of FLEXSPI.
685  * @param config    A pointer to the storage for the driver runtime state
686  * @param isParallelMode Indicates whether NOR flash is in parallel mode.
687  * @param address  Indicates the operation(erase/program/read) address for serial NOR flash.
688  *
689  * @retval kStatus_Success Api was executed successfully.
690  * @retval kStatus_InvalidArgument A invalid argument is provided.
691  * @retval kStatus_ROM_FLEXSPI_SequenceExecutionTimeout Sequence Execution timeout.
692  * @retval kStatus_ROM_FLEXSPI_InvalidSequence A invalid Sequence is provided.
693  * @retval kStatus_ROM_FLEXSPI_DeviceTimeout Device timeout.
694  */
695 status_t ROM_FLEXSPI_NorFlash_WaitBusy(uint32_t instance,
696                                        flexspi_nor_config_t *config,
697                                        bool isParallelMode,
698                                        uint32_t address);
699 /*@}*/
700 
701 /*!
702  * @name ClearCache
703  * @{
704  */
705 
706 /*!
707  * @name ClearCache
708  * @{
709  */
710 
711 /*!
712  * @brief Software reset for the FLEXSPI logic.
713  *
714  * This function sets the software reset flags for both AHB and buffer domain and
715  * resets both AHB buffer and also IP FIFOs.
716  *
717  * @param instance storage the index of FLEXSPI.
718  */
719 void ROM_FLEXSPI_NorFlash_ClearCache(uint32_t instance);
720 
721 /*@}*/
722 
723 #endif /* FSL_FEATURE_BOOT_ROM_HAS_ROMAPI */
724 
725 #ifdef __cplusplus
726 }
727 #endif
728 
729 /*! @}*/
730 
731 #endif /* _FSL_ROMAPI_H_ */
732