Merge tag 'xilinx-for-v2021.04-rc3' of https://gitlab.denx.de/u-boot/custodians/u...
authorTom Rini <trini@konsulko.com>
Tue, 23 Feb 2021 15:45:55 +0000 (10:45 -0500)
committerTom Rini <trini@konsulko.com>
Tue, 23 Feb 2021 15:45:55 +0000 (10:45 -0500)
Xilinx changes for v2021.04-rc3

qspi:
- Support for dual/quad mode
- Fix speed handling

clk:
- Add clock enable function for zynq/zynqmp/versal

gem:
- Enable clock for Versal
- Fix error path
- Fix mdio deregistration path

fpga:
- Fix buffer alignment for ZynqMP

xilinx:
- Fix reset reason clearing in ZynqMP
- Show silicon version in SPL for Zynq/ZynqMP
- Fix DTB selection for ZynqMP
- Rename zc1275 to zcu1275 to match DT name

18 files changed:
arch/arm/mach-zynqmp/include/mach/hardware.h
board/xilinx/common/board.c
board/xilinx/zynq/board.c
board/xilinx/zynqmp/zynqmp-zcu1275-revA [moved from board/xilinx/zynqmp/zynqmp-zc1275-revA with 100% similarity]
board/xilinx/zynqmp/zynqmp-zcu1275-revB/psu_init_gpl.c [moved from board/xilinx/zynqmp/zynqmp-zc1275-revB/psu_init_gpl.c with 100% similarity]
board/xilinx/zynqmp/zynqmp.c
drivers/clk/clk_versal.c
drivers/clk/clk_zynq.c
drivers/clk/clk_zynqmp.c
drivers/fpga/zynqpl.c
drivers/i2c/i2c-cdns.c
drivers/mmc/zynq_sdhci.c
drivers/net/zynq_gem.c
drivers/serial/serial_zynq.c
drivers/spi/zynq_qspi.c
drivers/spi/zynq_spi.c
drivers/spi/zynqmp_gqspi.c
drivers/watchdog/xilinx_wwdt.c

