📄 sh7615end.c
字号:
/* sh7615End.c - sh7615End END network interface driver *//* Copyright 1984-2003 Wind River Systems, Inc. */#include "copyright_wrs.h"/*modification history--------------------01n,30jan03,m_h IPv6 Support01m,27jan03,h_k fixed for multicast packet handling. prevented the receive routine from handing off our own multi-cast transmissions to the stack. (SPR #81223) fixed for compile error in Diab env. (SPR #81231) modified END_HADDR and END_HADDR_LEN macros.01l,28mar02,h_k added muxError() at failing of netClusterGet() and netClBlkGet(). moved E-DMAC Receive Request enable to sh7615EndRcvIntHandle() from sh7615EndInt(). added setting depth of FIFO. changed clNum and mBlkNum. (SPR #74021)01k,02nov01,zl corrected NULL usage.01j,19oct01,zl documentation fixes. Removed sh7615EndIASetup().01i,09may01,zl detect link status change, add restart routine.01h,05may01,zl made interrupt handling more efficient and robust.01g,30apr01,zl detect and set full duplex mode.01f,09nov00,rsh missing #ifdef01e,02nov00,frf Read and Write functions to a PHY registers: dp83843RegRead, dp83843RegWrite, dp83843RegPrint.01d,10oct00,zl got polled mode working. Code Cleanup.01c,27sep00,rsh add cache support.01b,26sep00,rsh remove bsp option to provide shared memory since this chip. doesn't provide special memory.01a,16aug00,rsh written based on dec21x40End.c*//*DESCRIPTIONThis module implements an network interface driver for the Hitachi SH7615on-chip Ethernet controller (EtherC) and EtherNet COntroller Direct Memory Access Controller (E-DMAC). The EtherC is fully compliant with the IEEE 802.310Base-T and 100Base-T specifications. Hardware support of the Media Independent Interface (MII) is off-chip.The Ethernet controller is connected to dedicated transmit and receive Ethernet DMACs (E-DMACs) in the SH7615, and carries out high-speed datatransfer to and from memory. The operation of the E-DMAC is controlled withthe transmit and receive descriptor rings. The start address of thedescriptors is set in the RDLAR and TDLAR registers, so they can resideanywhwere. The descriptors must reside on boundaries that are multipleof their size (16, 32, or 64 bytes).EXTERNAL INTERFACE The driver provides the standard external interface, sh7615EndLoad(), whichtakes a string of colon-separated parameters. The parameters should be specified in hexadecimal, optionally preceeded by "0x" or a minus sign "-".The parameter string is parsed using strtok_r() and each parameter isconverted from a string representation to binary by a call tostrtoul(parameter, NULL, 16).The format of the parameter string is:"<ivec>:<ilevel>:<numRds>:<numTds>:<phyDefMode>:<userFlags>"TARGET-SPECIFIC PARAMETERS.IP <ivec>This is the interrupt vector number of the hardware interrupt generated bythis Ethernet device. The driver uses intConnect() to attach an interrupthandler for this interrupt..IP <ilevel>This parameter defines the level of the hardware interrupt..IP <numRds>The number of receive descriptors to use. This controls how much datathe device can absorb under load. If this is specified as NONE (-1), the default of 32 is used..IP <numTds>The number of transmit descriptors to use. This controls how much datathe device can absorb under load. If this is specified as NONE (-1) thenthe default of 64 is used..IP <phyDefMode>This parameter specifies the operating mode that will be set upby the default physical layer initialization routine in case allthe attempts made to establish a valid link failed. If that happens,the first PHY that matches the specified abilities will be chosen towork in that mode, and the physical link will not be tested..IP <userFlags>This field enables the user to give some degree of customization to thedriver.Bit [0-3] reserved for receive FIFO depth and bit [4-7] reserved for transmitFIFO depth. The actual FIFO size is 256 times + 256 the set value for eachFIFO. The max FIFO depth is 512 bytes for SH7615 (i.e. 0x1 for receive FIFO,0x10 for transmit FIFO) and 2048 bytes for SH7616 (i.e. 0x7 for receive FIFO,0x70 for transmit FIFO).The macros SYS_INT_CONNECT, SYS_INT_DISCONNECT, and SYS_INT_ENABLE allowthe driver to be customized for BSPs that use special versions of theseroutines.The macro SYS_INT_CONNECT is used to connect the interrupt handler tothe appropriate vector. By default it is the routine intConnect().The macro SYS_INT_DISCONNECT is used to disconnect the interrupt handler priorto unloading the module. By default this is a dummy routine thatreturns OK.The macro SYS_INT_ENABLE is used to enable the interrupt level for theend device. It is called once during initialization. By default this isthe routine sysLanIntEnable(), defined in the module sysLib.o.The macro SYS_ENET_ADDR_GET is used to get the ethernet address (MAC)for the device. The single argument to this routine is the SH7615END_DRV_CTRLpointer. By default this routine copies the ethernet address stored inthe global variable sysTemplateEnetAddr into the SH7615END_DRV_CTRL structure.SEE ALSO: muxLib, endLib.I "Writing and Enhanced Network Driver".I "SH7615 Hardware Manual"*//* includes */#include "vxWorks.h"#include "stdlib.h"#include "cacheLib.h"#include "intLib.h"#include "end.h" /* Common END structures. */#include "endLib.h"#include "lstLib.h" /* Needed to maintain protocol list. */#include "wdLib.h"#include "iv.h"#include "semLib.h"#include "etherLib.h"#include "logLib.h"#include "netLib.h"#include "stdio.h"#include "sysLib.h"#include "errno.h"#include "errnoLib.h"#include "memLib.h"#include "iosLib.h"#undef ETHER_MAP_IP_MULTICAST#include "etherMultiLib.h" /* multicast stuff. */#include "net/mbuf.h"#include "sys/times.h"#include "net/unixLib.h"#include "net/protosw.h"#include "net/systm.h"#include "net/if_subr.h"#include "net/route.h"#include "sys/socket.h"#include "sys/ioctl.h"#ifdef WR_IPV6#include "adv_net.h"#endif /*WR_IPV6*/#include "drv/end/sh7615End.h"/* defines */#define INCLUDE_PHY#define DRV_CTRL SH7615END_DRV_CTRL#define SH7615END_DEV_NAME "shend"#define SH7615END_DEV_NAME_LEN 6#define SH7615END_BUFSIZ (ETHERMTU + ENET_HDR_REAL_SIZ + 6 + \ SH7615END_BD_ALIGN)#define SH7615END_SPEED 10000000 /* 10Mbs */ /* DRV_CTRL flags */#define SH7615END_INV_TBD_NUM 0x02 /* invalid numTds provided */#define SH7615END_INV_RBD_NUM 0x04 /* invalid numRds provided */#define SH7615END_POLLING 0x08 /* Poll mode, io mode */#define SH7615END_PROMISC 0x20 /* Promiscuous, rx mode */#define SH7615END_MCAST 0x40 /* Multicast, rx mode */#define SH7615END_FD 0x80 /* full duplex mode *//* * Default macro definitions for BSP interface. * These macros can be redefined in a wrapper file, to generate * a new module with an optimized interface. */#ifndef SYS_INT_CONNECT#define SYS_INT_CONNECT(pDrvCtrl,rtn,arg,pResult) \ { \ *pResult = intConnect ((VOIDFUNCPTR *)INUM_TO_IVEC (pDrvCtrl->ivec),\ rtn, (int)arg); \ }#endif /* SYS_INT_CONNECT */ #ifndef SYS_INT_DISCONNECT#define SYS_INT_DISCONNECT(pDrvCtrl,rtn,arg,pResult) \ { \ *pResult = OK; \ }#endif /* SYS_INT_DISCONNECT */#ifndef SYS_INT_ENABLE#define SYS_INT_ENABLE(pDrvCtrl) \ { \ IMPORT void sysLanIntEnable(); \ sysLanIntEnable (pDrvCtrl->ilevel); \ }#endif /* SYS_INT_ENABLE */ #ifndef SYS_INT_DISABLE#define SYS_INT_DISABLE(pDrvCtrl) \ { \ IMPORT STATUS sysLanIntDisable(); \ sysLanIntDisable(pDrvCtrl->ilevel); \ }#endif /*SYS_INT_DISABLE*/#define NET_BUF_ALLOC() \ netClusterGet (pDrvCtrl->end.pNetPool, pDrvCtrl->pClPoolId)#define NET_TO_SH7615END_BUF(netBuf) \ (((UINT32) (netBuf) + SH7615END_BD_ALIGN - 1) \ & ~(SH7615END_BD_ALIGN - 1)) #define NET_BUF_FREE(pBuf) \ netClFree (pDrvCtrl->end.pNetPool, pBuf) #define NET_MBLK_ALLOC() \ mBlkGet (pDrvCtrl->end.pNetPool, M_DONTWAIT, MT_DATA) #define NET_MBLK_FREE(pMblk) \ netMblkFree (pDrvCtrl->end.pNetPool, (M_BLK_ID)pMblk) #define NET_CL_BLK_ALLOC() \ clBlkGet (pDrvCtrl->end.pNetPool, M_DONTWAIT) #define NET_CL_BLK_FREE(pClblk) \ clBlkFree (pDrvCtrl->end.pNetPool, (CL_BLK_ID)pClBlk) #define NET_MBLK_BUF_FREE(pMblk) \ netMblkClFree ((M_BLK_ID)pMblk) #define NET_MBLK_CL_JOIN(pMblk, pClBlk) \ netMblkClJoin ((pMblk), (pClBlk)) #define NET_CL_BLK_JOIN(pClBlk, pBuf, len) \ netClBlkJoin ((pClBlk), (pBuf), (len), NULL, 0, 0, 0)#ifndef SYS_ENET_ADDR_GET#define SYS_ENET_ADDR_GET(pDrvCtrl, pAddress) \ { \ IMPORT STATUS sysEnetAddrGet (int, char*); \ sysEnetAddrGet (pDrvCtrl->unit, pAddress); \ }#endif /* SYS_ENET_ADDR_GET */#define SH7615END_REG_READ(regAddr, value) \ ((value) = (* (volatile UINT32 *) (regAddr))) #define SH7615END_REG_WRITE(regAddr, value) \ ((* (volatile UINT32 *) (regAddr)) = ((UINT32) value))#define SH7615END_BIT_SET(reg, val) \ { \ UINT32 temp = 0; \ SH7615END_REG_READ(reg, temp); \ SH7615END_REG_WRITE((reg), temp | (val)); \ } #define SH7615END_BIT_CLR(reg, val) \ { \ UINT32 temp = 0; \ SH7615END_REG_READ(reg, temp); \ SH7615END_REG_WRITE((reg), temp & ~(val)); \ }/* DRV_CTRL flags access macros */#define DRV_FLAGS_SET(setBits) \ (pDrvCtrl->flags |= (setBits)) #define DRV_FLAGS_ISSET(setBits) \ (pDrvCtrl->flags & (setBits)) #define DRV_FLAGS_CLR(clrBits) \ (pDrvCtrl->flags &= ~(clrBits)) #define DRV_FLAGS_GET() \ (pDrvCtrl->flags)#define END_FLAGS_ISSET(pEnd, setBits) \ ((pEnd)->flags & (setBits))/* A shortcut for getting the hardware address */#define END_HADDR(pDrvCtrl) (pDrvCtrl->enetAddr)#define END_HADDR_LEN(pDrvCtrl) (strlen (pDrvCtrl->enetAddr))/* Cache related macros */#define SH7615END_CACHE_FLUSH(address, len) \ cacheFlush(DATA_CACHE, (address), (len)) #define SH7615END_CACHE_INVALIDATE(address, len) \ cacheInvalidate (DATA_CACHE, (address), (len))/* DEBUG MACROS */#ifdef DRV_DEBUG#undef LOCAL#define LOCAL#define DRV_DEBUG_OFF 0x0000#define DRV_DEBUG_RX 0x0001#define DRV_DEBUG_TX 0x0002#define DRV_DEBUG_INT 0x0004#define DRV_DEBUG_POLL (DRV_DEBUG_POLL_RX | DRV_DEBUG_POLL_TX)#define DRV_DEBUG_POLL_RX 0x0008#define DRV_DEBUG_POLL_TX 0x0010#define DRV_DEBUG_LOAD 0x0020#define DRV_DEBUG_IOCTL 0x0040#define DRV_DEBUG_POLL_REDIR 0x10000#define DRV_DEBUG_LOG_NVRAM 0x20000#define DRV_DEBUG_PHY 0x40000 int sh7615EndDebug = 0x40000;int sh7615EndRfcof = 0;int sh7615EndEci = 0;int sh7615EndTc = 0;int sh7615EndTde = 0;int sh7615EndTfuf = 0;int sh7615EndFr = 0;int sh7615EndRde = 0;int sh7615EndRfof = 0;int sh7615EndItf = 0;int sh7615EndCnd = 0;int sh7615EndDlc = 0;int sh7615EndCd = 0;int sh7615EndTro = 0;int sh7615EndRmaf = 0;int sh7615EndRrf = 0;int sh7615EndRtlf = 0;int sh7615EndRtsf = 0;int sh7615EndPre = 0;int sh7615EndCerf = 0;int sh7615EndTfe = 0;/* globals for easy access */CL_POOL_ID sh7615ClPool;NET_POOL_ID sh7615NetPoolId;DRV_CTRL * pShEnd;#define DRV_LOG(FLG, X0, X1, X2, X3, X4, X5, X6) \ if (sh7615EndDebug & FLG) \ logMsg(X0, X1, X2, X3, X4, X5, X6);#define DRV_PRINT(FLG,X) \ if (sh7615EndDebug & FLG) printf X;#else /*DRV_DEBUG*/#define DRV_LOG(DBG_SW, X0, X1, X2, X3, X4, X5, X6)#define DRV_PRINT(DBG_SW,X)#endif /*DRV_DEBUG*//* LOCALS *//* forward static functions */LOCAL void sh7615EndReset (DRV_CTRL *pDrvCtrl); LOCAL void sh7615EndInt (DRV_CTRL *pDrvCtrl);LOCAL void sh7615EndRcvIntHandle (DRV_CTRL *pDrvCtrl);LOCAL STATUS sh7615EndRecv (DRV_CTRL *pDrvCtrl, SH7615_RD * pRxD );LOCAL void sh7615EndConfig (DRV_CTRL *pDrvCtrl);LOCAL void sh7615EndModeSet (DRV_CTRL *pDrvCtrl);LOCAL STATUS sh7615EndParse (DRV_CTRL * pDrvCtrl, char * initString); LOCAL STATUS sh7615EndMemInit (DRV_CTRL * pDrvCtrl);LOCAL void sh7615EnetAddrGet (DRV_CTRL* pDrvCtrl, char* addr);LOCAL SH7615_RD * sh7615EndRxDGet (DRV_CTRL *pDrvCtrl);LOCAL SH7615_TD * sh7615EndTxDGet (DRV_CTRL *pDrvCtrl);LOCAL void sh7615EndTxRingClean (DRV_CTRL *pDrvCtrl);LOCAL void sh7615EndRestart (DRV_CTRL *pDrvCtrl);#ifdef INCLUDE_PHYLOCAL void dp83843SingleBitWrite (int bitVal);#if 0 /* currently not used */LOCAL void dp83843RegWrite (UINT16 regAddr, UINT16 regData);#endifLOCAL UINT16 dp83843RegRead (UINT16 regAddr);#endif/* END Specific interfaces. */END_OBJ* sh7615EndLoad (char* initString);LOCAL STATUS sh7615EndUnload (DRV_CTRL* pDrvCtrl);LOCAL STATUS sh7615EndStart (DRV_CTRL* pDrvCtrl);LOCAL STATUS sh7615EndStop (DRV_CTRL* pDrvCtrl);LOCAL STATUS sh7615EndIoctl (DRV_CTRL* pDrvCtrl, int cmd, caddr_t data);LOCAL STATUS sh7615EndSend (DRV_CTRL *pDrvCtrl, M_BLK *pMblk);LOCAL STATUS sh7615EndMCastAddrAdd (DRV_CTRL *pDrvCtrl, char* pAddress);LOCAL STATUS sh7615EndMCastAddrDel (DRV_CTRL *pDrvCtrl, char* pAddress);LOCAL STATUS sh7615EndMCastAddrGet (DRV_CTRL *pDrvCtrl, MULTI_TABLE *pTable);LOCAL STATUS sh7615EndPollSend (DRV_CTRL *pDrvCtrl, M_BLK *pMblk);LOCAL STATUS sh7615EndPollReceive (DRV_CTRL *pDrvCtrl, M_BLK *pMblk);LOCAL STATUS sh7615EndPollStart (DRV_CTRL *pDrvCtrl);LOCAL STATUS sh7615EndPollStop (DRV_CTRL *pDrvCtrl);/* * Declare our function table. This is static across all driver * instances. */LOCAL NET_FUNCS sh7615EndFuncTable = { (FUNCPTR) sh7615EndStart, /* Function to start the device. */ (FUNCPTR) sh7615EndStop, /* Function to stop the device. */ (FUNCPTR) sh7615EndUnload, /* Unloading function for the driver. */ (FUNCPTR) sh7615EndIoctl, /* Ioctl function for the driver. */ (FUNCPTR) sh7615EndSend, /* send func. */ (FUNCPTR) sh7615EndMCastAddrAdd, /* multicast add func. */ (FUNCPTR) sh7615EndMCastAddrDel, /* multicast delete func. */ (FUNCPTR) sh7615EndMCastAddrGet, /* multicast get fun. */ (FUNCPTR) sh7615EndPollSend, /* polling send func. */ (FUNCPTR) sh7615EndPollReceive, /* polling receive func. */ endEtherAddressForm, /* put address info into a NET_BUFFER */ (FUNCPTR) endEtherPacketDataGet, /* get pointer to data in NET_BUFFER */ (FUNCPTR) endEtherPacketAddrGet /* Get packet addresses. */ };/********************************************************************************* sh7615EndLoad - initialize the driver and device** This routine initializes the driver and the device to the operational state.* All of the device specific parameters are passed in the initString.** The string contains the target specific parameters like this:* "ivec:ilevel:numRds:numTds:phyDefMode:userFlags"** RETURNS: An END object pointer or NULL on error.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -