Attempted patch for 3c515 for PnP

From: Stephen Frost (sfrost@ns.snowman.net)
Date: Sun Feb 27 2000 - 21:33:45 EST


        Welp, I took a crack at patching up 3c515.c to get it to support
the kernel-level isaPnP. Apparently I missed something somewhere. :) I
based my attempt off of what I saw in 3c509.c. I got it to come up and
detect the card and get an io port and irq that appeared reasonable. The
problem I ran into was when I would ifconfig the interface it would come
back and complain "SIOCSIFFLAGS: No such device." The patch follows, any
thoughts from folks out there as to what I missed? :) Thanks.

                Stephen

--- linux/drivers/net/3c515.c.orig Sun Feb 27 16:17:39 2000
+++ linux-2.3.48/drivers/net/3c515.c Sun Feb 27 21:17:27 2000
@@ -46,6 +46,7 @@
 
 #include <linux/module.h>
 #include <linux/version.h>
+#include <linux/isapnp.h>
 
 #include <linux/kernel.h>
 #include <linux/sched.h>
@@ -349,6 +350,21 @@
         { "Default", 0, 0xFF, XCVR_10baseT, 10000},
 };
 
+#ifdef CONFIG_ISAPNP
+struct corkscrew_isapnp_adapters_struct {
+ unsigned short vendor, function;
+ char *name;
+};
+struct corkscrew_isapnp_adapters_struct corkscrew_isapnp_adapters[] = {
+ {ISAPNP_VENDOR('T', 'C', 'M'), ISAPNP_FUNCTION(0x5051), "3Com Fast EtherLink ISA"},
+ {0, }
+};
+u16 corkscrew_isapnp_phys_addr[3] = {
+ 0, 0, 0
+};
+#endif
+static int nopnp = 0;
+
 static int corkscrew_scan(struct net_device *dev);
 static struct net_device *corkscrew_found_device(struct net_device *dev,
                                                  int ioaddr, int irq,
@@ -422,11 +438,79 @@
 static int corkscrew_scan(struct net_device *dev)
 {
         int cards_found = 0;
+ short i;
         static int ioaddr = 0x100;
+ static int pnp_cards = 0;
+
+#ifdef CONFIG_ISAPNP
+ if(nopnp == 1)
+ goto no_pnp;
+ for(i=0; corkscrew_isapnp_adapters[i].vendor != 0; i++) {
+ struct pci_dev *idev = NULL;
+ int irq, j;
+ while((idev = isapnp_find_dev(NULL,
+ corkscrew_isapnp_adapters[i].vendor,
+ corkscrew_isapnp_adapters[i].function,
+ idev))) {
+ if(idev->prepare(idev)<0)
+ continue;
+ if (!(idev->resource[0].flags & IORESOURCE_IO))
+ continue;
+ /* Deactivation is needed if the driver was called
+ with "nopnp=1" before, does not harm if not. */
+ idev->deactivate(idev);
+ if(idev->activate(idev)<0) {
+ printk("isapnp configure failed (out of resources?)\n");
+ return -ENOMEM;
+ }
+ if (!idev->resource[0].start || check_region(idev->resource[0].start,16))
+ continue;
+ ioaddr = idev->resource[0].start;
+ irq = idev->irq_resource[0].start;
+ if(corkscrew_debug)
+ printk ("ISAPNP reports %s at i/o 0x%x, irq %d\n",
+ corkscrew_isapnp_adapters[i].name,ioaddr, irq);
+
+ if ((inw(ioaddr + 0x2002) & 0x1f0) != (ioaddr & 0x1f0))
+ continue;
+ /* Verify by reading the device ID from the EEPROM. */
+ {
+ int timer;
+ outw(EEPROM_Read + 7, ioaddr + Wn0EepromCmd);
+ /* Pause for at least 162 us. for the read to take place. */
+ for (timer = 4; timer >= 0; timer--) {
+ udelay(162);
+ if ((inw(ioaddr + Wn0EepromCmd) & 0x0200)
+ == 0)
+ break;
+ }
+ if (inw(ioaddr + Wn0EepromData) != 0x6d50)
+ continue;
+ }
+ printk(KERN_INFO "3c515 Resource configuraiton register %#4.4x, DCR %4.4x.\n",
+ inl(ioaddr + 0x2002), inw(ioaddr + 0x2000));
+ /* irq = inw(ioaddr + 0x2002) & 15; */ /* Use the irq from isapnp */
+ corkscrew_isapnp_phys_addr[pnp_cards] = ioaddr;
+ corkscrew_found_device(dev, ioaddr, irq, CORKSCREW_ID, dev
+ && dev->mem_start ? dev->
+ mem_start : options[cards_found]);
+ dev = 0;
+ pnp_cards++;
+ cards_found++;
+ }
+ }
+no_pnp:
+#endif /* not CONFIG_ISAPNP */
 
         /* Check all locations on the ISA bus -- evil! */
         for (; ioaddr < 0x400; ioaddr += 0x20) {
                 int irq;
+#ifdef CONFIG_ISAPNP
+ /* Make sure this was not already picked up by isapnp */
+ if(ioaddr == corkscrew_isapnp_phys_addr[0]) continue;
+ if(ioaddr == corkscrew_isapnp_phys_addr[1]) continue;
+ if(ioaddr == corkscrew_isapnp_phys_addr[2]) continue;
+#endif
                 if (check_region(ioaddr, CORKSCREW_TOTAL_SIZE))
                         continue;
                 /* Check the resource configuration for a matching ioaddr. */
@@ -455,7 +539,6 @@
                 dev = 0;
                 cards_found++;
         }
-
         if (corkscrew_debug)
                 printk(KERN_INFO "%d 3c515 cards found.\n", cards_found);
         return cards_found;

-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@vger.rutgers.edu
Please read the FAQ at http://www.tux.org/lkml/



This archive was generated by hypermail 2b29 : Tue Feb 29 2000 - 21:00:18 EST