]> git.lizzy.rs Git - plan9front.git/blobdiff - sys/src/9/pc/ether82563.c
devether: mux bridges, portable netconsole
[plan9front.git] / sys / src / 9 / pc / ether82563.c
index 6cf819881a86568c70a5a00d079013a17ab5f3d8..1fa71c6f600f06cb0f10cafd23d1d7d8b8951895 100644 (file)
@@ -11,8 +11,7 @@
 #include "io.h"
 #include "../port/error.h"
 #include "../port/netif.h"
-
-#include "etherif.h"
+#include "../port/etherif.h"
 
 /*
  * note: the 82575, 82576 and 82580 are operated using registers aliased
@@ -105,6 +104,9 @@ enum {
        Torl            = 0xC0/4,       /* Total Octets Received */
        Totl            = 0xC8/4,       /* Total Octets Transmitted */
        Nstatistics     = 0x124/4,
+
+       /* iNVM (i211) */
+       Invmdata0       = 0x12120,
 };
 
 enum {                                 /* Ctrl */
@@ -128,6 +130,7 @@ enum {                                      /* Status */
 enum {                                 /* Eec */
        Nvpres          = 1<<8,
        Autord          = 1<<9,
+       Flupd           = 1<<19,
        Sec1val         = 1<<22,
 };
 
@@ -490,7 +493,7 @@ static Ctlrtype cttab[Nctlrtype] = {
 [i210]         "i210",         9728,   F75|Fnofct|Fert,
 [i217]         "i217",         9728,   Fload|Fnofct|Fert|Fbadcsum,
 [i218]         "i218",         9728,   Fload|Fert|F79phy|Fnofct|Fbadcsum,
-[i219]         "i219",         9728,   Fload|Fert|F79phy|Fnofct,
+[i219]         "i219",         9728,   Fload|Fert|F79phy|Fnofct|Fbadcsum,
 [i350]         "i350",         9728,   F75|F79phy|Fnofct,
 };
 
@@ -1059,7 +1062,7 @@ i82563rproc(void *arg)
                                        bp->checksum = rd->checksum;
                                        bp->flag |= Bpktck;
                                }
-                               etheriq(edev, bp, 1);
+                               etheriq(edev, bp);
                        } else
                                freeb(bp);
                        ctlr->rb[rdh] = nil;
@@ -1687,6 +1690,40 @@ out:
        return sum;
 }
 
+static int
+invmload(Ctlr *c)
+{
+       int i, a;
+       u32int w;
+
+       memset(c->eeprom, 0xFF, sizeof(c->eeprom));
+       for(i=0; i<64; i++){
+               w = csr32r(c, Invmdata0 + i*4);
+               switch(w & 7){
+               case 0: // uninitialized structure
+                       break;
+               case 1: // word auto load
+                       a = (w & 0xFE00) >> 9;
+                       if(a < nelem(c->eeprom))
+                               c->eeprom[a] = w >> 16;
+                       continue;
+               case 2: // csr auto load
+                       i++;
+               case 3: // phy auto load
+                       continue;
+               case 4: // rsa key sha256
+                       i += 256/32;
+               case 5: // invalidated structure
+                       continue;
+               default:
+                       print("invm: %.2x %.8ux\n", i, w);
+                       continue;
+               }
+               break;
+       }
+       return 0;
+}
+
 static void
 defaultea(Ctlr *ctlr, uchar *ra)
 {
@@ -1716,17 +1753,22 @@ static int
 i82563reset(Ctlr *ctlr)
 {
        uchar *ra;
-       int i, r;
+       int i, r, flag;
 
        if(i82563detach(ctlr))
                return -1;
-       if(cttab[ctlr->type].flag & Fload)
+       flag = cttab[ctlr->type].flag;
+
+       if(ctlr->type == i210 && (csr32r(ctlr, Eec) & Flupd) == 0)
+               r = invmload(ctlr);
+       else if(flag & Fload)
                r = fload(ctlr);
        else
                r = eeload(ctlr);
+
        if(r != 0 && r != 0xbaba){
                print("%s: bad eeprom checksum - %#.4ux", cname(ctlr), r);
-               if(cttab[ctlr->type].flag & Fbadcsum)
+               if(flag & Fbadcsum)
                        print("; ignored\n");
                else {
                        print("\n");
@@ -1747,12 +1789,12 @@ i82563reset(Ctlr *ctlr)
                csr32w(ctlr, Mta + i*4, 0);
        csr32w(ctlr, Fcal, 0x00C28001);
        csr32w(ctlr, Fcah, 0x0100);
-       if((cttab[ctlr->type].flag & Fnofct) == 0)
+       if((flag & Fnofct) == 0)
                csr32w(ctlr, Fct, 0x8808);
        csr32w(ctlr, Fcttv, 0x0100);
        csr32w(ctlr, Fcrtl, ctlr->fcrtl);
        csr32w(ctlr, Fcrth, ctlr->fcrth);
-       if(cttab[ctlr->type].flag & F75)
+       if(flag & F75)
                csr32w(ctlr, Eitr, 128<<2);             /* 128 ¼ microsecond intervals */
        return 0;
 }
@@ -1918,7 +1960,14 @@ didtype(int d)
        case 0x1506:            /* v */
        case 0x150c:            /* untested */
                return i82583;
-       case 0x1533:            /* copper */
+       case 0x1533:            /* i210-t1 */
+       case 0x1534:            /* i210 */
+       case 0x1536:            /* i210-fiber */
+       case 0x1537:            /* i210-backplane */
+       case 0x1538:            /* i210 sgmii */
+       case 0x1539:            /* i211 copper */
+       case 0x157b:            /* i210 copper flashless */
+       case 0x157c:            /* i210 serdes flashless */
                return i210;
        case 0x153a:            /* i217-lm */
        case 0x153b:            /* i217-v */
@@ -1940,12 +1989,16 @@ didtype(int d)
        case 0x15d8:            /* i219-v */
        case 0x15e3:            /* i219-lm */
                return i219;
-       case 0x151f:            /* “powerville” eeprom-less */
-       case 0x1521:            /* copper */
-       case 0x1522:            /* fiber */
-       case 0x1523:            /* serdes */
-       case 0x1524:            /* sgmii */
-       case 0x1546:            /* untested */
+       case 0x151f:            /* i350 “powerville” eeprom-less */
+       case 0x1521:            /* i350 copper */
+       case 0x1522:            /* i350 fiber */
+       case 0x1523:            /* i350 serdes */
+       case 0x1524:            /* i350 sgmii */
+       case 0x1546:            /* i350 DA4 (untested) */
+       case 0x1f40:            /* i354 backplane */
+       case 0x1f41:            /* i354 sgmii */
+       case 0x1f42:            /* i354 sgmii (c2000) */
+       case 0x1f45:            /* i354 backplane 2.5 */
                return i350;
        }
        return -1;
@@ -2051,7 +2104,6 @@ pnp(Ether *edev, int type)
         */
        edev->attach = i82563attach;
 //     edev->transmit = i82563transmit;
-       edev->interrupt = i82563interrupt;
        edev->ifstat = i82563ifstat;
        edev->ctl = i82563ctl;
 
@@ -2060,6 +2112,8 @@ pnp(Ether *edev, int type)
        edev->shutdown = i82563shutdown;
        edev->multicast = i82563multicast;
 
+       intrenable(edev->irq, i82563interrupt, edev, edev->tbdf, edev->name);
+
        return 0;
 }