index b328837..3d3c48e 100644 (file)
@@ -128,8 +128,8 @@ struct apu_regs {
 
 #define ZYNQMP_CSU_VERSION_EMPTY_SHIFT         20
 
-#define ZYNQMP_SILICON_VER_MASK                0xF000
-#define ZYNQMP_SILICON_VER_SHIFT       12
+#define ZYNQMP_SILICON_VER_MASK                0xF
+#define ZYNQMP_SILICON_VER_SHIFT       0
 
 struct csu_regs {
        u32 reserved0[4];
index 4a83d93..475628b 100644 (file)
@@ -327,7 +327,7 @@ void *board_fdt_blob_setup(void)
 
        if (!IS_ENABLED(CONFIG_SPL_BUILD) &&
            !IS_ENABLED(CONFIG_VERSAL_NO_DDR) &&
-           !IS_ENABLED(CONFIG_VERSAL_NO_DDR)) {
+           !IS_ENABLED(CONFIG_ZYNQMP_NO_DDR)) {
                fdt_blob = (void *)CONFIG_XILINX_OF_BOARD_DTB_ADDR;
 
                if (fdt_magic(fdt_blob) == FDT_MAGIC)
index 49ff3f0..7533ddd 100644 (file)
@@ -25,6 +25,9 @@ DECLARE_GLOBAL_DATA_PTR;
 
 int board_init(void)
 {
+       if (IS_ENABLED(CONFIG_SPL_BUILD))
+               printf("Silicon version:\t%d\n", zynq_get_silicon_version());
+
        return 0;
 }
 
index 43e322f..4466717 100644 (file)
@@ -329,6 +329,7 @@ int board_init(void)
        if (sizeof(CONFIG_ZYNQMP_SPL_PM_CFG_OBJ_FILE) > 1)
                zynqmp_pmufw_load_config_object(zynqmp_pm_cfg_obj,
                                                zynqmp_pm_cfg_obj_size);
+       printf("Silicon version:\t%d\n", zynqmp_get_silicon_version());
 #else
        if (CONFIG_IS_ENABLED(DM_I2C) && CONFIG_IS_ENABLED(I2C_EEPROM))
                xilinx_read_eeprom();
@@ -496,11 +497,7 @@ static int reset_reason(void)
 
        env_set("reset_reason", reason);
 
-       ret = zynqmp_mmio_write((ulong)&crlapb_base->reset_reason, ~0, ~0);
-       if (ret)
-               return -EINVAL;
-
-       return ret;
+       return 0;
 }
 
 static int set_fdtfile(void)
index 908bc75..62523d2 100644 (file)
@@ -718,9 +718,20 @@ static ulong versal_clk_set_rate(struct clk *clk, ulong rate)
        return clk_rate;
 }
 
+static int versal_clk_enable(struct clk *clk)
+{
+       struct versal_clk_priv *priv = dev_get_priv(clk->dev);
+       u32 clk_id;
+
+       clk_id = priv->clk[clk->id].clk_id;
+
+       return xilinx_pm_request(PM_CLOCK_ENABLE, clk_id, 0, 0, 0, NULL);
+}
+
 static struct clk_ops versal_clk_ops = {
        .set_rate = versal_clk_set_rate,
        .get_rate = versal_clk_get_rate,
+       .enable = versal_clk_enable,
 };
 
 static const struct udevice_id versal_clk_ids[] = {
index 3e33209..18915c3 100644 (file)
@@ -445,11 +445,21 @@ static ulong zynq_clk_get_rate(struct clk *clk)
 }
 #endif
 
+static int dummy_enable(struct clk *clk)
+{
+       /*
+        * Add implementation but by default all clocks are enabled
+        * after power up which is only one supported case now.
+        */
+       return 0;
+}
+
 static struct clk_ops zynq_clk_ops = {
        .get_rate = zynq_clk_get_rate,
 #ifndef CONFIG_SPL_BUILD
        .set_rate = zynq_clk_set_rate,
 #endif
+       .enable = dummy_enable,
 };
 
 static int zynq_clk_probe(struct udevice *dev)
index e8acca0..609d8e3 100644 (file)
@@ -199,6 +199,8 @@ static u32 zynqmp_clk_get_register(enum zynqmp_clk id)
                return CRF_APB_DDR_CTRL;
        case qspi_ref:
                return CRL_APB_QSPI_REF_CTRL;
+       case usb3_dual_ref:
+               return CRL_APB_USB3_DUAL_REF_CTRL;
        case gem0_ref:
                return CRL_APB_GEM0_REF_CTRL;
        case gem1_ref:
@@ -207,6 +209,10 @@ static u32 zynqmp_clk_get_register(enum zynqmp_clk id)
                return CRL_APB_GEM2_REF_CTRL;
        case gem3_ref:
                return CRL_APB_GEM3_REF_CTRL;
+       case usb0_bus_ref:
+               return CRL_APB_USB0_BUS_REF_CTRL;
+       case usb1_bus_ref:
+               return CRL_APB_USB1_BUS_REF_CTRL;
        case uart0_ref:
                return CRL_APB_UART0_REF_CTRL;
        case uart1_ref:
@@ -699,9 +705,52 @@ static int zynqmp_clk_probe(struct udevice *dev)
        return 0;
 }
 
