Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/sgimips/dev Checkpoint if_mec work (just in case I ...



details:   https://anonhg.NetBSD.org/src/rev/ab4743abd0d6
branches:  trunk
changeset: 557534:ab4743abd0d6
user:      sekiya <sekiya%NetBSD.org@localhost>
date:      Sun Jan 11 14:01:46 2004 +0000

description:
Checkpoint if_mec work (just in case I get hit by a bus).  This driver is still
not operational.  The MII code mostly works, DMA data structures are defined
and allocated, but tx/rx logic is missing.

diffstat:

 sys/arch/sgimips/dev/if_mec.c    |  787 +++++++++++++++++++++++++++++++++-----
 sys/arch/sgimips/dev/if_mecreg.h |  125 ++++-
 2 files changed, 776 insertions(+), 136 deletions(-)

diffs (truncated from 1081 to 300 lines):

diff -r d7774323d244 -r ab4743abd0d6 sys/arch/sgimips/dev/if_mec.c
--- a/sys/arch/sgimips/dev/if_mec.c     Sun Jan 11 13:57:56 2004 +0000
+++ b/sys/arch/sgimips/dev/if_mec.c     Sun Jan 11 14:01:46 2004 +0000
@@ -1,7 +1,7 @@
-/*     $NetBSD: if_mec.c,v 1.12 2003/11/17 10:07:58 keihan Exp $       */
+/* $NetBSD: if_mec.c,v 1.13 2004/01/11 14:01:46 sekiya Exp $    */
 
 /*
- * Copyright (c) 2000 Soren S. Jorvang
+ * Copyright (c) 2003 Christopher SEKIYA
  * All rights reserved.
  *
  * Redistribution and use in source and binary forms, with or without
@@ -37,7 +37,7 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: if_mec.c,v 1.12 2003/11/17 10:07:58 keihan Exp $");
+__KERNEL_RCSID(0, "$NetBSD: if_mec.c,v 1.13 2004/01/11 14:01:46 sekiya Exp $");
 
 #include "opt_inet.h"
 #include "opt_ns.h"
@@ -77,6 +77,7 @@
 
 #include <machine/bus.h>
 #include <machine/intr.h>
+#include <machine/machtype.h>
 
 #include <dev/mii/mii.h>
 #include <dev/mii/miivar.h>
@@ -84,142 +85,308 @@
 #include <sgimips/dev/macevar.h>
 
 #include <sgimips/dev/if_mecreg.h>
+#include <dev/arcbios/arcbios.h>
+#include <dev/arcbios/arcbiosvar.h>
+
+struct mec_tx_dma_desc {
+       u_int64_t       command;
+       u_int64_t       concat[3];
+       u_int8_t        buffer[120];
+};
+
+#define MEC_NTXDESC             64
+#define MEC_NRXDESC             16
+
+struct mec_control {
+       struct mec_tx_dma_desc tx_desc[MEC_NRXDESC];
+};
 
 struct mec_softc {
-       struct device sc_dev;
+       struct device   sc_dev;
 
        bus_space_tag_t sc_st;
        bus_space_handle_t sc_sh;
-       bus_dma_tag_t sc_dmat;
+       bus_dma_tag_t   sc_dmat;
 
        struct ethercom sc_ethercom;
 
-       unsigned char sc_enaddr[ETHER_ADDR_LEN];
+       unsigned char   sc_enaddr[ETHER_ADDR_LEN];
 
-       void *sc_sdhook;
+       void           *sc_sdhook;
 
        struct mii_data sc_mii;
-       struct callout sc_callout;
+       int             phy;
+       struct callout  sc_callout;
+
+       struct mec_control *sc_control;
+
+       /* DMA structures for control data (DMA RX/TX descriptors) */
+       int             sc_ncdseg;
+       bus_dma_segment_t sc_cdseg;
+       bus_dmamap_t    sc_cdmap;
+       int             sc_nextrx;
+
+       /* DMA structures for TX packet data */
+       bus_dma_segment_t sc_txseg[MEC_NTXDESC];
+       bus_dmamap_t    sc_txmap[MEC_NTXDESC];
+       struct mbuf    *sc_txmbuf[MEC_NTXDESC];
+
+       int             sc_nexttx;
+       int             sc_prevtx;
+       int             sc_nfreetx;
+
+
+       bus_dma_segment_t rx_seg[16];
+       bus_dmamap_t    rx_map[16];
+       unsigned char  *rx_buf[16];
+       struct mbuf    *rx_mbuf[16];
+       int             rx_nseg;
+
+
+       caddr_t        *rx_buffer[16];
+       caddr_t        *tx_buffer;
+       u_int64_t       rx_read_ptr;
+       u_int64_t       rx_write_ptr;
+       u_int64_t       rx_read_length;
+       u_int64_t       rx_boffset;
+       u_int64_t       tx_read_ptr;
+       u_int64_t       tx_write_ptr;
+       u_int64_t       tx_available;
+       u_int64_t       tx_read_length;
+       u_int64_t       tx_boffset;
+       u_int64_t       me_rxdelay;
 
 #if NRND > 0
        rndsource_element_t rnd_source; /* random source */
 #endif
 };
 
