smc911x: introduce platform data flags
This patch adds a new header file for platform data information together with code that adds run time bus width and irq flag support. Signed-off-by: Magnus Damm <damm@igel.co.jp> Cc: Jeff Garzik <jeff@garzik.org> Cc: Paul Mundt <lethal@linux-sh.org> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Jeff Garzik <jgarzik@redhat.com>
This commit is contained in:
parent
699559f84b
commit
12c03f59c3
|
@ -1819,6 +1819,7 @@ static int __init smc911x_probe(struct net_device *dev)
|
||||||
int i, retval;
|
int i, retval;
|
||||||
unsigned int val, chip_id, revision;
|
unsigned int val, chip_id, revision;
|
||||||
const char *version_string;
|
const char *version_string;
|
||||||
|
unsigned long irq_flags;
|
||||||
|
|
||||||
DBG(SMC_DEBUG_FUNC, "%s: --> %s\n", dev->name, __FUNCTION__);
|
DBG(SMC_DEBUG_FUNC, "%s: --> %s\n", dev->name, __FUNCTION__);
|
||||||
|
|
||||||
|
@ -1985,9 +1986,15 @@ static int __init smc911x_probe(struct net_device *dev)
|
||||||
lp->ctl_rfduplx = 1;
|
lp->ctl_rfduplx = 1;
|
||||||
lp->ctl_rspeed = 100;
|
lp->ctl_rspeed = 100;
|
||||||
|
|
||||||
|
#ifdef SMC_DYNAMIC_BUS_CONFIG
|
||||||
|
irq_flags = lp->cfg.irq_flags;
|
||||||
|
#else
|
||||||
|
irq_flags = IRQF_SHARED | SMC_IRQ_SENSE;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Grab the IRQ */
|
/* Grab the IRQ */
|
||||||
retval = request_irq(dev->irq, &smc911x_interrupt,
|
retval = request_irq(dev->irq, &smc911x_interrupt,
|
||||||
IRQF_SHARED | SMC_IRQ_SENSE, dev->name, dev);
|
irq_flags, dev->name, dev);
|
||||||
if (retval)
|
if (retval)
|
||||||
goto err_out;
|
goto err_out;
|
||||||
|
|
||||||
|
@ -2057,6 +2064,7 @@ err_out:
|
||||||
*/
|
*/
|
||||||
static int smc911x_drv_probe(struct platform_device *pdev)
|
static int smc911x_drv_probe(struct platform_device *pdev)
|
||||||
{
|
{
|
||||||
|
struct smc91x_platdata *pd = pdev->dev.platform_data;
|
||||||
struct net_device *ndev;
|
struct net_device *ndev;
|
||||||
struct resource *res;
|
struct resource *res;
|
||||||
struct smc911x_local *lp;
|
struct smc911x_local *lp;
|
||||||
|
@ -2090,6 +2098,13 @@ static int smc911x_drv_probe(struct platform_device *pdev)
|
||||||
ndev->irq = platform_get_irq(pdev, 0);
|
ndev->irq = platform_get_irq(pdev, 0);
|
||||||
lp = netdev_priv(ndev);
|
lp = netdev_priv(ndev);
|
||||||
lp->netdev = ndev;
|
lp->netdev = ndev;
|
||||||
|
#ifdef SMC_DYNAMIC_BUS_CONFIG
|
||||||
|
if (!pd) {
|
||||||
|
ret = -EINVAL;
|
||||||
|
goto release_both;
|
||||||
|
}
|
||||||
|
memcpy(&lp->cfg, pd, sizeof(lp->cfg));
|
||||||
|
#endif
|
||||||
|
|
||||||
addr = ioremap(res->start, SMC911X_IO_EXTENT);
|
addr = ioremap(res->start, SMC911X_IO_EXTENT);
|
||||||
if (!addr) {
|
if (!addr) {
|
||||||
|
|
|
@ -29,6 +29,7 @@
|
||||||
#ifndef _SMC911X_H_
|
#ifndef _SMC911X_H_
|
||||||
#define _SMC911X_H_
|
#define _SMC911X_H_
|
||||||
|
|
||||||
|
#include <linux/smc911x.h>
|
||||||
/*
|
/*
|
||||||
* Use the DMA feature on PXA chips
|
* Use the DMA feature on PXA chips
|
||||||
*/
|
*/
|
||||||
|
@ -42,6 +43,12 @@
|
||||||
#define SMC_USE_16BIT 0
|
#define SMC_USE_16BIT 0
|
||||||
#define SMC_USE_32BIT 1
|
#define SMC_USE_32BIT 1
|
||||||
#define SMC_IRQ_SENSE IRQF_TRIGGER_LOW
|
#define SMC_IRQ_SENSE IRQF_TRIGGER_LOW
|
||||||
|
#else
|
||||||
|
/*
|
||||||
|
* Default configuration
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define SMC_DYNAMIC_BUS_CONFIG
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* store this information for the driver.. */
|
/* store this information for the driver.. */
|
||||||
|
@ -92,12 +99,84 @@ struct smc911x_local {
|
||||||
struct device *dev;
|
struct device *dev;
|
||||||
#endif
|
#endif
|
||||||
void __iomem *base;
|
void __iomem *base;
|
||||||
|
#ifdef SMC_DYNAMIC_BUS_CONFIG
|
||||||
|
struct smc911x_platdata cfg;
|
||||||
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Define the bus width specific IO macros
|
* Define the bus width specific IO macros
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#ifdef SMC_DYNAMIC_BUS_CONFIG
|
||||||
|
static inline unsigned int SMC_inl(struct smc911x_local *lp, int reg)
|
||||||
|
{
|
||||||
|
void __iomem *ioaddr = lp->base + reg;
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_32BIT)
|
||||||
|
return readl(ioaddr);
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_16BIT)
|
||||||
|
return readw(ioaddr) | (readw(ioaddr + 2) << 16);
|
||||||
|
|
||||||
|
BUG();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void SMC_outl(unsigned int value, struct smc911x_local *lp,
|
||||||
|
int reg)
|
||||||
|
{
|
||||||
|
void __iomem *ioaddr = lp->base + reg;
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_32BIT) {
|
||||||
|
writel(value, ioaddr);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_16BIT) {
|
||||||
|
writew(value & 0xffff, ioaddr);
|
||||||
|
writew(value >> 16, ioaddr + 2);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
BUG();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void SMC_insl(struct smc911x_local *lp, int reg,
|
||||||
|
void *addr, unsigned int count)
|
||||||
|
{
|
||||||
|
void __iomem *ioaddr = lp->base + reg;
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_32BIT) {
|
||||||
|
readsl(ioaddr, addr, count);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_16BIT) {
|
||||||
|
readsw(ioaddr, addr, count * 2);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
BUG();
|
||||||
|
}
|
||||||
|
|
||||||
|
static inline void SMC_outsl(struct smc911x_local *lp, int reg,
|
||||||
|
void *addr, unsigned int count)
|
||||||
|
{
|
||||||
|
void __iomem *ioaddr = lp->base + reg;
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_32BIT) {
|
||||||
|
writesl(ioaddr, addr, count);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (lp->cfg.flags & SMC911X_USE_16BIT) {
|
||||||
|
writesw(ioaddr, addr, count * 2);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
BUG();
|
||||||
|
}
|
||||||
|
#else
|
||||||
#if SMC_USE_16BIT
|
#if SMC_USE_16BIT
|
||||||
#define SMC_inl(lp, r) ((readw((lp)->base + (r)) & 0xFFFF) + (readw((lp)->base + (r) + 2) << 16))
|
#define SMC_inl(lp, r) ((readw((lp)->base + (r)) & 0xFFFF) + (readw((lp)->base + (r) + 2) << 16))
|
||||||
#define SMC_outl(v, lp, r) \
|
#define SMC_outl(v, lp, r) \
|
||||||
|
@ -115,6 +194,8 @@ struct smc911x_local {
|
||||||
#define SMC_outsl(lp, r, p, l) writesl((int*)((lp)->base + (r)), p, l)
|
#define SMC_outsl(lp, r, p, l) writesl((int*)((lp)->base + (r)), p, l)
|
||||||
|
|
||||||
#endif /* SMC_USE_16BIT */
|
#endif /* SMC_USE_16BIT */
|
||||||
|
#endif /* SMC_DYNAMIC_BUS_CONFIG */
|
||||||
|
|
||||||
|
|
||||||
#ifdef SMC_USE_PXA_DMA
|
#ifdef SMC_USE_PXA_DMA
|
||||||
#define SMC_USE_DMA
|
#define SMC_USE_DMA
|
||||||
|
|
12
include/linux/smc911x.h
Normal file
12
include/linux/smc911x.h
Normal file
|
@ -0,0 +1,12 @@
|
||||||
|
#ifndef __SMC911X_H__
|
||||||
|
#define __SMC911X_H__
|
||||||
|
|
||||||
|
#define SMC911X_USE_16BIT (1 << 0)
|
||||||
|
#define SMC911X_USE_32BIT (1 << 1)
|
||||||
|
|
||||||
|
struct smc911x_platdata {
|
||||||
|
unsigned long flags;
|
||||||
|
unsigned long irq_flags; /* IRQF_... */
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* __SMC911X_H__ */
|
Loading…
Reference in a new issue