+static int zynqmp_clk_enable(struct clk *clk)
+{
+       enum zynqmp_clk id = clk->id;
+       u32 reg, clk_ctrl, clkact_shift, mask;
+       int ret;
+
+       reg = zynqmp_clk_get_register(id);
+       debug("%s, clk_id:%x, clk_base:0x%x\n", __func__, id, reg);
+
+       switch (id) {
+       case usb0_bus_ref ... usb1:
+               clkact_shift = 25;
+               mask = 0x1;
+               break;
+       case gem0_ref ... gem3_ref:
+               clkact_shift = 25;
+               mask = 0x3;
+               break;
+       case qspi_ref ... can1_ref:
+               clkact_shift = 24;
+               mask = 0x1;
+               break;
+       default:
+               return -ENXIO;
+       }
+
+       ret = zynqmp_mmio_read(reg, &clk_ctrl);
+       if (ret) {
+               printf("%s mio read fail\n", __func__);
+               return -EIO;
+       }
+
+       clk_ctrl |= (mask << clkact_shift);
+       ret = zynqmp_mmio_write(reg, mask << clkact_shift, clk_ctrl);
+       if (ret) {
+               printf("%s mio write fail\n", __func__);
+               return -EIO;
+       }
+
+       return ret;
+}
+
 static struct clk_ops zynqmp_clk_ops = {
        .set_rate = zynqmp_clk_set_rate,
        .get_rate = zynqmp_clk_get_rate,
+       .enable = zynqmp_clk_enable,
 };
 
 static const struct udevice_id zynqmp_clk_ids[] = {
index a11e485..2de4010 100644 (file)
@@ -315,7 +315,7 @@ static u32 *zynq_align_dma_buffer(u32 *buf, u32 len, u32 swap)
                if (new_buf > buf) {
                        debug("%s: Aligned buffer is after buffer start\n",
                              __func__);
-                       new_buf -= ARCH_DMA_MINALIGN;
+                       new_buf = (u32 *)((u32)new_buf - ARCH_DMA_MINALIGN);
                }
                printf("%s: Align buffer at %x to %x(swap %d)\n", __func__,
                       (u32)buf, (u32)new_buf, swap);
index db3c04f..a650dd6 100644 (file)
@@ -15,6 +15,7 @@
 #include <linux/types.h>
 #include <linux/io.h>
 #include <linux/errno.h>
+#include <dm/device_compat.h>
 #include <dm/root.h>
 #include <i2c.h>
 #include <fdtdec.h>
@@ -481,6 +482,12 @@ static int cdns_i2c_of_to_plat(struct udevice *dev)
 
        i2c_bus->input_freq = clk_get_rate(&clk);
 
+       ret = clk_enable(&clk);
+       if (ret) {
+               dev_err(dev, "failed to enable clock\n");
+               return ret;
+       }
+
        return 0;
 }
 
index d9ad0ff..b79c402 100644 (file)
@@ -577,7 +577,7 @@ static int arasan_sdhci_probe(struct udevice *dev)
        debug("%s: CLK %ld\n", __func__, clock);
 
        ret = clk_enable(&clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(dev, "failed to enable clock\n");
                return ret;
        }
index 5cb02bb..baf06a2 100644 (file)
 #define ZYNQ_GEM_FREQUENCY_100 25000000UL
 #define ZYNQ_GEM_FREQUENCY_1000        125000000UL
 
