Skip site navigation (1)Skip section navigation (2)
Date:      Thu, 1 May 1997 20:12:24 -0700 (MST)
From:      Richard Straka <straka@inficad.com>
To:        "Justin T. Gibbs" <gibbs@plutotech.com>
Cc:        current@freebsd.org
Subject:   ie driver fixes for EtherExpress 16
Message-ID:  <Pine.BSI.3.95.970501194202.14582A-100000@user2.inficad.com>

next in thread | raw e-mail | index | archive | help

The following is a patch for if_ie.c which can be applied
to the 2.2-970422-RELENG kernel to make it work with the 
EtherExpress 16 ethernet adapter. The patch does the
following.

1. Change the number of frame desciptors NFRAMES from 16 
to 8. This is consistent with the number of ether frame 
buffers NRXBUF (48) allocated. This solves the "descriptors
out of sync" error while receiving.

2. Commented out the at_shutdown call. This seems to be 
unnecessary. I have repeatedly rebooted between FreeBSD and
DOS/Packet Driver and have not noticed any problems with
the card settings. This solves the hang/panic at shutdown.

3. Moved the interrupt acknowledge call to the top of the
"event loop" in ieintr. This allows events to be recognized
while current events are being processed. This solves the
transmit problems.

4. Changed the initialization of the transmit buffers. Was
hard coded for 2 buffers. Changed to initialize NTXBUF buffers.
This would only be a problem if one wanted to increase NTXBUF
from its current value of 2.

5. Moved the block of code which take the adapter out of "loop
back" mode to the very end of ieinit. This seems cleaner and
may eliminate inadvertant packets sent during initialization.

Note that the number of buffers are setup for a 16k adapter.
With a 32k EtherExpress 16 NFRAMES, NRXBUF, and NTXBUF could
all be safely doubled. For my application (486dx4-100),
doubling NFRAMES and NRXBUF made a marginal improvement in 
receive performance while doubling NTXBUF didn't seem to make 
a difference in transmit performance.

With the patch applied, my EtherExpress is transmitting
725kB/sec and receiving 900kB/sec during FTP transfers.
These results seem to be better (especially receiving)
than the old ix driver.

If you have any questions, please let me know.


*** if_ie.c	Wed Apr 30 21:05:31 1997
--- if_ie.c	Thu May  1 16:04:07 1997
***************
*** 290,296 ****
  both transmit and receive buffers.
  */
  
! #define NFRAMES         16	        /* number of receive frames */
  #define NRXBUF          48	        /* number of buffers to allocate */
  #define IE_RBUF_SIZE    256	        /* size of each buffer, 
  					        MUST BE POWER OF TWO */
--- 290,296 ----
  both transmit and receive buffers.
  */
  
! #define NFRAMES         8	        /* number of receive frames */
  #define NRXBUF          48	        /* number of buffers to allocate */
  #define IE_RBUF_SIZE    256	        /* size of each buffer, 
  					        MUST BE POWER OF TWO */
***************
*** 828,835 ****
    ifp->if_addrlen = 6;
    ifp->if_hdrlen = 14;
  
!   if (ie->hard_type == IE_EE16)
! 	  at_shutdown(ee16_shutdown, ie, SHUTDOWN_POST_SYNC);
  
  #if NBPFILTER > 0
    bpfattach(ifp, DLT_EN10MB, sizeof(struct ether_header));
--- 828,835 ----
    ifp->if_addrlen = 6;
    ifp->if_hdrlen = 14;
  
! /*  if (ie->hard_type == IE_EE16)
! 	  at_shutdown(ee16_shutdown, ie, SHUTDOWN_POST_SYNC);*/
  
  #if NBPFILTER > 0
    bpfattach(ifp, DLT_EN10MB, sizeof(struct ether_header));
***************
*** 861,866 ****
--- 861,870 ----
    status = ie->scb->ie_status;
  
  loop:
+ 
+   /* Don't ack interrupts which we didn't receive */
+   ie_ack(ie->scb, IE_ST_WHENCE & status, unit, ie->ie_chan_attn);
+ 
    if(status & (IE_ST_RECV | IE_ST_RNR)) {
  #ifdef DEBUG
      in_ierint++;
***************
*** 898,906 ****
       && (ie_debug & IED_CNA))
      printf("ie%d: cna\n", unit);
  #endif
-   
-   /* Don't ack interrupts which we didn't receive */
-   ie_ack(ie->scb, IE_ST_WHENCE & status, unit, ie->ie_chan_attn);
  
    if ((status = ie->scb->ie_status) & IE_ST_WHENCE)
  	goto loop;
--- 902,907 ----
***************
*** 2108,2113 ****
--- 2109,2115 ----
    struct ie_softc *ie = &ie_softc[unit];
    volatile struct ie_sys_ctl_block *scb = ie->scb;
    caddr_t ptr;
