This is an automated email from the ASF dual-hosted git repository.

archer pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git

commit 31a6a4f5d0a01c164fdd68557f1849b3779cefbd
Author: Jouni Ukkonen <[email protected]>
AuthorDate: Wed May 29 14:38:22 2024 +0300

    imx9: Add flexspi support, ported from imxrt
    
    Signed-off-by: Jouni Ukkonen <[email protected]>
---
 arch/arm64/src/imx9/Kconfig                 |    5 +
 arch/arm64/src/imx9/Make.defs               |    4 +
 arch/arm64/src/imx9/hardware/imx9_flexspi.h |  598 +++++++++++++
 arch/arm64/src/imx9/imx9_flexspi.c          | 1258 +++++++++++++++++++++++++++
 arch/arm64/src/imx9/imx9_flexspi.h          |  573 ++++++++++++
 5 files changed, 2438 insertions(+)

diff --git a/arch/arm64/src/imx9/Kconfig b/arch/arm64/src/imx9/Kconfig
index 0f13bfeae8..1f52aa76e7 100644
--- a/arch/arm64/src/imx9/Kconfig
+++ b/arch/arm64/src/imx9/Kconfig
@@ -246,6 +246,11 @@ endmenu # LPUART Configuration
 
 endmenu # LPUART
 
+config IMX9_FLEXSPI
+       bool "ENABLE FLEXSPI interface"
+       default n
+
+
 config IMX9_FLEXIO1_PWM
        depends on PWM
        bool "Enable FLEXIO1 based PWM generation"
diff --git a/arch/arm64/src/imx9/Make.defs b/arch/arm64/src/imx9/Make.defs
index 38466ba370..f97bb2a676 100644
--- a/arch/arm64/src/imx9/Make.defs
+++ b/arch/arm64/src/imx9/Make.defs
@@ -67,3 +67,7 @@ endif
 ifeq ($(CONFIG_IMX9_USDHC),y)
   CHIP_CSRCS += imx9_usdhc.c
 endif