+#define RXCLK_EN               BIT(0)
+
 /* Device registers */
 struct zynq_gem_regs {
        u32 nwctrl; /* 0x0 - Network Control reg */
@@ -205,10 +207,12 @@ struct zynq_gem_priv {
        struct phy_device *phydev;
        ofnode phy_of_node;
        struct mii_dev *bus;
-       struct clk clk;
+       struct clk rx_clk;
+       struct clk tx_clk;
        u32 max_speed;
        bool int_pcs;
        bool dma_64bit;
+       u32 clk_en_info;
 };
 
 static int phy_setup_op(struct zynq_gem_priv *priv, u32 phy_addr, u32 regnum,
@@ -476,18 +480,25 @@ static int zynq_gem_init(struct udevice *dev)
                break;
        }
 
-       ret = clk_set_rate(&priv->clk, clk_rate);
-       if (IS_ERR_VALUE(ret) && ret != (unsigned long)-ENOSYS) {
+       ret = clk_set_rate(&priv->tx_clk, clk_rate);
+       if (IS_ERR_VALUE(ret)) {
                dev_err(dev, "failed to set tx clock rate\n");
                return ret;
        }
 
-       ret = clk_enable(&priv->clk);
-       if (ret && ret != -ENOSYS) {
+       ret = clk_enable(&priv->tx_clk);
+       if (ret) {
                dev_err(dev, "failed to enable tx clock\n");
                return ret;
        }
 
+       if (priv->clk_en_info & RXCLK_EN) {
+               ret = clk_enable(&priv->rx_clk);
+               if (ret) {
+                       dev_err(dev, "failed to enable rx clock\n");
+                       return ret;
+               }
+       }
        setbits_le32(&regs->nwctrl, ZYNQ_GEM_NWCTRL_RXEN_MASK |
                                        ZYNQ_GEM_NWCTRL_TXEN_MASK);
 
@@ -694,10 +705,18 @@ static int zynq_gem_probe(struct udevice *dev)
        priv->tx_bd = (struct emac_bd *)bd_space;
        priv->rx_bd = (struct emac_bd *)((ulong)bd_space + BD_SEPRN_SPACE);
 
-       ret = clk_get_by_name(dev, "tx_clk", &priv->clk);
+       ret = clk_get_by_name(dev, "tx_clk", &priv->tx_clk);
        if (ret < 0) {
-               dev_err(dev, "failed to get clock\n");
-               goto err1;
+               dev_err(dev, "failed to get tx_clock\n");
+               goto err2;
+       }
+
+       if (priv->clk_en_info & RXCLK_EN) {
+               ret = clk_get_by_name(dev, "rx_clk", &priv->rx_clk);
+               if (ret < 0) {
+                       dev_err(dev, "failed to get rx_clock\n");
+                       goto err2;
+               }
        }
 
        priv->bus = mdio_alloc();
@@ -711,14 +730,16 @@ static int zynq_gem_probe(struct udevice *dev)
 
        ret = zynq_phy_init(dev);
        if (ret)
-               goto err2;
+               goto err3;
 
        return ret;
 
+err3:
+       mdio_unregister(priv->bus);
 err2:
-       free(priv->rxbuffers);
-err1:
        free(priv->tx_bd);
+err1:
+       free(priv->rxbuffers);
        return ret;
 }
 
@@ -792,11 +813,13 @@ static int zynq_gem_of_to_plat(struct udevice *dev)
               (ulong)priv->iobase, (ulong)priv->mdiobase, priv->phyaddr,
               phy_string_for_interface(priv->interface));
 
+       priv->clk_en_info = dev_get_driver_data(dev);
+
        return 0;
 }
 
 static const struct udevice_id zynq_gem_ids[] = {
-       { .compatible = "cdns,versal-gem" },
+       { .compatible = "cdns,versal-gem", .data = RXCLK_EN },
        { .compatible = "cdns,zynqmp-gem" },
        { .compatible = "cdns,zynq-gem" },
        { .compatible = "cdns,gem" },
index 2883e24..799d524 100644 (file)
@@ -127,7 +127,7 @@ static int zynq_serial_setbrg(struct udevice *dev, int baudrate)
        debug("%s: CLK %ld\n", __func__, clock);
 
        ret = clk_enable(&clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(dev, "failed to enable clock\n");
                return ret;
        }
index 3d829bc..cf6da53 100644 (file)
@@ -194,7 +194,7 @@ static int zynq_qspi_probe(struct udevice *bus)
        }
 
        ret = clk_enable(&clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(bus, "failed to enable clock\n");
                return ret;
        }
index 52b8fbc..b3e0858 100644 (file)
@@ -144,7 +144,7 @@ static int zynq_spi_probe(struct udevice *bus)
        }
 
        ret = clk_enable(&clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(bus, "failed to enable clock\n");
                return ret;
        }
index f669974..f8d13d1 100644 (file)
@@ -17,6 +17,7 @@
 #include <malloc.h>
 #include <memalign.h>
 #include <spi.h>
+#include <spi-mem.h>
 #include <ubi_uboot.h>
 #include <wait_bit.h>
 #include <dm/device_compat.h>
@@ -172,8 +173,7 @@ struct zynqmp_qspi_priv {
        unsigned int len;
        int bytes_to_transfer;
        int bytes_to_receive;
-       unsigned int is_inst;
-       unsigned int cs_change:1;
+       const struct spi_mem_op *op;
 };
 
 static int zynqmp_qspi_of_to_plat(struct udevice *bus)
@@ -222,6 +222,21 @@ static u32 zynqmp_qspi_bus_select(struct zynqmp_qspi_priv *priv)
        return gqspi_fifo_reg;
 }
 
+static u32 zynqmp_qspi_genfifo_mode(u8 buswidth)
+{
+       switch (buswidth) {
+       case 1:
+               return GQSPI_SPI_MODE_SPI;
+       case 2:
+               return GQSPI_SPI_MODE_DUAL_SPI;
+       case 4:
+               return GQSPI_SPI_MODE_QSPI;
+       default:
+               debug("Unsupported bus width %u\n", buswidth);
+               return GQSPI_SPI_MODE_SPI;
+       }
+}
+
 static void zynqmp_qspi_fill_gen_fifo(struct zynqmp_qspi_priv *priv,
                                      u32 gqspi_fifo_reg)
 {
@@ -306,12 +321,9 @@ static int zynqmp_qspi_set_speed(struct udevice *bus, uint speed)
        if (speed > plat->frequency)
                speed = plat->frequency;
 
-       /* Set the clock frequency */
-       confr = readl(&regs->confr);
-       if (speed == 0) {
-               /* Set baudrate x8, if the freq is 0 */
-               baud_rate_val = GQSPI_DFLT_BAUD_RATE_VAL;
-       } else if (plat->speed_hz != speed) {
+       if (plat->speed_hz != speed) {
+               /* Set the clock frequency */
+               /* If speed == 0, default to lowest speed */
                while ((baud_rate_val < 8) &&
                       ((plat->frequency /
                       (2 << baud_rate_val)) > speed))
@@ -321,13 +333,15 @@ static int zynqmp_qspi_set_speed(struct udevice *bus, uint speed)
                        baud_rate_val = GQSPI_DFLT_BAUD_RATE_VAL;
 
                plat->speed_hz = plat->frequency / (2 << baud_rate_val);
-       }
-       confr &= ~GQSPI_BAUD_DIV_MASK;
-       confr |= (baud_rate_val << 3);
-       writel(confr, &regs->confr);
 
-       zynqmp_qspi_set_tapdelay(bus, baud_rate_val);
-       debug("regs=%p, speed=%d\n", priv->regs, plat->speed_hz);
+               confr = readl(&regs->confr);
+               confr &= ~GQSPI_BAUD_DIV_MASK;
+               confr |= (baud_rate_val << 3);
+               writel(confr, &regs->confr);
+               zynqmp_qspi_set_tapdelay(bus, baud_rate_val);
+
+               debug("regs=%p, speed=%d\n", priv->regs, plat->speed_hz);
+       }
 
        return 0;
 }
@@ -359,7 +373,7 @@ static int zynqmp_qspi_probe(struct udevice *bus)
        debug("%s: CLK %ld\n", __func__, clock);
 
        ret = clk_enable(&clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(bus, "failed to enable clock\n");
                return ret;
        }
