On 11/25/2016 03:38 PM, Phil Edworthy wrote: > The Cadence QSPI controller has specified overheads for the various CS > times that are in addition to those programmed in to the Device Delay > register. The overheads are different for the delays. > > In addition, the existing code does not handle the case when the delay > is less than a SCLK period. > > This change accurately calculates the additional delays in Ref clocks. > > Signed-off-by: Phil Edworthy <phil.edwor...@renesas.com>
Looks fine to me, but Dinh/Chin, can you check whether this doesn't break SoCFPGA ? > --- > v2: > Was "spi: cadence_qspi: Fix CQSPI_CAL_DELAY calculation" > Note only did the existing code not cope with the delay less than > an SCLK period, but the calculation didn't round properly, and > didn't take into account the delays that the QSPI Controller adds > to those programmed into the Device Delay reg. > --- > drivers/spi/cadence_qspi_apb.c | 23 ++++++++++++----------- > 1 file changed, 12 insertions(+), 11 deletions(-) > > diff --git a/drivers/spi/cadence_qspi_apb.c b/drivers/spi/cadence_qspi_apb.c > index 1cd636a..56ad952 100644 > --- a/drivers/spi/cadence_qspi_apb.c > +++ b/drivers/spi/cadence_qspi_apb.c > @@ -169,9 +169,6 @@ > ((readl(base + CQSPI_REG_CONFIG) >> \ > CQSPI_REG_CONFIG_IDLE_LSB) & 0x1) > > -#define CQSPI_CAL_DELAY(tdelay_ns, tref_ns, tsclk_ns) \ > - ((((tdelay_ns) - (tsclk_ns)) / (tref_ns))) > - > #define CQSPI_GET_RD_SRAM_LEVEL(reg_base) \ > (((readl(reg_base + CQSPI_REG_SDRAMLEVEL)) >> \ > CQSPI_REG_SDRAMLEVEL_RD_LSB) & CQSPI_REG_SDRAMLEVEL_RD_MASK) > @@ -357,16 +354,20 @@ void cadence_qspi_apb_delay(void *reg_base, > cadence_qspi_apb_controller_disable(reg_base); > > /* Convert to ns. */ > - ref_clk_ns = (1000000000) / ref_clk; > + ref_clk_ns = DIV_ROUND_UP(1000000000, ref_clk); > > /* Convert to ns. */ > - sclk_ns = (1000000000) / sclk_hz; > - > - /* Plus 1 to round up 1 clock cycle. */ > - tshsl = CQSPI_CAL_DELAY(tshsl_ns, ref_clk_ns, sclk_ns) + 1; > - tchsh = CQSPI_CAL_DELAY(tchsh_ns, ref_clk_ns, sclk_ns) + 1; > - tslch = CQSPI_CAL_DELAY(tslch_ns, ref_clk_ns, sclk_ns) + 1; > - tsd2d = CQSPI_CAL_DELAY(tsd2d_ns, ref_clk_ns, sclk_ns) + 1; > + sclk_ns = DIV_ROUND_UP(1000000000, sclk_hz); > + > + /* The controller adds additional delay to that programmed in the reg */ > + if (tshsl_ns >= sclk_ns + ref_clk_ns) > + tshsl_ns -= sclk_ns + ref_clk_ns; > + if (tchsh_ns >= sclk_ns + 3 * ref_clk_ns) > + tchsh_ns -= sclk_ns + 3 * ref_clk_ns; > + tshsl = DIV_ROUND_UP(tshsl_ns, ref_clk_ns); > + tchsh = DIV_ROUND_UP(tchsh_ns, ref_clk_ns); > + tslch = DIV_ROUND_UP(tslch_ns, ref_clk_ns); > + tsd2d = DIV_ROUND_UP(tsd2d_ns, ref_clk_ns); > > reg = ((tshsl & CQSPI_REG_DELAY_TSHSL_MASK) > << CQSPI_REG_DELAY_TSHSL_LSB); > -- Best regards, Marek Vasut _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot