diff options
author | Jean-Christophe PLAGNIOL-VILLARD <plagnioj@jcrosoft.com> | 2012-09-01 10:52:41 +0200 |
---|---|---|
committer | Sascha Hauer <s.hauer@pengutronix.de> | 2012-09-03 09:49:06 +0200 |
commit | 655dc6b8aa3b1b1340d257a33b6e05569e089f25 (patch) | |
tree | 2546c52c23e97fe91dc68e1b969a1d57e75e19b1 /drivers/net/smc911x.c | |
parent | 75880ac0ad974e9b2a2f2c77d00463bf7f354bc2 (diff) | |
download | barebox-655dc6b8aa3b1b1340d257a33b6e05569e089f25.tar.gz barebox-655dc6b8aa3b1b1340d257a33b6e05569e089f25.tar.xz |
smc911x: add support to pass the shift via platform data
switch ipe337: to it at the same time to do not brake it
Signed-off-by: Jean-Christophe PLAGNIOL-VILLARD <plagnioj@jcrosoft.com>
Signed-off-by: Sascha Hauer <s.hauer@pengutronix.de>
Diffstat (limited to 'drivers/net/smc911x.c')
-rw-r--r-- | drivers/net/smc911x.c | 60 |
1 files changed, 54 insertions, 6 deletions
diff --git a/drivers/net/smc911x.c b/drivers/net/smc911x.c index 917f99453e..75a332e134 100644 --- a/drivers/net/smc911x.c +++ b/drivers/net/smc911x.c @@ -37,9 +37,8 @@ #include <errno.h> #include <clock.h> #include <io.h> +#include <smc911x.h> - -#define AS CONFIG_DRIVER_NET_SMC911X_ADDRESS_SHIFT #include "smc911x.h" struct smc911x_priv { @@ -47,6 +46,8 @@ struct smc911x_priv { struct mii_device miidev; void __iomem *base; + int shift; + u32 (*reg_read)(struct smc911x_priv *priv, u32 reg); void (*reg_write)(struct smc911x_priv *priv, u32 reg, u32 val); }; @@ -71,6 +72,8 @@ static const struct chip_id chip_ids[] = { #define DRIVERNAME "smc911x" +#define __smc_shift(priv, reg) ((reg) << ((priv)->shift)) + static inline u32 smc911x_reg_read(struct smc911x_priv *priv, u32 reg) { return priv->reg_read(priv, reg); @@ -87,6 +90,22 @@ static inline u32 __smc911x_reg_readl(struct smc911x_priv *priv, u32 reg) return readl(priv->base + reg); } +static inline u32 +__smc911x_reg_readw_shift(struct smc911x_priv *priv, u32 reg) +{ + return (readw(priv->base + + __smc_shift(priv, reg)) & 0xFFFF) | + ((readw(priv->base + + __smc_shift(priv, reg + 2)) & 0xFFFF) << 16); + +} + +static inline u32 +__smc911x_reg_readl_shift(struct smc911x_priv *priv, u32 reg) +{ + return readl(priv->base + __smc_shift(priv, reg)); +} + static inline void smc911x_reg_write(struct smc911x_priv *priv, u32 reg, u32 val) { @@ -106,6 +125,21 @@ static inline void __smc911x_reg_writel(struct smc911x_priv *priv, u32 reg, writel(val, priv->base + reg); } +static inline void +__smc911x_reg_writew_shift(struct smc911x_priv *priv, u32 reg, u32 val) +{ + writew(val & 0xFFFF, + priv->base + __smc_shift(priv, reg)); + writew((val >> 16) & 0xFFFF, + priv->base + __smc_shift(priv, reg + 2)); +} + +static inline void +__smc911x_reg_writel_shift(struct smc911x_priv *priv, u32 reg, u32 val) +{ + writel(val, priv->base + __smc_shift(priv, reg)); +} + static int smc911x_mac_wait_busy(struct smc911x_priv *priv) { uint64_t start = get_time_ns(); @@ -404,6 +438,7 @@ static int smc911x_probe(struct device_d *dev) struct smc911x_priv *priv; uint32_t val; int i, is_32bit; + struct smc911x_plat *pdata = dev->platform_data; priv = xzalloc(sizeof(*priv)); is_32bit = dev->resource[0].flags & IORESOURCE_MEM_TYPE_MASK; @@ -413,12 +448,25 @@ static int smc911x_probe(struct device_d *dev) is_32bit = is_32bit == IORESOURCE_MEM_32BIT; priv->base = dev_request_mem_region(dev, 0); + if (pdata && pdata->shift) + priv->shift = pdata->shift; + if (is_32bit) { - priv->reg_read = __smc911x_reg_readl; - priv->reg_write = __smc911x_reg_writel; + if (pdata->shift) { + priv->reg_read = __smc911x_reg_readl_shift; + priv->reg_write = __smc911x_reg_writel_shift; + } else { + priv->reg_read = __smc911x_reg_readl; + priv->reg_write = __smc911x_reg_writel; + } } else { - priv->reg_read = __smc911x_reg_readw; - priv->reg_write = __smc911x_reg_writew; + if (pdata->shift) { + priv->reg_read = __smc911x_reg_readw_shift; + priv->reg_write = __smc911x_reg_writew_shift; + } else { + priv->reg_read = __smc911x_reg_readw; + priv->reg_write = __smc911x_reg_writew; + } } val = smc911x_reg_read(priv, BYTE_TEST); |