📄 sngks32cend.c
字号:
/* forward static functions */LOCAL void sngks32cEndReset (END_DEVICE *pDrvCtrl);LOCAL STATUS sngks32cEndStart (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndBdmaRxInt (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndBdmaTxInt (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndMacRxInt (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndMacTxInt (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndHandleRcvInt (END_DEVICE *pDrvCtrl, UINT32 stat);LOCAL STATUS sngks32cEndRecv (END_DEVICE *pDrvCtrl, RECEIVE_FRAME_DESC *pRxD);LOCAL void sngks32cEndConfig (END_DEVICE *pDrvCtrl);#ifdef DYNAMIC_PHYLOCAL UINT32 sngks32cEndPhyRead (UINT32 phyRegAddr, UINT32 phyAddr);#endif /* DYNAMIC_PHY */LOCAL void sngks32cEndPhyWrite (UINT32 phyRegAddr, UINT32 phyAddr, UINT32 phyData);LOCAL void sngks32cEndMacInitialize (END_DEVICE *pDevice);LOCAL STATUS sngks32cEndFdInitialize (END_DEVICE *pDrvCrtl);LOCAL void sngks32cEndFdFree (END_DEVICE *pDrvCtrl);LOCAL void sngks32cEndAddrFilterSet (END_DEVICE *pDrvCtrl);#ifdef BUG_KS32C5000LOCAL void sngks32cEndBugFix (UINT16 *);#endif /*BUG_KS32C5000*//* END Specific interfaces. *//* This is the only externally visible interface. */END_OBJ* sngks32cEndLoad (char* initString);LOCAL STATUS sngks32cEndStart (END_DEVICE* pDrvCtrl);LOCAL STATUS sngks32cEndStop (END_DEVICE* pDrvCtrl);LOCAL STATUS sngks32cEndUnload ();LOCAL int sngks32cEndIoctl (END_DEVICE* pDrvCtrl, int cmd, caddr_t data);LOCAL STATUS sngks32cEndSend (END_DEVICE* pDrvCtrl, M_BLK_ID pBuf); LOCAL STATUS sngks32cEndMCastAdd (END_DEVICE* pDrvCtrl, char* pAddress);LOCAL STATUS sngks32cEndMCastDel (END_DEVICE* pDrvCtrl, char* pAddress);LOCAL STATUS sngks32cEndMCastGet (END_DEVICE* pDrvCtrl, MULTI_TABLE* pTable);LOCAL STATUS sngks32cEndPollSend (END_DEVICE* pDrvCtrl, M_BLK_ID pBuf);LOCAL STATUS sngks32cEndPollRcv (END_DEVICE* pDrvCtrl, M_BLK_ID pBuf);LOCAL STATUS sngks32cEndPollStart (END_DEVICE* pDrvCtrl);LOCAL STATUS sngks32cEndPollStop (END_DEVICE* pDrvCtrl);LOCAL STATUS sngks32cEndParse ();LOCAL STATUS sngks32cEndMemInit ();/** Declare our function table. This is static across all driver* instances.*/LOCAL NET_FUNCS endFuncTable = { /* Function to start the device. */ (STATUS (*) (END_OBJ*))sngks32cEndStart, /* Function to stop the device. */ (STATUS (*) (END_OBJ*))sngks32cEndStop, /* Unloading function for the driver. */ (STATUS (*) (END_OBJ*))sngks32cEndUnload, /* Ioctl function for the driver. */ (int (*) (END_OBJ*, int, caddr_t))sngks32cEndIoctl, /* Send function for the driver. */ (STATUS (*) (END_OBJ* , M_BLK_ID))sngks32cEndSend, /* Multicast address add function for the driver. */ (STATUS (*) (END_OBJ*, char*))sngks32cEndMCastAdd, /* Multicast address delete function for the driver. */ (STATUS (*) (END_OBJ*, char*))sngks32cEndMCastDel, /* Multicast table retrieve function for the driver. */ (STATUS (*) (END_OBJ*, MULTI_TABLE*))sngks32cEndMCastGet, /* Polling send function for the driver. */ (STATUS (*) (END_OBJ*, M_BLK_ID))sngks32cEndPollSend, /* Polling receive function for the driver. */ (STATUS (*) (END_OBJ*, M_BLK_ID))sngks32cEndPollRcv, /* Put address info into a packet. */ endEtherAddressForm, /* Get a pointer to packet data. */ endEtherPacketDataGet, /* Get packet addresses. */ endEtherPacketAddrGet };extern CACHE_FUNCS sngks32cCacheFuncs;#ifdef DYNAMIC_PHY/********************************************************************************* phyPoll - checks the current status of the PHY** Description* Checks the current status of the PHY and sets the full duplex bit of maccon* accordingly. If not done, packets will be lost (very seldom)* * Caveat* We don't know if it's OK to change the MACCON during runtime*/LOCAL void phyPoll ( int dummy ) { MACCON macCon; UINT32 phyStat2; /* init MACCON register */ *(UINT32 *)(&macCon) = *(volatile UINT32 *)SNGKS32C_MACCON; phyStat2 = sngks32cEndPhyRead (PHY_STATUS2_REG,0); if ((phyStat2 & PHYSTAT2_FULLDUP) && (macCon.macCon_reg.fullDup == 0)) { macCon.macCon_reg.fullDup = 1; *(volatile UINT32 *)SNGKS32C_MACCON = macCon.macCon_resetval; } if (!(phyStat2 & PHYSTAT2_FULLDUP) && (macCon.macCon_reg.fullDup == 1)) { macCon.macCon_reg.fullDup = 0; *(volatile UINT32 *)SNGKS32C_MACCON = macCon.macCon_resetval; } (void) wdStart (phyPollWdog, PHY_WDOG_PERIOD , (FUNCPTR) phyPoll, 0); }#endif /*DYNAMIC_PHY*//******************************************************************************** sngks32cEndLoad - 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:** "<unit>:<Speed>:<duplex>:<autoneg>"** RETURNS: An END object pointer or NULL on error.*/END_OBJ* sngks32cEndLoad ( char* initString /* String to be parsed by the driver. */ ) { END_DEVICE *pDrvCtrl; DRV_LOG (DRV_DEBUG_LOAD, "Loading sngks32cEnd...\n", 1, 2, 3, 4, 5, 6); if (initString == NULL) { DRV_LOG (DRV_DEBUG_LOAD, "sngks32cEndLoad: NULL initString\r\n", 0,0,0,0,0,0); return NULL; } if (initString[0] == '\0') { strcpy (initString, SNGKS32CEND_DEV_NAME); return (END_OBJ *)0; } /* allocate the device structure */ pDrvCtrl = (END_DEVICE *)calloc (sizeof (END_DEVICE), 1); if (pDrvCtrl == NULL) { printf ("%s - Failed to allocate control structure\n", SNGKS32CEND_DEV_NAME ); goto errorExit; } /* parse the init string, filling in the device structure */ if (sngks32cEndParse (pDrvCtrl, initString) == ERROR) goto errorExit; pDrvCtrl->ivecBdmaTx = SNGKS32C_INT_LVL_BDMATx; pDrvCtrl->ivecBdmaRx = SNGKS32C_INT_LVL_BDMARx; pDrvCtrl->ivecMacTx = SNGKS32C_INT_LVL_MACTx; pDrvCtrl->ivecMacRx = SNGKS32C_INT_LVL_MACRx;#ifdef INCLUDE_CACHE_SUPPORT /* install cache functions defined in sysLib.c */ pDrvCtrl->cacheFuncs = &sngks32cCacheFuncs;#endif /*INCLUDE_CACHE_SUPPORT*/ /* Ask the BSP to provide the ethernet address. */ SYS_ENET_ADDR_GET(pDrvCtrl); strcpy (pDrvCtrl->end.devObject.name, SNGKS32CEND_DEV_NAME); strcpy (pDrvCtrl->end.devObject.description, "Samsung KS32C ARM7 END Driver"); /* initialize some flags */ pDrvCtrl->loaded = TRUE; /* initialize the END and MIB2 parts of the structure */ /* * The M2 element must come from m2Lib.h * This sngks32cEnd is set up for a DIX type ethernet device. */ if (END_OBJ_INIT (&pDrvCtrl->end, (DEV_OBJ *)pDrvCtrl, SNGKS32CEND_DEV_NAME, pDrvCtrl->unit, &endFuncTable, "Samsung KS32C ARM7 END Driver") == ERROR || END_MIB_INIT (&pDrvCtrl->end, M2_ifType_ethernet_csmacd, &pDrvCtrl->enetAddr[0], 6, ETHERMTU, END_SPEED) == ERROR) goto errorExit; /* Perform memory allocation/distribution */ if (sngks32cEndMemInit (pDrvCtrl) == ERROR) goto errorExit;#ifdef DYNAMIC_PHY if ((phyPollWdog = wdCreate ()) == NULL) { logMsg ("\nCould not create phyPollWdog\n",1,2,3,4,5,6); goto errorExit; }#endif /*DYNAMIC_PHY*/ /* reset and reconfigure the device */ sngks32cEndConfig (pDrvCtrl); /* set the flags to indicate readiness */ END_OBJ_READY (&pDrvCtrl->end, IFF_NOTRAILERS | IFF_BROADCAST | IFF_MULTICAST); DRV_LOG (DRV_DEBUG_LOAD, "Done loading sngks32cEnd...", 1, 2, 3, 4, 5, 6); return (&pDrvCtrl->end); errorExit: sngks32cEndUnload (pDrvCtrl); if (pDrvCtrl != NULL) free ((char *)pDrvCtrl); return NULL; }/******************************************************************************** sngks32cEndUnload - unload a driver from the system** This function first brings down the device, and then frees any* stuff that was allocated by the driver in the load function.** RETURNS: OK or ERROR.*/LOCAL STATUS sngks32cEndUnload ( END_DEVICE* pDrvCtrl /* device to be unloaded */ ) { DRV_LOG (DRV_DEBUG_LOAD, "EndUnload\n", 0, 0, 0, 0, 0, 0); if (pDrvCtrl == NULL) return (ERROR); pDrvCtrl->loaded = FALSE; /*this call will indicate protocol that the device will be unloaded */ END_OBJECT_UNLOAD (&pDrvCtrl->end); /* TODO - Free any shared DMA memory *//*before unloading the device will stop functioning*/ sngks32cEndStop(pDrvCtrl); /*then it will reset the registers in order to clear any pending interrupts */ sngks32cEndReset(pDrvCtrl); if (pDrvCtrl->fdInitialized) sngks32cEndFdFree(pDrvCtrl); if (pDrvCtrl->end.pNetPool) { netPoolDelete (pDrvCtrl->end.pNetPool); free (pDrvCtrl->end.pNetPool); pDrvCtrl->end.pNetPool = (NET_POOL_ID)0; } if (endClDescTbl[0].memArea) { free (endClDescTbl[0].memArea); endClDescTbl[0].memArea = (char *)0; } if (endMclConfig.memArea) { free (endMclConfig.memArea); endMclConfig.memArea = (char *)0; } free (pDrvCtrl); pDrvCtrl = NULL; return (OK); }/******************************************************************************** sngks32cEndParse - parse the init string** Parse the input string. Fill in values in the driver control structure.** The initialization string format is:* "<unit>:<Speed>:<duplex>:<autoneg>"** .bS* unit Device unit number, a small integer.* Speed 10 (10Mbps) or 100 (100 Mbps)* duplex 0 (HDX) or 1 (FDX)* autoneg Autonegotiation disabled (0) or enabled (1)* .bE** RETURNS: OK or ERROR for invalid arguments.*/LOCAL STATUS sngks32cEndParse ( END_DEVICE * pDrvCtrl, /* device pointer */ char * initString /* information string */ ) { char* tok; char* pHolder = NULL; /* Parse the initString */ /* Unit number. */ tok = strtok_r (initString, ":", &pHolder); if (tok == NULL) return ERROR; pDrvCtrl->unit = atoi (tok); /* netSpeed */ tok = strtok_r (NULL, ":", &pHolder); if (tok == NULL) return ERROR; pDrvCtrl->netSpeed = atoi (tok); /* DuplexMode */ tok = strtok_r (NULL, ":", &pHolder); if (tok == NULL) return ERROR; pDrvCtrl->duplexMode = atoi (tok); /* auto Negotiation */ tok = strtok_r (NULL, ":", &pHolder); if (tok == NULL) return ERROR; pDrvCtrl->autoNeg = atoi (tok); return OK; }/******************************************************************************** sngks32cEndMemInit - initialize memory for the chip** This routine is highly specific to the device. ** RETURNS: OK or ERROR.*/LOCAL STATUS sngks32cEndMemInit ( END_DEVICE * pDrvCtrl /* device to be initialized */ ) { DRV_LOG (DRV_DEBUG_LOAD, "InitMem\n", 0, 0, 0, 0, 0, 0); /* this driver can't handle write incoherent caches */ if (!CACHE_DMA_IS_WRITE_COHERENT ()) { DRV_LOG (DRV_DEBUG_LOAD, "sngks32cEndMemInit: shared memory not cache coherent\n", 1, 2, 3, 4, 5, 6); return (ERROR); } /* * Set up an END netPool using netBufLib(1). */ endMclConfig.mBlkNum = END_MBLK_NUM; endClDescTbl[0].clNum = END_CL_NUM; endMclConfig.clBlkNum = endClDescTbl[0].clNum; /* Calculate the total memory for all the M-Blks and CL-Blks. */ endMclConfig.memSize = (endMclConfig.mBlkNum * (MSIZE + sizeof (long))) + (endMclConfig.clBlkNum * (CL_BLK_SZ + sizeof(long))); if ((endMclConfig.memArea = (char *) memalign (sizeof(long), endMclConfig.memSize)) == NULL) return (ERROR); /* Calculate the memory size of all the clusters. */ endClDescTbl[0].memSize = (endClDescTbl[0].clNum *
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -