From owner-freebsd-stable Sat Dec 14 14:12:10 2002 Delivered-To: freebsd-stable@freebsd.org Received: from mx1.FreeBSD.org (mx1.freebsd.org [216.136.204.125]) by hub.freebsd.org (Postfix) with ESMTP id 4551137B401 for ; Sat, 14 Dec 2002 14:12:05 -0800 (PST) Received: from scatcat.saeab.se (c213-100-94-173.swipnet.se [213.100.94.173]) by mx1.FreeBSD.org (Postfix) with ESMTP id 1FD1643E4A for ; Sat, 14 Dec 2002 14:11:57 -0800 (PST) (envelope-from thn@saeab.se) Received: from saeab.se (home.thn.saeab.se [10.1.0.1]) by scatcat.saeab.se (8.12.6/8.12.6) with ESMTP id gBEMBlgE000392; Sat, 14 Dec 2002 23:11:52 +0100 (CET) (envelope-from thn@saeab.se) Message-ID: <3DFBACE7.1D60335F@saeab.se> Date: Sat, 14 Dec 2002 23:12:55 +0100 From: Thomas Nystrom Organization: Sv. Aktuell Elektronik AB X-Mailer: Mozilla 4.78 [en] (Win98; U) X-Accept-Language: sv,en MIME-Version: 1.0 To: stable@freebsd.org Subject: Fix for hanging of vr interface (Rhine Ethernet) Content-Type: multipart/mixed; boundary="------------8361301D639C7819FBE5AD82" Sender: owner-freebsd-stable@FreeBSD.ORG Precedence: bulk List-ID: List-Archive: (Web Archive) List-Help: (List Instructions) List-Subscribe: List-Unsubscribe: X-Loop: FreeBSD.ORG This is a multi-part message in MIME format. --------------8361301D639C7819FBE5AD82 Content-Type: text/plain; charset=iso-8859-1 Content-Transfer-Encoding: 8bit Hello list! There have been some issues with hanging of the vr-type of ethernetcontrollers. I have made a patch that solves some problems and I'm now seeking people to test it. Please apply the attached patch to your vr-driver and see if it solves any problems for you. I have tested (and made) the patch on a 4.7-RELEASE with the latest vr-drivers. /thn -- --------------------------------------------------------------- Svensk Aktuell Elektronik AB Thomas Nyström Box 10 Phone: +46 8 35 92 85 S-191 21 Sollentuna Fax: +46 8 59 47 45 36 Sweden Email: thn@saeab.se --------------------------------------------------------------- --------------8361301D639C7819FBE5AD82 Content-Type: text/plain; charset=us-ascii; name="vr.patch" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="vr.patch" --- /root/vr/if_vr.c Thu Dec 12 15:05:50 2002 +++ if_vr.c Fri Dec 13 15:25:13 2002 @@ -991,33 +991,23 @@ */ if (rxstat & VR_RXSTAT_RXERR) { ifp->if_ierrors++; - printf("vr%d: rx error: ", sc->vr_unit); - switch(rxstat & 0x000000FF) { - case VR_RXSTAT_CRCERR: - printf("crc error\n"); - break; - case VR_RXSTAT_FRAMEALIGNERR: - printf("frame alignment error\n"); - break; - case VR_RXSTAT_FIFOOFLOW: - printf("FIFO overflow\n"); - break; - case VR_RXSTAT_GIANT: - printf("received giant packet\n"); - break; - case VR_RXSTAT_RUNT: - printf("received runt packet\n"); - break; - case VR_RXSTAT_BUSERR: - printf("system bus error\n"); - break; - case VR_RXSTAT_BUFFERR: - printf("rx buffer error\n"); - break; - default: - printf("unknown rx error\n"); - break; - } + printf("vr%d: rx error (%02x):", + sc->vr_unit, rxstat & 0x000000ff); + if (rxstat & VR_RXSTAT_CRCERR) + printf(" crc error"); + if (rxstat & VR_RXSTAT_FRAMEALIGNERR) + printf(" frame alignment error\n"); + if (rxstat & VR_RXSTAT_FIFOOFLOW) + printf(" FIFO overflow"); + if (rxstat & VR_RXSTAT_GIANT) + printf(" received giant packet"); + if (rxstat & VR_RXSTAT_RUNT) + printf(" received runt packet"); + if (rxstat & VR_RXSTAT_BUSERR) + printf(" system bus error"); + if (rxstat & VR_RXSTAT_BUFFERR) + printf("rx buffer error"); + printf("\n"); vr_newbuf(sc, cur_rx, m); continue; } @@ -1058,9 +1048,29 @@ void vr_rxeoc(sc) struct vr_softc *sc; { + struct ifnet *ifp; + int i; + + ifp = &sc->arpcom.ac_if; + + ifp->if_ierrors++; + + VR_CLRBIT16(sc, VR_COMMAND, VR_CMD_RX_ON); + DELAY(10000); + + for (i = 0x400; + i && (CSR_READ_2(sc, VR_COMMAND) & VR_CMD_RX_ON); + i--) + ; /* Wait for receiver to stop */ + + if (!i) { + printf("vr%d: rx shutdown error!\n", sc->vr_unit); + sc->vr_flags |= VR_F_RESTART; + return; + } vr_rxeof(sc); - VR_CLRBIT16(sc, VR_COMMAND, VR_CMD_RX_ON); + CSR_WRITE_4(sc, VR_RXADDR, vtophys(sc->vr_cdata.vr_rx_head->vr_ptr)); VR_SETBIT16(sc, VR_COMMAND, VR_CMD_RX_ON); VR_SETBIT16(sc, VR_COMMAND, VR_CMD_RX_GO); @@ -1094,14 +1104,22 @@ */ while(sc->vr_cdata.vr_tx_head->vr_mbuf != NULL) { u_int32_t txstat; + int i; cur_tx = sc->vr_cdata.vr_tx_head; txstat = cur_tx->vr_ptr->vr_status; if ((txstat & VR_TXSTAT_ABRT) || (txstat & VR_TXSTAT_UDF)) { - while (CSR_READ_2(sc, VR_COMMAND) & VR_CMD_TX_ON) + for (i = 0x400; + i && (CSR_READ_2(sc, VR_COMMAND) & VR_CMD_TX_ON); + i--) ; /* Wait for chip to shutdown */ + if (!i) { + printf("vr%d: tx shutdown timeout\n", sc->vr_unit); + sc->vr_flags |= VR_F_RESTART; + break; + } VR_TXOWN(cur_tx) = VR_TXSTAT_OWN; CSR_WRITE_4(sc, VR_TXADDR, vtophys(cur_tx->vr_ptr)); break; @@ -1167,6 +1185,14 @@ s = splimp(); sc = xsc; + if (sc->vr_flags & VR_F_RESTART) { + printf("vr%d: restarting\n", sc->vr_unit); + vr_stop(sc); + vr_reset(sc); + vr_init(sc); + sc->vr_flags &= ~VR_F_RESTART; + } + mii = device_get_softc(sc->vr_miibus); mii_tick(mii); @@ -1208,10 +1234,22 @@ if (status & VR_ISR_RX_OK) vr_rxeof(sc); + if (status & VR_ISR_RX_DROPPED) { + printf("vr%d: rx packet lost\n", sc->vr_unit); + ifp->if_ierrors++; + } + if ((status & VR_ISR_RX_ERR) || (status & VR_ISR_RX_NOBUF) || - (status & VR_ISR_RX_NOBUF) || (status & VR_ISR_RX_OFLOW) || - (status & VR_ISR_RX_DROPPED)) { - vr_rxeof(sc); + (status & VR_ISR_RX_NOBUF) || (status & VR_ISR_RX_OFLOW)) { + printf("vr%d: receive error (%04x)", + sc->vr_unit, status); + if (status & VR_ISR_RX_NOBUF) + printf(" no buffers"); + if (status & VR_ISR_RX_OFLOW) + printf(" overflow"); + if (status & VR_ISR_RX_DROPPED) + printf(" packet lost"); + printf("\n"); vr_rxeoc(sc); } @@ -1430,13 +1468,13 @@ * so we must set both. */ VR_CLRBIT(sc, VR_BCR0, VR_BCR0_RX_THRESH); - VR_SETBIT(sc, VR_BCR0, VR_BCR0_RXTHRESHSTORENFWD); + VR_SETBIT(sc, VR_BCR0, VR_BCR0_RXTHRESH128BYTES); VR_CLRBIT(sc, VR_BCR1, VR_BCR1_TX_THRESH); VR_SETBIT(sc, VR_BCR1, VR_BCR1_TXTHRESHSTORENFWD); VR_CLRBIT(sc, VR_RXCFG, VR_RXCFG_RX_THRESH); - VR_SETBIT(sc, VR_RXCFG, VR_RXTHRESH_STORENFWD); + VR_SETBIT(sc, VR_RXCFG, VR_RXTHRESH_128BYTES); VR_CLRBIT(sc, VR_TXCFG, VR_TXCFG_TX_THRESH); VR_SETBIT(sc, VR_TXCFG, VR_TXTHRESH_STORENFWD); --- /root/vr/if_vrreg.h Thu Dec 12 15:07:25 2002 +++ if_vrreg.h Thu Dec 12 14:35:44 2002 @@ -464,10 +464,13 @@ u_int8_t vr_unit; /* interface number */ u_int8_t vr_type; u_int8_t vr_revid; /* Rhine chip revision */ + u_int8_t vr_flags; /* See VR_F_* below */ struct vr_list_data *vr_ldata; struct vr_chain_data vr_cdata; struct callout_handle vr_stat_ch; }; + +#define VR_F_RESTART 0x01 /* Restart unit on next tick */ /* * register space access macros --------------8361301D639C7819FBE5AD82-- To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-stable" in the body of the message