@@ -446,21 +460,42 @@ static int zynqmp_qspi_fill_tx_fifo(struct zynqmp_qspi_priv *priv, u32 size)
 
 static void zynqmp_qspi_genfifo_cmd(struct zynqmp_qspi_priv *priv)
 {
+       const struct spi_mem_op *op = priv->op;
        u32 gen_fifo_cmd;
-       u32 bytecount = 0;
+       u8 i, dummy_cycles, addr;
+
+       /* Send opcode */
+       gen_fifo_cmd = zynqmp_qspi_bus_select(priv);
+       gen_fifo_cmd |= zynqmp_qspi_genfifo_mode(op->cmd.buswidth);
+       gen_fifo_cmd |= GQSPI_GFIFO_TX;
+       gen_fifo_cmd |= op->cmd.opcode;
+       zynqmp_qspi_fill_gen_fifo(priv, gen_fifo_cmd);
+
+       /* Send address */
+       for (i = 0; i < op->addr.nbytes; i++) {
+               addr = op->addr.val >> (8 * (op->addr.nbytes - i - 1));
 
-       while (priv->len) {
                gen_fifo_cmd = zynqmp_qspi_bus_select(priv);
-               gen_fifo_cmd |= GQSPI_GFIFO_TX | GQSPI_SPI_MODE_SPI;
-               gen_fifo_cmd |= *(u8 *)priv->tx_buf;
-               bytecount++;
-               priv->len--;
-               priv->tx_buf = (u8 *)priv->tx_buf + 1;
+               gen_fifo_cmd |= zynqmp_qspi_genfifo_mode(op->addr.buswidth);
+               gen_fifo_cmd |= GQSPI_GFIFO_TX;
+               gen_fifo_cmd |= addr;
 
                debug("GFIFO_CMD_Cmd = 0x%x\n", gen_fifo_cmd);
 
                zynqmp_qspi_fill_gen_fifo(priv, gen_fifo_cmd);
        }
+
+       /* Send dummy */
+       if (op->dummy.nbytes) {
+               dummy_cycles = op->dummy.nbytes * 8 / op->dummy.buswidth;
+
+               gen_fifo_cmd = zynqmp_qspi_bus_select(priv);
+               gen_fifo_cmd |= zynqmp_qspi_genfifo_mode(op->dummy.buswidth);
+               gen_fifo_cmd &= ~(GQSPI_GFIFO_TX | GQSPI_GFIFO_RX);
+               gen_fifo_cmd |= GQSPI_GFIFO_DATA_XFR_MASK;
+               gen_fifo_cmd |= dummy_cycles;
+               zynqmp_qspi_fill_gen_fifo(priv, gen_fifo_cmd);
+       }
 }
 
 static u32 zynqmp_qspi_calc_exp(struct zynqmp_qspi_priv *priv,
@@ -497,11 +532,10 @@ static int zynqmp_qspi_genfifo_fill_tx(struct zynqmp_qspi_priv *priv)
        int ret = 0;
 
        gen_fifo_cmd = zynqmp_qspi_bus_select(priv);
+       gen_fifo_cmd |= zynqmp_qspi_genfifo_mode(priv->op->data.buswidth);
        gen_fifo_cmd |= GQSPI_GFIFO_TX |
                        GQSPI_GFIFO_DATA_XFR_MASK;
 
-       gen_fifo_cmd |= GQSPI_SPI_MODE_SPI;
-
        while (priv->len) {
                len = zynqmp_qspi_calc_exp(priv, &gen_fifo_cmd);
                zynqmp_qspi_fill_gen_fifo(priv, gen_fifo_cmd);
@@ -575,11 +609,10 @@ static int zynqmp_qspi_genfifo_fill_rx(struct zynqmp_qspi_priv *priv)
        u32 actuallen = priv->len;
 
        gen_fifo_cmd = zynqmp_qspi_bus_select(priv);
+       gen_fifo_cmd |= zynqmp_qspi_genfifo_mode(priv->op->data.buswidth);
        gen_fifo_cmd |= GQSPI_GFIFO_RX |
                        GQSPI_GFIFO_DATA_XFR_MASK;
 
-       gen_fifo_cmd |= GQSPI_SPI_MODE_SPI;
-
        /*
         * Check if receive buffer is aligned to 4 byte and length
         * is multiples of four byte as we are using dma to receive.
@@ -596,62 +629,6 @@ static int zynqmp_qspi_genfifo_fill_rx(struct zynqmp_qspi_priv *priv)
        return zynqmp_qspi_start_dma(priv, gen_fifo_cmd, buf);
 }
 
-static int zynqmp_qspi_start_transfer(struct zynqmp_qspi_priv *priv)
-{
-       int ret = 0;
-
-       if (priv->is_inst) {
-               if (priv->tx_buf)
-                       zynqmp_qspi_genfifo_cmd(priv);
-               else
-                       return -EINVAL;
-       } else {
-               if (priv->tx_buf)
-                       ret = zynqmp_qspi_genfifo_fill_tx(priv);
-               else if (priv->rx_buf)
-                       ret = zynqmp_qspi_genfifo_fill_rx(priv);
-               else
-                       return -EINVAL;
-       }
-       return ret;
-}
-
-static int zynqmp_qspi_transfer(struct zynqmp_qspi_priv *priv)
-{
-       static unsigned int cs_change = 1;
-       int status = 0;
-
-       debug("%s\n", __func__);
-
-       while (1) {
-               /* Select the chip if required */
-               if (cs_change)
-                       zynqmp_qspi_chipselect(priv, 1);
-
-               cs_change = priv->cs_change;
-
-               if (!priv->tx_buf && !priv->rx_buf && priv->len) {
-                       status = -EINVAL;
-                       break;
-               }
-
-               /* Request the transfer */
-               if (priv->len) {
-                       status = zynqmp_qspi_start_transfer(priv);
-                       priv->is_inst = 0;
-                       if (status < 0)
-                               break;
-               }
-
-               if (cs_change)
-                       /* Deselect the chip */
-                       zynqmp_qspi_chipselect(priv, 0);
-               break;
-       }
-
-       return status;
-}
-
 static int zynqmp_qspi_claim_bus(struct udevice *dev)
 {
        struct udevice *bus = dev->parent;
@@ -674,45 +651,43 @@ static int zynqmp_qspi_release_bus(struct udevice *dev)
        return 0;
 }
 
-int zynqmp_qspi_xfer(struct udevice *dev, unsigned int bitlen, const void *dout,
-                    void *din, unsigned long flags)
+static int zynqmp_qspi_exec_op(struct spi_slave *slave,
+                              const struct spi_mem_op *op)
 {
-       struct udevice *bus = dev->parent;
-       struct zynqmp_qspi_priv *priv = dev_get_priv(bus);
+       struct zynqmp_qspi_priv *priv = dev_get_priv(slave->dev->parent);
+       int ret = 0;
 
-       debug("%s: priv: 0x%08lx bitlen: %d dout: 0x%08lx ", __func__,
-             (unsigned long)priv, bitlen, (unsigned long)dout);
-       debug("din: 0x%08lx flags: 0x%lx\n", (unsigned long)din, flags);
+       priv->op = op;
+       priv->tx_buf = op->data.buf.out;
+       priv->rx_buf = op->data.buf.in;
+       priv->len = op->data.nbytes;
 
-       priv->tx_buf = dout;
-       priv->rx_buf = din;
-       priv->len = bitlen / 8;
+       zynqmp_qspi_chipselect(priv, 1);
 
-       /*
-        * Assume that the beginning of a transfer with bits to
-        * transmit must contain a device command.
-        */
-       if (dout && flags & SPI_XFER_BEGIN)
-               priv->is_inst = 1;
-       else
-               priv->is_inst = 0;
+       /* Send opcode, addr, dummy */
+       zynqmp_qspi_genfifo_cmd(priv);
 
-       if (flags & SPI_XFER_END)
-               priv->cs_change = 1;
-       else
-               priv->cs_change = 0;
+       /* Request the transfer */
+       if (op->data.dir == SPI_MEM_DATA_IN)
+               ret = zynqmp_qspi_genfifo_fill_rx(priv);
+       else if (op->data.dir == SPI_MEM_DATA_OUT)
+               ret = zynqmp_qspi_genfifo_fill_tx(priv);
 
-       zynqmp_qspi_transfer(priv);
+       zynqmp_qspi_chipselect(priv, 0);
 
-       return 0;
+       return ret;
 }
 
+static const struct spi_controller_mem_ops zynqmp_qspi_mem_ops = {
+       .exec_op = zynqmp_qspi_exec_op,
+};
+
 static const struct dm_spi_ops zynqmp_qspi_ops = {
        .claim_bus      = zynqmp_qspi_claim_bus,
        .release_bus    = zynqmp_qspi_release_bus,
-       .xfer           = zynqmp_qspi_xfer,
        .set_speed      = zynqmp_qspi_set_speed,
        .set_mode       = zynqmp_qspi_set_mode,
+       .mem_ops        = &zynqmp_qspi_mem_ops,
 };
 
 static const struct udevice_id zynqmp_qspi_ids[] = {
index 9137d87..11b30ae 100644 (file)
@@ -90,9 +90,8 @@ static int xlnx_wwdt_start(struct udevice *dev, u64 timeout, ulong flags)
        /* Calculate timeout count */
        count = timeout * clock_f;
 
-       /* clk_enable will return -ENOSYS when it is not implemented */
        ret = clk_enable(&wdt->clk);
-       if (ret && ret != -ENOSYS) {
+       if (ret) {
                dev_err(dev, "failed to enable clock\n");
                return ret;
        }