spi: cadence-qspi: minimise register accesses on each op if !DTR
authorThéo Lebrun <theo.lebrun@bootlin.com>
Fri, 5 Apr 2024 15:02:16 +0000 (17:02 +0200)
committerMark Brown <broonie@kernel.org>
Mon, 8 Apr 2024 14:18:10 +0000 (15:18 +0100)
cqspi_enable_dtr() is called for each operation, commands or not, reads
or writes. It writes CQSPI_REG_CONFIG then waits for idle (three
successful reads). Skip that in the no-DTR case if DTR is already
disabled.

It cannot be skipped in the DTR case as cqspi_setup_opcode_ext() writes
to a register and we must wait for idle state.

According to ftrace, the average cqspi_exec_mem_op() call goes from
85.4µs to 83.6µs when reading 235M over UBIFS on an octal flash.

Signed-off-by: Théo Lebrun <theo.lebrun@bootlin.com>
Link: https://msgid.link/r/20240405-cdns-qspi-mbly-v2-6-956679866d6d@bootlin.com
Signed-off-by: Mark Brown <broonie@kernel.org>
drivers/spi/spi-cadence-quadspi.c

index abc1c35929cc65d1e6314e5475ff77f9397aa53b..9896e9fe7ffb5937a9f657d9e37ae10bbd8cb4ec 100644 (file)
@@ -491,8 +491,11 @@ static int cqspi_enable_dtr(struct cqspi_flash_pdata *f_pdata,
                if (ret)
                        return ret;
        } else {
-               reg &= ~CQSPI_REG_CONFIG_DTR_PROTO;
-               reg &= ~CQSPI_REG_CONFIG_DUAL_OPCODE;
+               unsigned int mask = CQSPI_REG_CONFIG_DTR_PROTO | CQSPI_REG_CONFIG_DUAL_OPCODE;
+               /* Shortcut if DTR is already disabled. */
+               if ((reg & mask) == 0)
+                       return 0;
+               reg &= ~mask;
        }
 
        writel(reg, reg_base + CQSPI_REG_CONFIG);