+
+ifeq ($(CONFIG_IMX9_FLEXSPI), y)
+  CHIP_CSRCS += imx9_flexspi.c
+endif
diff --git a/arch/arm64/src/imx9/hardware/imx9_flexspi.h 
b/arch/arm64/src/imx9/hardware/imx9_flexspi.h
new file mode 100644
index 0000000000..929cdfb911
--- /dev/null
+++ b/arch/arm64/src/imx9/hardware/imx9_flexspi.h
@@ -0,0 +1,598 @@
+/****************************************************************************
+ * arch/arm64/src/imx9/hardware/imx9_flexspi.h
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+#ifndef __ARCH_ARM64_SRC_IMX9_HARDWARE_IMX9_FLEXSPI_H
+#define __ARCH_ARM64_SRC_IMX9_HARDWARE_IMX9_FLEXSPI_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+#include "hardware/imx9_memorymap.h"
+
+/* FLEXSPI - Register Layout Typedef */
+
+struct flexspi_type_s
+{
+  volatile uint32_t MCR0;                              /* Module Control 
Register 0, offset: 0x0 */
+  volatile uint32_t MCR1;                              /* Module Control 
Register 1, offset: 0x4 */
+  volatile uint32_t MCR2;                              /* Module Control 
Register 2, offset: 0x8 */
+  volatile uint32_t AHBCR;                             /* AHB Bus Control 
Register, offset: 0xc */
+  volatile uint32_t INTEN;                             /* Interrupt Enable 
Register, offset: 0x10 */
+  volatile uint32_t INTR;                              /* Interrupt Register, 
offset: 0x14 */
+  volatile uint32_t LUTKEY;                            /* LUT Key Register, 
offset: 0x18 */
+  volatile uint32_t LUTCR;                             /* LUT Control 
Register, offset: 0x1c */
+  volatile uint32_t AHBRXBUFCR0[8];                    /* AHB RX Buffer 0 
Control Register 0..AHB RX Buffer 7 Control Register 0, array offset: 0x20, 
array step: 0x4 */
+  volatile uint8_t RESERVED_0[32];
+  volatile uint32_t FLSHCR0[4];                        /* Flash A1 Control 
Register 0..Flash B2 Control Register 0, array offset: 0x60, array step: 0x4 */
+  volatile uint32_t FLSHCR1[4];                        /* Flash A1 Control 
Register 1..Flash B2 Control Register 1, array offset: 0x70, array step: 0x4 */
+  volatile uint32_t FLSHCR2[4];                        /* Flash A1 Control 
Register 2..Flash B2 Control Register 2, array offset: 0x80, array step: 0x4 */
+       uint8_t RESERVED_1[4];
+  volatile uint32_t FLSHCR4;                           /* Flash Control 
Register 4, offset: 0x94 */
+       uint8_t RESERVED_2[8];
+  volatile uint32_t IPCR0;                             /* IP Control Register 
0, offset: 0xa0 */
+  volatile uint32_t IPCR1;                             /* IP Control Register 
1, offset: 0xa4 */
+       uint8_t RESERVED_3[8];
+  volatile uint32_t IPCMD;                             /* IP Command Register, 
offset: 0xb0 */
+       uint8_t RESERVED_4[4];
+  volatile uint32_t IPRXFCR;                           /* IP RX FIFO Control 
Register, offset: 0xb8 */
+  volatile uint32_t IPTXFCR;                           /* IP TX FIFO Control 
Register, offset: 0xbc */
+  volatile uint32_t DLLCR[2];                          /* DLL Control Register 
0, array offset: 0xc0, array step: 0x4 */
+       uint8_t RESERVED_5[24];
+  volatile  uint32_t STS0;                              /* Status Register 0, 
offset: 0xe0 */
+  volatile  uint32_t STS1;                              /* Status Register 1, 
offset: 0xe4 */
+  volatile  uint32_t STS2;                              /* Status Register 2, 
offset: 0xe8 */
+  volatile  uint32_t AHBSPNDSTS;                        /* AHB Suspend Status 
Register, offset: 0xec */
+  volatile  uint32_t IPRXFSTS;                          /* IP RX FIFO Status 
Register, offset: 0xf0 */
+  volatile  uint32_t IPTXFSTS;                          /* IP TX FIFO Status 
Register, offset: 0xf4 */
+       uint8_t RESERVED_6[8];
+  volatile  uint32_t RFDR[32];                          /* IP RX FIFO Data 
Register 0..IP RX FIFO Data Register 31, array offset: 0x100, array step: 0x4 */
+  volatile  uint32_t TFDR[32];                          /* IP TX FIFO Data 
Register 0..IP TX FIFO Data Register 31, array offset: 0x180, array step: 0x4 */
+  volatile uint32_t LUT[128];                           /* LUT 0..LUT 127, 
array offset: 0x200, array step: 0x4 */
+};
+
+#define IMX9_FLEXSPI_AHBBUFREGIONSTART0_OFFSET  0x440
+#define IMX9_FLEXSPI_AHBBUFREGIONEND0_OFFSET    0x444
+#define IMX9_FLEXSPI_AHBBUFREGIONSTART1_OFFSET  0x448
+#define IMX9_FLEXSPI_AHBBUFREGIONEND1_OFFSET    0x44C
+#define IMX9_FLEXSPI_AHBBUFREGIONSTART2_OFFSET  0x450
+#define IMX9_FLEXSPI_AHBBUFREGIONEND2_OFFSET    0x454
+#define IMX9_FLEXSPI_AHBBUFREGIONSTART3_OFFSET  0x458
+#define IMX9_FLEXSPI_AHBBUFREGIONEND3_OFFSET    0x45C
+
+#define IMX9_FLEXSPI1_AHBBUFREGIONSTART0        (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONSTART0_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONEND0          (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONEND0_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONSTART1        (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONSTART1_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONEND1          (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONEND1_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONSTART2        (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONSTART2_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONEND2          (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONEND2_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONSTART3        (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONSTART3_OFFSET)
+#define IMX9_FLEXSPI1_AHBBUFREGIONEND3          (IMX9_FLEXSPI_BASE + 
IMX9_FLEXSPI_AHBBUFREGIONEND3_OFFSET)
+
+/* MCR0 - Module Control Register 0 */
+
+#define FLEXSPI_MCR0_SWRESET_MASK                (0x1u)
+#define FLEXSPI_MCR0_SWRESET_SHIFT               (0u)
+
+/* SWRESET - Software Reset */
+
+#define FLEXSPI_MCR0_SWRESET(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_SWRESET_SHIFT)) & FLEXSPI_MCR0_SWRESET_MASK)
+#define FLEXSPI_MCR0_MDIS_MASK                   (0x2u)
+#define FLEXSPI_MCR0_MDIS_SHIFT                  (1u)
+
+/* MDIS - Module Disable */
+
+#define FLEXSPI_MCR0_MDIS(x)                     (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_MDIS_SHIFT)) & FLEXSPI_MCR0_MDIS_MASK)
+#define FLEXSPI_MCR0_RXCLKSRC_MASK               (0x30u)
+#define FLEXSPI_MCR0_RXCLKSRC_SHIFT              (4u)
+
+#define FLEXSPI_MCR0_RXCLKSRC(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_RXCLKSRC_SHIFT)) & FLEXSPI_MCR0_RXCLKSRC_MASK)
+#define FLEXSPI_MCR0_ARDFEN_MASK                 (0x40u)
+#define FLEXSPI_MCR0_ARDFEN_SHIFT                (6u)
+
+#define FLEXSPI_MCR0_ARDFEN(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_ARDFEN_SHIFT)) & FLEXSPI_MCR0_ARDFEN_MASK)
+#define FLEXSPI_MCR0_ATDFEN_MASK                 (0x80u)
+#define FLEXSPI_MCR0_ATDFEN_SHIFT                (7u)
+
+#define FLEXSPI_MCR0_ATDFEN(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_ATDFEN_SHIFT)) & FLEXSPI_MCR0_ATDFEN_MASK)
+#define FLEXSPI_MCR0_HSEN_MASK                   (0x800u)
+#define FLEXSPI_MCR0_HSEN_SHIFT                  (11u)
+
+#define FLEXSPI_MCR0_HSEN(x)                     (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_HSEN_SHIFT)) & FLEXSPI_MCR0_HSEN_MASK)
+#define FLEXSPI_MCR0_DOZEEN_MASK                 (0x1000u)
+#define FLEXSPI_MCR0_DOZEEN_SHIFT                (12u)
+
+#define FLEXSPI_MCR0_DOZEEN(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_DOZEEN_SHIFT)) & FLEXSPI_MCR0_DOZEEN_MASK)
+#define FLEXSPI_MCR0_COMBINATIONEN_MASK          (0x2000u)
+#define FLEXSPI_MCR0_COMBINATIONEN_SHIFT         (13u)
+
+#define FLEXSPI_MCR0_COMBINATIONEN(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_COMBINATIONEN_SHIFT)) & FLEXSPI_MCR0_COMBINATIONEN_MASK)
+#define FLEXSPI_MCR0_SCKFREERUNEN_MASK           (0x4000u)
+#define FLEXSPI_MCR0_SCKFREERUNEN_SHIFT          (14u)
+
+#define FLEXSPI_MCR0_SCKFREERUNEN(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_SCKFREERUNEN_SHIFT)) & FLEXSPI_MCR0_SCKFREERUNEN_MASK)
+#define FLEXSPI_MCR0_IPGRANTWAIT_MASK            (0xff0000u)
+#define FLEXSPI_MCR0_IPGRANTWAIT_SHIFT           (16u)
+
+#define FLEXSPI_MCR0_IPGRANTWAIT(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_IPGRANTWAIT_SHIFT)) & FLEXSPI_MCR0_IPGRANTWAIT_MASK)
+#define FLEXSPI_MCR0_AHBGRANTWAIT_MASK           (0xff000000u)
+#define FLEXSPI_MCR0_AHBGRANTWAIT_SHIFT          (24u)
+
+#define FLEXSPI_MCR0_AHBGRANTWAIT(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR0_AHBGRANTWAIT_SHIFT)) & FLEXSPI_MCR0_AHBGRANTWAIT_MASK)
+
+#define FLEXSPI_MCR1_AHBBUSWAIT_MASK             (0xffffu)
+#define FLEXSPI_MCR1_AHBBUSWAIT_SHIFT            (0u)
+#define FLEXSPI_MCR1_AHBBUSWAIT(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR1_AHBBUSWAIT_SHIFT)) & FLEXSPI_MCR1_AHBBUSWAIT_MASK)
+#define FLEXSPI_MCR1_SEQWAIT_MASK                (0xffff0000u)
+#define FLEXSPI_MCR1_SEQWAIT_SHIFT               (16u)
+#define FLEXSPI_MCR1_SEQWAIT(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR1_SEQWAIT_SHIFT)) & FLEXSPI_MCR1_SEQWAIT_MASK)
+
+#define FLEXSPI_MCR2_CLRAHBBUFOPT_MASK           (0x800u)
+#define FLEXSPI_MCR2_CLRAHBBUFOPT_SHIFT          (11u)
+
+#define FLEXSPI_MCR2_CLRAHBBUFOPT(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR2_CLRAHBBUFOPT_SHIFT)) & FLEXSPI_MCR2_CLRAHBBUFOPT_MASK)
+#define FLEXSPI_MCR2_CLRLEARNPHASE_MASK          (0x4000u)
+#define FLEXSPI_MCR2_CLRLEARNPHASE_SHIFT         (14u)
+
+#define FLEXSPI_MCR2_CLRLEARNPHASE(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR2_CLRLEARNPHASE_SHIFT)) & FLEXSPI_MCR2_CLRLEARNPHASE_MASK)
+#define FLEXSPI_MCR2_SAMEDEVICEEN_MASK           (0x8000u)
+#define FLEXSPI_MCR2_SAMEDEVICEEN_SHIFT          (15u)
+
+#define FLEXSPI_MCR2_SAMEDEVICEEN(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR2_SAMEDEVICEEN_SHIFT)) & FLEXSPI_MCR2_SAMEDEVICEEN_MASK)
+#define FLEXSPI_MCR2_SCKBDIFFOPT_MASK            (0x80000u)
+#define FLEXSPI_MCR2_SCKBDIFFOPT_SHIFT           (19u)
+
+#define FLEXSPI_MCR2_SCKBDIFFOPT(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR2_SCKBDIFFOPT_SHIFT)) & FLEXSPI_MCR2_SCKBDIFFOPT_MASK)
+#define FLEXSPI_MCR2_RESUMEWAIT_MASK             (0xff000000u)
+#define FLEXSPI_MCR2_RESUMEWAIT_SHIFT            (24u)
+
+#define FLEXSPI_MCR2_RESUMEWAIT(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_MCR2_RESUMEWAIT_SHIFT)) & FLEXSPI_MCR2_RESUMEWAIT_MASK)
+
+#define FLEXSPI_AHBCR_APAREN_MASK                (0x1u)
+#define FLEXSPI_AHBCR_APAREN_SHIFT               (0u)
+
+#define FLEXSPI_AHBCR_APAREN(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBCR_APAREN_SHIFT)) & FLEXSPI_AHBCR_APAREN_MASK)
+#define FLEXSPI_AHBCR_CACHABLEEN_MASK            (0x8u)
+#define FLEXSPI_AHBCR_CACHABLEEN_SHIFT           (3u)
+
+#define FLEXSPI_AHBCR_CACHABLEEN(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBCR_CACHABLEEN_SHIFT)) & FLEXSPI_AHBCR_CACHABLEEN_MASK)
+#define FLEXSPI_AHBCR_BUFFERABLEEN_MASK          (0x10u)
+#define FLEXSPI_AHBCR_BUFFERABLEEN_SHIFT         (4u)
+
+#define FLEXSPI_AHBCR_BUFFERABLEEN(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBCR_BUFFERABLEEN_SHIFT)) & FLEXSPI_AHBCR_BUFFERABLEEN_MASK)
+#define FLEXSPI_AHBCR_PREFETCHEN_MASK            (0x20u)
+#define FLEXSPI_AHBCR_PREFETCHEN_SHIFT           (5u)
+
+#define FLEXSPI_AHBCR_PREFETCHEN(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBCR_PREFETCHEN_SHIFT)) & FLEXSPI_AHBCR_PREFETCHEN_MASK)
+#define FLEXSPI_AHBCR_READADDROPT_MASK           (0x40u)
+#define FLEXSPI_AHBCR_READADDROPT_SHIFT          (6u)
+
+#define FLEXSPI_AHBCR_READADDROPT(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBCR_READADDROPT_SHIFT)) & FLEXSPI_AHBCR_READADDROPT_MASK)
+
+#define FLEXSPI_INTEN_IPCMDDONEEN_MASK           (0x1u)
+#define FLEXSPI_INTEN_IPCMDDONEEN_SHIFT          (0u)
+
+#define FLEXSPI_INTEN_IPCMDDONEEN(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_IPCMDDONEEN_SHIFT)) & FLEXSPI_INTEN_IPCMDDONEEN_MASK)
+#define FLEXSPI_INTEN_IPCMDGEEN_MASK             (0x2u)
+#define FLEXSPI_INTEN_IPCMDGEEN_SHIFT            (1u)
+
+#define FLEXSPI_INTEN_IPCMDGEEN(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_IPCMDGEEN_SHIFT)) & FLEXSPI_INTEN_IPCMDGEEN_MASK)
+#define FLEXSPI_INTEN_AHBCMDGEEN_MASK            (0x4u)
+#define FLEXSPI_INTEN_AHBCMDGEEN_SHIFT           (2u)
+
+#define FLEXSPI_INTEN_AHBCMDGEEN(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_AHBCMDGEEN_SHIFT)) & FLEXSPI_INTEN_AHBCMDGEEN_MASK)
+#define FLEXSPI_INTEN_IPCMDERREN_MASK            (0x8u)
+#define FLEXSPI_INTEN_IPCMDERREN_SHIFT           (3u)
+
+#define FLEXSPI_INTEN_IPCMDERREN(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_IPCMDERREN_SHIFT)) & FLEXSPI_INTEN_IPCMDERREN_MASK)
+#define FLEXSPI_INTEN_AHBCMDERREN_MASK           (0x10u)
+#define FLEXSPI_INTEN_AHBCMDERREN_SHIFT          (4u)
+
+#define FLEXSPI_INTEN_AHBCMDERREN(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_AHBCMDERREN_SHIFT)) & FLEXSPI_INTEN_AHBCMDERREN_MASK)
+#define FLEXSPI_INTEN_IPRXWAEN_MASK              (0x20u)
+#define FLEXSPI_INTEN_IPRXWAEN_SHIFT             (5u)
+
+#define FLEXSPI_INTEN_IPRXWAEN(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_IPRXWAEN_SHIFT)) & FLEXSPI_INTEN_IPRXWAEN_MASK)
+#define FLEXSPI_INTEN_IPTXWEEN_MASK              (0x40u)
+#define FLEXSPI_INTEN_IPTXWEEN_SHIFT             (6u)
+
+#define FLEXSPI_INTEN_IPTXWEEN(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_IPTXWEEN_SHIFT)) & FLEXSPI_INTEN_IPTXWEEN_MASK)
+#define FLEXSPI_INTEN_SCKSTOPBYRDEN_MASK         (0x100u)
+#define FLEXSPI_INTEN_SCKSTOPBYRDEN_SHIFT        (8u)
+
+#define FLEXSPI_INTEN_SCKSTOPBYRDEN(x)           (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_SCKSTOPBYRDEN_SHIFT)) & FLEXSPI_INTEN_SCKSTOPBYRDEN_MASK)
+#define FLEXSPI_INTEN_SCKSTOPBYWREN_MASK         (0x200u)
+#define FLEXSPI_INTEN_SCKSTOPBYWREN_SHIFT        (9u)
+#define FLEXSPI_INTEN_SCKSTOPBYWREN(x)           (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_SCKSTOPBYWREN_SHIFT)) & FLEXSPI_INTEN_SCKSTOPBYWREN_MASK)
+
+#define FLEXSPI_INTEN_AHBBUSERROREN_MASK          (0x400u)
+#define FLEXSPI_INTEN_AHBBUSERROREN_SHIFT         (10u)
+#define FLEXSPI_INTEN_AHBBUSERROREN(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_AHBBUSERROREN_SHIFT)) & FLEXSPI_INTEN_AHBBUSERROREN_MASK)
+
+#define FLEXSPI_INTEN_SEQTIMEOUTEN_MASK          (0x800u)
+#define FLEXSPI_INTEN_SEQTIMEOUTEN_SHIFT         (11u)
+#define FLEXSPI_INTEN_SEQTIMEOUTEN(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_SEQTIMEOUTEN_SHIFT)) & FLEXSPI_INTEN_SEQTIMEOUTEN_MASK)
+
+#define FLEXSPI_INTEN_KEYDONE_MASK                (0x1000u)
+#define FLEXSPI_INTEN_KEYDONE_SHIFT               (12u)
+#define FLEXSPI_INTEN_KEYDONE(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_KEYDONE_SHIFT)) & FLEXSPI_INTEN_KEYDONE_MASK)
+
+#define FLEXSPI_INTEN_KEYERROR_MASK               (0x2000u)
+#define FLEXSPI_INTEN_KEYERROR_SHIFT              (13u)
+#define FLEXSPI_INTEN_KEYERROR(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTEN_KEYERROR_SHIFT)) & FLEXSPI_INTEN_KEYERROR_MASK)
+
+#define FLEXSPI_INTR_IPCMDDONE_MASK              (0x1u)
+#define FLEXSPI_INTR_IPCMDDONE_SHIFT             (0u)
+
+#define FLEXSPI_INTR_IPCMDDONE(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_IPCMDDONE_SHIFT)) & FLEXSPI_INTR_IPCMDDONE_MASK)
+#define FLEXSPI_INTR_IPCMDGE_MASK                (0x2u)
+#define FLEXSPI_INTR_IPCMDGE_SHIFT               (1u)
+
+#define FLEXSPI_INTR_IPCMDGE(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_IPCMDGE_SHIFT)) & FLEXSPI_INTR_IPCMDGE_MASK)
+#define FLEXSPI_INTR_AHBCMDGE_MASK               (0x4u)
+#define FLEXSPI_INTR_AHBCMDGE_SHIFT              (2u)
+
+#define FLEXSPI_INTR_AHBCMDGE(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_AHBCMDGE_SHIFT)) & FLEXSPI_INTR_AHBCMDGE_MASK)
+#define FLEXSPI_INTR_IPCMDERR_MASK               (0x8u)
+#define FLEXSPI_INTR_IPCMDERR_SHIFT              (3u)
+
+#define FLEXSPI_INTR_IPCMDERR(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_IPCMDERR_SHIFT)) & FLEXSPI_INTR_IPCMDERR_MASK)
+#define FLEXSPI_INTR_AHBCMDERR_MASK              (0x10u)
+#define FLEXSPI_INTR_AHBCMDERR_SHIFT             (4u)
+
+#define FLEXSPI_INTR_AHBCMDERR(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_AHBCMDERR_SHIFT)) & FLEXSPI_INTR_AHBCMDERR_MASK)
+#define FLEXSPI_INTR_IPRXWA_MASK                 (0x20u)
+#define FLEXSPI_INTR_IPRXWA_SHIFT                (5u)
+
+#define FLEXSPI_INTR_IPRXWA(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_IPRXWA_SHIFT)) & FLEXSPI_INTR_IPRXWA_MASK)
+#define FLEXSPI_INTR_IPTXWE_MASK                 (0x40u)
+#define FLEXSPI_INTR_IPTXWE_SHIFT                (6u)
+
+#define FLEXSPI_INTR_IPTXWE(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_IPTXWE_SHIFT)) & FLEXSPI_INTR_IPTXWE_MASK)
+#define FLEXSPI_INTR_SCKSTOPBYRD_MASK            (0x100u)
+#define FLEXSPI_INTR_SCKSTOPBYRD_SHIFT           (8u)
+
+#define FLEXSPI_INTR_SCKSTOPBYRD(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_SCKSTOPBYRD_SHIFT)) & FLEXSPI_INTR_SCKSTOPBYRD_MASK)
+#define FLEXSPI_INTR_SCKSTOPBYWR_MASK            (0x200u)
+#define FLEXSPI_INTR_SCKSTOPBYWR_SHIFT           (9u)
+
+#define FLEXSPI_INTR_SCKSTOPBYWR(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_SCKSTOPBYWR_SHIFT)) & FLEXSPI_INTR_SCKSTOPBYWR_MASK)
+#define FLEXSPI_INTR_AHBBUSTIMEOUT_MASK          (0x400u)
+#define FLEXSPI_INTR_AHBBUSTIMEOUT_SHIFT         (10u)
+
+#define FLEXSPI_INTR_AHBBUSTIMEOUT(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_AHBBUSTIMEOUT_SHIFT)) & FLEXSPI_INTR_AHBBUSTIMEOUT_MASK)
+#define FLEXSPI_INTR_SEQTIMEOUT_MASK             (0x800u)
+#define FLEXSPI_INTR_SEQTIMEOUT_SHIFT            (11u)
+
+#define FLEXSPI_INTR_SEQTIMEOUT(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_SEQTIMEOUT_SHIFT)) & FLEXSPI_INTR_SEQTIMEOUT_MASK)
+
+#define FLEXSPI_INTR_KEYDONE_MASK                (0x1000u)
+#define FLEXSPI_INTR_KEYDONE_SHIFT               (12u)
+#define FLEXSPI_INTR_KEYDONE(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_KEYDONE_SHIFT)) & FLEXSPI_INTR_KEYDONE_MASK)
+
+#define FLEXSPI_INTR_KEYERROR_MASK               (0x2000u)
+#define FLEXSPI_INTR_KEYERROR_SHIFT              (13u)
+#define FLEXSPI_INTR_KEYERROR(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_INTR_KEYERROR_SHIFT)) & FLEXSPI_INTR_KEYERROR_MASK)
+
+#define FLEXSPI_LUTKEY_KEY_MASK                  (0xffffffffu)
+#define FLEXSPI_LUTKEY_KEY_SHIFT                 (0u)
+
+#define FLEXSPI_LUTKEY_KEY(x)                    (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUTKEY_KEY_SHIFT)) & FLEXSPI_LUTKEY_KEY_MASK)
+
+#define FLEXSPI_LUTCR_LOCK_MASK                  (0x1u)
+#define FLEXSPI_LUTCR_LOCK_SHIFT                 (0u)
+
+#define FLEXSPI_LUTCR_LOCK(x)                    (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUTCR_LOCK_SHIFT)) & FLEXSPI_LUTCR_LOCK_MASK)
+#define FLEXSPI_LUTCR_UNLOCK_MASK                (0x2u)
+#define FLEXSPI_LUTCR_UNLOCK_SHIFT               (1u)
+
+#define FLEXSPI_LUTCR_UNLOCK(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUTCR_UNLOCK_SHIFT)) & FLEXSPI_LUTCR_UNLOCK_MASK)
+
+#define FLEXSPI_AHBRXBUFCR0_BUFSZ_MASK          (0x1ffu)
+
+#define FLEXSPI_AHBRXBUFCR0_BUFSZ_SHIFT          (0u)
+
+#define FLEXSPI_AHBRXBUFCR0_BUFSZ(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBRXBUFCR0_BUFSZ_SHIFT)) & FLEXSPI_AHBRXBUFCR0_BUFSZ_MASK)
+#define FLEXSPI_AHBRXBUFCR0_MSTRID_MASK          (0xf0000u)
+#define FLEXSPI_AHBRXBUFCR0_MSTRID_SHIFT         (16u)
+
+#define FLEXSPI_AHBRXBUFCR0_MSTRID(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBRXBUFCR0_MSTRID_SHIFT)) & FLEXSPI_AHBRXBUFCR0_MSTRID_MASK)
+#define FLEXSPI_AHBRXBUFCR0_PRIORITY_MASK        (0x7000000u)
+#define FLEXSPI_AHBRXBUFCR0_PRIORITY_SHIFT       (24u)
+
+#define FLEXSPI_AHBRXBUFCR0_PRIORITY(x)          (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBRXBUFCR0_PRIORITY_SHIFT)) & FLEXSPI_AHBRXBUFCR0_PRIORITY_MASK)
+
+#define FLEXSPI_AHBRXBUFCR0_REGIONEN_MASK        (0x40000000u)
+#define FLEXSPI_AHBRXBUFCR0_REGIONEN_SHIFT       (30u)
+
+#define FLEXSPI_AHBRXBUFCR0_REGIONEN(x)          (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBRXBUFCR0_REGIONEN_SHIFT)) & FLEXSPI_AHBRXBUFCR0_REGIONEN_MASK)
+
+#define FLEXSPI_AHBRXBUFCR0_PREFETCHEN_MASK      (0x80000000u)
+#define FLEXSPI_AHBRXBUFCR0_PREFETCHEN_SHIFT     (31u)
+
+#define FLEXSPI_AHBRXBUFCR0_PREFETCHEN(x)        (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBRXBUFCR0_PREFETCHEN_SHIFT)) & FLEXSPI_AHBRXBUFCR0_PREFETCHEN_MASK)
+
+#define FLEXSPI_AHBRXBUFCR0_COUNT                (4u)
+
+#define FLEXSPI_FLSHCR0_FLSHSZ_MASK              (0x7fffffu)
+#define FLEXSPI_FLSHCR0_FLSHSZ_SHIFT             (0u)
+
+#define FLEXSPI_FLSHCR0_FLSHSZ(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR0_FLSHSZ_SHIFT)) & FLEXSPI_FLSHCR0_FLSHSZ_MASK)
+
+#define FLEXSPI_FLSHCR0_COUNT                    (4u)
+
+#define FLEXSPI_FLSHCR1_TCSS_MASK                (0x1fu)
+#define FLEXSPI_FLSHCR1_TCSS_SHIFT               (0u)
+
+#define FLEXSPI_FLSHCR1_TCSS(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_TCSS_SHIFT)) & FLEXSPI_FLSHCR1_TCSS_MASK)
+#define FLEXSPI_FLSHCR1_TCSH_MASK                (0x3e0u)
+#define FLEXSPI_FLSHCR1_TCSH_SHIFT               (5u)
+
+#define FLEXSPI_FLSHCR1_TCSH(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_TCSH_SHIFT)) & FLEXSPI_FLSHCR1_TCSH_MASK)
+#define FLEXSPI_FLSHCR1_WA_MASK                  (0x400u)
+#define FLEXSPI_FLSHCR1_WA_SHIFT                 (10u)
+
+#define FLEXSPI_FLSHCR1_WA(x)                    (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_WA_SHIFT)) & FLEXSPI_FLSHCR1_WA_MASK)
+#define FLEXSPI_FLSHCR1_CAS_MASK                 (0x7800u)
+#define FLEXSPI_FLSHCR1_CAS_SHIFT                (11u)
+
+#define FLEXSPI_FLSHCR1_CAS(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_CAS_SHIFT)) & FLEXSPI_FLSHCR1_CAS_MASK)
+#define FLEXSPI_FLSHCR1_CSINTERVALUNIT_MASK      (0x8000u)
+#define FLEXSPI_FLSHCR1_CSINTERVALUNIT_SHIFT     (15u)
+
+#define FLEXSPI_FLSHCR1_CSINTERVALUNIT(x)        (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_CSINTERVALUNIT_SHIFT)) & FLEXSPI_FLSHCR1_CSINTERVALUNIT_MASK)
+#define FLEXSPI_FLSHCR1_CSINTERVAL_MASK          (0xffff0000u)
+#define FLEXSPI_FLSHCR1_CSINTERVAL_SHIFT         (16u)
+
+#define FLEXSPI_FLSHCR1_CSINTERVAL(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR1_CSINTERVAL_SHIFT)) & FLEXSPI_FLSHCR1_CSINTERVAL_MASK)
+
+#define FLEXSPI_FLSHCR1_COUNT                    (4u)
+
+#define FLEXSPI_FLSHCR2_ARDSEQID_MASK            (0xfu)
+#define FLEXSPI_FLSHCR2_ARDSEQID_SHIFT           (0u)
+
+#define FLEXSPI_FLSHCR2_ARDSEQID(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_ARDSEQID_SHIFT)) & FLEXSPI_FLSHCR2_ARDSEQID_MASK)
+#define FLEXSPI_FLSHCR2_ARDSEQNUM_MASK           (0xe0u)
+#define FLEXSPI_FLSHCR2_ARDSEQNUM_SHIFT          (5u)
+
+#define FLEXSPI_FLSHCR2_ARDSEQNUM(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_ARDSEQNUM_SHIFT)) & FLEXSPI_FLSHCR2_ARDSEQNUM_MASK)
+#define FLEXSPI_FLSHCR2_AWRSEQID_MASK            (0xf00u)
+#define FLEXSPI_FLSHCR2_AWRSEQID_SHIFT           (8u)
+
+#define FLEXSPI_FLSHCR2_AWRSEQID(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_AWRSEQID_SHIFT)) & FLEXSPI_FLSHCR2_AWRSEQID_MASK)
+#define FLEXSPI_FLSHCR2_AWRSEQNUM_MASK           (0xe000u)
+#define FLEXSPI_FLSHCR2_AWRSEQNUM_SHIFT          (13u)
+
+#define FLEXSPI_FLSHCR2_AWRSEQNUM(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_AWRSEQNUM_SHIFT)) & FLEXSPI_FLSHCR2_AWRSEQNUM_MASK)
+#define FLEXSPI_FLSHCR2_AWRWAIT_MASK             (0xfff0000u)
+#define FLEXSPI_FLSHCR2_AWRWAIT_SHIFT            (16u)
+#define FLEXSPI_FLSHCR2_AWRWAIT(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_AWRWAIT_SHIFT)) & FLEXSPI_FLSHCR2_AWRWAIT_MASK)
+#define FLEXSPI_FLSHCR2_AWRWAITUNIT_MASK         (0x70000000u)
+#define FLEXSPI_FLSHCR2_AWRWAITUNIT_SHIFT        (28u)
+
+#define FLEXSPI_FLSHCR2_AWRWAITUNIT(x)           (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_AWRWAITUNIT_SHIFT)) & FLEXSPI_FLSHCR2_AWRWAITUNIT_MASK)
+#define FLEXSPI_FLSHCR2_CLRINSTRPTR_MASK         (0x80000000u)
+#define FLEXSPI_FLSHCR2_CLRINSTRPTR_SHIFT        (31u)
+
+#define FLEXSPI_FLSHCR2_CLRINSTRPTR(x)           (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR2_CLRINSTRPTR_SHIFT)) & FLEXSPI_FLSHCR2_CLRINSTRPTR_MASK)
+
+#define FLEXSPI_FLSHCR2_COUNT                    (4u)
+
+#define FLEXSPI_FLSHCR4_WMOPT1_MASK              (0x1u)
+#define FLEXSPI_FLSHCR4_WMOPT1_SHIFT             (0u)
+
+#define FLEXSPI_FLSHCR4_WMOPT1(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR4_WMOPT1_SHIFT)) & FLEXSPI_FLSHCR4_WMOPT1_MASK)
+#define FLEXSPI_FLSHCR4_WMENA_MASK               (0x4u)
+#define FLEXSPI_FLSHCR4_WMENA_SHIFT              (2u)
+
+#define FLEXSPI_FLSHCR4_WMENA(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR4_WMENA_SHIFT)) & FLEXSPI_FLSHCR4_WMENA_MASK)
+#define FLEXSPI_FLSHCR4_WMENB_MASK               (0x8u)
+#define FLEXSPI_FLSHCR4_WMENB_SHIFT              (3u)
+
+#define FLEXSPI_FLSHCR4_WMENB(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_FLSHCR4_WMENB_SHIFT)) & FLEXSPI_FLSHCR4_WMENB_MASK)
+
+#define FLEXSPI_IPCR0_SFAR_MASK                  (0xffffffffu)
+#define FLEXSPI_IPCR0_SFAR_SHIFT                 (0u)
+
+#define FLEXSPI_IPCR0_SFAR(x)                    (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCR0_SFAR_SHIFT)) & FLEXSPI_IPCR0_SFAR_MASK)
+
+#define FLEXSPI_IPCR1_IDATSZ_MASK                (0xffffu)
+#define FLEXSPI_IPCR1_IDATSZ_SHIFT               (0u)
+
+#define FLEXSPI_IPCR1_IDATSZ(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCR1_IDATSZ_SHIFT)) & FLEXSPI_IPCR1_IDATSZ_MASK)
+#define FLEXSPI_IPCR1_ISEQID_MASK                (0xf0000u)
+#define FLEXSPI_IPCR1_ISEQID_SHIFT               (16u)
+
+#define FLEXSPI_IPCR1_ISEQID(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCR1_ISEQID_SHIFT)) & FLEXSPI_IPCR1_ISEQID_MASK)
+#define FLEXSPI_IPCR1_ISEQNUM_MASK               (0x7000000u)
+#define FLEXSPI_IPCR1_ISEQNUM_SHIFT              (24u)
+
+#define FLEXSPI_IPCR1_ISEQNUM(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCR1_ISEQNUM_SHIFT)) & FLEXSPI_IPCR1_ISEQNUM_MASK)
+#define FLEXSPI_IPCR1_IPAREN_MASK                (0x80000000u)
+#define FLEXSPI_IPCR1_IPAREN_SHIFT               (31u)
+
+#define FLEXSPI_IPCR1_IPAREN(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCR1_IPAREN_SHIFT)) & FLEXSPI_IPCR1_IPAREN_MASK)
+
+#define FLEXSPI_IPCMD_TRG_MASK                   (0x1u)
+#define FLEXSPI_IPCMD_TRG_SHIFT                  (0u)
+
+#define FLEXSPI_IPCMD_TRG(x)                     (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPCMD_TRG_SHIFT)) & FLEXSPI_IPCMD_TRG_MASK)
+
+#define FLEXSPI_IPRXFCR_CLRIPRXF_MASK            (0x1u)
+#define FLEXSPI_IPRXFCR_CLRIPRXF_SHIFT           (0u)
+
+#define FLEXSPI_IPRXFCR_CLRIPRXF(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPRXFCR_CLRIPRXF_SHIFT)) & FLEXSPI_IPRXFCR_CLRIPRXF_MASK)
+#define FLEXSPI_IPRXFCR_RXDMAEN_MASK             (0x2u)
+#define FLEXSPI_IPRXFCR_RXDMAEN_SHIFT            (1u)
+
+#define FLEXSPI_IPRXFCR_RXDMAEN(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPRXFCR_RXDMAEN_SHIFT)) & FLEXSPI_IPRXFCR_RXDMAEN_MASK)
+#define FLEXSPI_IPRXFCR_RXWMRK_MASK              (0x3cu)
+#define FLEXSPI_IPRXFCR_RXWMRK_SHIFT             (2u)
+
+#define FLEXSPI_IPRXFCR_RXWMRK(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPRXFCR_RXWMRK_SHIFT)) & FLEXSPI_IPRXFCR_RXWMRK_MASK)
+
+#define FLEXSPI_IPTXFCR_CLRIPTXF_MASK            (0x1u)
+#define FLEXSPI_IPTXFCR_CLRIPTXF_SHIFT           (0u)
+
+#define FLEXSPI_IPTXFCR_CLRIPTXF(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPTXFCR_CLRIPTXF_SHIFT)) & FLEXSPI_IPTXFCR_CLRIPTXF_MASK)
+#define FLEXSPI_IPTXFCR_TXDMAEN_MASK             (0x2u)
+#define FLEXSPI_IPTXFCR_TXDMAEN_SHIFT            (1u)
+
+#define FLEXSPI_IPTXFCR_TXDMAEN(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPTXFCR_TXDMAEN_SHIFT)) & FLEXSPI_IPTXFCR_TXDMAEN_MASK)
+#define FLEXSPI_IPTXFCR_TXWMRK_MASK              (0x3cu)
+#define FLEXSPI_IPTXFCR_TXWMRK_SHIFT             (2u)
+
+#define FLEXSPI_IPTXFCR_TXWMRK(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPTXFCR_TXWMRK_SHIFT)) & FLEXSPI_IPTXFCR_TXWMRK_MASK)
+
+#define FLEXSPI_DLLCR_DLLEN_MASK                 (0x1u)
+#define FLEXSPI_DLLCR_DLLEN_SHIFT                (0u)
+
+#define FLEXSPI_DLLCR_DLLEN(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_DLLCR_DLLEN_SHIFT)) & FLEXSPI_DLLCR_DLLEN_MASK)
+#define FLEXSPI_DLLCR_DLLRESET_MASK              (0x2u)
+#define FLEXSPI_DLLCR_DLLRESET_SHIFT             (1u)
+
+#define FLEXSPI_DLLCR_DLLRESET(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_DLLCR_DLLRESET_SHIFT)) & FLEXSPI_DLLCR_DLLRESET_MASK)
+#define FLEXSPI_DLLCR_SLVDLYTARGET_MASK          (0x78u)
+#define FLEXSPI_DLLCR_SLVDLYTARGET_SHIFT         (3u)
+
+#define FLEXSPI_DLLCR_SLVDLYTARGET(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_DLLCR_SLVDLYTARGET_SHIFT)) & FLEXSPI_DLLCR_SLVDLYTARGET_MASK)
+#define FLEXSPI_DLLCR_OVRDEN_MASK                (0x100u)
+#define FLEXSPI_DLLCR_OVRDEN_SHIFT               (8u)
+
+#define FLEXSPI_DLLCR_OVRDEN(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_DLLCR_OVRDEN_SHIFT)) & FLEXSPI_DLLCR_OVRDEN_MASK)
+#define FLEXSPI_DLLCR_OVRDVAL_MASK               (0x7e00u)
+#define FLEXSPI_DLLCR_OVRDVAL_SHIFT              (9u)
+
+#define FLEXSPI_DLLCR_OVRDVAL(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_DLLCR_OVRDVAL_SHIFT)) & FLEXSPI_DLLCR_OVRDVAL_MASK)
+
+#define FLEXSPI_DLLCR_COUNT                      (2u)
+
+#define FLEXSPI_STS0_SEQIDLE_MASK                (0x1u)
+#define FLEXSPI_STS0_SEQIDLE_SHIFT               (0u)
+
+#define FLEXSPI_STS0_SEQIDLE(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS0_SEQIDLE_SHIFT)) & FLEXSPI_STS0_SEQIDLE_MASK)
+#define FLEXSPI_STS0_ARBIDLE_MASK                (0x2u)
+#define FLEXSPI_STS0_ARBIDLE_SHIFT               (1u)
+
+#define FLEXSPI_STS0_ARBIDLE(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS0_ARBIDLE_SHIFT)) & FLEXSPI_STS0_ARBIDLE_MASK)
+#define FLEXSPI_STS0_ARBCMDSRC_MASK              (0xcu)
+#define FLEXSPI_STS0_ARBCMDSRC_SHIFT             (2u)
+
+#define FLEXSPI_STS0_ARBCMDSRC(x)                (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS0_ARBCMDSRC_SHIFT)) & FLEXSPI_STS0_ARBCMDSRC_MASK)
+
+#define FLEXSPI_STS1_AHBCMDERRID_MASK            (0xfu)
+#define FLEXSPI_STS1_AHBCMDERRID_SHIFT           (0u)
+
+#define FLEXSPI_STS1_AHBCMDERRID(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS1_AHBCMDERRID_SHIFT)) & FLEXSPI_STS1_AHBCMDERRID_MASK)
+#define FLEXSPI_STS1_AHBCMDERRCODE_MASK          (0xf00u)
+#define FLEXSPI_STS1_AHBCMDERRCODE_SHIFT         (8u)
+
+#define FLEXSPI_STS1_AHBCMDERRCODE(x)            (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS1_AHBCMDERRCODE_SHIFT)) & FLEXSPI_STS1_AHBCMDERRCODE_MASK)
+#define FLEXSPI_STS1_IPCMDERRID_MASK             (0xf0000u)
+#define FLEXSPI_STS1_IPCMDERRID_SHIFT            (16u)
+
+#define FLEXSPI_STS1_IPCMDERRID(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS1_IPCMDERRID_SHIFT)) & FLEXSPI_STS1_IPCMDERRID_MASK)
+#define FLEXSPI_STS1_IPCMDERRCODE_MASK           (0xf000000u)
+#define FLEXSPI_STS1_IPCMDERRCODE_SHIFT          (24u)
+
+#define FLEXSPI_STS1_IPCMDERRCODE(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS1_IPCMDERRCODE_SHIFT)) & FLEXSPI_STS1_IPCMDERRCODE_MASK)
+
+#define FLEXSPI_STS2_ASLVLOCK_MASK               (0x1u)
+#define FLEXSPI_STS2_ASLVLOCK_SHIFT              (0u)
+
+#define FLEXSPI_STS2_ASLVLOCK(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_ASLVLOCK_SHIFT)) & FLEXSPI_STS2_ASLVLOCK_MASK)
+#define FLEXSPI_STS2_AREFLOCK_MASK               (0x2u)
+#define FLEXSPI_STS2_AREFLOCK_SHIFT              (1u)
+
+#define FLEXSPI_STS2_AREFLOCK(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_AREFLOCK_SHIFT)) & FLEXSPI_STS2_AREFLOCK_MASK)
+#define FLEXSPI_STS2_ASLVSEL_MASK                (0xfcu)
+#define FLEXSPI_STS2_ASLVSEL_SHIFT               (2u)
+
+#define FLEXSPI_STS2_ASLVSEL(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_ASLVSEL_SHIFT)) & FLEXSPI_STS2_ASLVSEL_MASK)
+#define FLEXSPI_STS2_AREFSEL_MASK                (0x3f00u)
+#define FLEXSPI_STS2_AREFSEL_SHIFT               (8u)
+
+#define FLEXSPI_STS2_AREFSEL(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_AREFSEL_SHIFT)) & FLEXSPI_STS2_AREFSEL_MASK)
+#define FLEXSPI_STS2_BSLVLOCK_MASK               (0x10000u)
+#define FLEXSPI_STS2_BSLVLOCK_SHIFT              (16u)
+
+#define FLEXSPI_STS2_BSLVLOCK(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_BSLVLOCK_SHIFT)) & FLEXSPI_STS2_BSLVLOCK_MASK)
+#define FLEXSPI_STS2_BREFLOCK_MASK               (0x20000u)
+#define FLEXSPI_STS2_BREFLOCK_SHIFT              (17u)
+
+#define FLEXSPI_STS2_BREFLOCK(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_BREFLOCK_SHIFT)) & FLEXSPI_STS2_BREFLOCK_MASK)
+#define FLEXSPI_STS2_BSLVSEL_MASK                (0xfc0000u)
+#define FLEXSPI_STS2_BSLVSEL_SHIFT               (18u)
+
+#define FLEXSPI_STS2_BSLVSEL(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_BSLVSEL_SHIFT)) & FLEXSPI_STS2_BSLVSEL_MASK)
+#define FLEXSPI_STS2_BREFSEL_MASK                (0x3f000000u)
+#define FLEXSPI_STS2_BREFSEL_SHIFT               (24u)
+
+#define FLEXSPI_STS2_BREFSEL(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_STS2_BREFSEL_SHIFT)) & FLEXSPI_STS2_BREFSEL_MASK)
+
+#define FLEXSPI_AHBSPNDSTS_ACTIVE_MASK           (0x1u)
+#define FLEXSPI_AHBSPNDSTS_ACTIVE_SHIFT          (0u)
+
+#define FLEXSPI_AHBSPNDSTS_ACTIVE(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBSPNDSTS_ACTIVE_SHIFT)) & FLEXSPI_AHBSPNDSTS_ACTIVE_MASK)
+#define FLEXSPI_AHBSPNDSTS_BUFID_MASK            (0xeU)
+#define FLEXSPI_AHBSPNDSTS_BUFID_SHIFT           (1u)
+
+#define FLEXSPI_AHBSPNDSTS_BUFID(x)              (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBSPNDSTS_BUFID_SHIFT)) & FLEXSPI_AHBSPNDSTS_BUFID_MASK)
+#define FLEXSPI_AHBSPNDSTS_DATLFT_MASK           (0xffff0000u)
+#define FLEXSPI_AHBSPNDSTS_DATLFT_SHIFT          (16u)
+
+#define FLEXSPI_AHBSPNDSTS_DATLFT(x)             (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_AHBSPNDSTS_DATLFT_SHIFT)) & FLEXSPI_AHBSPNDSTS_DATLFT_MASK)
+
+#define FLEXSPI_IPRXFSTS_FILL_MASK               (0xffu)
+#define FLEXSPI_IPRXFSTS_FILL_SHIFT              (0u)
+
+#define FLEXSPI_IPRXFSTS_FILL(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPRXFSTS_FILL_SHIFT)) & FLEXSPI_IPRXFSTS_FILL_MASK)
+#define FLEXSPI_IPRXFSTS_RDCNTR_MASK             (0xffff0000u)
+#define FLEXSPI_IPRXFSTS_RDCNTR_SHIFT            (16u)
+
+#define FLEXSPI_IPRXFSTS_RDCNTR(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPRXFSTS_RDCNTR_SHIFT)) & FLEXSPI_IPRXFSTS_RDCNTR_MASK)
+
+#define FLEXSPI_IPTXFSTS_FILL_MASK               (0xffu)
+#define FLEXSPI_IPTXFSTS_FILL_SHIFT              (0u)
+
+#define FLEXSPI_IPTXFSTS_FILL(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPTXFSTS_FILL_SHIFT)) & FLEXSPI_IPTXFSTS_FILL_MASK)
+#define FLEXSPI_IPTXFSTS_WRCNTR_MASK             (0xffff0000u)
+#define FLEXSPI_IPTXFSTS_WRCNTR_SHIFT            (16u)
+
+#define FLEXSPI_IPTXFSTS_WRCNTR(x)               (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_IPTXFSTS_WRCNTR_SHIFT)) & FLEXSPI_IPTXFSTS_WRCNTR_MASK)
+
+#define FLEXSPI_RFDR_RXDATA_MASK                 (0xffffffffu)
+#define FLEXSPI_RFDR_RXDATA_SHIFT                (0u)
+
+#define FLEXSPI_RFDR_RXDATA(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_RFDR_RXDATA_SHIFT)) & FLEXSPI_RFDR_RXDATA_MASK)
+
+#define FLEXSPI_RFDR_COUNT                       (32u)
+
+#define FLEXSPI_TFDR_TXDATA_MASK                 (0xffffffffu)
+#define FLEXSPI_TFDR_TXDATA_SHIFT                (0u)
+
+#define FLEXSPI_TFDR_TXDATA(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_TFDR_TXDATA_SHIFT)) & FLEXSPI_TFDR_TXDATA_MASK)
+
+#define FLEXSPI_TFDR_COUNT                       (32u)
+
+#define FLEXSPI_LUT_COUNT                        (128u)
+
+#endif /* __ARCH_ARM_SRC_IMX9_HARDWARE_IMX9_FLEXSPI_H */
diff --git a/arch/arm64/src/imx9/imx9_flexspi.c 
b/arch/arm64/src/imx9/imx9_flexspi.c
new file mode 100644
index 0000000000..9ccb0a439c
--- /dev/null
+++ b/arch/arm64/src/imx9/imx9_flexspi.c
@@ -0,0 +1,1258 @@
+/****************************************************************************
+ * arch/arm64/src/imx9/imx9_flexspi.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <sys/types.h>
+#include <stdint.h>
+#include <stdbool.h>
+#include <stdlib.h>
+#include <string.h>
+#include <errno.h>
+#include <assert.h>
+#include <debug.h>
+
+#include <arch/board/board.h>
+
+#include <nuttx/arch.h>
+#include <nuttx/wdog.h>
+#include <nuttx/clock.h>
+#include <nuttx/kmalloc.h>
+#include <nuttx/mutex.h>
+
+#include "arm64_internal.h"
+#include "barriers.h"
+
+#include "imx9_gpio.h"
+#include "imx9_ccm.h"
+#include "imx9_clockconfig.h"
+#include "imx9_flexspi.h"
+#include "imx9_iomuxc.h"
+#include "hardware/imx9_ccm.h"
+#include "hardware/imx9_flexspi.h"
+#include "hardware/imx9_pinmux.h"
+
+#ifdef CONFIG_IMX9_FLEXSPI
+
+/****************************************************************************
+ * Private Types
+ ****************************************************************************/
+
+/* The state of the FlexSPI controller.
+ *
+ */
+
+struct imx9_flexspidev_s
+{
+  struct flexspi_dev_s flexspi; /* Externally visible part of the FlexSPI
+                                 * interface */
+
+  struct flexspi_type_s *base; /* FlexSPI controller register base address */
+
+  bool initialized;            /* TRUE: Controller has been initialized */
+
+  mutex_t lock;                /* Assures mutually exclusive access to
+                                * FlexSPI */
+};
+
+/* FlexSPI methods */
+
+static int imx9_flexspi_lock(struct flexspi_dev_s *dev, bool lock);
+static int imx9_flexspi_transfer_blocking(struct flexspi_dev_s *dev,
+                                      struct flexspi_transfer_s *xfer);
+static void imx9_flexspi_software_reset(struct flexspi_dev_s *dev);
+static void imx9_flexspi_update_lut(struct flexspi_dev_s *dev,
+                                     uint32_t index,
+                                     const uint32_t *cmd,
+                                     uint32_t count);
+static void imx9_flexspi_set_device_config(struct flexspi_dev_s *dev,
+                                      struct flexspi_device_config_s *config,
+                                      enum flexspi_port_e port);
+
+/****************************************************************************
+ * Private Data
+ ****************************************************************************/
+
+/* FlexSPI0 driver operations */
+
+static const struct flexspi_ops_s g_flexspi0ops =
+{
+  .lock              = imx9_flexspi_lock,
+  .transfer_blocking = imx9_flexspi_transfer_blocking,
+  .software_reset    = imx9_flexspi_software_reset,
+  .update_lut        = imx9_flexspi_update_lut,
+  .set_device_config  = imx9_flexspi_set_device_config,
+};
+
+/* This is the overall state of the FlexSPI0 controller */
+
+static struct imx9_flexspidev_s g_flexspi0dev =
+{
+  .flexspi =
+  {
+    .ops = &g_flexspi0ops,
+  },
+  .base = (struct flexspi_type_s *)IMX9_FLEXSPI_BASE,
+  .lock = NXMUTEX_INITIALIZER,
+};
+
+#define FREQ_1MHz             (1000000ul)
+#define FLEXSPI_DLLCR_DEFAULT (0x100ul)
+#define FLEXSPI_LUT_KEY_VAL   (0x5af05af0ul)
+
+enum
+{
+  FLEXSPI_DELAY_CELL_UNIT_MIN = 75,  /* 75ps */
+
+  FLEXSPI_DELAY_CELL_UNIT_MAX = 225, /* 225ps */
+};
+
+enum
+{
+  FLEXSPI_FLASH_A_SAMPLE_CLOCK_SLAVE_DELAY_LOCKED =
+      FLEXSPI_STS2_ASLVLOCK_MASK, /* Flash A sample clock slave delay line 
locked */
+
+  FLEXSPI_FLASH_A_SAMPLE_CLOCK_REF_DELAY_LOCKED =
+      FLEXSPI_STS2_AREFLOCK_MASK, /* Flash A sample clock reference delay line 
locked */
+
+  FLEXSPI_FLASH_B_SAMPLE_CLOCK_SLAVE_DELAY_LOCKED =
+      FLEXSPI_STS2_BSLVLOCK_MASK, /* Flash B sample clock slave delay line 
locked */
+
+  FLEXSPI_FLASH_B_SAMPLE_CLOCK_REF_DELAY_LOCKED =
+      FLEXSPI_STS2_BREFLOCK_MASK, /* Flash B sample clock reference delay line 
locked */
+};
+
+/* FLEXSPI interrupt status flags */
+
+enum flexspi_flags_e
+{
+  FLEXSPI_KEYERROR_FLAG = FLEXSPI_INTEN_KEYERROR_MASK ,
+
+  FLEXSPI_KEYDONE_FLAG = FLEXSPI_INTEN_KEYDONE_MASK,
+
+  FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT_FLAG = FLEXSPI_INTEN_SEQTIMEOUTEN_MASK, 
/* Sequence execution timeout */
+
+  FLEXSPI_AHB_BUS_ERROR_FLAG = FLEXSPI_INTEN_AHBBUSERROREN_MASK, /* AHB Bus 
error flag */
+
+  FLEXSPI_SCK_STOPPED_BECAUSE_TX_EMPTY_FLAG =
+      FLEXSPI_INTEN_SCKSTOPBYWREN_MASK, /* SCK is stopped during command
+                                         * sequence because Async TX FIFO 
empty */
+
+  FLEXSPI_SCK_STOPPED_BECAUSE_RX_FULL_FLAG =
+      FLEXSPI_INTEN_SCKSTOPBYRDEN_MASK, /* SCK is stopped during command
+                                         * sequence because Async RX FIFO full 
*/
+
+  FLEXSPI_IP_TX_FIFO_WATERMARK_EMPTY_FLAG     = FLEXSPI_INTEN_IPTXWEEN_MASK, 
/* IP TX FIFO WaterMark empty */
+
+  FLEXSPI_IP_RX_FIFO_WATERMARK_AVAILABLE_FLAG = FLEXSPI_INTEN_IPRXWAEN_MASK, 
/* IP RX FIFO WaterMark available */
+
+  FLEXSPI_AHB_COMMAND_SEQUENCE_ERROR_FLAG =
+      FLEXSPI_INTEN_AHBCMDERREN_MASK,                                  /* AHB 
triggered Command Sequences Error */
+
+  FLEXSPI_IP_COMMAND_SEQUENCE_ERROR_FLAG = FLEXSPI_INTEN_IPCMDERREN_MASK, /* 
IP triggered Command Sequences Error */
+
+  FLEXSPI_AHB_COMMAND_GRANT_TIMEOUT_FLAG =
+      FLEXSPI_INTEN_AHBCMDGEEN_MASK, /* AHB triggered Command Sequences Grant 
Timeout */
+
+  FLEXSPI_IP_COMMAND_GRANT_TIMEOUT_FLAG =
+      FLEXSPI_INTEN_IPCMDGEEN_MASK, /* IP triggered Command Sequences Grant 
Timeout */
+
+  FLEXSPI_IP_COMMAND_EXECUTION_DONE_FLAG =
+      FLEXSPI_INTEN_IPCMDDONEEN_MASK,  /* IP triggered Command Sequences 
Execution finished */
+
+  FLEXSPI_ALL_INTERRUPT_FLAGS = 0x3fffu, /* All flags */
+};
+
+/* Common sets of flags used by the driver */
+
+enum flexspi_flag_constants_e
+{
+  /*  Errors to check for */
+
+  ERROR_FLAGS = FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT_FLAG |
+                FLEXSPI_IP_COMMAND_SEQUENCE_ERROR_FLAG |
+                FLEXSPI_IP_COMMAND_GRANT_TIMEOUT_FLAG,
+};
+
+#define FLEXSPI_AHB_BUFFER_COUNT (8)
+
+struct flexspi_ahb_buffer_config_s
+{
+  uint8_t priority;    /* This priority for AHB Master Read which this AHB RX 
Buffer is assigned */
+
+  uint8_t master_index; /* AHB Master ID the AHB RX Buffer is assigned */
+
+  uint16_t buffer_size; /* AHB buffer size in byte */
+
+  bool enable_prefetch; /* AHB Read Prefetch Enable for current AHB RX Buffer 
corresponding Master, allows
+                         * prefetch disable/enable separately for each master 
*/
+};
+
+/*   FLEXSPI configuration structure */
+
+struct flexspi_config_s
+{
+  enum flexspi_read_sample_clock_e rx_sample_clock; /* Sample Clock source 
selection for Flash Reading */
+
+  bool enable_sck_free_running;                 /* Enable/disable SCK output 
free-running */
+
+  bool enable_combination;                    /* Enable/disable combining PORT 
A and B Data Pins
+                                               * (SIOA[3:0] and SIOB[3:0]) to 
support Flash Octal mode */
+
+  bool enable_doze;                           /* Enable/disable doze mode 
support */
+
+  bool enable_half_speed_access;                /* Enable/disable divide by 2 
of the clock for half
+                                                 * speed commands */
+
+  bool enable_sckb_diff_opt;                    /* Enable/disable SCKB pad use 
as SCKA differential clock
+                                                 * output, when enable, Port B 
flash access is not available */
+
+  bool enable_same_config_for_all;               /* Enable/disable same 
configuration for all connected devices
+                                                  * when enabled, same 
configuration in FLASHA1CRx is applied to all */
+
+  uint16_t seq_timeout_cycle;                  /* Timeout wait cycle for 
command sequence execution,
+                                                * timeout after 
ahb_grant_timeout_cyle*1024 serial root clock cycles */
+
+  uint8_t ip_grant_timeout_cycle;               /* Timeout wait cycle for IP 
command grant, timeout after
+                                                 * ip_grant_timeout_cycle*1024 
AHB clock cycles */
+
+  uint8_t tx_watermark;                       /* FLEXSPI IP transmit watermark 
value */
+
+  uint8_t rx_watermark;                       /* FLEXSPI receive watermark 
value */
+
+  struct
+  {
+    bool enable_ahb_write_ip_tx_fifo; /* Enable AHB bus write access to IP TX 
FIFO */
+    bool enable_ahb_write_ip_rx_fifo; /* Enable AHB bus write access to IP RX 
FIFO */
+
+    uint8_t ahb_grant_timeout_cycle; /* Timeout wait cycle for AHB command 
grant,
+                                      * timeout after 
ahb_grant_timeout_cyle*1024 AHB clock cycles */
+
+    uint16_t ahb_bus_timeout_cycle;  /* Timeout wait cycle for AHB read/write 
access,
+                                      * timeout after 
ahb_bus_timeout_cycle*1024 AHB clock cycles */
+
+    uint8_t resume_wait_cycle;      /* Wait cycle for idle state before 
suspended command sequence
+                                     * resume, timeout after 
ahb_bus_timeout_cycle AHB clock cycles */
+
+    struct flexspi_ahb_buffer_config_s buffer[FLEXSPI_AHB_BUFFER_COUNT]; /* 
AHB buffer size */
+
+    bool enable_clear_ahb_buffer_opt; /* Enable/disable automatically clean 
AHB RX Buffer and TX Buffer
+                                       * when FLEXSPI returns STOP mode ACK */
+
+    bool enable_read_address_opt;    /* Enable/disable remove AHB read burst 
start address alignment limitation.
+                                      * when enable, there is no AHB read 
burst start address alignment limitation */
+
+    bool enable_ahb_prefetch;       /* Enable/disable AHB read prefetch 
feature, when enabled, FLEXSPI
+                                     * will fetch more data than current AHB 
burst */
+
+    bool enable_ahb_bufferable;     /* Enable/disable AHB bufferable write 
access support, when enabled,
+                                     * FLEXSPI return before waiting for 
command execution finished */
+
+    bool enable_ahb_cachable;       /* Enable AHB bus cachable read access 
support */
+  } ahb_config;
+};
+
+/****************************************************************************
+ * Prototypes
+ ****************************************************************************/
+
+/* Check and clear IP command execution errors.
+ *
+ * @param base FLEXSPI base pointer.
+ * @param status interrupt status.
+ */
+
+static int imx9_flexspi_check_and_clear_error(struct flexspi_type_s *base,
+                                               uint32_t status);
+
+/****************************************************************************
+ * Variables
+ ****************************************************************************/
+
+/****************************************************************************
+ * Code
+ ****************************************************************************/
+
+/* Software reset for the FLEXSPI logic.
+ *
+ * This function sets the software reset flags for both AHB and buffer domain
+ * and resets both AHB buffer and also IP FIFOs.
+ *
+ * @param base FLEXSPI peripheral base address.
+ */
+
+static inline void imx9_flexspi_software_reset_private(
+                        struct flexspi_type_s *base)
+{
+  base->MCR0 |= FLEXSPI_MCR0_SWRESET_MASK;
+  while (0u != (base->MCR0 & FLEXSPI_MCR0_SWRESET_MASK))
+    {
+    }
+}
+
+/* Returns whether the bus is idle.
+ *
+ * @param base FLEXSPI peripheral base address.
+ * @retval true Bus is idle.
+ * @retval false Bus is busy.
+ */
+
+static inline bool imx9_flexspi_get_bus_idle_status(
+                        struct flexspi_type_s *base)
+{
+  return (0u != (base->STS0 & FLEXSPI_STS0_ARBIDLE_MASK)) &&
+          (0u != (base->STS0 & FLEXSPI_STS0_SEQIDLE_MASK));
+}
+
+static uint32_t imx9_flexspi_configure_dll(struct flexspi_type_s *base,
+                                  struct flexspi_device_config_s *config)
+{
+  bool is_unified_config = true;
+  uint32_t flexspi_dll_value;
+  uint32_t dll_value;
+  uint32_t temp;
+
+  uint32_t rx_sample_clock = (base->MCR0 & FLEXSPI_MCR0_RXCLKSRC_MASK) >>
+                              FLEXSPI_MCR0_RXCLKSRC_SHIFT;
+  switch (rx_sample_clock)
+    {
+      case (uint32_t)FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_INTERNALLY:
+      case (uint32_t)FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_FROM_DQS_PAD:
+      case (uint32_t)FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_FROM_SCK_PAD:
+        is_unified_config = true;
+        break;
+      case (uint32_t)FLEXSPI_READ_SAMPLE_CLK_EXTERNAL_INPUT_FROM_DQS_PAD:
+        if (config->is_sck2_enabled)
+          {
+            is_unified_config = true;
+          }
+        else
+          {
+            is_unified_config = false;
+          }
+        break;
+      default:
+          assert(false);
+          break;
+  }
+
+  if (is_unified_config)
+    {
+      flexspi_dll_value = FLEXSPI_DLLCR_DEFAULT; /* 1 fixed delay cells in DLL 
delay chain */
+    }
+  else
+    {
+      if (config->flexspi_root_clk >= 100u * FREQ_1MHz)
+        {
+          /* DLLEN = 1, SLVDLYTARGET = 0xF, */
+
+          flexspi_dll_value = FLEXSPI_DLLCR_DLLEN(1) |
+                              FLEXSPI_DLLCR_SLVDLYTARGET(0x0f);
+        }
+      else
+        {
+          temp     = (uint32_t)config->data_valid_time * 1000u; /* Convert 
data valid time in ns to ps */
+
+          dll_value = temp / (uint32_t)FLEXSPI_DELAY_CELL_UNIT_MIN;
+          if (dll_value * (uint32_t)FLEXSPI_DELAY_CELL_UNIT_MIN < temp)
+            {
+              dll_value++;
+            }
+          flexspi_dll_value = FLEXSPI_DLLCR_OVRDEN(1) |
+                              FLEXSPI_DLLCR_OVRDVAL(dll_value);
+        }
+    }
+  return flexspi_dll_value;
+}
+
+static int imx9_flexspi_check_and_clear_error(struct flexspi_type_s *base,
+                                               uint32_t status)
+{
+  int result = 0;
+
+  /* Check for error */
+
+  status &= (uint32_t)ERROR_FLAGS;
+  if (0u != status)
+    {
+      /* Select the correct error code */
+
+      if (0u != (status & (uint32_t)FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT_FLAG))
+        {
+          result = STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT;
+        }
+      else if (0u != (status &
+                      (uint32_t)FLEXSPI_IP_COMMAND_SEQUENCE_ERROR_FLAG))
+        {
+          result = STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR;
+        }
+      else if (0u != (status &
+                      (uint32_t)FLEXSPI_IP_COMMAND_GRANT_TIMEOUT_FLAG))
+        {
+          result = STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT;
+        }
+      else
+        {
+          assert(false);
+        }
+
+      /* Clear the flags */
+
+      base->INTR |= status;
+
+      /* Reset fifos. These flags clear automatically */
+
+      base->IPTXFCR |= FLEXSPI_IPTXFCR_CLRIPTXF_MASK;
+      base->IPRXFCR |= FLEXSPI_IPRXFCR_CLRIPRXF_MASK;
+  }
+
+  return result;
+}
+
+/* Initializes the FLEXSPI module and internal state.
+ *
+ * This function enables the clock for FLEXSPI and also configures the
+ * FLEXSPI with the input configure parameters. Users should call this
+ * function before any FLEXSPI operations.
+ *
+ * param base FLEXSPI peripheral base address.
+ * param config FLEXSPI configure structure.
+ */
+
+void imx9_flexspi_init(struct flexspi_type_s *base,
+                        const struct flexspi_config_s *config)
+{
+  uint32_t config_value = 0;
+  uint8_t i            = 0;
+
+  /* Reset peripheral before configuring it */
+
+  base->MCR0 &= ~FLEXSPI_MCR0_MDIS_MASK;
+  imx9_flexspi_software_reset_private(base);
+
+  /* Configure MCR0 configuration items */
+
+  config_value = FLEXSPI_MCR0_RXCLKSRC(config->rx_sample_clock) |
+                 FLEXSPI_MCR0_DOZEEN(config->enable_doze) |
+                 FLEXSPI_MCR0_IPGRANTWAIT(config->ip_grant_timeout_cycle) |
+                 FLEXSPI_MCR0_AHBGRANTWAIT(
+                   config->ahb_config.ahb_grant_timeout_cycle) |
+                 FLEXSPI_MCR0_SCKFREERUNEN(config->enable_sck_free_running) |
+                 FLEXSPI_MCR0_HSEN(config->enable_half_speed_access) |
+                 FLEXSPI_MCR0_COMBINATIONEN(config->enable_combination) |
+                 FLEXSPI_MCR0_ATDFEN(
+                   config->ahb_config.enable_ahb_write_ip_tx_fifo) |
+                 FLEXSPI_MCR0_ARDFEN(
+                   config->ahb_config.enable_ahb_write_ip_rx_fifo) |
+                 FLEXSPI_MCR0_MDIS_MASK;
+  base->MCR0 = config_value;
+
+  /* Configure MCR1 configurations */
+
+  config_value =
+      FLEXSPI_MCR1_SEQWAIT(config->seq_timeout_cycle) |
+      FLEXSPI_MCR1_AHBBUSWAIT(config->ahb_config.ahb_bus_timeout_cycle);
+
+  base->MCR1 = config_value;
+
+  /* Configure MCR2 configurations */
+
+  config_value = base->MCR2;
+  config_value &= ~(FLEXSPI_MCR2_RESUMEWAIT_MASK |
+                    FLEXSPI_MCR2_SCKBDIFFOPT_MASK |
+                    FLEXSPI_MCR2_SAMEDEVICEEN_MASK |
+                    FLEXSPI_MCR2_CLRAHBBUFOPT_MASK);
+
+  config_value |= FLEXSPI_MCR2_RESUMEWAIT(
+                    config->ahb_config.resume_wait_cycle) |
+                  FLEXSPI_MCR2_SCKBDIFFOPT(
+                    config->enable_sckb_diff_opt) |
+                  FLEXSPI_MCR2_SAMEDEVICEEN(
+                    config->enable_same_config_for_all) |
+                  FLEXSPI_MCR2_CLRAHBBUFOPT(
+                    config->ahb_config.enable_clear_ahb_buffer_opt);
+
+  base->MCR2 = config_value;
+
+  /* Configure AHB control items */
+
+  config_value = base->AHBCR;
+  config_value &= ~(FLEXSPI_AHBCR_READADDROPT_MASK |
+                    FLEXSPI_AHBCR_PREFETCHEN_MASK |
+                    FLEXSPI_AHBCR_BUFFERABLEEN_MASK |
+                    FLEXSPI_AHBCR_CACHABLEEN_MASK);
+
+  config_value |= FLEXSPI_AHBCR_READADDROPT(
+                    config->ahb_config.enable_read_address_opt) |
+                  FLEXSPI_AHBCR_PREFETCHEN(
+                    config->ahb_config.enable_ahb_prefetch) |
+                  FLEXSPI_AHBCR_BUFFERABLEEN(
+                    config->ahb_config.enable_ahb_bufferable) |
+                  FLEXSPI_AHBCR_CACHABLEEN(
+                    config->ahb_config.enable_ahb_cachable);
+
+  base->AHBCR = config_value;
+
+  /* Configure AHB rx buffers */
+
+  for (i = 0; i < (uint32_t)FLEXSPI_AHB_BUFFER_COUNT; i++)
+    {
+      config_value = base->AHBRXBUFCR0[i];
+
+      config_value &= ~(FLEXSPI_AHBRXBUFCR0_PREFETCHEN_MASK |
+                        FLEXSPI_AHBRXBUFCR0_PRIORITY_MASK |
+                        FLEXSPI_AHBRXBUFCR0_MSTRID_MASK |
+                        FLEXSPI_AHBRXBUFCR0_BUFSZ_MASK);
+
+      config_value |= FLEXSPI_AHBRXBUFCR0_PREFETCHEN(
+                        config->ahb_config.buffer[i].enable_prefetch) |
+                      FLEXSPI_AHBRXBUFCR0_PRIORITY(
+                        config->ahb_config.buffer[i].priority) |
+                      FLEXSPI_AHBRXBUFCR0_MSTRID(
+                        config->ahb_config.buffer[i].master_index) |
+                      FLEXSPI_AHBRXBUFCR0_BUFSZ((uint32_t)
+                        config->ahb_config.buffer[i].buffer_size / 8u);
+
+      base->AHBRXBUFCR0[i] = config_value;
+    }
+
+  /* Configure IP FIFO watermarks */
+
+  base->IPRXFCR &= ~FLEXSPI_IPRXFCR_RXWMRK_MASK;
+  base->IPRXFCR |=
+        FLEXSPI_IPRXFCR_RXWMRK((uint32_t)config->rx_watermark / 8u - 1u);
+  base->IPTXFCR &= ~FLEXSPI_IPTXFCR_TXWMRK_MASK;
+  base->IPTXFCR |=
+        FLEXSPI_IPTXFCR_TXWMRK((uint32_t)config->tx_watermark / 8u - 1u);
+
+  /* Reset flash size on all ports */
+
+  for (i = 0; i < (uint32_t)FLEXSPI_PORT_COUNT; i++)
+    {
+      base->FLSHCR0[i] = 0;
+    }
+}
+
+/* Gets default settings for FLEXSPI.
+ *
+ * param config FLEXSPI configuration structure.
+ */
+
+void imx9_flexspi_get_default_config(struct flexspi_config_s *config)
+{
+  /* Initializes the configure structure to zero */
+
+  memset(config, 0, sizeof(*config));
+
+  config->rx_sample_clock = FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_FROM_DQS_PAD;
+  config->enable_sck_free_running     = false;
+  config->enable_combination          = false;
+  config->enable_doze                 = true;
+  config->enable_half_speed_access    = false;
+  config->enable_sckb_diff_opt        = false;
+  config->enable_same_config_for_all  = false;
+  config->seq_timeout_cycle           = 0xffff;
+  config->ip_grant_timeout_cycle      = 0xff;
+  config->tx_watermark                = 8;
+  config->rx_watermark                = 8;
+  config->ahb_config.enable_ahb_write_ip_tx_fifo = false;
+  config->ahb_config.enable_ahb_write_ip_rx_fifo = false;
+  config->ahb_config.ahb_grant_timeout_cycle  = 0xff;
+  config->ahb_config.ahb_bus_timeout_cycle    = 0xffff;
+  config->ahb_config.resume_wait_cycle        = 0x20;
+  memset(config->ahb_config.buffer, 0,
+         sizeof(config->ahb_config.buffer));
+
+  /* Use invalid master ID 0xF and buffer size 0 for the first several
+   * buffers.
+   */
+
+  for (uint8_t i = 0; i < ((uint8_t)FLEXSPI_AHB_BUFFER_COUNT - 2u); i++)
+    {
+      /* Default enable AHB prefetch */
+
+      config->ahb_config.buffer[i].enable_prefetch = true;
+
+      /* Invalid master index which is no used, so will never hit */
+
+      config->ahb_config.buffer[i].master_index = 0xf;
+
+      /* Default buffer size 0 for buffer0 to
+       * buffer(FLEXSPI_AHB_BUFFER_COUNT - 3)
+       */
+
+      config->ahb_config.buffer[i].buffer_size = 0;
+    }
+
+  for (uint8_t i = ((uint8_t)FLEXSPI_AHB_BUFFER_COUNT - 2);
+       i < (uint8_t)FLEXSPI_AHB_BUFFER_COUNT; i++)
+    {
+      config->ahb_config.buffer[i].enable_prefetch = true; /* Default enable
+                                                            * AHB prefetch.
+                                                            */
+
+      config->ahb_config.buffer[i].buffer_size     = 256u; /* Default buffer
+                                                            * size 256 bytes.
+                                                            */
+    }
+
+  config->ahb_config.enable_clear_ahb_buffer_opt  = false;
+  config->ahb_config.enable_read_address_opt      = false;
+  config->ahb_config.enable_ahb_prefetch          = false;
+  config->ahb_config.enable_ahb_bufferable        = false;
+  config->ahb_config.enable_ahb_cachable          = false;
+}
+
+/* Configures the connected device parameter.
+ *
+ * This function configures the connected device relevant parameters, such
+ * as the size, command, and so on. The flash configuration value cannot have
+ * a default value. The user needs to configure it according to the connected
+ * device.
+ *
+ * param base   FLEXSPI peripheral base address.
+ * param config Device configuration parameters.
+ * param port   FLEXSPI Operation port.
+ */
+
+void imx9_flexspi_set_device_config_private(struct flexspi_type_s *base,
+                                    struct flexspi_device_config_s *config,
+                                    enum flexspi_port_e port)
+{
+  uint32_t config_value = 0;
+  uint32_t status_value = 0;
+  uint8_t index        = (uint8_t)port >> 1u; /* PortA with index 0, PortB 
with index 1 */
+
+  /* Wait for bus idle before change flash configuration */
+
+  while (!imx9_flexspi_get_bus_idle_status(base))
+    {
+    }
+
+  /* Configure flash size */
+
+  base->FLSHCR0[port] = config->flash_size;
+
+  /* Configure flash parameters */
+
+  base->FLSHCR1[port] =
+        FLEXSPI_FLSHCR1_CSINTERVAL(config->cs_interval) |
+        FLEXSPI_FLSHCR1_CSINTERVALUNIT(config->cs_interval_unit) |
+        FLEXSPI_FLSHCR1_TCSH(config->cs_hold_time) |
+        FLEXSPI_FLSHCR1_TCSS(config->cs_setup_time) |
+        FLEXSPI_FLSHCR1_CAS(config->columnspace) |
+        FLEXSPI_FLSHCR1_WA(config->enable_word_address);
+
+  /* Configure AHB operation items */
+
+  config_value = base->FLSHCR2[port];
+
+  config_value &= ~(FLEXSPI_FLSHCR2_AWRWAITUNIT_MASK |
+                    FLEXSPI_FLSHCR2_AWRWAIT_MASK |
+                    FLEXSPI_FLSHCR2_AWRSEQNUM_MASK |
+                    FLEXSPI_FLSHCR2_AWRSEQID_MASK |
+                    FLEXSPI_FLSHCR2_ARDSEQNUM_MASK |
+                    FLEXSPI_FLSHCR2_ARDSEQID_MASK);
+
+  config_value |=
+      FLEXSPI_FLSHCR2_AWRWAITUNIT(config->ahb_write_wait_unit) |
+      FLEXSPI_FLSHCR2_AWRWAIT(config->ahb_write_wait_interval);
+
+  if (config->awr_seq_number > 0u)
+    {
+      config_value |= FLEXSPI_FLSHCR2_AWRSEQID(
+                       (uint32_t)config->awr_seq_index) |
+                      FLEXSPI_FLSHCR2_AWRSEQNUM(
+                       (uint32_t)config->awr_seq_number - 1u);
+    }
+
+  if (config->ard_seq_number > 0u)
+    {
+      config_value |= FLEXSPI_FLSHCR2_ARDSEQID(
+                       (uint32_t)config->ard_seq_index) |
+                      FLEXSPI_FLSHCR2_ARDSEQNUM(
+                       (uint32_t)config->ard_seq_number - 1u);
+    }
+
+  base->FLSHCR2[port] = config_value;
+
+  /* Configure DLL */
+
+  config_value        = imx9_flexspi_configure_dll(base, config);
+  base->DLLCR[index] = config_value;
+
+  /* Configure write mask */
+
+  if (config->enable_write_mask)
+    {
+      base->FLSHCR4 &= ~FLEXSPI_FLSHCR4_WMOPT1_MASK;
+    }
+  else
+    {
+      base->FLSHCR4 |= FLEXSPI_FLSHCR4_WMOPT1_MASK;
+    }
+
+  if (index == 0u) /* Port A */
+    {
+      base->FLSHCR4 &= ~FLEXSPI_FLSHCR4_WMENA_MASK;
+      base->FLSHCR4 |= FLEXSPI_FLSHCR4_WMENA(config->enable_write_mask);
+    }
+  else
+    {
+      base->FLSHCR4 &= ~FLEXSPI_FLSHCR4_WMENB_MASK;
+      base->FLSHCR4 |= FLEXSPI_FLSHCR4_WMENB(config->enable_write_mask);
+    }
+
+  /* Set RX Sample Clock */
+
+  config_value = base->MCR0;
+  config_value &= ~FLEXSPI_MCR0_RXCLKSRC_MASK;
+  config_value |= FLEXSPI_MCR0_RXCLKSRC(config->rx_sample_clock);
+
+  /* Exit stop mode */
+
+  config_value &= ~FLEXSPI_MCR0_MDIS_MASK;
+
+  base->MCR0 = config_value;
+
+  /* According to ERR011377, need to delay at least 100 NOPs to ensure the
+   * DLL is locked.
+   */
+
+  status_value =
+      (index == 0u) ?
+          ((uint32_t)FLEXSPI_FLASH_A_SAMPLE_CLOCK_SLAVE_DELAY_LOCKED |
+           (uint32_t)FLEXSPI_FLASH_A_SAMPLE_CLOCK_REF_DELAY_LOCKED) :
+          ((uint32_t)FLEXSPI_FLASH_B_SAMPLE_CLOCK_SLAVE_DELAY_LOCKED |
+           (uint32_t)FLEXSPI_FLASH_B_SAMPLE_CLOCK_REF_DELAY_LOCKED);
+
+  if (0u != (config_value & FLEXSPI_DLLCR_DLLEN_MASK))
+    {
+      /* Wait slave delay line locked and slave reference delay line locked */
+
+      while ((base->STS2 & status_value) != status_value)
+        {
+        }
+
+      /* Wait at least 100 NOPs */
+
+      for (uint8_t delay = 100u; delay > 0u; delay--)
+        {
+          asm("NOP");
+        }
+    }
+}
+
+/* Updates the LUT table.
+ *
+ * param base  FLEXSPI peripheral base address.
+ * param index From which index start to update.
+ *             It could be any index of the LUT table, which also allows
+ *             user to update command content inside a command. Each command
+ *             consists of up to 8 instructions and occupy 4*32-bit memory.
+ * param cmd   Command sequence array.
+ * param count Number of sequences.
+ */
+
+void imx9_flexspi_update_lut_private(struct flexspi_type_s *base,
+                                      uint32_t index,
+                                      const uint32_t *cmd,
+                                      uint32_t count)
+{
+  assert(index < 128u);
+
+  uint32_t i = 0;
+  volatile uint32_t *lut_base;
+
+  /* Wait for bus idle before change flash configuration */
+
+  while (!imx9_flexspi_get_bus_idle_status(base))
+    {
+    }
+
+  /* Unlock LUT for update */
+
+  base->LUTKEY = FLEXSPI_LUT_KEY_VAL;
+  base->LUTCR  = 0x02;
+
+  lut_base = &base->LUT[index];
+  for (i = 0; i < count; i++)
+    {
+      *lut_base++ = *cmd++;
+    }
+
+  /* Lock LUT */
+
+  base->LUTKEY = FLEXSPI_LUT_KEY_VAL;
+  base->LUTCR  = 0x01;
+}
+
+/* Sends a buffer of data bytes using blocking method.
+ * note This function blocks via polling until all bytes have been sent.
+ * param base FLEXSPI peripheral base address
+ * param buffer The data bytes to send
+ * param size The number of data bytes to send
+ * retval 0 write success without error
+ * STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT sequence execution timeout
+ * STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR IP command sequence error
+ * detected
+ * STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT IP command grant
+ * timeout detected.
+ */
+
+static int imx9_flexspi_write_blocking(struct flexspi_type_s *base,
+                                        uint32_t *buffer, size_t size)
+{
+  uint32_t tx_watermark = ((base->IPTXFCR & FLEXSPI_IPTXFCR_TXWMRK_MASK) >>
+                           FLEXSPI_IPTXFCR_TXWMRK_SHIFT) + 1u;
+  uint32_t status;
+  int result = 0;
+  uint32_t i      = 0;
+
+  /* Send data buffer */
+
+  while (0u != size)
+    {
+      /* Wait until there is room in the fifo. This also checks for errors */
+
+      while (0u == ((status = base->INTR) &
+             (uint32_t)FLEXSPI_IP_TX_FIFO_WATERMARK_EMPTY_FLAG))
+        {
+        }
+
+      result = imx9_flexspi_check_and_clear_error(base, status);
+
+      if (0 != result)
+        {
+          return result;
+        }
+
+      /* Write watermark level data into tx fifo  */
+
+      if (size >= 8u * tx_watermark)
+        {
+          for (i = 0u; i < 2u * tx_watermark; i++)
+            {
+              base->TFDR[i] = *buffer++;
+            }
+
+          size = size - 8u * tx_watermark;
+        }
+      else
+        {
+          for (i = 0u; i < (size / 4u + 1u); i++)
+            {
+              base->TFDR[i] = *buffer++;
+            }
+          size = 0u;
+        }
+
+      /* Push a watermark level data into IP TX FIFO */
+
+      base->INTR |= (uint32_t)FLEXSPI_IP_TX_FIFO_WATERMARK_EMPTY_FLAG;
+    }
+
+  return result;
+}
+
+/* Receives a buffer of data bytes using a blocking method.
+ * note This function blocks via polling until all bytes have been sent.
+ * param base FLEXSPI peripheral base address
+ * param buffer The data bytes to send
+ * param size The number of data bytes to receive
+ * retval 0 read success without error
+ * retval STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT sequence execution
+ * timeout retval STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR IP command
+ * sequence error detected retval STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT
+ * IP command grant timeout detected.
+ */
+
+static int imx9_flexspi_read_blocking(struct flexspi_type_s *base,
+                                       uint32_t *buffer, size_t size)
+{
+  uint32_t rx_watermark = ((base->IPRXFCR & FLEXSPI_IPRXFCR_RXWMRK_MASK) >>
+                          FLEXSPI_IPRXFCR_RXWMRK_SHIFT) + 1u;
+  uint32_t status;
+  int result = 0;
+  uint32_t i = 0;
+  bool is_return   = false;
+
+  /* Send data buffer */
+
+  while (0u != size)
+    {
+      if (size >= 8u * rx_watermark)
+        {
+          /* Wait until there is room in the fifo. This also checks for
+           * errors.
+           */
+
+          while (0u == ((status = base->INTR) &
+                 (uint32_t)FLEXSPI_IP_RX_FIFO_WATERMARK_AVAILABLE_FLAG))
+            {
+              result = imx9_flexspi_check_and_clear_error(base, status);
+
+              if (0 != result)
+                {
+                  is_return = true;
+                  break;
+                }
+            }
+        }
+      else
+        {
+          /* Wait fill level. This also checks for errors */
+
+          while (size > ((((base->IPRXFSTS) & FLEXSPI_IPRXFSTS_FILL_MASK) >>
+                 FLEXSPI_IPRXFSTS_FILL_SHIFT) * 8u))
+            {
+              result = imx9_flexspi_check_and_clear_error(base, base->INTR);
+
+              if (0 != result)
+                {
+                  is_return = true;
+                  break;
+                }
+            }
+        }
+
+      if (is_return)
+        {
+          break;
+        }
+
+      result = imx9_flexspi_check_and_clear_error(base, base->INTR);
+
+      if (0 != result)
+        {
+          break;
+        }
+
+      /* Read watermark level data from rx fifo  */
+
+      if (size >= 8u * rx_watermark)
+        {
+          for (i = 0u; i < 2u * rx_watermark; i++)
+            {
+              *buffer++ = base->RFDR[i];
+            }
+
+          size = size - 8u * rx_watermark;
+        }
+      else
+        {
+          for (i = 0u; i < ((size + 3u) / 4u); i++)
+            {
+              *buffer++ = base->RFDR[i];
+            }
+          size = 0;
+        }
+
+      /* Pop out a watermark level datas from IP RX FIFO */
+
+      base->INTR |= (uint32_t)FLEXSPI_IP_RX_FIFO_WATERMARK_AVAILABLE_FLAG;
+    }
+
+  return result;
+}
+
+/* Brief Execute command to transfer a buffer data bytes using a blocking
+ * method. param base FLEXSPI peripheral base address param xfer pointer to
+ * the transfer structure. retval 0 command transfer success without error
+ * retval STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT sequence execution
+ * timeout retval STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR IP command
+ * sequence error detected retval STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT
+ * IP command grant timeout detected.
+ */
+
+int imx9_flexspi_transfer_blocking_private(struct flexspi_type_s *base,
+                                            struct flexspi_transfer_s *xfer)
+{
+  uint32_t config_value = 0;
+  int result      = 0;
+
+  /* Clear sequence pointer before sending data to external devices */
+
+  base->FLSHCR2[xfer->port] |= FLEXSPI_FLSHCR2_CLRINSTRPTR_MASK;
+
+  /* Clear former pending status before start this transfer */
+
+  base->INTR |= FLEXSPI_INTR_AHBCMDERR_MASK |
+                FLEXSPI_INTR_IPCMDERR_MASK |
+                FLEXSPI_INTR_AHBCMDGE_MASK |
+                FLEXSPI_INTR_IPCMDGE_MASK;
+
+  /* Configure base address */
+
+  base->IPCR0 = xfer->device_address;
+
+  /* Reset fifos */
+
+  base->IPTXFCR |= FLEXSPI_IPTXFCR_CLRIPTXF_MASK;
+  base->IPRXFCR |= FLEXSPI_IPRXFCR_CLRIPRXF_MASK;
+
+  /* Configure data size */
+
+  if ((xfer->cmd_type == FLEXSPI_READ)  ||
+      (xfer->cmd_type == FLEXSPI_WRITE) ||
+      (xfer->cmd_type == FLEXSPI_CONFIG))
+    {
+      config_value = FLEXSPI_IPCR1_IDATSZ(xfer->data_size);
+    }
+
+  /* Configure sequence ID */
+
+  config_value |=
+      FLEXSPI_IPCR1_ISEQID((uint32_t)xfer->seq_index) | \
+      FLEXSPI_IPCR1_ISEQNUM((uint32_t)xfer->seq_number - 1u);
+  base->IPCR1 = config_value;
+
+  /* Start Transfer */
+
+  base->IPCMD |= FLEXSPI_IPCMD_TRG_MASK;
+
+  if ((xfer->cmd_type == FLEXSPI_WRITE) ||
+      (xfer->cmd_type == FLEXSPI_CONFIG))
+    {
+      result = imx9_flexspi_write_blocking(base, xfer->data,
+                                            xfer->data_size);
+    }
+  else if (xfer->cmd_type == FLEXSPI_READ)
+    {
+      result = imx9_flexspi_read_blocking(base, xfer->data,
+                                           xfer->data_size);
+    }
+
+  /* Wait for bus idle */
+
+  while (!imx9_flexspi_get_bus_idle_status(base))
+    {
+    }
+
+  if (xfer->cmd_type == FLEXSPI_COMMAND)
+    {
+      result = imx9_flexspi_check_and_clear_error(base, base->INTR);
+    }
+
+  return result;
+}
+
+/****************************************************************************
+ * Name: imx9_flexspi_lock
+ *
+ * Description:
+ *   On FlexSPI buses where there are multiple devices, it will be necessary
+ *   to lock FlexSPI to have exclusive access to the buses for a sequence of
+ *   transfers.  The bus should be locked before the chip is selected.
+ *
+ * Input Parameters:
+ *   dev  - Device-specific state data
+ *   lock - true: Lock FlexSPI bus, false: unlock FlexSPI bus
+ *
+ * Returned Value:
+ *   Semaphore status
+ *
+ ****************************************************************************/
+
+static int imx9_flexspi_lock(struct flexspi_dev_s *dev, bool lock)
+{
+  struct imx9_flexspidev_s *priv = (struct imx9_flexspidev_s *)dev;
+  int ret;
+
+  spiinfo("lock=%d\n", lock);
+  if (lock)
+    {
+      ret = nxmutex_lock(&priv->lock);
+    }
+  else
+    {
+      ret = nxmutex_unlock(&priv->lock);
+    }
+
+  return ret;
+}
+
+/****************************************************************************
+ * Name: imx9_flexspi_transfer_blocking
+ *
+ * Description:
+ *   Perform one FlexSPI transfer
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   xfer    - Describes the transfer to be performed.
+ *
+ * Returned Value:
+ *   0 on SUCCESS, STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT,
+ *   STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR or
+ *   STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT otherwise
+ *
+ ****************************************************************************/
+
+static int imx9_flexspi_transfer_blocking(struct flexspi_dev_s *dev,
+                                           struct flexspi_transfer_s *xfer)
+{
+  struct imx9_flexspidev_s *priv = (struct imx9_flexspidev_s *)dev;
+
+  return (int)imx9_flexspi_transfer_blocking_private(priv->base, xfer);
+}
+
+/****************************************************************************
+ * Name: imx9_flexspi_software_reset
+ *
+ * Description:
+ *   Performs a software reset of FlexSPI
+ *
+ * Input Parameters:
+ *   dev  - Device-specific state data
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+static void imx9_flexspi_software_reset(struct flexspi_dev_s *dev)
+{
+  struct imx9_flexspidev_s *priv = (struct imx9_flexspidev_s *)dev;
+
+  imx9_flexspi_software_reset_private(priv->base);
+}
+
+/****************************************************************************
+ * Name: imx9_flexspi_update_lut
+ *
+ * Description:
+ *   Perform FlexSPI LUT table update
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   index   - Index start to update
+ *   cmd     - Command array
+ *   count   - Size of the array
+ *
+ * Returned Value:
+ *   none
+ *
+ ****************************************************************************/
+
+static void imx9_flexspi_update_lut(struct flexspi_dev_s *dev,
+                                     uint32_t index,
+                                     const uint32_t *cmd,
+                                     uint32_t count)
+{
+  struct imx9_flexspidev_s *priv = (struct imx9_flexspidev_s *)dev;
+
+  imx9_flexspi_update_lut_private(priv->base, index, cmd, count);
+}
+
+/****************************************************************************
+ * Name: imx9_flexspi_set_device_config
+ *
+ * Description:
+ *   Perform FlexSPI device config
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   config  - Config data for external device
+ *   port    - Port
+ *
+ * Returned Value:
+ *   none
+ *
+ ****************************************************************************/
+
+static void imx9_flexspi_set_device_config(struct flexspi_dev_s *dev,
+                                    struct flexspi_device_config_s *config,
+                                    enum flexspi_port_e port)
+{
+  struct imx9_flexspidev_s *priv = (struct imx9_flexspidev_s *)dev;
+
+  imx9_flexspi_set_device_config_private(priv->base, config, port);
+}
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: imx9_flexspi_initialize
+ *
+ * Description:
+ *   Initialize the selected FlexSPI port in master mode
+ *
+ * Input Parameters:
+ *   intf - Interface number(must be zero)
+ *
+ * Returned Value:
+ *   Valid FlexSPI device structure reference on success; a NULL on failure
+ *
+ ****************************************************************************/
+
+struct flexspi_dev_s *imx9_flexspi_initialize(int intf)
+{
+  struct imx9_flexspidev_s *priv;
+  struct flexspi_config_s flexspi_config;
+
+  /* The supported i.MX9 parts have only a single FlexSPI port. */
+
+  DEBUGASSERT(intf == 0);
+
+  if (intf != 0)
+    {
+      return NULL;
+    }
+
+  /* If this function is called multiple times, the following operations
+   * will be performed multiple times.
+   */
+
+  /* Select FlexSPI */
+
+  priv = &g_flexspi0dev;
+
+  /* Enable clocking to the FlexSPI peripheral */
+
+  imx9_ccm_gate_on(CCM_LPCG_FLEXSPI1, true);
+
+  /* Configure clock to safe 50MHz, src clock is 800Mhz */
+
+  imx9_ccm_configure_root_clock(CCM_CR_FLEXSPI1, SYS_PLL1PFD1, 16);
+
+  /* Has the FlexSPI hardware been initialized? */
+
+  if (!priv->initialized)
+    {
+      /* Perform hardware initialization. Puts the FlexSPI into an active
+       * state.
+       */
+
+      imx9_flexspi_get_default_config(&flexspi_config);
+      imx9_flexspi_init(priv->base, &flexspi_config);
+      priv->initialized = true;
+    }
+
+  return &priv->flexspi;
+}
+
+#endif /* CONFIG_IMX9_FLEXSPI */
diff --git a/arch/arm64/src/imx9/imx9_flexspi.h 
b/arch/arm64/src/imx9/imx9_flexspi.h
new file mode 100644
index 0000000000..012197d599
--- /dev/null
+++ b/arch/arm64/src/imx9/imx9_flexspi.h
@@ -0,0 +1,573 @@
+/****************************************************************************
+ * arch/arm64/src/imx9/imx9_flexspi.h
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+#ifndef __ARCH_ARM64_SRC_IMX9_IMX9_FLEXSPI_H
+#define __ARCH_ARM64_SRC_IMX9_IMX9_FLEXSPI_H
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <nuttx/config.h>
+
+#include <stdint.h>
+#include <stdbool.h>
+
+#include "chip.h"
+
+#ifdef CONFIG_IMX9_FLEXSPI
+
+/****************************************************************************
+ * Pre-processor Definitions
+ ****************************************************************************/
+
+/* LUT - LUT 0..LUT 63 */
+
+#define FLEXSPI_LUT_OPERAND0_MASK                (0xffU)
+#define FLEXSPI_LUT_OPERAND0_SHIFT               (0U)
+
+/* OPERAND0 */
+
+#define FLEXSPI_LUT_OPERAND0(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_OPERAND0_SHIFT)) & FLEXSPI_LUT_OPERAND0_MASK)
+#define FLEXSPI_LUT_NUM_PADS0_MASK               (0x300U)
+#define FLEXSPI_LUT_NUM_PADS0_SHIFT              (8U)
+
+/* NUM_PADS0 */
+
+#define FLEXSPI_LUT_NUM_PADS0(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_NUM_PADS0_SHIFT)) & FLEXSPI_LUT_NUM_PADS0_MASK)
+#define FLEXSPI_LUT_OPCODE0_MASK                 (0xfc00U)
+#define FLEXSPI_LUT_OPCODE0_SHIFT                (10U)
+
+/* OPCODE0 */
+
+#define FLEXSPI_LUT_OPCODE0(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_OPCODE0_SHIFT)) & FLEXSPI_LUT_OPCODE0_MASK)
+#define FLEXSPI_LUT_OPERAND1_MASK                (0xff0000U)
+#define FLEXSPI_LUT_OPERAND1_SHIFT               (16U)
+
+/* OPERAND1 */
+
+#define FLEXSPI_LUT_OPERAND1(x)                  (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_OPERAND1_SHIFT)) & FLEXSPI_LUT_OPERAND1_MASK)
+#define FLEXSPI_LUT_NUM_PADS1_MASK               (0x3000000U)
+#define FLEXSPI_LUT_NUM_PADS1_SHIFT              (24U)
+
+/* NUM_PADS1 - NUM_PADS1 */
+
+#define FLEXSPI_LUT_NUM_PADS1(x)                 (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_NUM_PADS1_SHIFT)) & FLEXSPI_LUT_NUM_PADS1_MASK)
+#define FLEXSPI_LUT_OPCODE1_MASK                 (0xfc000000U)
+#define FLEXSPI_LUT_OPCODE1_SHIFT                (26U)
+
+/* OPCODE1 */
+
+#define FLEXSPI_LUT_OPCODE1(x)                   (((uint32_t)(((uint32_t)(x)) 
<< FLEXSPI_LUT_OPCODE1_SHIFT)) & FLEXSPI_LUT_OPCODE1_MASK)
+
+/* Formula to form FLEXSPI instructions in LUT table */
+
+#define FLEXSPI_LUT_SEQ(cmd0, pad0, op0, cmd1, pad1, op1) \
+    (FLEXSPI_LUT_OPERAND0(op0) | FLEXSPI_LUT_NUM_PADS0(pad0) | \
+     FLEXSPI_LUT_OPCODE0(cmd0) | FLEXSPI_LUT_OPERAND1(op1) | \
+     FLEXSPI_LUT_NUM_PADS1(pad1) | FLEXSPI_LUT_OPCODE1(cmd1))
+
+/* Access macros ************************************************************/
+
+/****************************************************************************
+ * Name: FLEXSPI_LOCK
+ *
+ * Description:
+ *   On FlexSPI buses where there are multiple devices, it will be necessary
+ *   to lock FlexSPI to have exclusive access to the buses for a sequence of
+ *   transfers.  The bus should be locked before the chip is selected.
+ *
+ * Input Parameters:
+ *   dev  - Device-specific state data
+ *   lock - true: Lock FlexSPI bus, false: unlock FlexSPI bus
+ *
+ * Returned Value:
+ *   None
+ *
+ ****************************************************************************/
+
+#define FLEXSPI_LOCK(d,l) (d)->ops->lock(d,l)
+
+/****************************************************************************
+ * Name: FLEXSPI_TRANSFER
+ *
+ * Description:
+ *   Perform one FlexSPI transfer
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   xfer    - Describes the transfer to be performed.
+ *
+ * Returned Value:
+ *   0 on SUCCESS, STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT,
+ *   STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR or
+ *   STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT otherwise
+ *
+ ****************************************************************************/
+
+#define FLEXSPI_TRANSFER(d,x) (d)->ops->transfer_blocking(d,x)
+
+/****************************************************************************
+ * Name: FLEXSPI_SOFTWARE_RESET
+ *
+ * Description:
+ *   Perform FlexSPI software reset
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *
+ * Returned Value:
+ *   none
+ *
+ ****************************************************************************/
+
+#define FLEXSPI_SOFTWARE_RESET(d) (d)->ops->software_reset(d)
+
+/****************************************************************************
+ * Name: FLEXSPI_UPDATE_LUT
+ *
+ * Description:
+ *   Perform FlexSPI LUT table update
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   index   - Index start to update
+ *   cmd     - Command array
+ *   count   - Size of the array
+ *
+ * Returned Value:
+ *   none
+ *
+ ****************************************************************************/
+
+#define FLEXSPI_UPDATE_LUT(d,i,c,n) (d)->ops->update_lut(d,i,c,n)
+
+/****************************************************************************
+ * Name: FLEXSPI_SET_DEVICE_CONFIG
+ *
+ * Description:
+ *   Perform FlexSPI device config
+ *
+ * Input Parameters:
+ *   dev     - Device-specific state data
+ *   config  - Config data for external device
+ *   port    - Port
+ *
+ * Returned Value:
+ *   none
+ *
+ ****************************************************************************/
+
+#define FLEXSPI_SET_DEVICE_CONFIG(d,c,p) (d)->ops->set_device_config(d,c,p)
+
+/****************************************************************************
+ * Public Types
+ ****************************************************************************/
+
+/* CMD definition of FLEXSPI, use to form LUT instruction, flexspi_command */
+
+enum
+{
+  FLEXSPI_COMMAND_STOP           = 0x00,  /* Stop execution, deassert CS */
+  FLEXSPI_COMMAND_SDR            = 0x01,  /* Transmit Command code to Flash,
+                                           * using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_RADDR_SDR      = 0x02,  /* Transmit Row Address to Flash,
+                                           * using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_CADDR_SDR      = 0x03,  /* Transmit Column Address to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE1_SDR      = 0x04,  /* Transmit 1-bit Mode bits to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE2_SDR      = 0x05,  /* Transmit 2-bit Mode bits to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE4_SDR      = 0x06,  /* Transmit 4-bit Mode bits to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE8_SDR      = 0x07,  /* Transmit 8-bit Mode bits to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_WRITE_SDR      = 0x08,  /* Transmit Programming Data to
+                                           * Flash, using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_READ_SDR       = 0x09,  /* Receive Read Data from Flash,
+                                           * using SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_LEARN_SDR      = 0x0a,  /* Receive Read Data or Preamble
+                                           * bit from Flash, SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_DATSZ_SDR      = 0x0b,  /* Transmit Read/Program Data size
+                                           * (byte) to Flash, SDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_DUMMY_SDR      = 0x0c,  /* Leave data lines undriven by
+                                           * FlexSPI controller.
+                                           */
+
+  FLEXSPI_COMMAND_DUMMY_RWDS_SDR = 0x0d,  /* Leave data lines undriven by
+                                           * FlexSPI controller, dummy cycles
+                                           * decided by RWDS.
+                                           */
+
+  FLEXSPI_COMMAND_DDR            = 0x21,  /* Transmit Command code to Flash,
+                                           * using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_RADDR_DDR      = 0x22,  /* Transmit Row Address to Flash,
+                                           * using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_CADDR_DDR      = 0x23,  /* Transmit Column Address to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE1_DDR      = 0x24,  /* Transmit 1-bit Mode bits to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE2_DDR      = 0x25,  /* Transmit 2-bit Mode bits to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE4_DDR      = 0x26,  /* Transmit 4-bit Mode bits to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_MODE8_DDR      = 0x27,  /* Transmit 8-bit Mode bits to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_WRITE_DDR      = 0x28,  /* Transmit Programming Data to
+                                           * Flash, using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_READ_DDR       = 0x29,  /* Receive Read Data from Flash,
+                                           * using DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_LEARN_DDR      = 0x2a,  /* Receive Read Data or Preamble
+                                           * bit from Flash, DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_DATSZ_DDR      = 0x2b,  /* Transmit Read/Program Data size
+                                           * (byte) to Flash, DDR mode.
+                                           */
+
+  FLEXSPI_COMMAND_DUMMY_DDR      = 0x2c,  /* Leave data lines undriven by
+                                           * FlexSPI controller.
+                                           */
+
+  FLEXSPI_COMMAND_DUMMY_RWDS_DDR = 0x2d,  /* Leave data lines undriven by
+                                           * FlexSPI controller, dummy cycles
+                                           * decided by RWDS.
+                                           */
+
+  FLEXSPI_COMMAND_JUMP_ON_CS     = 0x1f,  /* Stop execution, deassert CS and
+                                           * save operand[7:0] as the
+                                           * instruction start pointer for
+                                           * next sequence
+                                           */
+};
+
+/* Pad definition of FLEXSPI, use to form LUT instruction */
+
+enum flexspi_pad_e
+{
+  FLEXSPI_1PAD = 0x00,  /* Transmit command/address and transmit/receive data
+                         * only through DATA0/DATA1.
+                         */
+
+  FLEXSPI_2PAD = 0x01,  /* Transmit command/address and transmit/receive data
+                         * only through DATA[1:0].
+                         */
+
+  FLEXSPI_4PAD = 0x02,  /* Transmit command/address and transmit/receive data
+                         * only through DATA[3:0].
+                         */
+
+  FLEXSPI_8PAD = 0x03,  /* Transmit command/address and transmit/receive data
+                         * only through DATA[7:0].
+                         */
+};
+
+/* FLEXSPI operation port select */
+
+enum flexspi_port_e
+{
+  FLEXSPI_PORT_A1 = 0x0,  /* Access flash on A1 port */
+  FLEXSPI_PORT_A2,        /* Access flash on A2 port */
+  FLEXSPI_PORT_B1,        /* Access flash on B1 port */
+  FLEXSPI_PORT_B2,        /* Access flash on B2 port */
+  FLEXSPI_PORT_COUNT
+};
+
+/* Command type */
+
+enum flexspi_command_type_e
+{
+  FLEXSPI_COMMAND, /* FlexSPI operation: Only command, both TX and Rx buffer
+                    * are ignored.
+                    */
+
+  FLEXSPI_CONFIG,  /* FlexSPI operation: Configure device mode, the TX fifo
+                    * size is fixed in LUT.
+                    */
+
+  FLEXSPI_READ,    /* FlexSPI operation: Read, only Rx Buffer is
+                    * effective.
+                    */
+
+  FLEXSPI_WRITE,   /* FlexSPI operation: Read, only Tx Buffer is
+                    * effective.
+                    */
+};
+
+/* Status structure of FLEXSPI */
+
+enum
+{
+  STATUS_FLEXSPI_BUSY = 0,                        /* FLEXSPI is busy */
+
+  STATUS_FLEXSPI_SEQUENCE_EXECUTION_TIMEOUT = 1,  /* Sequence execution
+                                                   * timeout error occurred
+                                                   * during FLEXSPI transfer.
+                                                   */
+
+  STATUS_FLEXSPI_IP_COMMAND_SEQUENCE_ERROR = 2,   /* IP command Sequence
+                                                   * execution timeout error
+                                                   * occurred during FLEXSPI
+                                                   * transfer.
+                                                   */
+
+  STATUS_FLEXSPI_IP_COMMAND_GRANT_TIMEOUT = 3,    /* IP command grant timeout
+                                                   * error occurred during
+                                                   * FLEXSPI transfer.
+                                                   */
+};
+
+/* Transfer structure for FLEXSPI */
+
+struct flexspi_transfer_s
+{
+  uint32_t device_address;              /* Operation device address */
+  enum flexspi_port_e port;             /* Operation port */
+  enum flexspi_command_type_e cmd_type; /* Execution command type */
+  uint8_t seq_index;                    /* Sequence ID for command */
+  uint8_t seq_number;                   /* Sequence number for command */
+  uint32_t *data;                       /* Data buffer */
+  size_t data_size;                     /* Data size in bytes */
+};
+
+/* FLEXSPI interval unit for flash device select */
+
+enum flexspi_cs_interval_cycle_unit_e
+{
+  FLEXSPI_CS_INTERVAL_UNIT1_SCK_CYCLE   = 0x0,  /* Chip selection interval:
+                                                 * CSINTERVAL * 1 serial
+                                                 * clock cycle.
+                                                 */
+
+  FLEXSPI_CS_INTERVAL_UNIT256_SCK_CYCLE = 0x1,  /* Chip selection interval:
+                                                 * CSINTERVAL * 256 serial
+                                                 * clock cycle.
+                                                 */
+};
+
+/* FLEXSPI AHB wait interval unit for writing */
+
+enum flexspi_ahb_write_wait_unit_e
+{
+  FLEXSPI_AHB_WRITE_WAIT_UNIT2_AHB_CYCLE     = 0x0,  /* AWRWAIT unit is 2
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT8_AHB_CYCLE     = 0x1,  /* AWRWAIT unit is 8
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT32_AHB_CYCLE    = 0x2,  /* AWRWAIT unit is 32
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT128_AHB_CYCLE   = 0x3,  /* AWRWAIT unit is 128
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT512_AHB_CYCLE   = 0x4,  /* AWRWAIT unit is 512
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT2048_AHB_CYCLE  = 0x5,  /* AWRWAIT unit is 2048
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT8192_AHB_CYCLE  = 0x6,  /* AWRWAIT unit is 8192
+                                                      * ahb clock cycle.
+                                                      */
+
+  FLEXSPI_AHB_WRITE_WAIT_UNIT32768_AHB_CYCLE = 0x7,  /* AWRWAIT unit is 32768
+                                                      * ahb clock cycle.
+                                                      */
+};
+
+/* FLEXSPI sample clock source selection for Flash Reading */
+
+enum flexspi_read_sample_clock_e
+{
+  FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_INTERNALLY =         0x0u,      /* Dummy 
Read strobe generated by FlexSPI Controller
+                                                                    * and 
loopback internally */
+
+  FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_FROM_DQS_PAD =       0x1u,      /* Dummy 
Read strobe generated by FlexSPI Controller
+                                                                    * and 
loopback from DQS pad */
+
+  FLEXSPI_READ_SAMPLE_CLK_LOOPBACK_FROM_SCK_PAD =       0x2u, /* SCK output 
clock and loopback from SCK pad */
+
+  FLEXSPI_READ_SAMPLE_CLK_EXTERNAL_INPUT_FROM_DQS_PAD = 0x3u, /* Flash 
provided Read strobe and input from DQS pad */
+};
+
+/* External device configuration items */
+
+struct flexspi_device_config_s
+{
+  uint32_t flexspi_root_clk; /* FLEXSPI serial root clock */
+  bool is_sck2_enabled;      /* FLEXSPI use SCK2 */
+  uint32_t flash_size;       /* Flash size in KByte */
+
+  enum flexspi_cs_interval_cycle_unit_e cs_interval_unit; /* CS interval unit, 
1
+                                                      * or 256 cycle.
+                                                      */
+
+  uint16_t cs_interval;     /* CS line assert interval, multiply CS
+                             * interval unit to get the CS line assert
+                             * interval cycles.
+                             */
+
+  uint8_t cs_hold_time;     /* CS line hold time */
+  uint8_t cs_setup_time;    /* CS line setup time */
+  uint8_t data_valid_time;  /* Data valid time for external device */
+  uint8_t columnspace;      /* Column space size */
+  bool enable_word_address; /* If enable word address */
+  uint8_t awr_seq_index;    /* Sequence ID for AHB write command */
+  uint8_t awr_seq_number;   /* Sequence number for AHB write command */
+  uint8_t ard_seq_index;    /* Sequence ID for AHB read command */
+  uint8_t ard_seq_number;   /* Sequence number for AHB read command */
+
+  enum flexspi_ahb_write_wait_unit_e ahb_write_wait_unit;  /* AHB write wait 
unit */
+
+  uint16_t ahb_write_wait_interval;  /* AHB write wait interval, multiply AHB
+                                      * write interval unit to get the AHB
+                                      * write wait cycles.
+                                      */
+
+  bool enable_write_mask;   /* Enable/Disable FLEXSPI drive DQS pin as write 
mask
+                             * when writing to external device.
+                             */
+
+  enum flexspi_read_sample_clock_e rx_sample_clock; /* Sample Clock source 
selection for Flash Reading */
+};
+
+/* The FlexSPI vtable */
+
+struct flexspi_dev_s;
+struct flexspi_ops_s
+{
+  int (*lock)(struct flexspi_dev_s *dev, bool lock);
+  int (*transfer_blocking)(struct flexspi_dev_s *dev,
+                           struct flexspi_transfer_s *xfer);
+  void (*software_reset)(struct flexspi_dev_s *dev);
+  void (*update_lut)(struct flexspi_dev_s *dev,
+                     uint32_t index, const uint32_t *cmd,
+                     uint32_t count);
+  void (*set_device_config)(struct flexspi_dev_s *dev,
+                            struct flexspi_device_config_s *config,
+                            enum flexspi_port_e port);
+};
+
+/* FlexSPI private data.  This structure only defines the initial fields of
+ * the structure visible to the FlexSPI client.  The specific implementation
+ * may add additional, device specific fields
+ */
+
+struct flexspi_dev_s
+{
+  const struct flexspi_ops_s *ops;
+};
+
+/****************************************************************************
+ * Inline Functions
+ ****************************************************************************/
+
+#ifndef __ASSEMBLY__
+
+/****************************************************************************
+ * Public Data
+ ****************************************************************************/
+
+#undef EXTERN
+#if defined(__cplusplus)
+#define EXTERN extern "C"
+extern "C"
+{
+#else
+#define EXTERN extern
+#endif
+
+/****************************************************************************
+ * Public Function Prototypes
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: imx9_flexspi_initialize
+ *
+ * Description:
+ *   Initialize the selected FlexSPI port in master mode
+ *
+ * Input Parameters:
+ *   intf - Interface number(must be zero)
+ *
+ * Returned Value:
+ *   Valid FlexSPI device structure reference on success; a NULL on failure
+ *
+ ****************************************************************************/
+
+struct flexspi_dev_s;
+struct flexspi_dev_s *imx9_flexspi_initialize(int intf);
+
+#undef EXTERN
+#if defined(__cplusplus)
+}
+#endif
+
+#endif /* __ASSEMBLY__ */
+#endif /* CONFIG_IMX9_FLEXSPI */
+#endif /* __ARCH_ARM_SRC_IMX9_IMX9_FLEXSPI_H */

Reply via email to