File:  [DragonFly] / src / sys / contrib / dev / oltr / Attic / if_oltr.c
Revision 1.8: download - view: text, annotated - select for diffs
Tue Jan 6 01:40:45 2004 UTC (10 years, 10 months ago) by dillon
Branches: MAIN
CVS tags: HEAD
if_xname support Part 1/2: Convert most of the netif devices to use
if_initname().

Submitted-by: Max Laier <max@love2party.net>

    1: /*
    2:  * Copyright (c) 1998, Larry Lile
    3:  * All rights reserved.
    4:  *
    5:  * For latest sources and information on this driver, please
    6:  * go to http://anarchy.stdio.com.
    7:  *
    8:  * Questions, comments or suggestions should be directed to
    9:  * Larry Lile <lile@stdio.com>.
   10:  *
   11:  * Redistribution and use in source and binary forms, with or without
   12:  * modification, are permitted provided that the following conditions
   13:  * are met:
   14:  * 1. Redistributions of source code must retain the above copyright
   15:  *    notice unmodified, this list of conditions, and the following
   16:  *    disclaimer.
   17:  * 2. Redistributions in binary form must reproduce the above copyright
   18:  *    notice, this list of conditions and the following disclaimer in the
   19:  *    documentation and/or other materials provided with the distribution.
   20:  *
   21:  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
   22:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
   23:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
   24:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
   25:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
   26:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
   27:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
   28:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
   29:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
   30:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
   31:  * SUCH DAMAGE.
   32:  *
   33:  * $FreeBSD: src/sys/contrib/dev/oltr/if_oltr.c,v 1.11.2.5 2001/10/20 04:15:21 mdodd Exp $
   34:  * $DragonFly: src/sys/contrib/dev/oltr/if_oltr.c,v 1.8 2004/01/06 01:40:45 dillon Exp $
   35:  */
   36: 
   37: #include <sys/param.h>
   38: #include <sys/systm.h>
   39: #include <sys/sockio.h>
   40: #include <sys/mbuf.h>
   41: #include <sys/malloc.h>
   42: #include <sys/kernel.h>
   43: #include <sys/socket.h>
   44: #include <sys/param.h>
   45: 
   46: #include <net/if.h>
   47: #include <net/if_arp.h>
   48: #include <net/iso88025.h>
   49: #include <net/ethernet.h>
   50: #include <net/if_dl.h>
   51: #include <net/if_media.h>
   52: #include <net/iso88025.h>
   53: 
   54: #if (__FreeBSD_version < 400000)
   55: #include <bpfilter.h>
   56: #endif
   57: 
   58: #if (NBPFILTER > 0) || (__FreeBSD_version > 400000)
   59: #include <net/bpf.h>
   60: #endif
   61: 
   62: #include <vm/vm.h>              /* for vtophys */
   63: #include <vm/pmap.h>            /* for vtophys */
   64: #include <machine/bus_memio.h>
   65: #include <machine/bus_pio.h>
   66: #include <machine/bus.h>
   67: #include <machine/resource.h>
   68: #include <machine/clock.h>
   69: #include <sys/bus.h>
   70: #include <sys/rman.h>
   71: 
   72: #include <bus/pci/pcireg.h>
   73: #include <bus/pci/pcivar.h>
   74: 
   75: #include "contrib/dev/oltr/trlld.h"
   76: 
   77: /*#define DEBUG_MASK DEBUG_POLL*/
   78: 
   79: #ifndef DEBUG_MASK
   80: #define DEBUG_MASK 0x0000
   81: #endif
   82: 
   83: #define DEBUG_POLL	0x0001
   84: #define DEBUG_INT	0x0002
   85: #define DEBUG_INIT	0x0004
   86: #define DEBUG_FN_ENT	0x8000
   87: 
   88: #define PCI_VENDOR_OLICOM 0x108D
   89: 
   90: #define MIN3(A,B,C) (MIN(A, (MIN(B, C))))
   91: 
   92: char *AdapterName[] = {
   93: 	/*  0 */ "Olicom XT Adapter [unsupported]",
   94: 	/*  1 */ "Olicom OC-3115",
   95: 	/*  2 */ "Olicom ISA 16/4 Adapter (OC-3117)",
   96: 	/*  3 */ "Olicom ISA 16/4 Adapter (OC-3118)",
   97: 	/*  4 */ "Olicom MCA 16/4 Adapter (OC-3129) [unsupported]",
   98: 	/*  5 */ "Olicom MCA 16/4 Adapter (OC-3129) [unsupported]",
   99: 	/*  6 */ "Olicom MCA 16/4 Adapter (OC-3129) [unsupported]",
  100: 	/*  7 */ "Olicom EISA 16/4 Adapter (OC-3133)",
  101: 	/*  8 */ "Olicom EISA 16/4 Adapter (OC-3133)",
  102: 	/*  9 */ "Olicom EISA 16/4 Server Adapter (OC-3135)",
  103: 	/* 10 */ "Olicom PCI 16/4 Adapter (OC-3136)",
  104: 	/* 11 */ "Olicom PCI 16/4 Adapter (OC-3136)",
  105: 	/* 12 */ "Olicom PCI/II 16/4 Adapter (OC-3137)",
  106: 	/* 13 */ "Olicom PCI 16/4 Adapter (OC-3139)",
  107: 	/* 14 */ "Olicom RapidFire 3140 16/4 PCI Adapter (OC-3140)",
  108: 	/* 15 */ "Olicom RapidFire 3141 Fiber Adapter (OC-3141)",
  109: 	/* 16 */ "Olicom PCMCIA 16/4 Adapter (OC-3220) [unsupported]",
  110: 	/* 17 */ "Olicom PCMCIA 16/4 Adapter (OC-3121, OC-3230, OC-3232) [unsupported]",
  111: 	/* 18 */ "Olicom PCMCIA 16/4 Adapter (OC-3250)",
  112: 	/* 19 */ "Olicom RapidFire 3540 100/16/4 Adapter (OC-3540)"
  113: };
  114: 
  115: /*
  116:  * Glue function prototypes for PMW kit IO
  117:  */
  118: 
  119: #ifndef TRlldInlineIO
  120: static void DriverOutByte	(unsigned short, unsigned char);
  121: static void DriverOutWord	(unsigned short, unsigned short);
  122: static void DriverOutDword	(unsigned short, unsigned long);
  123: static void DriverRepOutByte	(unsigned short, unsigned char  *, int);
  124: static void DriverRepOutWord	(unsigned short, unsigned short *, int);
  125: static void DriverRepOutDword	(unsigned short, unsigned long  *, int);
  126: static unsigned char  DriverInByte (unsigned short);
  127: static unsigned short DriverInWord (unsigned short);
  128: static unsigned long  DriverInDword (unsigned short);
  129: static void DriverRepInByte	(unsigned short, unsigned char  *, int);
  130: static void DriverRepInWord	(unsigned short, unsigned short *, int);
  131: static void DriverRepInDword	(unsigned short, unsigned long  *, int);
  132: #endif /*TRlldInlineIO*/
  133: static void DriverSuspend	(unsigned short);
  134: static void DriverStatus	(void *, TRlldStatus_t *);
  135: static void DriverCloseCompleted (void *);
  136: static void DriverStatistics	(void *, TRlldStatistics_t *);
  137: static void DriverTransmitFrameCompleted (void *, void *, int);
  138: static void DriverReceiveFrameCompleted	(void *, int, int, void *, int);
  139: 
  140: static TRlldDriver_t LldDriver = {
  141: 	TRLLD_VERSION,
  142: #ifndef TRlldInlineIO
  143: 	DriverOutByte,
  144: 	DriverOutWord,
  145: 	DriverOutDword,
  146: 	DriverRepOutByte,
  147: 	DriverRepOutWord,
  148: 	DriverRepOutDword,
  149: 	DriverInByte,
  150: 	DriverInWord,
  151: 	DriverInDword,
  152: 	DriverRepInByte,
  153: 	DriverRepInWord,
  154: 	DriverRepInDword,
  155: #endif /*TRlldInlineIO*/
  156: 	DriverSuspend,
  157: 	DriverStatus,
  158: 	DriverCloseCompleted,
  159: 	DriverStatistics,
  160: 	DriverTransmitFrameCompleted,
  161: 	DriverReceiveFrameCompleted,
  162: };
  163: 
  164: struct oltr_rx_buf {
  165: 	int			index;
  166: 	char			*data;
  167: 	u_long			address;
  168: };
  169: 
  170: struct oltr_tx_buf {
  171: 	int			index;
  172: 	char 			*data;
  173: 	u_long			address;
  174: };
  175: 
  176: #define RING_BUFFER_LEN		16
  177: #define RING_BUFFER(x)		((RING_BUFFER_LEN - 1) & x)
  178: #define RX_BUFFER_LEN		2048
  179: #define TX_BUFFER_LEN		2048
  180: 
  181: struct oltr_softc {
  182: 	struct arpcom		arpcom;
  183: 	struct ifmedia		ifmedia;
  184: 	bus_space_handle_t	oltr_bhandle;
  185: 	bus_space_tag_t		oltr_btag;
  186: 	void			*oltr_intrhand;
  187: 	struct resource		*oltr_irq;
  188: 	struct resource		*oltr_res;
  189: 	int			unit;
  190: 	int 			state;
  191: #define OL_UNKNOWN	0
  192: #define OL_INIT		1
  193: #define OL_READY	2
  194: #define OL_CLOSING	3
  195: #define OL_CLOSED	4
  196: #define OL_OPENING	5
  197: #define OL_OPEN		6
  198: #define OL_PROMISC	7
  199: #define OL_DEAD		8
  200: 	struct oltr_rx_buf	rx_ring[RING_BUFFER_LEN];
  201: 	int			tx_head, tx_avail, tx_frame;
  202: 	struct oltr_tx_buf	tx_ring[RING_BUFFER_LEN];
  203: 	TRlldTransmit_t		frame_ring[RING_BUFFER_LEN];
  204: 	struct mbuf		*restart;
  205: 	TRlldAdapter_t		TRlldAdapter;
  206: 	TRlldStatistics_t	statistics;
  207: 	TRlldStatistics_t	current;
  208:         TRlldAdapterConfig_t    config;
  209: 	u_short			AdapterMode;
  210: 	u_long			GroupAddress;
  211: 	u_long			FunctionalAddress;
  212: 	struct callout_handle	oltr_poll_ch;
  213: 	/*struct callout_handle	oltr_stat_ch;*/
  214: 	void			*work_memory;
  215: };
  216: 
  217: #define SELF_TEST_POLLS	32
  218: 
  219: void oltr_poll 			(void *);
  220: /*void oltr_stat 			(void *);*/
  221: 
  222: static void oltr_start		(struct ifnet *);
  223: static void oltr_stop		(struct oltr_softc *);
  224: static void oltr_close		(struct oltr_softc *);
  225: static void oltr_init		(void *);
  226: static int oltr_ioctl		(struct ifnet *, u_long, caddr_t);
  227: static void oltr_intr		(void *);
  228: static int oltr_ifmedia_upd	(struct ifnet *);
  229: static void oltr_ifmedia_sts	(struct ifnet *, struct ifmediareq *);
  230: 
  231: #if __FreeBSD_version > 400000
  232: 
  233: static int oltr_pci_probe		(device_t);
  234: static int oltr_pci_attach	(device_t);
  235: static int oltr_pci_detach	(device_t);
  236: static void oltr_pci_shutdown	(device_t);
  237: 
  238: static device_method_t oltr_methods[] = {
  239: 	DEVMETHOD(device_probe,		oltr_pci_probe),
  240: 	DEVMETHOD(device_attach,	oltr_pci_attach),
  241: 	DEVMETHOD(device_detach,	oltr_pci_detach),
  242: 	DEVMETHOD(device_shutdown,	oltr_pci_shutdown),
  243:         { 0, 0 }
  244: };
  245: 
  246: static driver_t oltr_driver = {
  247: 	"oltr",
  248: 	oltr_methods,
  249: 	sizeof(struct oltr_softc)
  250: };
  251: 
  252: static devclass_t oltr_devclass;
  253: 
  254: DRIVER_MODULE(oltr, pci, oltr_driver, oltr_devclass, 0, 0);
  255: 
  256: static int
  257: oltr_pci_probe(device_t dev)
  258: {
  259:         int                     i, rc;
  260:         char                    PCIConfigHeader[64];
  261:         TRlldAdapterConfig_t    config;
  262: 
  263:         if ((pci_get_vendor(dev) == PCI_VENDOR_OLICOM) &&
  264:            ((pci_get_device(dev) == 0x0001) ||
  265: 	    (pci_get_device(dev) == 0x0004) ||
  266:             (pci_get_device(dev) == 0x0005) ||
  267: 	    (pci_get_device(dev) == 0x0007) ||
  268:             (pci_get_device(dev) == 0x0008))) {
  269: 
  270:                 for (i = 0; i < sizeof(PCIConfigHeader); i++)
  271:                         PCIConfigHeader[i] = pci_read_config(dev, i, 1);
  272: 
  273:                 rc = TRlldPCIConfig(&LldDriver, &config, PCIConfigHeader);
  274:                 if (rc == TRLLD_PCICONFIG_FAIL) {
  275:                         device_printf(dev, "TRlldPciConfig failed!\n");
  276:                         return(ENXIO);
  277:                 }
  278:                 if (rc == TRLLD_PCICONFIG_VERSION) {
  279:                         device_printf(dev, "wrong LLD version\n");
  280:                         return(ENXIO);
  281:                 }
  282:                 device_set_desc(dev, AdapterName[config.type]);
  283:                 return(0);
  284:         }
  285:         return(ENXIO);
  286: }
  287: 
  288: static int
  289: oltr_pci_attach(device_t dev)
  290: {
  291:         int 			i, s, rc = 0, rid,
  292: 				scratch_size;
  293: 	int			media = IFM_TOKEN|IFM_TOK_UTP16;
  294: 	u_long 			command;
  295: 	char 			PCIConfigHeader[64];
  296: 	struct oltr_softc		*sc = device_get_softc(dev);
  297: 	struct ifnet		*ifp = &sc->arpcom.ac_if;
  298: 
  299:         s = splimp();
  300: 
  301:        	bzero(sc, sizeof(struct oltr_softc));
  302: 	sc->unit = device_get_unit(dev);
  303: 	sc->state = OL_UNKNOWN;
  304: 
  305: 	for (i = 0; i < sizeof(PCIConfigHeader); i++)
  306: 		PCIConfigHeader[i] = pci_read_config(dev, i, 1);
  307: 
  308: 	switch(TRlldPCIConfig(&LldDriver, &sc->config, PCIConfigHeader)) {
  309: 	case TRLLD_PCICONFIG_OK:
  310: 		break;
  311: 	case TRLLD_PCICONFIG_SET_COMMAND:
  312: 		device_printf(dev, "enabling bus master mode\n");
  313: 		command = pci_read_config(dev, PCIR_COMMAND, 4);
  314: 		pci_write_config(dev, PCIR_COMMAND,
  315: 			(command | PCIM_CMD_BUSMASTEREN), 4);
  316: 		command = pci_read_config(dev, PCIR_COMMAND, 4);
  317: 		if (!(command & PCIM_CMD_BUSMASTEREN)) {
  318: 			device_printf(dev, "failed to enable bus master mode\n");
  319: 			goto config_failed;
  320: 		}
  321: 		break;
  322: 	case TRLLD_PCICONFIG_FAIL:
  323: 		device_printf(dev, "TRlldPciConfig failed!\n");
  324: 		goto config_failed;
  325: 		break;
  326: 	case TRLLD_PCICONFIG_VERSION:
  327: 		device_printf(dev, "wrong LLD version\n");
  328: 		goto config_failed;
  329: 		break;
  330: 	}
  331: 	device_printf(dev, "MAC address %6D\n", sc->config.macaddress, ":");
  332: 
  333: 	scratch_size = TRlldAdapterSize();
  334: 	if (bootverbose)
  335: 		device_printf(dev, "adapter memory block size %d bytes\n", scratch_size);
  336: 	sc->TRlldAdapter = (TRlldAdapter_t)malloc(scratch_size, M_DEVBUF, M_NOWAIT);
  337: 	if (sc->TRlldAdapter == NULL) {
  338: 		device_printf(dev, "couldn't allocate scratch buffer (%d bytes)\n", scratch_size);
  339: 		goto config_failed;
  340: 	}
  341: 
  342: 	/*
  343: 	 * Allocate RX/TX Pools
  344: 	 */
  345: 	for (i = 0; i < RING_BUFFER_LEN; i++) {
  346: 		sc->rx_ring[i].index = i;
  347: 		sc->rx_ring[i].data = (char *)malloc(RX_BUFFER_LEN, M_DEVBUF, M_NOWAIT);
  348: 		sc->rx_ring[i].address = vtophys(sc->rx_ring[i].data);
  349: 		sc->tx_ring[i].index = i;
  350: 		sc->tx_ring[i].data = (char *)malloc(TX_BUFFER_LEN, M_DEVBUF, M_NOWAIT);
  351: 		sc->tx_ring[i].address = vtophys(sc->tx_ring[i].data);
  352: 		if ((!sc->rx_ring[i].data) || (!sc->tx_ring[i].data)) {
  353: 			device_printf(dev, "unable to allocate ring buffers\n");
  354: 			while (i > 0) {
  355: 				if (sc->rx_ring[i].data)
  356: 					free(sc->rx_ring[i].data, M_DEVBUF);
  357: 				if (sc->tx_ring[i].data)
  358: 					free(sc->tx_ring[i].data, M_DEVBUF);
  359: 				i--;
  360: 			}
  361: 			goto config_failed;
  362: 		}
  363: 	}
  364: 	
  365: 	/*
  366: 	 * Allocate interrupt and DMA channel
  367: 	 */
  368: 	rid = 0;
  369: 	sc->oltr_irq = bus_alloc_resource(dev, SYS_RES_IRQ, &rid, 0, ~0, 1,
  370: 		(sc->config.mode & TRLLD_MODE_SHARE_INTERRUPT ? RF_ACTIVE | RF_SHAREABLE : RF_ACTIVE));
  371: 	if (sc->oltr_irq == NULL) {
  372: 		device_printf(dev, "couldn't map interrupt\n");
  373: 		goto config_failed;
  374: 	}
  375: 	if (bus_setup_intr(dev, sc->oltr_irq, INTR_TYPE_NET, oltr_intr, sc, &sc->oltr_intrhand)) {
  376: 		device_printf(dev, "couldn't setup interrupt\n");
  377: 		bus_release_resource(dev, SYS_RES_IRQ, 0, sc->oltr_irq);
  378: 		goto config_failed;
  379: 	}
  380: 
  381: 	/*
  382: 	 * Do the ifnet initialization
  383: 	 */
  384: 	ifp->if_softc	= sc;
  385: 	if_initname(ifp, "oltr", device_get_unit(dev));
  386: 	ifp->if_output	= iso88025_output;
  387: 	ifp->if_init	= oltr_init;
  388: 	ifp->if_start	= oltr_start;
  389: 	ifp->if_ioctl	= oltr_ioctl;
  390: 	ifp->if_flags	= IFF_BROADCAST;
  391: 	bcopy(sc->config.macaddress, sc->arpcom.ac_enaddr, sizeof(sc->config.macaddress));
  392: 
  393: 	/*
  394: 	 * Do ifmedia setup.
  395: 	 */
  396: 	ifmedia_init(&sc->ifmedia, 0, oltr_ifmedia_upd, oltr_ifmedia_sts);
  397: 	rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_16MBPS);
  398: 	switch(sc->config.type) {
  399: 	case TRLLD_ADAPTER_PCI7:	/* OC-3540 */
  400: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP100, 0, NULL);
  401: 		/* FALL THROUGH */
  402: 	case TRLLD_ADAPTER_PCI4:	/* OC-3139 */
  403: 	case TRLLD_ADAPTER_PCI5:	/* OC-3140 */
  404: 	case TRLLD_ADAPTER_PCI6:	/* OC-3141 */
  405: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_AUTO, 0, NULL);
  406: 		media = IFM_TOKEN|IFM_AUTO;
  407: 		rc = TRlldSetSpeed(sc->TRlldAdapter, 0);
  408: 		/* FALL THROUGH */
  409: 	default:
  410: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP4, 0, NULL);
  411: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP16, 0, NULL);
  412: 		break;
  413: 	}
  414: 	sc->ifmedia.ifm_media = media;
  415: 	ifmedia_set(&sc->ifmedia, media);
  416: 
  417: 	/*
  418: 	 * Attach the interface
  419: 	 */
  420: 	if_attach(ifp);
  421: 	ifp->if_snd.ifq_maxlen = IFQ_MAXLEN;
  422: 	iso88025_ifattach(ifp);
  423: 
  424: #if (NBPFILTER > 0) || (__FreeBSD_version > 400000)
  425: 	bpfattach(ifp, DLT_IEEE802, sizeof(struct iso88025_header));
  426: #endif
  427: 
  428: 	splx(s);
  429: 	return(0);
  430: 
  431: config_failed:
  432: 
  433: 	splx(s);
  434: 	return(ENXIO);
  435: }
  436: 
  437: static int
  438: oltr_pci_detach(device_t dev)
  439: {
  440: 	struct oltr_softc	*sc = device_get_softc(dev);
  441: 	struct ifnet		*ifp = &sc->arpcom.ac_if;
  442: 	int s, i;
  443: 
  444: 	device_printf(dev, "driver unloading\n");
  445: 
  446: 	s = splimp();
  447: 
  448: 	if_detach(ifp);
  449: 	if (sc->state > OL_CLOSED)
  450: 		oltr_stop(sc);
  451: 
  452: 	untimeout(oltr_poll, (void *)sc, sc->oltr_poll_ch);
  453: 	/*untimeout(oltr_stat, (void *)sc, sc->oltr_stat_ch);*/
  454: 
  455: 	bus_teardown_intr(dev, sc->oltr_irq, sc->oltr_intrhand);
  456: 	bus_release_resource(dev, SYS_RES_IRQ, 0, sc->oltr_irq);
  457: 
  458: 	/* Deallocate all dynamic memory regions */
  459: 	for (i = 0; i < RING_BUFFER_LEN; i++) {
  460: 		free(sc->rx_ring[i].data, M_DEVBUF);
  461: 		free(sc->tx_ring[i].data, M_DEVBUF);
  462: 	}
  463: 	if (sc->work_memory)
  464: 		free(sc->work_memory, M_DEVBUF);
  465: 	free(sc->TRlldAdapter, M_DEVBUF);
  466: 
  467: 	(void)splx(s);
  468: 
  469: 	return(0);
  470: }
  471: 
  472: static void
  473: oltr_pci_shutdown(device_t dev)
  474: {
  475: 	struct oltr_softc		*sc = device_get_softc(dev);
  476: 
  477: 	device_printf(dev, "oltr_pci_shutdown called\n");
  478: 
  479: 	if (sc->state > OL_CLOSED)
  480: 		oltr_stop(sc);
  481: 
  482: 	return;
  483: }
  484: 
  485: #else
  486: 
  487: static const char *oltr_pci_probe	(pcici_t, pcidi_t);
  488: static void oltr_pci_attach		(pcici_t, int);
  489: 
  490: static unsigned long oltr_count = 0;
  491: 
  492: static struct pci_device oltr_device = {
  493: 	"oltr",
  494: 	oltr_pci_probe,
  495: 	oltr_pci_attach,
  496: 	&oltr_count,
  497: 	NULL
  498: };
  499: 
  500: DATA_SET(pcidevice_set, oltr_device);
  501: 
  502: static const char *
  503: oltr_pci_probe(pcici_t config_id, pcidi_t device_id)
  504: {
  505:         int                     i, rc;
  506:         char                    PCIConfigHeader[64];
  507:         TRlldAdapterConfig_t    config;
  508: 	
  509: 	if (((device_id & 0xffff) == PCI_VENDOR_OLICOM) && (
  510: 	    (((device_id >> 16) & 0xffff) == 0x0001) ||
  511: 	    (((device_id >> 16) & 0xffff) == 0x0004) ||
  512: 	    (((device_id >> 16) & 0xffff) == 0x0005) ||
  513: 	    (((device_id >> 16) & 0xffff) == 0x0007) ||
  514: 	    (((device_id >> 16) & 0xffff) == 0x0008))) {
  515: 	
  516: 		for (i = 0; i < 64; i++)
  517: 			PCIConfigHeader[i] = pci_cfgread(config_id, i, /* bytes */ 1);
  518: 
  519: 		rc = TRlldPCIConfig(&LldDriver, &config, PCIConfigHeader);
  520: 
  521: 		if (rc == TRLLD_PCICONFIG_FAIL) {
  522: 			printf("oltr: TRlldPciConfig failed!\n");
  523: 			return(NULL);
  524: 		}
  525: 		if (rc == TRLLD_PCICONFIG_VERSION) {
  526: 			printf("oltr: wrong LLD version.\n");
  527: 			return(NULL);
  528: 		}
  529: 		return(AdapterName[config.type]);
  530: 	}
  531: 
  532: 	return(NULL);
  533: }
  534: 
  535: static void
  536: oltr_pci_attach(pcici_t config_id, int unit)
  537: {
  538:         int 			i, s, rc = 0, scratch_size;
  539: 	int			media = IFM_TOKEN|IFM_TOK_UTP16;
  540: 	u_long 			command;
  541: 	char 			PCIConfigHeader[64];
  542: 	struct oltr_softc		*sc;
  543: 	struct ifnet		*ifp; /* = &sc->arpcom.ac_if; */
  544: 
  545:         s = splimp();
  546: 
  547: 	sc = malloc(sizeof(struct oltr_softc), M_DEVBUF, M_NOWAIT | M_ZERO);
  548: 	if (sc == NULL) {
  549: 		printf("oltr%d: no memory for softc struct!\n", unit);
  550: 		goto config_failed;
  551: 	}
  552: 	sc->unit = unit;
  553: 	sc->state = OL_UNKNOWN;
  554: 	ifp = &sc->arpcom.ac_if;
  555: 
  556: 	for (i = 0; i < sizeof(PCIConfigHeader); i++)
  557: 		PCIConfigHeader[i] = pci_cfgread(config_id, i, 1);
  558: 
  559: 	switch(TRlldPCIConfig(&LldDriver, &sc->config, PCIConfigHeader)) {
  560: 	case TRLLD_PCICONFIG_OK:
  561: 		break;
  562: 	case TRLLD_PCICONFIG_SET_COMMAND:
  563: 		printf("oltr%d: enabling bus master mode\n", unit);
  564: 		command = pci_conf_read(config_id, PCIR_COMMAND);
  565: 		pci_conf_write(config_id, PCIR_COMMAND, (command | PCIM_CMD_BUSMASTEREN));
  566: 		command = pci_conf_read(config_id, PCIR_COMMAND);
  567: 		if (!(command & PCIM_CMD_BUSMASTEREN)) {
  568: 			printf("oltr%d: failed to enable bus master mode\n", unit);
  569: 			goto config_failed;
  570: 		}
  571: 		break;
  572: 	case TRLLD_PCICONFIG_FAIL:
  573: 		printf("oltr%d: TRlldPciConfig failed!\n", unit);
  574: 		goto config_failed;
  575: 		break;
  576: 	case TRLLD_PCICONFIG_VERSION:
  577: 		printf("oltr%d: wrong LLD version\n", unit);
  578: 		goto config_failed;
  579: 		break;
  580: 	}
  581: 	printf("oltr%d: MAC address %6D\n", unit, sc->config.macaddress, ":");
  582: 
  583: 	scratch_size = TRlldAdapterSize();
  584: 	if (bootverbose)
  585: 		printf("oltr%d: adapter memory block size %d bytes\n", unit, scratch_size);
  586: 	sc->TRlldAdapter = (TRlldAdapter_t)malloc(scratch_size, M_DEVBUF, M_NOWAIT);
  587: 	if (sc->TRlldAdapter == NULL) {
  588: 		printf("oltr%d: couldn't allocate scratch buffer (%d bytes)\n",unit, scratch_size);
  589: 		goto config_failed;
  590: 	}
  591: 
  592: 	/*
  593: 	 * Allocate RX/TX Pools
  594: 	 */
  595: 	for (i = 0; i < RING_BUFFER_LEN; i++) {
  596: 		sc->rx_ring[i].index = i;
  597: 		sc->rx_ring[i].data = (char *)malloc(RX_BUFFER_LEN, M_DEVBUF, M_NOWAIT);
  598: 		sc->rx_ring[i].address = vtophys(sc->rx_ring[i].data);
  599: 		sc->tx_ring[i].index = i;
  600: 		sc->tx_ring[i].data = (char *)malloc(TX_BUFFER_LEN, M_DEVBUF, M_NOWAIT);
  601: 		sc->tx_ring[i].address = vtophys(sc->tx_ring[i].data);
  602: 		if ((!sc->rx_ring[i].data) || (!sc->tx_ring[i].data)) {
  603: 			printf("oltr%d: unable to allocate ring buffers\n", unit);
  604: 			while (i > 0) {
  605: 				if (sc->rx_ring[i].data)
  606: 					free(sc->rx_ring[i].data, M_DEVBUF);
  607: 				if (sc->tx_ring[i].data)
  608: 					free(sc->tx_ring[i].data, M_DEVBUF);
  609: 				i--;
  610: 			}
  611: 			goto config_failed;
  612: 		}
  613: 	}
  614: 	
  615: 	/*
  616: 	 * Allocate interrupt and DMA channel
  617: 	 */
  618: 	if (!pci_map_int(config_id, oltr_intr, sc, &net_imask)) {
  619: 		printf("oltr%d: couldn't setup interrupt\n", unit);
  620: 		goto config_failed;
  621: 	}
  622: 
  623: 	/*
  624: 	 * Do the ifnet initialization
  625: 	 */
  626: 	ifp->if_softc	= sc;
  627: 	if_initname(ifp, "oltr", unit);
  628: 	ifp->if_output	= iso88025_output;
  629: 	ifp->if_init	= oltr_init;
  630: 	ifp->if_start	= oltr_start;
  631: 	ifp->if_ioctl	= oltr_ioctl;
  632: 	ifp->if_flags	= IFF_BROADCAST;
  633: 	bcopy(sc->config.macaddress, sc->arpcom.ac_enaddr, sizeof(sc->config.macaddress));
  634: 
  635: 	/*
  636: 	 * Do ifmedia setup.
  637: 	 */
  638: 	ifmedia_init(&sc->ifmedia, 0, oltr_ifmedia_upd, oltr_ifmedia_sts);
  639: 	rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_16MBPS);
  640: 	switch(sc->config.type) {
  641: 	case TRLLD_ADAPTER_PCI7:	/* OC-3540 */
  642: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP100, 0, NULL);
  643: 		/* FALL THROUGH */
  644: 	case TRLLD_ADAPTER_PCI4:	/* OC-3139 */
  645: 	case TRLLD_ADAPTER_PCI5:	/* OC-3140 */
  646: 	case TRLLD_ADAPTER_PCI6:	/* OC-3141 */
  647: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_AUTO, 0, NULL);
  648: 		media = IFM_TOKEN|IFM_AUTO;
  649: 		rc = TRlldSetSpeed(sc->TRlldAdapter, 0);
  650: 		/* FALL THROUGH */
  651: 	default:
  652: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP4, 0, NULL);
  653: 		ifmedia_add(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP16, 0, NULL);
  654: 		break;
  655: 	}
  656: 	sc->ifmedia.ifm_media = media;
  657: 	ifmedia_set(&sc->ifmedia, media);
  658: 
  659: 	/*
  660: 	 * Attach the interface
  661: 	 */
  662: 	if_attach(ifp);
  663: 	ifp->if_snd.ifq_maxlen = IFQ_MAXLEN;
  664: 	iso88025_ifattach(ifp);
  665: 
  666: #if (NBPFILTER > 0) || (__FreeBSD_version > 400000)
  667: 	bpfattach(ifp, DLT_IEEE802, sizeof(struct iso88025_header));
  668: #endif
  669: 
  670: 	splx(s);
  671: 	return;
  672: 
  673: config_failed:
  674:         (void)splx(s);
  675: 
  676: 	return;
  677: }
  678: 
  679: #endif
  680: 
  681: static void
  682: oltr_intr(void *xsc)
  683: {
  684: 	struct oltr_softc		*sc = (struct oltr_softc *)xsc;
  685: 
  686: 	if (DEBUG_MASK & DEBUG_INT)
  687: 		printf("I");
  688: 
  689: 	TRlldInterruptService(sc->TRlldAdapter);
  690: 
  691: 	return;
  692: }
  693: 
  694: static void
  695: oltr_start(struct ifnet *ifp)
  696: {
  697: 	struct oltr_softc 	*sc = ifp->if_softc;
  698: 	struct mbuf		*m0, *m;
  699: 	int			copy_len, buffer, frame, fragment, rc, s;
  700: 	
  701: 	/*
  702: 	 * Check to see if output is already active
  703: 	 */
  704: 	if (ifp->if_flags & IFF_OACTIVE)
  705: 		return;
  706: 
  707: outloop:
  708: 
  709: 	/*
  710: 	 * Make sure we have buffers to transmit with
  711: 	 */
  712: 	if (sc->tx_avail <= 0) {
  713: 		printf("oltr%d: tx queue full\n", sc->unit);
  714: 		ifp->if_flags |= IFF_OACTIVE;
  715: 		return;
  716: 	}
  717: 
  718: 	if (sc->restart == NULL) {
  719: 		IF_DEQUEUE(&ifp->if_snd, m);
  720: 		if (m == NULL)
  721: 			return;
  722: 	} else {
  723: 		m = sc->restart;
  724: 		sc->restart = NULL;
  725: 	}
  726: 
  727: 	m0 = m;
  728: 	frame = RING_BUFFER(sc->tx_frame);
  729: 	buffer = RING_BUFFER(sc->tx_head);
  730: 	fragment = 0;
  731: 	copy_len = 0;
  732: 	sc->frame_ring[frame].FragmentCount = 0;
  733: 	
  734: 	while (copy_len < m0->m_pkthdr.len) {
  735: 		sc->frame_ring[frame].FragmentCount++;
  736: 		if (sc->frame_ring[frame].FragmentCount > sc->tx_avail)
  737: 			goto nobuffers;
  738: 		sc->frame_ring[frame].TransmitFragment[fragment].VirtualAddress = sc->tx_ring[buffer].data;
  739: 		sc->frame_ring[frame].TransmitFragment[fragment].PhysicalAddress = sc->tx_ring[buffer].address;
  740: 		sc->frame_ring[frame].TransmitFragment[fragment].count = MIN(m0->m_pkthdr.len - copy_len, TX_BUFFER_LEN);
  741: 		m_copydata(m0, copy_len, MIN(m0->m_pkthdr.len - copy_len, TX_BUFFER_LEN), sc->tx_ring[buffer].data);
  742: 		copy_len += MIN(m0->m_pkthdr.len - copy_len, TX_BUFFER_LEN);
  743: 		fragment++;
  744: 		buffer = RING_BUFFER((buffer + 1));
  745: 	}
  746: 
  747: 	s = splimp();
  748: 	rc = TRlldTransmitFrame(sc->TRlldAdapter, &sc->frame_ring[frame], (void *)&sc->frame_ring[frame]);
  749: 	(void)splx(s);
  750: 
  751: 	if (rc != TRLLD_TRANSMIT_OK) {
  752: 		printf("oltr%d: TRlldTransmitFrame returned %d\n", sc->unit, rc);
  753: 		ifp->if_oerrors++;
  754: 		goto bad;
  755: 	}
  756: 
  757: 	sc->tx_avail -= sc->frame_ring[frame].FragmentCount;
  758: 	sc->tx_head = RING_BUFFER((sc->tx_head + sc->frame_ring[frame].FragmentCount));
  759: 	sc->tx_frame++;
  760: 
  761: #if (NBPFILTER > 0) || (__FreeBSD_version > 400000)
  762: 	if (ifp->if_bpf)
  763: 		bpf_mtap(ifp, m0);
  764: #endif
  765: 	/*ifp->if_opackets++;*/
  766: 
  767: bad:
  768: 	m_freem(m0);
  769: 
  770: 	goto outloop;
  771: 
  772: nobuffers:
  773: 
  774: 	printf("oltr%d: queue full\n", sc->unit);
  775: 	ifp->if_flags |= IFF_OACTIVE;
  776: 	ifp->if_oerrors++;
  777: 	/*m_freem(m0);*/
  778: 	sc->restart = m0;
  779: 
  780: 	return;
  781: }
  782: 
  783: static void
  784: oltr_close(struct oltr_softc *sc)
  785: {
  786: 	/*printf("oltr%d: oltr_close\n", sc->unit);*/
  787: 
  788: 	oltr_stop(sc);
  789: 
  790: 	tsleep(sc, 0, "oltrclose", 30*hz);
  791: }
  792: 
  793: static void
  794: oltr_stop(struct oltr_softc *sc)
  795: {
  796: 	struct ifnet 		*ifp = &sc->arpcom.ac_if;
  797: 
  798: 	/*printf("oltr%d: oltr_stop\n", sc->unit);*/
  799: 
  800: 	ifp->if_flags &= ~(IFF_UP | IFF_RUNNING | IFF_OACTIVE);
  801: 	TRlldClose(sc->TRlldAdapter, 0);
  802: 	sc->state = OL_CLOSING;
  803: }
  804: 
  805: static void
  806: oltr_init(void * xsc)
  807: {
  808: 	struct oltr_softc 	*sc = (struct oltr_softc *)xsc;
  809: 	struct ifnet		*ifp = &sc->arpcom.ac_if;
  810: 	struct ifmedia		*ifm = &sc->ifmedia;
  811: 	int			poll = 0, i, rc = 0, s;
  812: 	int			work_size;
  813: 
  814: 	/*
  815: 	 * Check adapter state, don't allow multiple inits
  816: 	 */
  817: 	if (sc->state > OL_CLOSED) {
  818: 		printf("oltr%d: adapter not ready\n", sc->unit);
  819: 		return;
  820: 	}
  821: 
  822: 	s = splimp();
  823: 
  824: 	/*
  825: 	 * Initialize Adapter
  826: 	 */
  827: 	if ((rc = TRlldAdapterInit(&LldDriver, sc->TRlldAdapter, vtophys(sc->TRlldAdapter),
  828: 	    (void *)sc, &sc->config)) != TRLLD_INIT_OK) {
  829: 		switch(rc) {
  830: 		case TRLLD_INIT_NOT_FOUND:
  831: 			printf("oltr%d: adapter not found\n", sc->unit);
  832: 			break;
  833: 		case TRLLD_INIT_UNSUPPORTED:
  834: 			printf("oltr%d: adapter not supported by low level driver\n", sc->unit);
  835: 			break;
  836: 		case TRLLD_INIT_PHYS16:
  837: 			printf("oltr%d: adapter memory block above 16M cannot DMA\n", sc->unit);
  838: 			break;
  839: 		case TRLLD_INIT_VERSION:
  840: 			printf("oltr%d: low level driver version mismatch\n", sc->unit);
  841: 			break;
  842: 		default:
  843: 			printf("oltr%d: unknown init error %d\n", sc->unit, rc);
  844: 			break;
  845: 		}
  846: 		goto init_failed;
  847: 	}
  848: 	sc->state = OL_INIT;
  849: 
  850: 	switch(sc->config.type) {
  851: 	case TRLLD_ADAPTER_PCI4:        /* OC-3139 */
  852: 		work_size = 32 * 1024;
  853: 		break;
  854: 	case TRLLD_ADAPTER_PCI7:        /* OC-3540 */
  855: 		work_size = 256;
  856: 		break;
  857: 	default:
  858: 		work_size = 0;
  859: 	}
  860: 
  861: 	if (work_size) {
  862: 		if ((sc->work_memory = malloc(work_size, M_DEVBUF, M_NOWAIT)) == NULL) {
  863: 			printf("oltr%d: failed to allocate work memory (%d octets).\n", sc->unit, work_size);
  864: 		} else {
  865: 		TRlldAddMemory(sc->TRlldAdapter, sc->work_memory,
  866: 		    vtophys(sc->work_memory), work_size);
  867: 		}
  868: 	}
  869: 
  870: 	switch(IFM_SUBTYPE(ifm->ifm_media)) {
  871: 	case IFM_AUTO:
  872: 		rc = TRlldSetSpeed(sc->TRlldAdapter, 0); /* TRLLD_SPEED_AUTO */
  873: 		break;
  874: 	case IFM_TOK_UTP4:
  875: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_4MBPS);
  876: 		break;
  877: 	case IFM_TOK_UTP16:
  878: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_16MBPS);
  879: 		break;
  880: 	case IFM_TOK_UTP100:
  881: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_100MBPS);
  882: 		break;
  883: 	}
  884: 
  885: 	/*
  886: 	 * Download adapter micro-code
  887: 	 */
  888: 	if (bootverbose)
  889: 		printf("oltr%d: Downloading adapter microcode: ", sc->unit);
  890: 
  891: 	switch(sc->config.mactype) {
  892: 	case TRLLD_MAC_TMS:
  893: 		rc = TRlldDownload(sc->TRlldAdapter, TRlldMacCode);
  894: 		if (bootverbose)
  895: 			printf("TMS-380");
  896: 		break;
  897: 	case TRLLD_MAC_HAWKEYE:
  898: 		rc = TRlldDownload(sc->TRlldAdapter, TRlldHawkeyeMac);
  899: 		if (bootverbose)
  900: 			printf("Hawkeye");
  901: 		break;
  902: 	case TRLLD_MAC_BULLSEYE:
  903: 		rc = TRlldDownload(sc->TRlldAdapter, TRlldBullseyeMac);
  904: 		if (bootverbose)
  905: 			printf("Bullseye");
  906: 		break;
  907: 	default:
  908: 		if (bootverbose)
  909: 			printf("unknown - failed!\n");
  910: 		goto init_failed;
  911: 		break;
  912: 	}
  913: 
  914: 	/*
  915: 	 * Check download status
  916: 	 */
  917: 	switch(rc) {
  918: 	case TRLLD_DOWNLOAD_OK:
  919: 		if (bootverbose)
  920: 			printf(" - ok\n");
  921: 		break;
  922: 	case TRLLD_DOWNLOAD_ERROR:
  923: 		if (bootverbose)
  924: 			printf(" - failed\n");
  925: 		else
  926: 			printf("oltr%d: adapter microcode download failed\n", sc->unit);
  927: 		goto init_failed;
  928: 		break;
  929: 	case TRLLD_STATE:
  930: 		if (bootverbose)
  931: 			printf(" - not ready\n");
  932: 		goto init_failed;
  933: 		break;
  934: 	}
  935: 
  936: 	/*
  937: 	 * Wait for self-test to complete
  938: 	 */
  939: 	i = 0;
  940: 	while ((poll++ < SELF_TEST_POLLS) && (sc->state < OL_READY)) {
  941: 		if (DEBUG_MASK & DEBUG_INIT)
  942: 			printf("p");
  943: 		DELAY(TRlldPoll(sc->TRlldAdapter) * 1000);
  944: 		if (TRlldInterruptService(sc->TRlldAdapter) != 0)
  945: 			if (DEBUG_MASK & DEBUG_INIT) printf("i");
  946: 	}
  947: 
  948: 	if (sc->state != OL_CLOSED) {
  949: 		printf("oltr%d: self-test failed\n", sc->unit);
  950: 		goto init_failed;
  951: 	}
  952: 
  953: 	/*
  954: 	 * Set up adapter poll
  955: 	 */
  956: 	callout_handle_init(&sc->oltr_poll_ch);
  957: 	sc->oltr_poll_ch = timeout(oltr_poll, (void *)sc, 1);
  958: 
  959: 	sc->state = OL_OPENING;
  960: 
  961: 	/*
  962: 	 * Open the adapter
  963: 	 */
  964: 	rc = TRlldOpen(sc->TRlldAdapter, sc->arpcom.ac_enaddr, sc->GroupAddress,
  965: 		sc->FunctionalAddress, 1552, sc->AdapterMode);
  966: 	switch(rc) {
  967: 		case TRLLD_OPEN_OK:
  968: 			break;
  969: 		case TRLLD_OPEN_STATE:
  970: 			printf("oltr%d: adapter not ready for open\n", sc->unit);
  971: 			(void)splx(s);
  972: 			return;
  973: 		case TRLLD_OPEN_ADDRESS_ERROR:
  974: 			printf("oltr%d: illegal MAC address\n", sc->unit);
  975: 			(void)splx(s);
  976: 			return;
  977: 		case TRLLD_OPEN_MODE_ERROR:
  978: 			printf("oltr%d: illegal open mode\n", sc->unit);
  979: 			(void)splx(s);
  980: 			return;
  981: 		default:
  982: 			printf("oltr%d: unknown open error (%d)\n", sc->unit, rc);
  983: 			(void)splx(s);
  984: 			return;
  985: 	}
  986: 
  987: 	/*
  988: 	 * Set promiscious mode for now...
  989: 	 */
  990: 	TRlldSetPromiscuousMode(sc->TRlldAdapter, TRLLD_PROM_LLC);
  991: 	ifp->if_flags |= IFF_PROMISC;
  992: 
  993: 	/*
  994: 	 * Block on the ring insert and set a timeout
  995: 	 */
  996: 	tsleep(sc, 0, "oltropen", 30*hz);
  997: 
  998: 	/*
  999: 	 * Set up receive buffer ring
 1000: 	 */
 1001: 	for (i = 0; i < RING_BUFFER_LEN; i++) {
 1002: 		rc = TRlldReceiveFragment(sc->TRlldAdapter, (void *)sc->rx_ring[i].data,
 1003: 			sc->rx_ring[i].address, RX_BUFFER_LEN, (void *)sc->rx_ring[i].index);
 1004: 		if (rc != TRLLD_RECEIVE_OK) {
 1005: 			printf("oltr%d: adapter refused receive fragment %d (rc = %d)\n", sc->unit, i, rc);
 1006: 			break;
 1007: 		}	
 1008: 	}
 1009: 
 1010: 	sc->tx_avail = RING_BUFFER_LEN;
 1011: 	sc->tx_head = 0;
 1012: 	sc->tx_frame = 0;
 1013: 
 1014: 	sc->restart = NULL;
 1015: 
 1016: 	ifp->if_flags |= IFF_RUNNING;
 1017: 	ifp->if_flags &= ~IFF_OACTIVE;
 1018: 
 1019: 	/*
 1020: 	 * Set up adapter statistics poll
 1021: 	 */
 1022: 	/*callout_handle_init(&sc->oltr_stat_ch);*/
 1023: 	/*sc->oltr_stat_ch = timeout(oltr_stat, (void *)sc, 1*hz);*/
 1024: 
 1025: 	(void)splx(s);
 1026: 	return;
 1027: 
 1028: init_failed:
 1029: 	sc->state = OL_DEAD;
 1030: 	(void)splx(s);
 1031: 	return;
 1032: }
 1033: 
 1034: static int
 1035: oltr_ioctl(struct ifnet *ifp, u_long command, caddr_t data)
 1036: {
 1037: 	struct oltr_softc 	*sc = ifp->if_softc;
 1038: 	struct ifreq		*ifr = (struct ifreq *)data;
 1039: 	int 			error = 0, s;
 1040: 
 1041: 	s = splimp();
 1042: 
 1043: 	switch(command) {
 1044: 	case SIOCSIFADDR:
 1045: 	case SIOCGIFADDR:
 1046: 	case SIOCSIFMTU:
 1047: 		error = iso88025_ioctl(ifp, command, data);
 1048: 		break;
 1049: 
 1050: 	case SIOCSIFFLAGS:
 1051: 		if (ifp->if_flags & IFF_UP) {
 1052: 			oltr_init(sc);
 1053: 		} else {
 1054: 			if (ifp->if_flags & IFF_RUNNING) {
 1055: 				oltr_close(sc);
 1056: 			}
 1057: 		}
 1058: 		break;
 1059: 	case SIOCGIFMEDIA:
 1060: 	case SIOCSIFMEDIA:
 1061: 		error = ifmedia_ioctl(ifp, ifr, &sc->ifmedia, command);
 1062: 		break;
 1063: 	default:
 1064: 		error = EINVAL;
 1065: 		break;
 1066: 	}
 1067: 
 1068: 	(void)splx(s);	
 1069: 
 1070: 	return(error);
 1071: }
 1072: 
 1073: 
 1074: void
 1075: oltr_poll(void *arg)
 1076: {
 1077: 	struct oltr_softc *sc = (struct oltr_softc *)arg;
 1078: 	int s;
 1079: 
 1080: 	s = splimp();
 1081: 
 1082: 	if (DEBUG_MASK & DEBUG_POLL) printf("P");
 1083: 
 1084: 	/* Set up next adapter poll */
 1085: 	sc->oltr_poll_ch = timeout(oltr_poll, (void *)sc, (TRlldPoll(sc->TRlldAdapter) * hz / 1000));
 1086: 
 1087: 	(void)splx(s);
 1088: }
 1089: 
 1090: #ifdef NOTYET
 1091: void
 1092: oltr_stat(void *arg)
 1093: {
 1094: 	struct oltr_softc	*sc = (struct oltr_softc *)arg;
 1095: 	int			s;
 1096: 
 1097: 	s = splimp();
 1098: 
 1099: 	/* Set up next adapter poll */
 1100: 	sc->oltr_stat_ch = timeout(oltr_stat, (void *)sc, 1*hz);
 1101: 	if (TRlldGetStatistics(sc->TRlldAdapter, &sc->current, 0) != 0) {
 1102: 		/*printf("oltr%d: statistics available immediately...\n", sc->unit);*/
 1103: 		DriverStatistics((void *)sc, &sc->current);
 1104: 	}
 1105: 
 1106: 	(void)splx(s);
 1107: }
 1108: #endif
 1109: static int
 1110: oltr_ifmedia_upd(struct ifnet *ifp)
 1111: {
 1112: 	struct oltr_softc 	*sc = ifp->if_softc;
 1113: 	struct ifmedia		*ifm = &sc->ifmedia;
 1114: 	int			rc;
 1115: 
 1116: 	if (IFM_TYPE(ifm->ifm_media) != IFM_TOKEN)
 1117: 		return(EINVAL);
 1118: 
 1119: 	switch(IFM_SUBTYPE(ifm->ifm_media)) {
 1120: 	case IFM_AUTO:
 1121: 		rc = TRlldSetSpeed(sc->TRlldAdapter, 0); /* TRLLD_SPEED_AUTO */
 1122: 		break;
 1123: 	case IFM_TOK_UTP4:
 1124: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_4MBPS);
 1125: 		break;
 1126: 	case IFM_TOK_UTP16:
 1127: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_16MBPS);
 1128: 		break;
 1129: 	case IFM_TOK_UTP100:
 1130: 		rc = TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_100MBPS);
 1131: 		break;
 1132: 	default:
 1133: 		return(EINVAL);
 1134: 		break;
 1135: 	}
 1136: 
 1137: 	return(0);
 1138: 
 1139: }
 1140: 
 1141: static void
 1142: oltr_ifmedia_sts(struct ifnet *ifp, struct ifmediareq *ifmr)
 1143: {
 1144: 	struct oltr_softc	*sc = ifp->if_softc;
 1145: 	struct ifmedia		*ifm = &sc->ifmedia;
 1146: 
 1147: 	/*printf("oltr%d: oltr_ifmedia_sts\n", sc->unit);*/
 1148: 
 1149: 	ifmr->ifm_active = IFM_TYPE(ifm->ifm_media)|IFM_SUBTYPE(ifm->ifm_media);
 1150: 
 1151: }
 1152: 
 1153: /*
 1154:  * ---------------------- PMW Callback Functions -----------------------
 1155:  */
 1156: 
 1157: void
 1158: DriverStatistics(void *DriverHandle, TRlldStatistics_t *statistics)
 1159: {
 1160: #ifdef NOTYET
 1161: 	struct oltr_softc		*sc = (struct oltr_softc *)DriverHandle;
 1162: 
 1163: 	if (sc->statistics.LineErrors != statistics->LineErrors)
 1164: 		printf("oltr%d: Line Errors %lu\n", sc->unit,
 1165: 		    statistics->LineErrors);
 1166: 	if (sc->statistics.InternalErrors != statistics->InternalErrors)
 1167: 		printf("oltr%d: Internal Errors %lu\n", sc->unit,
 1168: 		    statistics->InternalErrors);
 1169: 	if (sc->statistics.BurstErrors != statistics->BurstErrors)
 1170: 		printf("oltr%d: Burst Errors %lu\n", sc->unit,
 1171: 		    statistics->BurstErrors);
 1172: 	if (sc->statistics.AbortDelimiters != statistics->AbortDelimiters)
 1173: 		printf("oltr%d: Abort Delimiters %lu\n", sc->unit,
 1174: 		    statistics->AbortDelimiters);
 1175: 	if (sc->statistics.ARIFCIErrors != statistics->ARIFCIErrors)
 1176: 		printf("oltr%d: ARIFCI Errors %lu\n", sc->unit,
 1177: 		    statistics->ARIFCIErrors);
 1178: 	if (sc->statistics.LostFrames != statistics->LostFrames)
 1179: 		printf("oltr%d: Lost Frames %lu\n", sc->unit,
 1180: 		    statistics->LostFrames);
 1181: 	if (sc->statistics.CongestionErrors != statistics->CongestionErrors)
 1182: 		printf("oltr%d: Congestion Errors %lu\n", sc->unit,
 1183: 		    statistics->CongestionErrors);
 1184: 	if (sc->statistics.FrequencyErrors != statistics->FrequencyErrors)
 1185: 		printf("oltr%d: Frequency Errors %lu\n", sc->unit,
 1186: 		    statistics->FrequencyErrors);
 1187: 	if (sc->statistics.TokenErrors != statistics->TokenErrors)
 1188: 		printf("oltr%d: Token Errors %lu\n", sc->unit,
 1189: 		    statistics->TokenErrors);
 1190: 	if (sc->statistics.DMABusErrors != statistics->DMABusErrors)
 1191: 		printf("oltr%d: DMA Bus Errors %lu\n", sc->unit,
 1192: 		    statistics->DMABusErrors);
 1193: 	if (sc->statistics.DMAParityErrors != statistics->DMAParityErrors)
 1194: 		printf("oltr%d: DMA Parity Errors %lu\n", sc->unit,
 1195: 		    statistics->DMAParityErrors);
 1196: 	if (sc->statistics.ReceiveLongFrame != statistics->ReceiveLongFrame)
 1197: 		printf("oltr%d: Long frames received %lu\n", sc->unit,
 1198: 		    statistics->ReceiveLongFrame);
 1199: 	if (sc->statistics.ReceiveCRCErrors != statistics->ReceiveCRCErrors)
 1200: 		printf("oltr%d: Receive CRC Errors %lu\n", sc->unit,
 1201: 		    statistics->ReceiveCRCErrors);
 1202: 	if (sc->statistics.ReceiveOverflow != statistics->ReceiveOverflow)
 1203: 		printf("oltr%d: Recieve overflows %lu\n", sc->unit,
 1204: 		    statistics->ReceiveOverflow);
 1205: 	if (sc->statistics.TransmitUnderrun != statistics->TransmitUnderrun)
 1206: 		printf("oltr%d: Frequency Errors %lu\n", sc->unit,
 1207: 		    statistics->TransmitUnderrun);
 1208: 	bcopy(statistics, &sc->statistics, sizeof(TRlldStatistics_t));
 1209: #endif
 1210: }
 1211: 
 1212: static void
 1213: DriverSuspend(unsigned short MicroSeconds)
 1214: {
 1215:     DELAY(MicroSeconds);
 1216: }
 1217: 
 1218: 
 1219: static void
 1220: DriverStatus(void *DriverHandle, TRlldStatus_t *Status)
 1221: {
 1222: 	struct oltr_softc	*sc = (struct oltr_softc *)DriverHandle;
 1223: 	struct ifnet		*ifp = &sc->arpcom.ac_if;
 1224: 
 1225: 	char *Protocol[] = { /* 0 */ "Unknown",
 1226: 			     /* 1 */ "TKP",
 1227: 			     /* 2 */ "TXI" };
 1228: 	char *Timeout[]  = { /* 0 */ "command",
 1229: 			     /* 1 */ "transmit",
 1230: 			     /* 2 */ "interrupt" };
 1231: 	
 1232: 	switch (Status->Type) {
 1233: 
 1234: 	case TRLLD_STS_ON_WIRE:
 1235: 		printf("oltr%d: ring insert (%d Mbps - %s)\n", sc->unit,
 1236: 		    Status->Specification.OnWireInformation.Speed,
 1237: 		    Protocol[Status->Specification.OnWireInformation.AccessProtocol]);
 1238: 		sc->state = OL_OPEN;
 1239: 		wakeup(sc);
 1240: 		break;
 1241: 	case TRLLD_STS_SELFTEST_STATUS:
 1242: 		if (Status->Specification.SelftestStatus == TRLLD_ST_OK) {
 1243: 			sc->state = OL_CLOSED;
 1244: 			if (bootverbose)
 1245: 				printf("oltr%d: self test complete\n", sc->unit);
 1246: 		}
 1247: 		if (Status->Specification.SelftestStatus & TRLLD_ST_ERROR) {
 1248: 			printf("oltr%d: Adapter self test error %d", sc->unit,
 1249: 			Status->Specification.SelftestStatus & ~TRLLD_ST_ERROR);
 1250: 			sc->state = OL_DEAD;
 1251: 		}
 1252: 		if (Status->Specification.SelftestStatus & TRLLD_ST_TIMEOUT) {
 1253: 			printf("oltr%d: Adapter self test timed out.\n", sc->unit);
 1254: 			sc->state = OL_DEAD;
 1255: 		}
 1256: 		break;
 1257: 	case TRLLD_STS_INIT_STATUS:
 1258: 		if (Status->Specification.InitStatus == 0x800) {
 1259: 			oltr_stop(sc);
 1260: 			ifmedia_set(&sc->ifmedia, IFM_TOKEN|IFM_TOK_UTP16);
 1261: 			TRlldSetSpeed(sc->TRlldAdapter, TRLLD_SPEED_16MBPS);
 1262: 			oltr_init(sc);
 1263: 			break;
 1264: 		}
 1265: 		printf("oltr%d: adapter init failure 0x%03x\n", sc->unit,
 1266: 		    Status->Specification.InitStatus);
 1267: 		oltr_stop(sc);
 1268: 		break;
 1269: 	case TRLLD_STS_RING_STATUS:
 1270: 		if (Status->Specification.RingStatus) {
 1271: 			printf("oltr%d: Ring status change: ", sc->unit);
 1272: 			if (Status->Specification.RingStatus &
 1273: 			    TRLLD_RS_SIGNAL_LOSS)
 1274: 				printf(" [Signal Loss]");
 1275: 			if (Status->Specification.RingStatus &
 1276: 			    TRLLD_RS_HARD_ERROR)
 1277: 				printf(" [Hard Error]");
 1278: 			if (Status->Specification.RingStatus &
 1279: 			    TRLLD_RS_SOFT_ERROR)
 1280: 				printf(" [Soft Error]");
 1281: 			if (Status->Specification.RingStatus &
 1282: 			    TRLLD_RS_TRANSMIT_BEACON)
 1283: 				printf(" [Beacon]");
 1284: 			if (Status->Specification.RingStatus &
 1285: 			    TRLLD_RS_LOBE_WIRE_FAULT)
 1286: 				printf(" [Wire Fault]");
 1287: 			if (Status->Specification.RingStatus &
 1288: 			    TRLLD_RS_AUTO_REMOVAL_ERROR)
 1289: 				printf(" [Auto Removal]");
 1290: 			if (Status->Specification.RingStatus &
 1291: 			    TRLLD_RS_REMOVE_RECEIVED)
 1292: 				printf(" [Remove Received]");
 1293: 			if (Status->Specification.RingStatus &
 1294: 			    TRLLD_RS_COUNTER_OVERFLOW)
 1295: 				printf(" [Counter Overflow]");
 1296: 			if (Status->Specification.RingStatus &
 1297: 			    TRLLD_RS_SINGLE_STATION)
 1298: 				printf(" [Single Station]");
 1299: 			if (Status->Specification.RingStatus &
 1300: 				TRLLD_RS_RING_RECOVERY)
 1301: 				printf(" [Ring Recovery]");
 1302: 			printf("\n");	
 1303: 		}
 1304: 		break;
 1305: 	case TRLLD_STS_ADAPTER_CHECK:
 1306: 		printf("oltr%d: adapter check (%04x %04x %04x %04x)\n", sc->unit,
 1307: 		    Status->Specification.AdapterCheck[0],
 1308: 		    Status->Specification.AdapterCheck[1],
 1309: 		    Status->Specification.AdapterCheck[2],
 1310: 		    Status->Specification.AdapterCheck[3]);
 1311: 		sc->state = OL_DEAD;
 1312: 		oltr_stop(sc);
 1313: 		break;
 1314: 	case TRLLD_STS_PROMISCUOUS_STOPPED:
 1315: 		printf("oltr%d: promiscuous mode ", sc->unit);
 1316: 		if (Status->Specification.PromRemovedCause == 1)
 1317: 			printf("remove received.");
 1318: 		if (Status->Specification.PromRemovedCause == 2)
 1319: 			printf("poll failure.");
 1320: 		if (Status->Specification.PromRemovedCause == 2)
 1321: 			printf("buffer size failure.");
 1322: 		printf("\n");
 1323: 		ifp->if_flags &= ~IFF_PROMISC;
 1324: 		break;
 1325: 	case TRLLD_STS_LLD_ERROR:
 1326: 		printf("oltr%d: low level driver internal error ", sc->unit);
 1327: 		printf("(%04x %04x %04x %04x).\n",
 1328: 		    Status->Specification.InternalError[0],
 1329: 		    Status->Specification.InternalError[1],
 1330: 		    Status->Specification.InternalError[2],
 1331: 		    Status->Specification.InternalError[3]);
 1332: 		sc->state = OL_DEAD;
 1333: 		oltr_stop(sc);
 1334: 		break;
 1335: 	case TRLLD_STS_ADAPTER_TIMEOUT:
 1336: 		printf("oltr%d: adapter %s timeout.\n", sc->unit,
 1337: 		    Timeout[Status->Specification.AdapterTimeout]);
 1338: 		break;
 1339: 	default:
 1340: 		printf("oltr%d: driver status Type = %d\n", sc->unit, Status->Type);
 1341: 		break;
 1342: 
 1343: 	}
 1344: 	if (Status->Closed) {
 1345: 		sc->state = OL_CLOSING;
 1346: 		oltr_stop(sc);
 1347: 	}
 1348: 
 1349: }
 1350: 
 1351: static void
 1352: DriverCloseCompleted(void *DriverHandle)
 1353: {
 1354: 	struct oltr_softc		*sc = (struct oltr_softc *)DriverHandle;
 1355: 	
 1356: 	printf("oltr%d: adapter closed\n", sc->unit);
 1357: 	wakeup(sc);
 1358: 	sc->state = OL_CLOSED;
 1359: }
 1360: 
 1361: static void
 1362: DriverTransmitFrameCompleted(void *DriverHandle, void *FrameHandle, int TransmitStatus)
 1363: {
 1364: 	struct oltr_softc	*sc = (struct oltr_softc *)DriverHandle;
 1365: 	struct ifnet		*ifp = &sc->arpcom.ac_if;
 1366: 	TRlldTransmit_t		*frame = (TRlldTransmit_t *)FrameHandle;
 1367: 	
 1368: 	/*printf("oltr%d: DriverTransmitFrameCompleted\n", sc->unit);*/
 1369: 
 1370: 	if (TransmitStatus != TRLLD_TRANSMIT_OK) {
 1371: 		ifp->if_oerrors++;
 1372: 		printf("oltr%d: transmit error %d\n", sc->unit, TransmitStatus);
 1373: 	} else {
 1374: 		ifp->if_opackets++;
 1375: 	}
 1376: 	
 1377: 	sc->tx_avail += frame->FragmentCount;
 1378: 
 1379: 	if (ifp->if_flags & IFF_OACTIVE) {
 1380: 		printf("oltr%d: queue restart\n", sc->unit);
 1381: 		ifp->if_flags &= ~IFF_OACTIVE;
 1382: 		oltr_start(ifp);
 1383: 	}
 1384: 
 1385: 
 1386: }
 1387: 
 1388: static void
 1389: DriverReceiveFrameCompleted(void *DriverHandle, int ByteCount, int FragmentCount, void *FragmentHandle, int ReceiveStatus)
 1390: {
 1391: 	struct oltr_softc 	*sc = (struct oltr_softc *)DriverHandle;
 1392: 	struct ifnet		*ifp = (struct ifnet *)&sc->arpcom.ac_if;
 1393: 	struct mbuf		*m0, *m1, *m;
 1394: 	struct iso88025_header	*th;
 1395: 	int			frame_len = ByteCount, hdr_len, i = (int)FragmentHandle, rc, s;
 1396: 	int			mbuf_offset, mbuf_size, frag_offset, copy_length;
 1397: 	char			*fragment = sc->rx_ring[RING_BUFFER(i)].data;
 1398: 	
 1399: 	if (sc->state > OL_CLOSED) {
 1400: 		if (ReceiveStatus == TRLLD_RCV_OK) {
 1401: 			MGETHDR(m0, M_DONTWAIT, MT_DATA);
 1402: 			mbuf_size = MHLEN - 2;
 1403: 			if (!m0) {
 1404: 				ifp->if_ierrors++;
 1405: 				goto dropped;
 1406: 			}
 1407: 			if (ByteCount + 2 > MHLEN) {
 1408: 				MCLGET(m0, M_DONTWAIT);
 1409: 				mbuf_size = MCLBYTES - 2;
 1410: 				if (!(m0->m_flags & M_EXT)) {
 1411: 					m_freem(m0);
 1412: 					ifp->if_ierrors++;
 1413: 					goto dropped;
 1414: 				}
 1415: 			}
 1416: 			m0->m_pkthdr.rcvif = ifp;
 1417: 			m0->m_pkthdr.len = ByteCount;
 1418: 			m0->m_len = 0;
 1419: 			m0->m_data += 2;
 1420: 			th = mtod(m0, struct iso88025_header *);
 1421: 			m0->m_pkthdr.header = (void *)th;
 1422: 
 1423: 			m = m0;
 1424: 			mbuf_offset = 0;
 1425: 			frag_offset = 0;
 1426: 			while (frame_len) {
 1427: 				copy_length = MIN3(frame_len,
 1428: 				    (RX_BUFFER_LEN - frag_offset),
 1429: 				    (mbuf_size - mbuf_offset));
 1430: 				bcopy(fragment + frag_offset, mtod(m, char *) +
 1431: 				    mbuf_offset, copy_length);
 1432: 				m->m_len += copy_length;
 1433: 				mbuf_offset += copy_length;
 1434: 				frag_offset += copy_length;
 1435: 				frame_len -= copy_length;
 1436: 			
 1437: 				if (frag_offset == RX_BUFFER_LEN) {
 1438: 					fragment =
 1439: 					    sc->rx_ring[RING_BUFFER(++i)].data;
 1440: 					frag_offset = 0;
 1441: 				}
 1442: 				if ((mbuf_offset == mbuf_size) && (frame_len > 0)) {
 1443: 					MGET(m1, M_DONTWAIT, MT_DATA);
 1444: 					mbuf_size = MHLEN;
 1445: 					if (!m1) {
 1446: 						ifp->if_ierrors++;
 1447: 						m_freem(m0);
 1448: 						goto dropped;
 1449: 					}
 1450: 					if (frame_len > MHLEN) {
 1451: 						MCLGET(m1, M_DONTWAIT);
 1452: 						mbuf_size = MCLBYTES;
 1453: 						if (!(m1->m_flags & M_EXT)) {
 1454: 							m_freem(m0);
 1455: 							m_freem(m1);
 1456: 							ifp->if_ierrors++;
 1457: 							goto dropped;
 1458: 						}
 1459: 					}
 1460: 					m->m_next = m1;
 1461: 					m = m1;
 1462: 					mbuf_offset = 0;
 1463: 					m->m_len = 0;
 1464: 				}
 1465: 			}
 1466: #if (NBPFILTER > 0) || (__FreeBSD_version > 400000)
 1467: 			if (ifp->if_bpf)
 1468: 				bpf_mtap(ifp, m0);
 1469: #endif
 1470: 
 1471: 			/*if (ifp->if_flags & IFF_PROMISC) {*/
 1472: 				if (bcmp(th->iso88025_dhost, etherbroadcastaddr
 1473: 				    , sizeof(th->iso88025_dhost))) {
 1474: 					if ((bcmp(th->iso88025_dhost + 1, sc->arpcom.ac_enaddr + 1, ISO88025_ADDR_LEN - 1)) ||
 1475: 					    ((th->iso88025_dhost[0] & 0x7f) != sc->arpcom.ac_enaddr[0])) {
 1476: 						m_freem(m0);
 1477: 						goto dropped;
 1478: 					}
 1479: 				}
 1480: 			/*}*/
 1481: 			ifp->if_ipackets++;
 1482: 
 1483: 			hdr_len = ISO88025_HDR_LEN;
 1484: 			if (th->iso88025_shost[0] & 0x80)
 1485: 				hdr_len += (ntohs(th->rcf) & 0x1f00) >> 8;
 1486: 
 1487: 			m0->m_pkthdr.len -= hdr_len;
 1488: 			m0->m_len -= hdr_len;
 1489: 			m0->m_data += hdr_len;
 1490: 
 1491: 			iso88025_input(ifp, th, m0);
 1492: 
 1493: 		} else {	/* Receiver error */
 1494: 			if (ReceiveStatus != TRLLD_RCV_NO_DATA) {
 1495: 				printf("oltr%d: receive error %d\n", sc->unit,
 1496: 				    ReceiveStatus);
 1497: 				ifp->if_ierrors++;
 1498: 			}
 1499: 		}
 1500: 
 1501: dropped:
 1502: 		s = splimp();
 1503: 		i = (int)FragmentHandle;
 1504: 		while (FragmentCount--) {
 1505: 			rc = TRlldReceiveFragment(sc->TRlldAdapter,
 1506: 			    (void *)sc->rx_ring[RING_BUFFER(i)].data,
 1507: 			    sc->rx_ring[RING_BUFFER(i)].address,
 1508: 			    RX_BUFFER_LEN, (void *)sc->rx_ring[RING_BUFFER(i)].index);
 1509: 			if (rc != TRLLD_RECEIVE_OK) {
 1510: 				printf("oltr%d: adapter refused receive fragment %d (rc = %d)\n", sc->unit, i, rc);
 1511: 				break;
 1512: 			}
 1513: 			i++;
 1514: 		}
 1515: 		(void)splx(s);
 1516: 	}
 1517: }
 1518: 
 1519: 
 1520: /*
 1521:  * ---------------------------- PMW Glue -------------------------------
 1522:  */
 1523: 
 1524: #ifndef TRlldInlineIO
 1525: 
 1526: static void
 1527: DriverOutByte(unsigned short IOAddress, unsigned char value)
 1528: {
 1529: 	outb(IOAddress, value);
 1530: }
 1531: 
 1532: static void
 1533: DriverOutWord(unsigned short IOAddress, unsigned short value)
 1534: {
 1535: 	outw(IOAddress, value);
 1536: }
 1537: 
 1538: static void
 1539: DriverOutDword(unsigned short IOAddress, unsigned long value)
 1540: {
 1541: 	outl(IOAddress, value);
 1542: }
 1543: 
 1544: static void
 1545: DriverRepOutByte(unsigned short IOAddress, unsigned char *DataPointer, int ByteCount)
 1546: {
 1547: 	outsb(IOAddress, (void *)DataPointer, ByteCount);
 1548: }
 1549: 
 1550: static void
 1551: DriverRepOutWord(unsigned short IOAddress, unsigned short *DataPointer, int WordCount)
 1552: {
 1553: 	outsw(IOAddress, (void *)DataPointer, WordCount);
 1554: }
 1555: 
 1556: static void
 1557: DriverRepOutDword(unsigned short IOAddress, unsigned long *DataPointer, int DWordCount)
 1558: {
 1559: 	outsl(IOAddress, (void *)DataPointer, DWordCount);
 1560: }
 1561: 
 1562: static unsigned char
 1563: DriverInByte(unsigned short IOAddress)
 1564: {
 1565: 	return(inb(IOAddress));
 1566: }
 1567: 
 1568: static unsigned short
 1569: DriverInWord(unsigned short IOAddress)
 1570: {
 1571: 	return(inw(IOAddress));
 1572: }
 1573: 
 1574: static unsigned long
 1575: DriverInDword(unsigned short IOAddress)
 1576: {
 1577: 	return(inl(IOAddress));
 1578: }
 1579: 
 1580: static void
 1581: DriverRepInByte(unsigned short IOAddress, unsigned char *DataPointer, int ByteCount)
 1582: {
 1583: 	insb(IOAddress, (void *)DataPointer, ByteCount);
 1584: }
 1585: 
 1586: static void
 1587: DriverRepInWord(unsigned short IOAddress, unsigned short *DataPointer, int WordCount)
 1588: {
 1589: 	insw(IOAddress, (void *)DataPointer, WordCount);
 1590: }
 1591: static void
 1592: DriverRepInDword( unsigned short IOAddress, unsigned long *DataPointer, int DWordCount)
 1593: {
 1594: 	insl(IOAddress, (void *)DataPointer, DWordCount);
 1595: }
 1596: #endif /* TRlldInlineIO */