#include <linux/ioport.h>
#include <linux/bitops.h>
-#include <pcmcia/version.h>
#include <pcmcia/cs_types.h>
#include <pcmcia/cs.h>
#include <pcmcia/cistpl.h>
#define XIRCREG45_REV 15 /* Revision Register (rd) */
#define XIRCREG50_IA 8 /* Individual Address (8-13) */
-static char *if_names[] = { "Auto", "10BaseT", "10Base2", "AUI", "100BaseT" };
+static const char *if_names[] = { "Auto", "10BaseT", "10Base2", "AUI", "100BaseT" };
/****************
* All the PCMCIA modules use PCMCIA_DEBUG to control debugging. If
* and ejection events. They are invoked from the event handler.
*/
-static int has_ce2_string(dev_link_t * link);
-static void xirc2ps_config(dev_link_t * link);
-static void xirc2ps_release(dev_link_t * link);
-static int xirc2ps_event(event_t event, int priority,
- event_callback_args_t * args);
+static int has_ce2_string(struct pcmcia_device * link);
+static int xirc2ps_config(struct pcmcia_device * link);
+static void xirc2ps_release(struct pcmcia_device * link);
/****************
* The attach() and detach() entry points are used to create and destroy
* needed to manage one actual PCMCIA card.
*/
-static dev_link_t *xirc2ps_attach(void);
-static void xirc2ps_detach(dev_link_t *);
+static void xirc2ps_detach(struct pcmcia_device *p_dev);
/****************
* You'll also need to prototype all the functions that will actually
* less on other parts of the kernel.
*/
-static irqreturn_t xirc2ps_interrupt(int irq, void *dev_id, struct pt_regs *regs);
-
-/*
- * The dev_info variable is the "key" that is used to match up this
- * device driver with appropriate cards, through the card configuration
- * database.
- */
-
-static dev_info_t dev_info = "xirc2ps_cs";
+static irqreturn_t xirc2ps_interrupt(int irq, void *dev_id);
/****************
* A linked list of "instances" of the device. Each actual
* PCMCIA card corresponds to one device instance, and is described
- * by one dev_link_t structure (defined in ds.h).
+ * by one struct pcmcia_device structure (defined in ds.h).
*
* You may not want to use a linked list for this -- for example, the
- * memory card driver uses an array of dev_link_t pointers, where minor
+ * memory card driver uses an array of struct pcmcia_device pointers, where minor
* device numbers are used to derive the corresponding array index.
*/
-static dev_link_t *dev_list;
-
/****************
- * A dev_link_t structure has fields for most things that are needed
- * to keep track of a socket, but there will usually be some device
- * specific information that also needs to be kept track of. The
- * 'priv' pointer in a dev_link_t structure can be used to point to
- * a device-specific private data structure, like this.
- *
* A driver needs to provide a dev_node_t structure for each device
* on a card. In some cases, there is only one device per card (for
* example, ethernet cards, modems). In other cases, there may be
* many actual or logical devices (SCSI adapters, memory cards with
* multiple partitions). The dev_node_t structures need to be kept
- * in a linked list starting at the 'dev' field of a dev_link_t
+ * in a linked list starting at the 'dev' field of a struct pcmcia_device
* structure. We allocate them in the card's private data structure,
* because they generally can't be allocated dynamically.
*/
typedef struct local_info_t {
- dev_link_t link;
+ struct net_device *dev;
+ struct pcmcia_device *p_dev;
dev_node_t node;
struct net_device_stats stats;
int card_type;
void __iomem *dingo_ccr; /* only used for CEM56 cards */
unsigned last_ptr_value; /* last packets transmitted value */
const char *manf_str;
+ struct work_struct tx_timeout_task;
} local_info_t;
/****************
*/
static int do_start_xmit(struct sk_buff *skb, struct net_device *dev);
static void do_tx_timeout(struct net_device *dev);
+static void xirc2ps_tx_timeout_task(struct work_struct *work);
static struct net_device_stats *do_get_stats(struct net_device *dev);
static void set_addresses(struct net_device *dev);
static void set_multicast_list(struct net_device *dev);
-static int set_card_type(dev_link_t *link, const void *s);
+static int set_card_type(struct pcmcia_device *link, const void *s);
static int do_config(struct net_device *dev, struct ifmap *map);
static int do_open(struct net_device *dev);
static int do_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
-static struct ethtool_ops netdev_ethtool_ops;
+static const struct ethtool_ops netdev_ethtool_ops;
static void hardreset(struct net_device *dev);
static void do_reset(struct net_device *dev, int full);
static int init_mii(struct net_device *dev);
/*=============== Helper functions =========================*/
static int
-first_tuple(client_handle_t handle, tuple_t *tuple, cisparse_t *parse)
+first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse)
{
int err;
}
static int
-next_tuple(client_handle_t handle, tuple_t *tuple, cisparse_t *parse)
+next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse)
{
int err;
#define PutByte(reg,value) outb((value), ioaddr+(reg))
#define PutWord(reg,value) outw((value), ioaddr+(reg))
-#define Wait(n) do { \
- set_current_state(TASK_UNINTERRUPTIBLE); \
- schedule_timeout(n); \
-} while (0)
-
/*====== Functions used for debugging =================================*/
#if defined(PCMCIA_DEBUG) && 0 /* reading regs may change system status */
static void
* card insertion event.
*/
-static dev_link_t *
-xirc2ps_attach(void)
+static int
+xirc2ps_probe(struct pcmcia_device *link)
{
- client_reg_t client_reg;
- dev_link_t *link;
struct net_device *dev;
local_info_t *local;
- int err;
DEBUG(0, "attach()\n");
/* Allocate the device structure */
dev = alloc_etherdev(sizeof(local_info_t));
if (!dev)
- return NULL;
+ return -ENOMEM;
local = netdev_priv(dev);
- link = &local->link;
+ local->dev = dev;
+ local->p_dev = link;
link->priv = dev;
/* General socket configuration */
link->conf.Attributes = CONF_ENABLE_IRQ;
- link->conf.Vcc = 50;
link->conf.IntType = INT_MEMORY_AND_IO;
link->conf.ConfigIndex = 1;
- link->conf.Present = PRESENT_OPTION;
link->irq.Handler = xirc2ps_interrupt;
link->irq.Instance = dev;
#ifdef HAVE_TX_TIMEOUT
dev->tx_timeout = do_tx_timeout;
dev->watchdog_timeo = TX_TIMEOUT;
+ INIT_WORK(&local->tx_timeout_task, xirc2ps_tx_timeout_task);
#endif
- /* Register with Card Services */
- link->next = dev_list;
- dev_list = link;
- client_reg.dev_info = &dev_info;
- client_reg.EventMask =
- CS_EVENT_CARD_INSERTION | CS_EVENT_CARD_REMOVAL |
- CS_EVENT_RESET_PHYSICAL | CS_EVENT_CARD_RESET |
- CS_EVENT_PM_SUSPEND | CS_EVENT_PM_RESUME;
- client_reg.event_handler = &xirc2ps_event;
- client_reg.Version = 0x0210;
- client_reg.event_callback_args.client_data = link;
- if ((err = pcmcia_register_client(&link->handle, &client_reg))) {
- cs_error(link->handle, RegisterClient, err);
- xirc2ps_detach(link);
- return NULL;
- }
-
- return link;
+ return xirc2ps_config(link);
} /* xirc2ps_attach */
/****************
*/
static void
-xirc2ps_detach(dev_link_t * link)
+xirc2ps_detach(struct pcmcia_device *link)
{
struct net_device *dev = link->priv;
- dev_link_t **linkp;
DEBUG(0, "detach(0x%p)\n", link);
- /* Locate device structure */
- for (linkp = &dev_list; *linkp; linkp = &(*linkp)->next)
- if (*linkp == link)
- break;
- if (!*linkp) {
- DEBUG(0, "detach(0x%p): dev_link lost\n", link);
- return;
- }
-
- if (link->dev)
+ if (link->dev_node)
unregister_netdev(dev);
- /*
- * If the device is currently configured and active, we won't
- * actually delete it yet. Instead, it is marked so that when
- * the release() function is called, that will trigger a proper
- * detach().
- */
- if (link->state & DEV_CONFIG)
- xirc2ps_release(link);
-
- /* Break the link with Card Services */
- if (link->handle)
- pcmcia_deregister_client(link->handle);
+ xirc2ps_release(link);
- /* Unlink device structure, free it */
- *linkp = link->next;
free_netdev(dev);
} /* xirc2ps_detach */
*
*/
static int
-set_card_type(dev_link_t *link, const void *s)
+set_card_type(struct pcmcia_device *link, const void *s)
{
struct net_device *dev = link->priv;
local_info_t *local = netdev_priv(dev);
* Returns: true if this is a CE2
*/
static int
-has_ce2_string(dev_link_t * link)
+has_ce2_string(struct pcmcia_device * p_dev)
{
- client_handle_t handle = link->handle;
- tuple_t tuple;
- cisparse_t parse;
- u_char buf[256];
-
- tuple.Attributes = 0;
- tuple.TupleData = buf;
- tuple.TupleDataMax = 254;
- tuple.TupleOffset = 0;
- tuple.DesiredTuple = CISTPL_VERS_1;
- if (!first_tuple(handle, &tuple, &parse) && parse.version_1.ns > 2) {
- if (strstr(parse.version_1.str + parse.version_1.ofs[2], "CE2"))
- return 1;
- }
- return 0;
+ if (p_dev->prod_id[2] && strstr(p_dev->prod_id[2], "CE2"))
+ return 1;
+ return 0;
}
/****************
* is received, to configure the PCMCIA socket, and to make the
* ethernet device available to the system.
*/
-static void
-xirc2ps_config(dev_link_t * link)
+static int
+xirc2ps_config(struct pcmcia_device * link)
{
- client_handle_t handle = link->handle;
struct net_device *dev = link->priv;
local_info_t *local = netdev_priv(dev);
tuple_t tuple;
/* Is this a valid card */
tuple.DesiredTuple = CISTPL_MANFID;
- if ((err=first_tuple(handle, &tuple, &parse))) {
+ if ((err=first_tuple(link, &tuple, &parse))) {
printk(KNOT_XIRC "manfid not found in CIS\n");
goto failure;
}
goto failure;
}
- /* get configuration stuff */
- tuple.DesiredTuple = CISTPL_CONFIG;
- if ((err=first_tuple(handle, &tuple, &parse)))
- goto cis_error;
- link->conf.ConfigBase = parse.config.base;
- link->conf.Present = parse.config.rmask[0];
-
/* get the ethernet address from the CIS */
tuple.DesiredTuple = CISTPL_FUNCE;
- for (err = first_tuple(handle, &tuple, &parse); !err;
- err = next_tuple(handle, &tuple, &parse)) {
+ for (err = first_tuple(link, &tuple, &parse); !err;
+ err = next_tuple(link, &tuple, &parse)) {
/* Once I saw two CISTPL_FUNCE_LAN_NODE_ID entries:
* the first one with a length of zero the second correct -
* so I skip all entries with length 0 */
}
if (err) { /* not found: try to get the node-id from tuple 0x89 */
tuple.DesiredTuple = 0x89; /* data layout looks like tuple 0x22 */
- if ((err = pcmcia_get_first_tuple(handle, &tuple)) == 0 &&
- (err = pcmcia_get_tuple_data(handle, &tuple)) == 0) {
+ if ((err = pcmcia_get_first_tuple(link, &tuple)) == 0 &&
+ (err = pcmcia_get_tuple_data(link, &tuple)) == 0) {
if (tuple.TupleDataLen == 8 && *buf == CISTPL_FUNCE_LAN_NODE_ID)
memcpy(&parse, buf, 8);
else
}
if (err) { /* another try (James Lehmer's CE2 version 4.1)*/
tuple.DesiredTuple = CISTPL_FUNCE;
- for (err = first_tuple(handle, &tuple, &parse); !err;
- err = next_tuple(handle, &tuple, &parse)) {
+ for (err = first_tuple(link, &tuple, &parse); !err;
+ err = next_tuple(link, &tuple, &parse)) {
if (parse.funce.type == 0x02 && parse.funce.data[0] == 1
&& parse.funce.data[1] == 6 && tuple.TupleDataLen == 13) {
buf[1] = 4;
for (i=0; i < 6; i++)
dev->dev_addr[i] = node_id->id[i];
- /* Configure card */
- link->state |= DEV_CONFIG;
-
link->io.IOAddrLines =10;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
link->irq.Attributes = IRQ_HANDLE_PRESENT;
* Ethernet port */
link->io.NumPorts1 = 16; /* no Mako stuff anymore */
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
- for (err = first_tuple(handle, &tuple, &parse); !err;
- err = next_tuple(handle, &tuple, &parse)) {
+ for (err = first_tuple(link, &tuple, &parse); !err;
+ err = next_tuple(link, &tuple, &parse)) {
if (cf->io.nwin > 0 && (cf->io.win[0].base & 0xf) == 8) {
for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) {
link->conf.ConfigIndex = cf->index ;
link->io.BasePort2 = cf->io.win[0].base;
link->io.BasePort1 = ioaddr;
- if (!(err=pcmcia_request_io(link->handle, &link->io)))
+ if (!(err=pcmcia_request_io(link, &link->io)))
goto port_found;
}
}
*/
for (pass=0; pass < 2; pass++) {
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
- for (err = first_tuple(handle, &tuple, &parse); !err;
- err = next_tuple(handle, &tuple, &parse)){
+ for (err = first_tuple(link, &tuple, &parse); !err;
+ err = next_tuple(link, &tuple, &parse)){
if (cf->io.nwin > 0 && (cf->io.win[0].base & 0xf) == 8){
link->conf.ConfigIndex = cf->index ;
link->io.BasePort2 = cf->io.win[0].base;
link->io.BasePort1 = link->io.BasePort2
+ (pass ? (cf->index & 0x20 ? -24:8)
: (cf->index & 0x20 ? 8:-24));
- if (!(err=pcmcia_request_io(link->handle, &link->io)))
+ if (!(err=pcmcia_request_io(link, &link->io)))
goto port_found;
}
}
link->io.NumPorts1 = 16;
for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) {
link->io.BasePort1 = ioaddr;
- if (!(err=pcmcia_request_io(link->handle, &link->io)))
+ if (!(err=pcmcia_request_io(link, &link->io)))
goto port_found;
}
link->io.BasePort1 = 0; /* let CS decide */
- if ((err=pcmcia_request_io(link->handle, &link->io))) {
- cs_error(link->handle, RequestIO, err);
+ if ((err=pcmcia_request_io(link, &link->io))) {
+ cs_error(link, RequestIO, err);
goto config_error;
}
}
* Now allocate an interrupt line. Note that this does not
* actually assign a handler to the interrupt.
*/
- if ((err=pcmcia_request_irq(link->handle, &link->irq))) {
- cs_error(link->handle, RequestIRQ, err);
+ if ((err=pcmcia_request_irq(link, &link->irq))) {
+ cs_error(link, RequestIRQ, err);
goto config_error;
}
* This actually configures the PCMCIA socket -- setting up
* the I/O windows and the interrupt mapping.
*/
- if ((err=pcmcia_request_configuration(link->handle, &link->conf))) {
- cs_error(link->handle, RequestConfiguration, err);
+ if ((err=pcmcia_request_configuration(link, &link->conf))) {
+ cs_error(link, RequestConfiguration, err);
goto config_error;
}
reg.Action = CS_WRITE;
reg.Offset = CISREG_IOBASE_0;
reg.Value = link->io.BasePort2 & 0xff;
- if ((err = pcmcia_access_configuration_register(link->handle, ®))) {
- cs_error(link->handle, AccessConfigurationRegister, err);
+ if ((err = pcmcia_access_configuration_register(link, ®))) {
+ cs_error(link, AccessConfigurationRegister, err);
goto config_error;
}
reg.Action = CS_WRITE;
reg.Offset = CISREG_IOBASE_1;
reg.Value = (link->io.BasePort2 >> 8) & 0xff;
- if ((err = pcmcia_access_configuration_register(link->handle, ®))) {
- cs_error(link->handle, AccessConfigurationRegister, err);
+ if ((err = pcmcia_access_configuration_register(link, ®))) {
+ cs_error(link, AccessConfigurationRegister, err);
goto config_error;
}
req.Attributes = WIN_DATA_WIDTH_8|WIN_MEMORY_TYPE_AM|WIN_ENABLE;
req.Base = req.Size = 0;
req.AccessSpeed = 0;
- if ((err = pcmcia_request_window(&link->handle, &req, &link->win))) {
- cs_error(link->handle, RequestWindow, err);
+ if ((err = pcmcia_request_window(&link, &req, &link->win))) {
+ cs_error(link, RequestWindow, err);
goto config_error;
}
local->dingo_ccr = ioremap(req.Base,0x1000) + 0x0800;
mem.CardOffset = 0x0;
mem.Page = 0;
if ((err = pcmcia_map_mem_page(link->win, &mem))) {
- cs_error(link->handle, MapMemPage, err);
+ cs_error(link, MapMemPage, err);
goto config_error;
}
if (local->dingo)
do_reset(dev, 1); /* a kludge to make the cem56 work */
- link->dev = &local->node;
- link->state &= ~DEV_CONFIG_PENDING;
- SET_NETDEV_DEV(dev, &handle_to_dev(handle));
+ link->dev_node = &local->node;
+ SET_NETDEV_DEV(dev, &handle_to_dev(link));
if ((err=register_netdev(dev))) {
printk(KNOT_XIRC "register_netdev() failed\n");
- link->dev = NULL;
+ link->dev_node = NULL;
goto config_error;
}
printk("%c%02X", i?':':' ', dev->dev_addr[i]);
printk("\n");
- return;
+ return 0;
config_error:
- link->state &= ~DEV_CONFIG_PENDING;
xirc2ps_release(link);
- return;
+ return -ENODEV;
- cis_error:
- printk(KNOT_XIRC "unable to parse CIS\n");
failure:
- link->state &= ~DEV_CONFIG_PENDING;
+ return -ENODEV;
} /* xirc2ps_config */
/****************
* still open, this will be postponed until it is closed.
*/
static void
-xirc2ps_release(dev_link_t *link)
+xirc2ps_release(struct pcmcia_device *link)
{
+ DEBUG(0, "release(0x%p)\n", link);
- DEBUG(0, "release(0x%p)\n", link);
-
- if (link->win) {
- struct net_device *dev = link->priv;
- local_info_t *local = netdev_priv(dev);
- if (local->dingo)
- iounmap(local->dingo_ccr - 0x0800);
- pcmcia_release_window(link->win);
- }
- pcmcia_release_configuration(link->handle);
- pcmcia_release_io(link->handle, &link->io);
- pcmcia_release_irq(link->handle, &link->irq);
- link->state &= ~DEV_CONFIG;
-
+ if (link->win) {
+ struct net_device *dev = link->priv;
+ local_info_t *local = netdev_priv(dev);
+ if (local->dingo)
+ iounmap(local->dingo_ccr - 0x0800);
+ }
+ pcmcia_disable_device(link);
} /* xirc2ps_release */
/*====================================================================*/
-/****************
- * The card status event handler. Mostly, this schedules other
- * stuff to run after an event is received. A CARD_REMOVAL event
- * also sets some flags to discourage the net drivers from trying
- * to talk to the card any more.
- *
- * When a CARD_REMOVAL event is received, we immediately set a flag
- * to block future accesses to this device. All the functions that
- * actually access the device should check this flag to make sure
- * the card is still present.
- */
-static int
-xirc2ps_event(event_t event, int priority,
- event_callback_args_t * args)
+static int xirc2ps_suspend(struct pcmcia_device *link)
{
- dev_link_t *link = args->client_data;
- struct net_device *dev = link->priv;
-
- DEBUG(0, "event(%d)\n", (int)event);
+ struct net_device *dev = link->priv;
- switch (event) {
- case CS_EVENT_REGISTRATION_COMPLETE:
- DEBUG(0, "registration complete\n");
- break;
- case CS_EVENT_CARD_REMOVAL:
- link->state &= ~DEV_PRESENT;
- if (link->state & DEV_CONFIG)
- netif_device_detach(dev);
- break;
- case CS_EVENT_CARD_INSERTION:
- link->state |= DEV_PRESENT | DEV_CONFIG_PENDING;
- xirc2ps_config(link);
- break;
- case CS_EVENT_PM_SUSPEND:
- link->state |= DEV_SUSPEND;
- /* Fall through... */
- case CS_EVENT_RESET_PHYSICAL:
- if (link->state & DEV_CONFIG) {
- if (link->open) {
+ if (link->open) {
netif_device_detach(dev);
do_powerdown(dev);
- }
- pcmcia_release_configuration(link->handle);
}
- break;
- case CS_EVENT_PM_RESUME:
- link->state &= ~DEV_SUSPEND;
- /* Fall through... */
- case CS_EVENT_CARD_RESET:
- if (link->state & DEV_CONFIG) {
- pcmcia_request_configuration(link->handle, &link->conf);
- if (link->open) {
+
+ return 0;
+}
+
+static int xirc2ps_resume(struct pcmcia_device *link)
+{
+ struct net_device *dev = link->priv;
+
+ if (link->open) {
do_reset(dev,1);
netif_device_attach(dev);
- }
}
- break;
- }
- return 0;
-} /* xirc2ps_event */
+
+ return 0;
+}
+
/*====================================================================*/
* This is the Interrupt service route.
*/
static irqreturn_t
-xirc2ps_interrupt(int irq, void *dev_id, struct pt_regs *regs)
+xirc2ps_interrupt(int irq, void *dev_id)
{
struct net_device *dev = (struct net_device *)dev_id;
local_info_t *lp = netdev_priv(dev);
/*====================================================================*/
static void
-do_tx_timeout(struct net_device *dev)
+xirc2ps_tx_timeout_task(struct work_struct *work)
{
- local_info_t *lp = netdev_priv(dev);
- printk(KERN_NOTICE "%s: transmit timed out\n", dev->name);
- lp->stats.tx_errors++;
+ local_info_t *local =
+ container_of(work, local_info_t, tx_timeout_task);
+ struct net_device *dev = local->dev;
/* reset the card */
do_reset(dev,1);
dev->trans_start = jiffies;
netif_wake_queue(dev);
}
+static void
+do_tx_timeout(struct net_device *dev)
+{
+ local_info_t *lp = netdev_priv(dev);
+ lp->stats.tx_errors++;
+ printk(KERN_NOTICE "%s: transmit timed out\n", dev->name);
+ schedule_work(&lp->tx_timeout_task);
+}
+
static int
do_start_xmit(struct sk_buff *skb, struct net_device *dev)
{
kio_addr_t ioaddr = dev->base_addr;
int okay;
unsigned freespace;
- unsigned pktlen = skb? skb->len : 0;
+ unsigned pktlen = skb->len;
DEBUG(1, "do_start_xmit(skb=%p, dev=%p) len=%u\n",
skb, dev, pktlen);
*/
if (pktlen < ETH_ZLEN)
{
- skb = skb_padto(skb, ETH_ZLEN);
- if (skb == NULL)
+ if (skb_padto(skb, ETH_ZLEN))
return 0;
pktlen = ETH_ZLEN;
}
do_open(struct net_device *dev)
{
local_info_t *lp = netdev_priv(dev);
- dev_link_t *link = &lp->link;
+ struct pcmcia_device *link = lp->p_dev;
DEBUG(0, "do_open(%p)\n", dev);
/* Check that the PCMCIA card is still here. */
/* Physical device present signature. */
- if (!DEV_OK(link))
+ if (!pcmcia_dev_present(link))
return -ENODEV;
/* okay */
sprintf(info->bus_info, "PCMCIA 0x%lx", dev->base_addr);
}
-static struct ethtool_ops netdev_ethtool_ops = {
+static const struct ethtool_ops netdev_ethtool_ops = {
.get_drvinfo = netdev_get_drvinfo,
};
switch(cmd) {
case SIOCGMIIPHY: /* Get the address of the PHY in use. */
data[0] = 0; /* we have only this address */
- /* fall trough */
+ /* fall through */
case SIOCGMIIREG: /* Read the specified MII register. */
data[3] = mii_rd(ioaddr, data[0] & 0x1f, data[1] & 0x1f);
break;
SelectPage(4);
udelay(1);
PutByte(XIRCREG4_GPR1, 0); /* clear bit 0: power down */
- Wait(HZ/25); /* wait 40 msec */
+ msleep(40); /* wait 40 msec */
if (local->mohawk)
PutByte(XIRCREG4_GPR1, 1); /* set bit 0: power up */
else
PutByte(XIRCREG4_GPR1, 1 | 4); /* set bit 0: power up, bit 2: AIC */
- Wait(HZ/50); /* wait 20 msec */
+ msleep(20); /* wait 20 msec */
}
static void
hardreset(dev);
PutByte(XIRCREG_CR, SoftReset); /* set */
- Wait(HZ/50); /* wait 20 msec */
+ msleep(20); /* wait 20 msec */
PutByte(XIRCREG_CR, 0); /* clear */
- Wait(HZ/25); /* wait 40 msec */
+ msleep(40); /* wait 40 msec */
if (local->mohawk) {
SelectPage(4);
/* set pin GP1 and GP2 to output (0x0c)
}
/* give the circuits some time to power up */
- Wait(HZ/2); /* about 500ms */
+ msleep(500); /* about 500ms */
local->last_ptr_value = 0;
local->silicon = local->mohawk ? (GetByte(XIRCREG4_BOV) & 0x70) >> 4
SelectPage(0x42);
PutByte(XIRCREG42_SWC1, 0x80);
}
- Wait(HZ/25); /* wait 40 msec to let it complete */
+ msleep(40); /* wait 40 msec to let it complete */
#ifdef PCMCIA_DEBUG
if (pc_debug) {
printk(KERN_INFO "%s: MII selected\n", dev->name);
SelectPage(2);
PutByte(XIRCREG2_MSR, GetByte(XIRCREG2_MSR) | 0x08);
- Wait(HZ/50);
+ msleep(20);
} else {
printk(KERN_INFO "%s: MII detected; using 10mbs\n",
dev->name);
PutByte(XIRCREG42_SWC1, 0xC0);
else /* enable 10BaseT */
PutByte(XIRCREG42_SWC1, 0x80);
- Wait(HZ/25); /* wait 40 msec to let it complete */
+ msleep(40); /* wait 40 msec to let it complete */
}
if (full_duplex)
PutByte(XIRCREG1_ECR, GetByte(XIRCREG1_ECR | FullDuplex));
* Fixme: Better to use a timer here!
*/
for (i=0; i < 35; i++) {
- Wait(HZ/10); /* wait 100 msec */
+ msleep(100); /* wait 100 msec */
status = mii_rd(ioaddr, 0, 1);
if ((status & 0x0020) && (status & 0x0004))
break;
{
kio_addr_t ioaddr = dev->base_addr;
local_info_t *lp = netdev_priv(dev);
- dev_link_t *link = &lp->link;
+ struct pcmcia_device *link = lp->p_dev;
DEBUG(0, "do_stop(%p)\n", dev);
return 0;
}
+static struct pcmcia_device_id xirc2ps_ids[] = {
+ PCMCIA_PFC_DEVICE_MANF_CARD(0, 0x0089, 0x110a),
+ PCMCIA_PFC_DEVICE_MANF_CARD(0, 0x0138, 0x110a),
+ PCMCIA_PFC_DEVICE_PROD_ID13(0, "Xircom", "CEM28", 0x2e3ee845, 0x0ea978ea),
+ PCMCIA_PFC_DEVICE_PROD_ID13(0, "Xircom", "CEM33", 0x2e3ee845, 0x80609023),
+ PCMCIA_PFC_DEVICE_PROD_ID13(0, "Xircom", "CEM56", 0x2e3ee845, 0xa650c32a),
+ PCMCIA_PFC_DEVICE_PROD_ID13(0, "Xircom", "REM10", 0x2e3ee845, 0x76df1d29),
+ PCMCIA_PFC_DEVICE_PROD_ID13(0, "Xircom", "XEM5600", 0x2e3ee845, 0xf1403719),
+ PCMCIA_PFC_DEVICE_PROD_ID12(0, "Xircom", "CreditCard Ethernet+Modem II", 0x2e3ee845, 0xeca401bf),
+ PCMCIA_DEVICE_MANF_CARD(0x01bf, 0x010a),
+ PCMCIA_DEVICE_PROD_ID13("Toshiba Information Systems", "TPCENET", 0x1b3b94fe, 0xf381c1a2),
+ PCMCIA_DEVICE_PROD_ID13("Xircom", "CE3-10/100", 0x2e3ee845, 0x0ec0ac37),
+ PCMCIA_DEVICE_PROD_ID13("Xircom", "PS-CE2-10", 0x2e3ee845, 0x947d9073),
+ PCMCIA_DEVICE_PROD_ID13("Xircom", "R2E-100BTX", 0x2e3ee845, 0x2464a6e3),
+ PCMCIA_DEVICE_PROD_ID13("Xircom", "RE-10", 0x2e3ee845, 0x3e08d609),
+ PCMCIA_DEVICE_PROD_ID13("Xircom", "XE2000", 0x2e3ee845, 0xf7188e46),
+ PCMCIA_DEVICE_PROD_ID12("Compaq", "Ethernet LAN Card", 0x54f7c49c, 0x9fd2f0a2),
+ PCMCIA_DEVICE_PROD_ID12("Compaq", "Netelligent 10/100 PC Card", 0x54f7c49c, 0xefe96769),
+ PCMCIA_DEVICE_PROD_ID12("Intel", "EtherExpress(TM) PRO/100 PC Card Mobile Adapter16", 0x816cc815, 0x174397db),
+ PCMCIA_DEVICE_PROD_ID12("Toshiba", "10/100 Ethernet PC Card", 0x44a09d9c, 0xb44deecf),
+ /* also matches CFE-10 cards! */
+ /* PCMCIA_DEVICE_MANF_CARD(0x0105, 0x010a), */
+ PCMCIA_DEVICE_NULL,
+};
+MODULE_DEVICE_TABLE(pcmcia, xirc2ps_ids);
+
+
static struct pcmcia_driver xirc2ps_cs_driver = {
.owner = THIS_MODULE,
.drv = {
.name = "xirc2ps_cs",
},
- .attach = xirc2ps_attach,
- .detach = xirc2ps_detach,
+ .probe = xirc2ps_probe,
+ .remove = xirc2ps_detach,
+ .id_table = xirc2ps_ids,
+ .suspend = xirc2ps_suspend,
+ .resume = xirc2ps_resume,
};
static int __init
exit_xirc2ps_cs(void)
{
pcmcia_unregister_driver(&xirc2ps_cs_driver);
- BUG_ON(dev_list != NULL);
}
module_init(init_xirc2ps_cs);
MAYBE_SET(lockup_hack, 6);
#undef MAYBE_SET
- return 0;
+ return 1;
}
__setup("xirc2ps_cs=", setup_xirc2ps_cs);