-static int     mec_match(struct device *, struct cfdata *, void *);
-static void    mec_attach(struct device *, struct device *, void *);
-#if 0
-static void    mec_start(struct ifnet *);
-static void    mec_watchdog(struct ifnet *);
-static int     mec_ioctl(struct ifnet *, u_long, caddr_t);
-#endif
-static int     mec_mii_readreg(struct device *, int, int);
-static void    mec_mii_writereg(struct device *, int, int, int);
-static int     mec_mii_wait(struct mec_softc *);
-static void    mec_statchg(struct device *);
-static int     mec_mediachange(struct ifnet *);
-static void    mec_mediastatus(struct ifnet *, struct ifmediareq *);
+#define TX_RING_SIZE   16
+
+static int      mec_match(struct device *, struct cfdata *, void *);
+static void     mec_attach(struct device *, struct device *, void *);
+static void     mec_start(struct ifnet *);
+static void     mec_watchdog(struct ifnet *);
+static int      mec_ioctl(struct ifnet *, u_long, caddr_t);
+static int      mec_mii_readreg(struct device *, int, int);
+static void     mec_mii_writereg(struct device *, int, int, int);
+static int      mec_mii_wait(struct mec_softc *);
+static void     mec_statchg(struct device *);
+int             mec_mediachange(struct ifnet *);
+void            mec_mediastatus(struct ifnet *, struct ifmediareq *);
+void            enaddr_aton(const char *, u_int8_t *);
+void            mec_reset(struct mec_softc *);
+int             mec_init(struct ifnet * ifp);
+int             mec_intr(void *arg);
+void            mec_stop(struct ifnet * ifp, int disable);
+
+static void     mec_rxintr(struct mec_softc * sc, u_int64_t status);
 
 CFATTACH_DECL(mec, sizeof(struct mec_softc),
-    mec_match, mec_attach, NULL, NULL);
+             mec_match, mec_attach, NULL, NULL);
 
 static int
-mec_match(parent, match, aux)
-       struct device *parent;
-       struct cfdata *match;
-       void *aux;
+mec_match(struct device * parent, struct cfdata * match, void *aux)
 {
+       if (mach_type != MACH_SGI_IP32)
+               return 0;
        return 1;
 }
 
 static void
-mec_attach(parent, self, aux)
-       struct device *parent;
-       struct device *self;
-       void *aux;
+mec_attach(struct device * parent, struct device * self, void *aux)
 {
-       struct mec_softc *sc = (void *)self;
+       struct mec_softc *sc = (void *) self;
        struct mace_attach_args *maa = aux;
-       struct ifnet *ifp = &sc->sc_ethercom.ec_if;
-       u_int64_t address, command;
-       int i;
+       struct ifnet   *ifp = &sc->sc_ethercom.ec_if;
+       u_int64_t       command;
+       u_int64_t       address = 0;
+       char           *macaddr;
+       struct mii_softc *child;
+       int             i, err;
 
        sc->sc_st = maa->maa_st;
-       sc->sc_sh = maa->maa_sh;
+       if (bus_space_subregion(sc->sc_st, maa->maa_sh,
+                               maa->maa_offset, 0,
+                               &sc->sc_sh) != 0) {
+               printf(": can't map i/o space\n");
+               return;
+       }
+
+       /* Reset device */
+       bus_space_write_8(sc->sc_st, sc->sc_sh, MEC_MAC_CONTROL, MEC_MAC_CORE_RESET);
+       bus_space_write_8(sc->sc_st, sc->sc_sh, MEC_MAC_CONTROL, 0);
 
        printf(": MAC-110 Ethernet, ");
        command = bus_space_read_8(sc->sc_st, sc->sc_sh, MEC_MAC_CONTROL);
        printf("rev %lld\n",
-           (command & MEC_MAC_REVISION) >> MEC_MAC_REVISION_SHIFT);
+              (command & MEC_MAC_REVISION) >> MEC_MAC_REVISION_SHIFT);
 