+   int i;
  
    ptr = (caddr_t)Align((caddr_t)scb + sizeof *scb); /* ignore cast-qual */
  
***************
*** 2161,2181 ****
     */
    ie_ack(ie->scb, IE_ST_WHENCE, unit, ie->ie_chan_attn);
  
-   /* take the ee16 out of loopback */
-   {
- 	  u_char	bart_config;
- 	  
- 	  if(ie->hard_type == IE_EE16) {
- 		  bart_config = inb(PORT + IEE16_CONFIG);
- 		  bart_config &= ~IEE16_BART_LOOPBACK;
- 		  /* inb doesn't get bit! */
- 		  bart_config |= IEE16_BART_MCS16_TEST; 
- 		  outb(PORT + IEE16_CONFIG, bart_config);
- 		  ee16_interrupt_enable(ie); 
- 		  ee16_chan_attn(unit);
- 	  }
-   }
- 
    /*
     * Set up the RFA.
     */
--- 2163,2168 ----
***************
*** 2184,2214 ****
    /*
     * Finally, the transmit command and buffer are the last little bit of work.
     */
-   ie->xmit_cmds[0] = (void *)ptr;
-   ptr += sizeof *ie->xmit_cmds[0];
-   ptr = Align(ptr);
-   ie->xmit_buffs[0] = (void *)ptr;
-   ptr += sizeof *ie->xmit_buffs[0];
-   ptr = Align(ptr);
- 
-   /* Second transmit command */
-   ie->xmit_cmds[1] = (void *)ptr;
-   ptr += sizeof *ie->xmit_cmds[1];
-   ptr = Align(ptr);
-   ie->xmit_buffs[1] = (void *)ptr;
-   ptr += sizeof *ie->xmit_buffs[1];
-   ptr = Align(ptr);
  
!   /* Both transmit buffers */
!   ie->xmit_cbuffs[0] = (void *)ptr;
!   ptr += IE_BUF_LEN;
!   ptr = Align(ptr);
!   ie->xmit_cbuffs[1] = (void *)ptr;
! 
!   bzero((caddr_t)ie->xmit_cmds[0], sizeof *ie->xmit_cmds[0]); /* ignore */
!   bzero((caddr_t)ie->xmit_buffs[0], sizeof *ie->xmit_buffs[0]);	/* cast-qual */
!   bzero((caddr_t)ie->xmit_cmds[1], sizeof *ie->xmit_cmds[0]); /* warnings */
!   bzero((caddr_t)ie->xmit_buffs[1], sizeof *ie->xmit_buffs[0]);	/* here */
  
    /*
     * This must be coordinated with iestart() and ietint().
--- 2171,2199 ----
    /*
     * Finally, the transmit command and buffer are the last little bit of work.
     */
  
!   /* transmit command buffers */
!   for (i=0;i<NTXBUF;i++) {
!     ie->xmit_cmds[i] = (void *)ptr;
!     ptr += sizeof *ie->xmit_cmds[i];
!     ptr = Align(ptr);
!     ie->xmit_buffs[i] = (void *)ptr;
!     ptr += sizeof *ie->xmit_buffs[i];
!     ptr = Align(ptr);
!   }
! 
!   /* transmit buffers */
!   for (i=0;i<NTXBUF-1;i++) {
!     ie->xmit_cbuffs[i] = (void *)ptr;
!     ptr += IE_BUF_LEN;
!     ptr = Align(ptr);
!   }
!   ie->xmit_cbuffs[NTXBUF-1] = (void *)ptr;
! 
!   for (i=1;i<NTXBUF;i++) {                                    /* ignore */
!     bzero((caddr_t)ie->xmit_cmds[i], sizeof *ie->xmit_cmds[i]); /* cast-qual */
!     bzero((caddr_t)ie->xmit_buffs[i], sizeof *ie->xmit_buffs[i]);/* warnings */
!   }                                                            /* here */
  
    /*
     * This must be coordinated with iestart() and ietint().
***************
*** 2217,2222 ****
--- 2202,2222 ----
  
    ie->arpcom.ac_if.if_flags |= IFF_RUNNING; /* tell higher levels we're here */
    start_receiver(unit);
+ 
+   /* take the ee16 out of loopback */
+   {
+ 	  u_char	bart_config;
+ 	  
+ 	  if(ie->hard_type == IE_EE16) {
+ 		  bart_config = inb(PORT + IEE16_CONFIG);
+ 		  bart_config &= ~IEE16_BART_LOOPBACK;
+ 		  /* inb doesn't get bit! */
+ 		  bart_config |= IEE16_BART_MCS16_TEST; 
+ 		  outb(PORT + IEE16_CONFIG, bart_config);
+ 		  ee16_interrupt_enable(ie); 
+ 		  ee16_chan_attn(unit);
+ 	  }
+   }
    return;
  }
  

Richard Straka
straka@inficad.com





Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?Pine.BSI.3.95.970501194202.14582A-100000>