summaryrefslogtreecommitdiffstats
path: root/drivers/net/pcmcia/axnet_cs.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net/pcmcia/axnet_cs.c')
-rw-r--r--drivers/net/pcmcia/axnet_cs.c141
1 files changed, 48 insertions, 93 deletions
diff --git a/drivers/net/pcmcia/axnet_cs.c b/drivers/net/pcmcia/axnet_cs.c
index 1cc94b2d76c1..2ea66aca648b 100644
--- a/drivers/net/pcmcia/axnet_cs.c
+++ b/drivers/net/pcmcia/axnet_cs.c
@@ -86,8 +86,8 @@ static char *version =
/*====================================================================*/
-static void axnet_config(dev_link_t *link);
-static void axnet_release(dev_link_t *link);
+static int axnet_config(struct pcmcia_device *link);
+static void axnet_release(struct pcmcia_device *link);
static int axnet_open(struct net_device *dev);
static int axnet_close(struct net_device *dev);
static int axnet_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
@@ -117,7 +117,7 @@ static irqreturn_t ax_interrupt(int irq, void *dev_id, struct pt_regs *regs);
/*====================================================================*/
typedef struct axnet_dev_t {
- dev_link_t link;
+ struct pcmcia_device *p_dev;
dev_node_t node;
caddr_t base;
struct timer_list watchdog;
@@ -142,10 +142,9 @@ static inline axnet_dev_t *PRIV(struct net_device *dev)
======================================================================*/
-static int axnet_attach(struct pcmcia_device *p_dev)
+static int axnet_probe(struct pcmcia_device *link)
{
axnet_dev_t *info;
- dev_link_t *link;
struct net_device *dev;
DEBUG(0, "axnet_attach()\n");
@@ -157,7 +156,7 @@ static int axnet_attach(struct pcmcia_device *p_dev)
return -ENOMEM;
info = PRIV(dev);
- link = &info->link;
+ info->p_dev = link;
link->priv = dev;
link->irq.Attributes = IRQ_TYPE_EXCLUSIVE;
link->irq.IRQInfo1 = IRQ_LEVEL_ID;
@@ -169,13 +168,7 @@ static int axnet_attach(struct pcmcia_device *p_dev)
dev->do_ioctl = &axnet_ioctl;
SET_ETHTOOL_OPS(dev, &netdev_ethtool_ops);
- link->handle = p_dev;
- p_dev->instance = link;
-
- link->state |= DEV_PRESENT | DEV_CONFIG_PENDING;
- axnet_config(link);
-
- return 0;
+ return axnet_config(link);
} /* axnet_attach */
/*======================================================================
@@ -187,18 +180,16 @@ static int axnet_attach(struct pcmcia_device *p_dev)
======================================================================*/
-static void axnet_detach(struct pcmcia_device *p_dev)
+static void axnet_detach(struct pcmcia_device *link)
{
- dev_link_t *link = dev_to_instance(p_dev);
struct net_device *dev = link->priv;
DEBUG(0, "axnet_detach(0x%p)\n", link);
- if (link->dev)
+ if (link->dev_node)
unregister_netdev(dev);
- if (link->state & DEV_CONFIG)
- axnet_release(link);
+ axnet_release(link);
free_netdev(dev);
} /* axnet_detach */
@@ -209,7 +200,7 @@ static void axnet_detach(struct pcmcia_device *p_dev)
======================================================================*/
-static int get_prom(dev_link_t *link)
+static int get_prom(struct pcmcia_device *link)
{
struct net_device *dev = link->priv;
kio_addr_t ioaddr = dev->base_addr;
@@ -263,7 +254,7 @@ static int get_prom(dev_link_t *link)
#define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
-static int try_io_port(dev_link_t *link)
+static int try_io_port(struct pcmcia_device *link)
{
int j, ret;
if (link->io.NumPorts1 == 32) {
@@ -284,25 +275,23 @@ static int try_io_port(dev_link_t *link)
for (j = 0; j < 0x400; j += 0x20) {
link->io.BasePort1 = j ^ 0x300;
link->io.BasePort2 = (j ^ 0x300) + 0x10;
- ret = pcmcia_request_io(link->handle, &link->io);
+ ret = pcmcia_request_io(link, &link->io);
if (ret == CS_SUCCESS) return ret;
}
return ret;
} else {
- return pcmcia_request_io(link->handle, &link->io);
+ return pcmcia_request_io(link, &link->io);
}
}
-static void axnet_config(dev_link_t *link)
+static int axnet_config(struct pcmcia_device *link)
{
- client_handle_t handle = link->handle;
struct net_device *dev = link->priv;
axnet_dev_t *info = PRIV(dev);
tuple_t tuple;
cisparse_t parse;
int i, j, last_ret, last_fn;
u_short buf[64];
- config_info_t conf;
DEBUG(0, "axnet_config(0x%p)\n", link);
@@ -311,29 +300,22 @@ static void axnet_config(dev_link_t *link)
tuple.TupleDataMax = sizeof(buf);
tuple.TupleOffset = 0;
tuple.DesiredTuple = CISTPL_CONFIG;
- CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(handle, &tuple));
- CS_CHECK(GetTupleData, pcmcia_get_tuple_data(handle, &tuple));
- CS_CHECK(ParseTuple, pcmcia_parse_tuple(handle, &tuple, &parse));
+ CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
+ CS_CHECK(GetTupleData, pcmcia_get_tuple_data(link, &tuple));
+ CS_CHECK(ParseTuple, pcmcia_parse_tuple(link, &tuple, &parse));
link->conf.ConfigBase = parse.config.base;
/* don't trust the CIS on this; Linksys got it wrong */
link->conf.Present = 0x63;
- /* Configure card */
- link->state |= DEV_CONFIG;
-
- /* Look up current Vcc */
- CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(handle, &conf));
- link->conf.Vcc = conf.Vcc;
-
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
tuple.Attributes = 0;
- CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(handle, &tuple));
+ CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
while (last_ret == CS_SUCCESS) {
cistpl_cftable_entry_t *cfg = &(parse.cftable_entry);
cistpl_io_t *io = &(parse.cftable_entry.io);
- if (pcmcia_get_tuple_data(handle, &tuple) != 0 ||
- pcmcia_parse_tuple(handle, &tuple, &parse) != 0 ||
+ if (pcmcia_get_tuple_data(link, &tuple) != 0 ||
+ pcmcia_parse_tuple(link, &tuple, &parse) != 0 ||
cfg->index == 0 || cfg->io.nwin == 0)
goto next_entry;
@@ -355,21 +337,21 @@ static void axnet_config(dev_link_t *link)
if (last_ret == CS_SUCCESS) break;
}
next_entry:
- last_ret = pcmcia_get_next_tuple(handle, &tuple);
+ last_ret = pcmcia_get_next_tuple(link, &tuple);
}
if (last_ret != CS_SUCCESS) {
- cs_error(handle, RequestIO, last_ret);
+ cs_error(link, RequestIO, last_ret);
goto failed;
}
- CS_CHECK(RequestIRQ, pcmcia_request_irq(handle, &link->irq));
+ CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
if (link->io.NumPorts2 == 8) {
link->conf.Attributes |= CONF_ENABLE_SPKR;
link->conf.Status = CCSR_AUDIO_ENA;
}
- CS_CHECK(RequestConfiguration, pcmcia_request_configuration(handle, &link->conf));
+ CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf));
dev->irq = link->irq.AssignedIRQ;
dev->base_addr = link->io.BasePort1;
@@ -406,7 +388,7 @@ static void axnet_config(dev_link_t *link)
Bit 2 of CCSR is active low. */
if (i == 32) {
conf_reg_t reg = { 0, CS_WRITE, CISREG_CCSR, 0x04 };
- pcmcia_access_configuration_register(link->handle, &reg);
+ pcmcia_access_configuration_register(link, &reg);
for (i = 0; i < 32; i++) {
j = mdio_read(dev->base_addr + AXNET_MII_EEP, i, 1);
if ((j != 0) && (j != 0xffff)) break;
@@ -414,13 +396,12 @@ static void axnet_config(dev_link_t *link)
}
info->phy_id = (i < 32) ? i : -1;
- link->dev = &info->node;
- link->state &= ~DEV_CONFIG_PENDING;
- SET_NETDEV_DEV(dev, &handle_to_dev(handle));
+ link->dev_node = &info->node;
+ SET_NETDEV_DEV(dev, &handle_to_dev(link));
if (register_netdev(dev) != 0) {
printk(KERN_NOTICE "axnet_cs: register_netdev() failed\n");
- link->dev = NULL;
+ link->dev_node = NULL;
goto failed;
}
@@ -436,14 +417,13 @@ static void axnet_config(dev_link_t *link)
} else {
printk(KERN_NOTICE " No MII transceivers found!\n");
}
- return;
+ return 0;
cs_failed:
- cs_error(link->handle, last_fn, last_ret);
+ cs_error(link, last_fn, last_ret);
failed:
axnet_release(link);
- link->state &= ~DEV_CONFIG_PENDING;
- return;
+ return -ENODEV;
} /* axnet_config */
/*======================================================================
@@ -454,45 +434,29 @@ failed:
======================================================================*/
-static void axnet_release(dev_link_t *link)
+static void axnet_release(struct pcmcia_device *link)
{
- DEBUG(0, "axnet_release(0x%p)\n", link);
-
- pcmcia_release_configuration(link->handle);
- pcmcia_release_io(link->handle, &link->io);
- pcmcia_release_irq(link->handle, &link->irq);
-
- link->state &= ~DEV_CONFIG;
+ pcmcia_disable_device(link);
}
-static int axnet_suspend(struct pcmcia_device *p_dev)
+static int axnet_suspend(struct pcmcia_device *link)
{
- dev_link_t *link = dev_to_instance(p_dev);
struct net_device *dev = link->priv;
- link->state |= DEV_SUSPEND;
- if (link->state & DEV_CONFIG) {
- if (link->open)
- netif_device_detach(dev);
- pcmcia_release_configuration(link->handle);
- }
+ if (link->open)
+ netif_device_detach(dev);
return 0;
}
-static int axnet_resume(struct pcmcia_device *p_dev)
+static int axnet_resume(struct pcmcia_device *link)
{
- dev_link_t *link = dev_to_instance(p_dev);
struct net_device *dev = link->priv;
- link->state &= ~DEV_SUSPEND;
- if (link->state & DEV_CONFIG) {
- pcmcia_request_configuration(link->handle, &link->conf);
- if (link->open) {
- axnet_reset_8390(dev);
- AX88190_init(dev, 1);
- netif_device_attach(dev);
- }
+ if (link->open) {
+ axnet_reset_8390(dev);
+ AX88190_init(dev, 1);
+ netif_device_attach(dev);
}
return 0;
@@ -562,11 +526,11 @@ static void mdio_write(kio_addr_t addr, int phy_id, int loc, int value)
static int axnet_open(struct net_device *dev)
{
axnet_dev_t *info = PRIV(dev);
- dev_link_t *link = &info->link;
+ struct pcmcia_device *link = info->p_dev;
DEBUG(2, "axnet_open('%s')\n", dev->name);
- if (!DEV_OK(link))
+ if (!pcmcia_dev_present(link))
return -ENODEV;
link->open++;
@@ -588,7 +552,7 @@ static int axnet_open(struct net_device *dev)
static int axnet_close(struct net_device *dev)
{
axnet_dev_t *info = PRIV(dev);
- dev_link_t *link = &info->link;
+ struct pcmcia_device *link = info->p_dev;
DEBUG(2, "axnet_close('%s')\n", dev->name);
@@ -833,7 +797,7 @@ static struct pcmcia_driver axnet_cs_driver = {
.drv = {
.name = "axnet_cs",
},
- .probe = axnet_attach,
+ .probe = axnet_probe,
.remove = axnet_detach,
.id_table = axnet_ids,
.suspend = axnet_suspend,
@@ -1596,7 +1560,7 @@ static void ei_receive(struct net_device *dev)
static void ei_rx_overrun(struct net_device *dev)
{
- axnet_dev_t *info = (axnet_dev_t *)dev;
+ axnet_dev_t *info = PRIV(dev);
long e8390_base = dev->base_addr;
unsigned char was_txing, must_resend = 0;
struct ei_device *ei_local = (struct ei_device *) netdev_priv(dev);
@@ -1727,17 +1691,6 @@ static void do_set_multicast_list(struct net_device *dev)
memset(ei_local->mcfilter, 0xFF, 8);
}
- /*
- * DP8390 manuals don't specify any magic sequence for altering
- * the multicast regs on an already running card. To be safe, we
- * ensure multicast mode is off prior to loading up the new hash
- * table. If this proves to be not enough, we can always resort
- * to stopping the NIC, loading the table and then restarting.
- */
-
- if (netif_running(dev))
- outb_p(E8390_RXCONFIG, e8390_base + EN0_RXCR);
-
outb_p(E8390_NODMA + E8390_PAGE1, e8390_base + E8390_CMD);
for(i = 0; i < 8; i++)
{
@@ -1751,6 +1704,8 @@ static void do_set_multicast_list(struct net_device *dev)
outb_p(E8390_RXCONFIG | 0x48, e8390_base + EN0_RXCR);
else
outb_p(E8390_RXCONFIG | 0x40, e8390_base + EN0_RXCR);
+
+ outb_p(E8390_NODMA+E8390_PAGE0+E8390_START, e8390_base+E8390_CMD);
}
/*
OpenPOWER on IntegriCloud