From a89103f67112453fa36c9513e951c19eed9d2d92 Mon Sep 17 00:00:00 2001 From: Haibo Chen Date: Mon, 22 Sep 2025 16:47:13 +0800 Subject: spi: spi-nxp-fspi: re-config the clock rate when operation require new clock rate Current operation contain the max_freq, so new coming operation may use new clock rate, need to re-config the clock rate to match the requirement. Fixes: 26851cf65ffc ("spi: nxp-fspi: Support per spi-mem operation frequency switches") Signed-off-by: Haibo Chen Link: https://patch.msgid.link/20250922-fspi-fix-v1-1-ff4315359d31@nxp.com Signed-off-by: Mark Brown --- drivers/spi/spi-nxp-fspi.c | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) (limited to 'drivers/spi/spi-nxp-fspi.c') diff --git a/drivers/spi/spi-nxp-fspi.c b/drivers/spi/spi-nxp-fspi.c index f9371f98a65b..4e82f9e900ac 100644 --- a/drivers/spi/spi-nxp-fspi.c +++ b/drivers/spi/spi-nxp-fspi.c @@ -404,6 +404,8 @@ struct nxp_fspi { #define FSPI_NEED_INIT BIT(0) #define FSPI_DTR_MODE BIT(1) int flags; + /* save the previous operation clock rate */ + unsigned long pre_op_rate; }; static inline int needs_ip_only(struct nxp_fspi *f) @@ -780,11 +782,17 @@ static void nxp_fspi_select_mem(struct nxp_fspi *f, struct spi_device *spi, uint64_t size_kb; /* - * Return, if previously selected target device is same as current - * requested target device. Also the DTR or STR mode do not change. + * Return when following condition all meet, + * 1, if previously selected target device is same as current + * requested target device. + * 2, the DTR or STR mode do not change. + * 3, previous operation max rate equals current one. + * + * For other case, need to re-config. */ if ((f->selected == spi_get_chipselect(spi, 0)) && - (!!(f->flags & FSPI_DTR_MODE) == op_is_dtr)) + (!!(f->flags & FSPI_DTR_MODE) == op_is_dtr) && + (f->pre_op_rate == op->max_freq)) return; /* Reset FLSHxxCR0 registers */ @@ -832,6 +840,8 @@ static void nxp_fspi_select_mem(struct nxp_fspi *f, struct spi_device *spi, else nxp_fspi_dll_override(f); + f->pre_op_rate = op->max_freq; + f->selected = spi_get_chipselect(spi, 0); } -- cgit v1.2.3 From b93b4269791fdebbac2a9ad26f324dc2abb9e60f Mon Sep 17 00:00:00 2001 From: Han Xu Date: Mon, 22 Sep 2025 16:47:14 +0800 Subject: spi: spi-nxp-fspi: add extra delay after dll locked Due to the erratum ERR050272, the DLL lock status register STS2 [xREFLOCK, xSLVLOCK] bit may indicate DLL is locked before DLL is actually locked. Add an extra 4us delay as a workaround. refer to ERR050272, on Page 20. https://www.nxp.com/docs/en/errata/IMX8_1N94W.pdf Fixes: 99d822b3adc4 ("spi: spi-nxp-fspi: use DLL calibration when clock rate > 100MHz") Signed-off-by: Han Xu Signed-off-by: Haibo Chen Link: https://patch.msgid.link/20250922-fspi-fix-v1-2-ff4315359d31@nxp.com Signed-off-by: Mark Brown --- drivers/spi/spi-nxp-fspi.c | 6 ++++++ 1 file changed, 6 insertions(+) (limited to 'drivers/spi/spi-nxp-fspi.c') diff --git a/drivers/spi/spi-nxp-fspi.c b/drivers/spi/spi-nxp-fspi.c index 4e82f9e900ac..96b3654b45ab 100644 --- a/drivers/spi/spi-nxp-fspi.c +++ b/drivers/spi/spi-nxp-fspi.c @@ -721,6 +721,12 @@ static void nxp_fspi_dll_calibration(struct nxp_fspi *f) 0, POLL_TOUT, true); if (ret) dev_warn(f->dev, "DLL lock failed, please fix it!\n"); + + /* + * For ERR050272, DLL lock status bit is not accurate, + * wait for 4us more as a workaround. + */ + udelay(4); } /* -- cgit v1.2.3 From f43579ef3500527649b1c233be7cf633806353aa Mon Sep 17 00:00:00 2001 From: Haibo Chen Date: Mon, 22 Sep 2025 16:47:15 +0800 Subject: spi: spi-nxp-fspi: limit the clock rate for different sample clock source selection For different sample clock source selection, the max frequency flexspi supported are different. For mode 0, max frequency is 66MHz. For mode 3, the max frequency is 166MHz. Refer to 3.9.9 FlexSPI timing parameters on page 65. https://www.nxp.com/docs/en/data-sheet/IMX8MNCEC.pdf Though flexspi maybe still work under higher frequency, but can't guarantee the stability. IC suggest to add this limitation on all SoCs which contain flexspi. Fixes: c07f27032317 ("spi: spi-nxp-fspi: add the support for sample data from DQS pad") Signed-off-by: Haibo Chen Link: https://patch.msgid.link/20250922-fspi-fix-v1-3-ff4315359d31@nxp.com Signed-off-by: Mark Brown --- drivers/spi/spi-nxp-fspi.c | 10 ++++++++-- 1 file changed, 8 insertions(+), 2 deletions(-) (limited to 'drivers/spi/spi-nxp-fspi.c') diff --git a/drivers/spi/spi-nxp-fspi.c b/drivers/spi/spi-nxp-fspi.c index 96b3654b45ab..b6c79e50d842 100644 --- a/drivers/spi/spi-nxp-fspi.c +++ b/drivers/spi/spi-nxp-fspi.c @@ -406,6 +406,8 @@ struct nxp_fspi { int flags; /* save the previous operation clock rate */ unsigned long pre_op_rate; + /* the max clock rate fspi output to device */ + unsigned long max_rate; }; static inline int needs_ip_only(struct nxp_fspi *f) @@ -687,10 +689,13 @@ static void nxp_fspi_select_rx_sample_clk_source(struct nxp_fspi *f, * change the mode back to mode 0. */ reg = fspi_readl(f, f->iobase + FSPI_MCR0); - if (op_is_dtr) + if (op_is_dtr) { reg |= FSPI_MCR0_RXCLKSRC(3); - else /*select mode 0 */ + f->max_rate = 166000000; + } else { /*select mode 0 */ reg &= ~FSPI_MCR0_RXCLKSRC(3); + f->max_rate = 66000000; + } fspi_writel(f, reg, f->iobase + FSPI_MCR0); } @@ -816,6 +821,7 @@ static void nxp_fspi_select_mem(struct nxp_fspi *f, struct spi_device *spi, dev_dbg(f->dev, "Target device [CS:%x] selected\n", spi_get_chipselect(spi, 0)); nxp_fspi_select_rx_sample_clk_source(f, op_is_dtr); + rate = min(f->max_rate, op->max_freq); if (op_is_dtr) { f->flags |= FSPI_DTR_MODE; -- cgit v1.2.3