-       /*
-        * The firmware has left us the station address.
-        */
-       address = bus_space_read_8(sc->sc_st, sc->sc_sh, MEC_STATION);
-       for (i = 0; i < ETHER_ADDR_LEN; i++) {
-               sc->sc_enaddr[ETHER_ADDR_LEN - 1 - i] = address & 0xff;
-               address >>= 8;
-       }
+       /* set up DMA structures */
 
-       printf("%s: station address %s\n", sc->sc_dev.dv_xname,
-           ether_sprintf(sc->sc_enaddr));
+       sc->sc_dmat = maa->maa_dmat;
 
        /*
-        * Reset device.
+        * Allocate the control data structures, and create and load the
+        * DMA map for it.
         */
-       bus_space_write_8(sc->sc_st, sc->sc_sh, MEC_MAC_CONTROL, 0);
-       delay(1000);
-
-       printf("%s: sorry, this is not a real driver\n", sc->sc_dev.dv_xname);
+       if ((err = bus_dmamem_alloc(sc->sc_dmat, sizeof(struct mec_control),
+                                   PAGE_SIZE, PAGE_SIZE, &sc->sc_cdseg,
+                                1, &sc->sc_ncdseg, BUS_DMA_NOWAIT)) != 0) {
+               printf(": unable to allocate control data, error = %d\n", err);
+               goto fail_0;
+       }
+       if ((err = bus_dmamem_map(sc->sc_dmat, &sc->sc_cdseg, sc->sc_ncdseg,
+                                 sizeof(struct mec_control),
+                                 (caddr_t *) & sc->sc_control,
+                                 BUS_DMA_NOWAIT | BUS_DMA_COHERENT)) != 0) {
+               printf(": unable to map control data, error = %d\n", err);
+               goto fail_1;
+       }
+       memset(sc->sc_control, 0, sizeof(struct mec_control));
 
-#if 0
-       strcpy(ifp->if_xname, sc->sc_dev.dv_xname);
-       ifp->if_softc = sc;
-       ifp->if_mtu = ETHERMTU;
-       ifp->if_flags = IFF_BROADCAST | IFF_SIMPLEX | IFF_MULTICAST;
-       ifp->if_ioctl = mec_ioctl;
-       ifp->if_start = mec_start;
-       ifp->if_watchdog = mec_watchdog;
-#endif
+       if ((err = bus_dmamap_create(sc->sc_dmat, sizeof(struct mec_control),
+                                  1, sizeof(struct mec_control), PAGE_SIZE,
+                                    BUS_DMA_NOWAIT, &sc->sc_cdmap)) != 0) {
+               printf(": unable to create DMA map for control data, error "
+                      "= %d\n", err);
+               goto fail_2;
+       }
+       if ((err = bus_dmamap_load(sc->sc_dmat, sc->sc_cdmap, sc->sc_control,
+                                  sizeof(struct mec_control),
+                                  NULL, BUS_DMA_NOWAIT)) != 0) {
+               printf(": unable to load DMA map for control data, error "
+                      "= %d\n", err);
+               goto fail_3;
+       }
+       /* Create transmit buffer DMA maps */
+       for (i = 0; i < MEC_NTXDESC; i++) {
+               if ((err = bus_dmamap_create(sc->sc_dmat, MCLBYTES, 1, MCLBYTES,
+                                            0, BUS_DMA_NOWAIT,
+                                            &sc->sc_txmap[i])) != 0) {
+                       printf(": unable to create tx DMA map %d, error = %d\n",
+                              i, err);
+                       goto fail_4;
+               }
+       }
+
+       /* Create the receive buffer DMA maps */
+       for (i = 0; i < 16; i++) {
+               if ((err = bus_dmamap_create(sc->sc_dmat, 4096,
+                                            1, 4096, PAGE_SIZE,
+                                   BUS_DMA_NOWAIT, &sc->rx_map[i])) != 0) {
+                       printf("%s: unable to create rx DMA map %d",
+                              sc->sc_dev.dv_xname, err);
+                       goto fail_5;
+               }
+       }
+
+       if ((macaddr = ARCBIOS->GetEnvironmentVariable("eaddr")) == NULL) {
+               panic(": unable to get MAC address!");
+       }
+       enaddr_aton(macaddr, sc->sc_enaddr);
+
+       for (i = 0; i < 6; i++) {
+               address = address << 8;
+               address += sc->sc_enaddr[i];
+       }
+
+       bus_space_write_8(sc->sc_st, sc->sc_sh, MEC_STATION, (address));
+
+       printf("%s: station address %s\n", sc->sc_dev.dv_xname,



Home | Main Index | Thread Index | Old Index