|
| 1 | +From a89f6202fb0cdca043a7864cdc469b7ffd63b825 Mon Sep 17 00:00:00 2001 |
| 2 | +From: Josua Mayer <josua@solid-run.com> |
| 3 | +Date: Thu, 11 Sep 2025 15:25:47 +0200 |
| 4 | +Subject: [PATCH 23/24] spi: kirkwood: add quirk for cn9132 cex7: miso sample |
| 5 | + delay |
| 6 | + |
| 7 | +Set miso sample delay to 3 core-clk cycles to avoid bit errros that are |
| 8 | +consistent with 1 cycle delay and sporadic with 2 cycles. |
| 9 | +At 3 cycles access is stable. |
| 10 | + |
| 11 | +Signed-off-by: Josua Mayer <josua@solid-run.com> |
| 12 | +--- |
| 13 | + arch/arm/include/asm/arch-mvebu/spi.h | 1 + |
| 14 | + drivers/spi/kirkwood_spi.c | 43 ++++++++++++++++++++++----- |
| 15 | + 2 files changed, 36 insertions(+), 8 deletions(-) |
| 16 | + |
| 17 | +diff --git a/arch/arm/include/asm/arch-mvebu/spi.h b/arch/arm/include/asm/arch-mvebu/spi.h |
| 18 | +index 58b6c32c4d..7bfee7343e 100644 |
| 19 | +--- a/arch/arm/include/asm/arch-mvebu/spi.h |
| 20 | ++++ b/arch/arm/include/asm/arch-mvebu/spi.h |
| 21 | +@@ -50,6 +50,7 @@ struct kwspi_registers { |
| 22 | + #define KW_SPI_TMISO_SAMPLE_MASK (0x3 << KW_SPI_TMISO_SAMPLE_OFFSET) |
| 23 | + #define KW_SPI_TMISO_SAMPLE_1 (1 << KW_SPI_TMISO_SAMPLE_OFFSET) |
| 24 | + #define KW_SPI_TMISO_SAMPLE_2 (2 << KW_SPI_TMISO_SAMPLE_OFFSET) |
| 25 | ++#define KW_SPI_TMISO_SAMPLE_3 (3 << KW_SPI_TMISO_SAMPLE_OFFSET) |
| 26 | + |
| 27 | + #define KWSPI_IRQUNMASK 1 /* unmask SPI interrupt */ |
| 28 | + #define KWSPI_IRQMASK 0 /* mask SPI interrupt */ |
| 29 | +diff --git a/drivers/spi/kirkwood_spi.c b/drivers/spi/kirkwood_spi.c |
| 30 | +index bc5da0a1e6..3fb9dde34e 100644 |
| 31 | +--- a/drivers/spi/kirkwood_spi.c |
| 32 | ++++ b/drivers/spi/kirkwood_spi.c |
| 33 | +@@ -182,12 +182,39 @@ static int mvebu_spi_set_speed(struct udevice *bus, uint hz) |
| 34 | + return 0; |
| 35 | + } |
| 36 | + |
| 37 | +-static void mvebu_spi_50mhz_ac_timing_erratum(struct udevice *bus, uint mode) |
| 38 | ++/* configure extra miso sample delay */ |
| 39 | ++static int mvebu_spi_set_miso_sample_delay(struct udevice *bus, const uint8_t cycles) |
| 40 | + { |
| 41 | + struct mvebu_spi_plat *plat = dev_get_plat(bus); |
| 42 | + struct kwspi_registers *reg = plat->spireg; |
| 43 | + u32 data; |
| 44 | + |
| 45 | ++ data = readl(®->timing1); |
| 46 | ++ data &= ~KW_SPI_TMISO_SAMPLE_MASK; |
| 47 | ++ |
| 48 | ++ switch (cycles) { |
| 49 | ++ case 0: |
| 50 | ++ break; |
| 51 | ++ case 1: |
| 52 | ++ data |= KW_SPI_TMISO_SAMPLE_1; |
| 53 | ++ break; |
| 54 | ++ case 2: |
| 55 | ++ data |= KW_SPI_TMISO_SAMPLE_2; |
| 56 | ++ break; |
| 57 | ++ case 3: |
| 58 | ++ data |= KW_SPI_TMISO_SAMPLE_3; |
| 59 | ++ break; |
| 60 | ++ default: |
| 61 | ++ return -EINVAL; |
| 62 | ++ } |
| 63 | ++ |
| 64 | ++ writel(data, ®->timing1); |
| 65 | ++ |
| 66 | ++ return 0; |
| 67 | ++} |
| 68 | ++ |
| 69 | ++static void mvebu_spi_50mhz_ac_timing_erratum(struct udevice *bus, uint mode) |
| 70 | ++{ |
| 71 | + /* |
| 72 | + * Erratum description: (Erratum NO. FE-9144572) The device |
| 73 | + * SPI interface supports frequencies of up to 50 MHz. |
| 74 | +@@ -202,17 +229,12 @@ static void mvebu_spi_50mhz_ac_timing_erratum(struct udevice *bus, uint mode) |
| 75 | + * 2. Set TMISO_SAMPLE value to 0x2 in "SPI Timing Parameters 1 |
| 76 | + * Register" before setting the interface. |
| 77 | + */ |
| 78 | +- data = readl(®->timing1); |
| 79 | +- data &= ~KW_SPI_TMISO_SAMPLE_MASK; |
| 80 | +- |
| 81 | + if (CONFIG_SYS_TCLK == 250000000 && |
| 82 | + mode & SPI_CPOL && |
| 83 | + mode & SPI_CPHA) |
| 84 | +- data |= KW_SPI_TMISO_SAMPLE_2; |
| 85 | ++ mvebu_spi_set_miso_sample_delay(bus, 2); |
| 86 | + else |
| 87 | +- data |= KW_SPI_TMISO_SAMPLE_1; |
| 88 | +- |
| 89 | +- writel(data, ®->timing1); |
| 90 | ++ mvebu_spi_set_miso_sample_delay(bus, 1); |
| 91 | + } |
| 92 | + |
| 93 | + static int mvebu_spi_set_mode(struct udevice *bus, uint mode) |
| 94 | +@@ -235,6 +257,11 @@ static int mvebu_spi_set_mode(struct udevice *bus, uint mode) |
| 95 | + if (plat->is_errata_50mhz_ac) |
| 96 | + mvebu_spi_50mhz_ac_timing_erratum(bus, mode); |
| 97 | + |
| 98 | ++ /* CN9132 CEX-7 requires 3 cycles delay before sampling miso to avoid bit errors */ |
| 99 | ++ if (of_machine_is_compatible("solidrun,cn9132-sr-cex7") && |
| 100 | ++ ofnode_to_offset(dev_ofnode(bus)) == ofnode_to_offset(ofnode_path("/cp0/config-space/spi@700680"))) |
| 101 | ++ mvebu_spi_set_miso_sample_delay(bus, 3); |
| 102 | ++ |
| 103 | + return 0; |
| 104 | + } |
| 105 | + |
| 106 | +-- |
| 107 | +2.51.0 |
| 108 | + |
0 commit comments