Skip to content
Snippets Groups Projects
Commit 27a19876 authored by Tom Rini's avatar Tom Rini
Browse files

Merge branch 'master' of git://git.denx.de/u-boot-spi

parents a63d8001 2f542058
No related branches found
No related tags found
No related merge requests found
...@@ -296,6 +296,9 @@ static void atmel_spi_cs_activate(struct udevice *dev) ...@@ -296,6 +296,9 @@ static void atmel_spi_cs_activate(struct udevice *dev)
struct dm_spi_slave_platdata *slave_plat = dev_get_parent_platdata(dev); struct dm_spi_slave_platdata *slave_plat = dev_get_parent_platdata(dev);
u32 cs = slave_plat->cs; u32 cs = slave_plat->cs;
if (!dm_gpio_is_valid(&priv->cs_gpios[cs]))
return;
dm_gpio_set_value(&priv->cs_gpios[cs], 0); dm_gpio_set_value(&priv->cs_gpios[cs], 0);
} }
...@@ -306,6 +309,9 @@ static void atmel_spi_cs_deactivate(struct udevice *dev) ...@@ -306,6 +309,9 @@ static void atmel_spi_cs_deactivate(struct udevice *dev)
struct dm_spi_slave_platdata *slave_plat = dev_get_parent_platdata(dev); struct dm_spi_slave_platdata *slave_plat = dev_get_parent_platdata(dev);
u32 cs = slave_plat->cs; u32 cs = slave_plat->cs;
if (!dm_gpio_is_valid(&priv->cs_gpios[cs]))
return;
dm_gpio_set_value(&priv->cs_gpios[cs], 1); dm_gpio_set_value(&priv->cs_gpios[cs], 1);
} }
...@@ -473,6 +479,9 @@ static int atmel_spi_probe(struct udevice *bus) ...@@ -473,6 +479,9 @@ static int atmel_spi_probe(struct udevice *bus)
} }
for(i = 0; i < ARRAY_SIZE(priv->cs_gpios); i++) { for(i = 0; i < ARRAY_SIZE(priv->cs_gpios); i++) {
if (!dm_gpio_is_valid(&priv->cs_gpios[i]))
continue;
dm_gpio_set_dir_flags(&priv->cs_gpios[i], dm_gpio_set_dir_flags(&priv->cs_gpios[i],
GPIOD_IS_OUT | GPIOD_IS_OUT_ACTIVE); GPIOD_IS_OUT | GPIOD_IS_OUT_ACTIVE);
} }
......
...@@ -692,6 +692,5 @@ U_BOOT_DRIVER(omap3_spi) = { ...@@ -692,6 +692,5 @@ U_BOOT_DRIVER(omap3_spi) = {
.probe = omap3_spi_probe, .probe = omap3_spi_probe,
.ops = &omap3_spi_ops, .ops = &omap3_spi_ops,
.priv_auto_alloc_size = sizeof(struct omap3_spi_priv), .priv_auto_alloc_size = sizeof(struct omap3_spi_priv),
.probe = omap3_spi_probe,
}; };
#endif #endif
...@@ -56,6 +56,8 @@ struct zynq_spi_platdata { ...@@ -56,6 +56,8 @@ struct zynq_spi_platdata {
struct zynq_spi_regs *regs; struct zynq_spi_regs *regs;
u32 frequency; /* input frequency */ u32 frequency; /* input frequency */
u32 speed_hz; u32 speed_hz;
uint deactivate_delay_us; /* Delay to wait after deactivate */
uint activate_delay_us; /* Delay to wait after activate */
}; };
/* zynq spi priv */ /* zynq spi priv */
...@@ -63,6 +65,7 @@ struct zynq_spi_priv { ...@@ -63,6 +65,7 @@ struct zynq_spi_priv {
struct zynq_spi_regs *regs; struct zynq_spi_regs *regs;
u8 cs; u8 cs;
u8 mode; u8 mode;
ulong last_transaction_us; /* Time of last transaction end */
u8 fifo_depth; u8 fifo_depth;
u32 freq; /* required frequency */ u32 freq; /* required frequency */
}; };
...@@ -78,6 +81,10 @@ static int zynq_spi_ofdata_to_platdata(struct udevice *bus) ...@@ -78,6 +81,10 @@ static int zynq_spi_ofdata_to_platdata(struct udevice *bus)
/* FIXME: Use 250MHz as a suitable default */ /* FIXME: Use 250MHz as a suitable default */
plat->frequency = fdtdec_get_int(blob, node, "spi-max-frequency", plat->frequency = fdtdec_get_int(blob, node, "spi-max-frequency",
250000000); 250000000);
plat->deactivate_delay_us = fdtdec_get_int(blob, node,
"spi-deactivate-delay", 0);
plat->activate_delay_us = fdtdec_get_int(blob, node,
"spi-activate-delay", 0);
plat->speed_hz = plat->frequency / 2; plat->speed_hz = plat->frequency / 2;
debug("%s: regs=%p max-frequency=%d\n", __func__, debug("%s: regs=%p max-frequency=%d\n", __func__,
...@@ -133,10 +140,19 @@ static int zynq_spi_probe(struct udevice *bus) ...@@ -133,10 +140,19 @@ static int zynq_spi_probe(struct udevice *bus)
static void spi_cs_activate(struct udevice *dev) static void spi_cs_activate(struct udevice *dev)
{ {
struct udevice *bus = dev->parent; struct udevice *bus = dev->parent;
struct zynq_spi_platdata *plat = bus->platdata;
struct zynq_spi_priv *priv = dev_get_priv(bus); struct zynq_spi_priv *priv = dev_get_priv(bus);
struct zynq_spi_regs *regs = priv->regs; struct zynq_spi_regs *regs = priv->regs;
u32 cr; u32 cr;
/* If it's too soon to do another transaction, wait */
if (plat->deactivate_delay_us && priv->last_transaction_us) {
ulong delay_us; /* The delay completed so far */
delay_us = timer_get_us() - priv->last_transaction_us;
if (delay_us < plat->deactivate_delay_us)
udelay(plat->deactivate_delay_us - delay_us);
}
clrbits_le32(&regs->cr, ZYNQ_SPI_CR_CS_MASK); clrbits_le32(&regs->cr, ZYNQ_SPI_CR_CS_MASK);
cr = readl(&regs->cr); cr = readl(&regs->cr);
/* /*
...@@ -147,15 +163,23 @@ static void spi_cs_activate(struct udevice *dev) ...@@ -147,15 +163,23 @@ static void spi_cs_activate(struct udevice *dev)
*/ */
cr |= (~(1 << priv->cs) << ZYNQ_SPI_CR_SS_SHIFT) & ZYNQ_SPI_CR_CS_MASK; cr |= (~(1 << priv->cs) << ZYNQ_SPI_CR_SS_SHIFT) & ZYNQ_SPI_CR_CS_MASK;
writel(cr, &regs->cr); writel(cr, &regs->cr);
if (plat->activate_delay_us)
udelay(plat->activate_delay_us);
} }
static void spi_cs_deactivate(struct udevice *dev) static void spi_cs_deactivate(struct udevice *dev)
{ {
struct udevice *bus = dev->parent; struct udevice *bus = dev->parent;
struct zynq_spi_platdata *plat = bus->platdata;
struct zynq_spi_priv *priv = dev_get_priv(bus); struct zynq_spi_priv *priv = dev_get_priv(bus);
struct zynq_spi_regs *regs = priv->regs; struct zynq_spi_regs *regs = priv->regs;
setbits_le32(&regs->cr, ZYNQ_SPI_CR_CS_MASK); setbits_le32(&regs->cr, ZYNQ_SPI_CR_CS_MASK);
/* Remember time of this transaction so we can honour the bus delay */
if (plat->deactivate_delay_us)
priv->last_transaction_us = timer_get_us();
} }
static int zynq_spi_claim_bus(struct udevice *dev) static int zynq_spi_claim_bus(struct udevice *dev)
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment