?? motfecend.c
字號(hào):
{
pDrvCtrl->rbdNum = ((MOT_FEC_MEM_SZ (pDrvCtrl)
- MOT_FEC_TBD_MEM (pDrvCtrl))
/ MOT_FEC_RBD_SZ);
}
else
{
if (MOT_FEC_MEM_SZ (pDrvCtrl) < bdSize)
{
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("motFecInitMem: not enough
memory\n"),
1, 2, 3, 4, 5, 6);
Drv_Print("motFecInitMem: not enough memory\r\n");
return (ERROR);
}
}
if ((pDrvCtrl->tbdNum <= MOT_FEC_TBD_MIN)
|| (pDrvCtrl->rbdNum <= MOT_FEC_RBD_MIN))
{
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("motFecInitMem: not enough
memory\n"),
1, 2, 3, 4, 5, 6);
Drv_Print("motFecInitMem: not enough memory\n\n");
return (ERROR);
}
MOT_FEC_FLAG_CLEAR (MOT_FEC_OWN_MEM);
pDrvCtrl->bdCacheFuncs = cacheNullFuncs;
break;
}
/* cache functions descriptor for data buffers */
motFecBufCacheFuncs.flushRtn = motFecBufFlushRtn;
motFecBufCacheFuncs.invalidateRtn = motFecBufInvRtn;
motFecBufCacheFuncs.virtToPhysRtn = NULL;
motFecBufCacheFuncs.physToVirtRtn = NULL;
pDrvCtrl->bufCacheFuncs = motFecBufCacheFuncs;
/* zero the shared memory */
memset (pDrvCtrl->pBufBase, 0, (int) pDrvCtrl->bufSize);
/*
* number of clusters, including loaning buffers, a min number
* of transmit clusters for copy-mode transmit, and one transmit
* cluster for polling operation.
*/
clNum = pDrvCtrl->rbdNum + MOT_FEC_BD_LOAN_NUM
+ 1 + MOT_FEC_TX_CL_NUM;
clSize = (MOT_FEC_TX_MEM (pDrvCtrl) + MOT_FEC_RX_MEM (pDrvCtrl)
+ (CL_OVERHEAD * clNum)
+ MOT_FEC_BD_ALIGN);
/* pool of mblks */
if (mclBlkConfig.mBlkNum == 0)
mclBlkConfig.mBlkNum = clNum * 2;
/* pool of clusters, including loaning buffers */
if (clDescTbl[0].clNum == 0)
{
clDescTbl[0].clNum = clNum;
clDescTbl[0].clSize = MOT_FEC_MAX_CL_LEN;
}
/* there's a cluster overhead and an alignment issue */
clDescTbl[0].memSize = (clDescTbl[0].clNum *
(clDescTbl[0].clSize + CL_OVERHEAD));
clDescTbl[0].memArea = (char *) (memalign (CL_ALIGNMENT, clSize));
if (clDescTbl[0].memArea == NULL)
{
return (ERROR);
}
/* store the pointer to the clBlock area */
pDrvCtrl->pClBlkArea = clDescTbl[0].memArea;
pDrvCtrl->clBlkSize = clDescTbl[0].memSize;
/* pool of cluster blocks */
if (mclBlkConfig.clBlkNum == 0)
mclBlkConfig.clBlkNum = clDescTbl[0].clNum;
/* get memory for mblks */
if (mclBlkConfig.memArea == NULL)
{
/* memory size adjusted to hold the netPool pointer at the head */
mclBlkConfig.memSize = ((mclBlkConfig.mBlkNum
* (M_BLK_SZ + MBLK_ALIGNMENT))
+ (mclBlkConfig.clBlkNum
* (CL_BLK_SZ + CL_ALIGNMENT)));
mclBlkConfig.memArea = (char *) memalign (MBLK_ALIGNMENT,
mclBlkConfig.memSize);
if (mclBlkConfig.memArea == NULL)
{
return (ERROR);
}
/* store the pointer to the mBlock area */
pDrvCtrl->pMBlkArea = mclBlkConfig.memArea;
pDrvCtrl->mBlkSize = mclBlkConfig.memSize;
}
/* init the mem pool */
if (netPoolInit (pDrvCtrl->endObj.pNetPool, &mclBlkConfig,
&clDescTbl[0], clDescTblNumEnt, NULL)
== ERROR)
{
return (ERROR);
}
if ((pDrvCtrl->pClPoolId = netClPoolIdGet (pDrvCtrl->endObj.pNetPool,
MOT_FEC_MAX_CL_LEN, FALSE))
== NULL)
{
return (ERROR);
}
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("motFecInitMem... Done\n"),
0, 0, 0, 0, 0, 0);
Drv_Print("motFecInitMem... Done\r\n");
return OK;
}
/**************************************************************************
*
* motFecStart - start the device
*
* This routine starts the FEC device and brings it up to an operational
* state. The driver must have already been loaded with the motFecEndLoad()
* routine.
*
* RETURNS: OK, or ERROR if the device could not be initialized.
*
* INTERNAL
* The speed field inthe phyInfo structure is only set after the call
* to the physical layer init routine. On the other hand, the mib2
* interface is initialized in the motFecEndLoad() routine, and the default
* value of 10Mbit assumed there is not always correct. We need to
* correct it here.
*
*/
LOCAL STATUS motFecStart
(
DRV_CTRL *pDrvCtrl /* pointer to DRV_CTRL structure */
)
{
int retVal; /* convenient holder for return value */
char bucket[4];
MOT_FEC_LOG (MOT_FEC_DBG_START, ("Starting end...\n"), 1, 2, 3, 4, 5, 6);
/*Drv_Print("starting end...\n");*/
/* must have been loaded */
if (!pDrvCtrl->loaded)
return (ERROR);
if (vxMemProbe ((char *) (pDrvCtrl->motCpmAddr + MOT_FEC_CSR_OFF),
VX_READ, 4, &bucket[0]) != OK)
{
MOT_FEC_LOG (MOT_FEC_DBG_START,
(": need MMU mapping for address 0x%x\n"),
(UINT32) pDrvCtrl->motCpmAddr, 2, 3, 4, 5, 6);
Drv_Print (" need MMU mapping for address 0x%x\n",
(UINT32) pDrvCtrl->motCpmAddr);
return (ERROR);
}
/* reset the chip */
MOT_FEC_ETH_SET;
if (motFecReset (pDrvCtrl) != OK)
return (ERROR);
if (motFecTbdInit (pDrvCtrl) == ERROR)
return (ERROR);
if (motFecRbdInit (pDrvCtrl) == ERROR)
return (ERROR);
/* set some flags to default values */
pDrvCtrl->txStall = FALSE;
pDrvCtrl->tbdIndex = 0;
pDrvCtrl->usedTbdIndex = 0;
pDrvCtrl->cleanTbdNum = pDrvCtrl->tbdNum;
pDrvCtrl->rbdIndex = 0;
/* connect the interrupt handler */
SYS_FEC_INT_CONNECT (pDrvCtrl, motFecInt, (int) pDrvCtrl, retVal);
if (retVal == ERROR)
return (ERROR);
/* enable system interrupt: set relevant bit in SIMASK */
SYS_FEC_INT_ENABLE (pDrvCtrl, retVal);
if (retVal == ERROR)
return (ERROR);
/* call the BSP to do any other initialization (port D) */
SYS_FEC_ENET_ENABLE;
/* configure some chip's registers */
if (motFecPrePhyConfig (pDrvCtrl) == ERROR)
return (ERROR);
/* initialize some fields in the PHY info structure */
if (motFecPhyPreInit (pDrvCtrl) != OK)
{
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("Failed to pre-initialize the PHY\n"),
0, 0, 0, 0, 0, 0);
return (ERROR);
}
/* initialize the Physical medium layer */
if (_func_motFecPhyInit == NULL)
return (ERROR);
if (((* _func_motFecPhyInit) (pDrvCtrl)) != OK)
{
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("Failed to initialize the PHY\n"),
0, 0, 0, 0, 0, 0);
return (ERROR);
}
/* configure other chip's registers */
if (motFecPostPhyConfig (pDrvCtrl) == ERROR)
return (ERROR);
/* correct the speed for the mib2 stuff */
pDrvCtrl->endObj.mib2Tbl.ifSpeed = pDrvCtrl->phyInfo->phySpeed;
if (END_FLAGS_ISSET (IFF_MULTICAST))
MOT_FEC_FLAG_SET (MOT_FEC_MCAST);
/* enable the Ethernet Controller */
MOT_FEC_ETH_ENABLE;
/* mark the interface as up */
END_FLAGS_SET (&pDrvCtrl->endObj, (IFF_UP | IFF_RUNNING));
/* startup the receiver */
MOT_FEC_RX_ACTIVATE;
/* Flush the write pipe */
CACHE_PIPE_FLUSH ();
MOT_FEC_LOG (MOT_FEC_DBG_START, ("Starting end... Done\n"),
1, 2, 3, 4, 5, 6);
/*Drv_Print("Starting end... Done\n");*/
return (OK);
}
/**************************************************************************
*
* motFecStop - stop the 'motfec' interface
*
* This routine marks the interface as inactive, disables interrupts and
* the Ethernet Controller. As a result, reception is stopped immediately,
* and transmission is stopped after a bad CRC is appended to any frame
* currently being transmitted. The reception/transmission control logic
* (FIFO pointers, buffer descriptors, etc.) is reset. To bring the
* interface back up, motFecStart() must be called.
*
* RETURNS: OK, always.
*/
LOCAL STATUS motFecStop
(
DRV_CTRL * pDrvCtrl /* pointer to DRV_CTRL structure */
)
{
int retVal; /* convenient holder for return value */
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("motFecStop...\n"), 1, 2, 3, 4, 5, 6);
Drv_Print("stop done\r\n");
/* make sure driver is operational before stopping it */
if (END_FLAGS_GET(&pDrvCtrl->endObj) & (IFF_UP | IFF_RUNNING))
{
/* mark the interface as down */
END_FLAGS_CLR (&pDrvCtrl->endObj, (IFF_UP | IFF_RUNNING));
/* issue a graceful transmit command */
MOT_FEC_CSR_WR (MOT_FEC_TX_CTRL_OFF, MOT_FEC_TX_CTRL_GRA);
/* wait for the related interrupt */
MOT_FEC_GRA_SEM_TAKE;
/* mask chip interrupts */
MOT_FEC_INT_DISABLE;
/* disable the Ethernet Controller */
MOT_FEC_ETH_DISABLE;
/* disable system interrupt: reset relevant bit in SIMASK */
SYS_FEC_INT_DISABLE (pDrvCtrl, retVal);
if (retVal == ERROR)
return (ERROR);
/* disconnect the interrupt handler */
SYS_FEC_INT_DISCONNECT (pDrvCtrl, motFecInt, (int)pDrvCtrl, retVal);
if (retVal == ERROR)
return (ERROR);
/* call the BSP to disable the Port D */
SYS_FEC_ENET_DISABLE;
if (motFecBdFree (pDrvCtrl) != OK)
return (ERROR);
}
MOT_FEC_LOG (MOT_FEC_DBG_LOAD, ("motFecStop... Done \n"),
1, 2, 3, 4, 5, 6);
return OK;
}
/**************************************************************************
*
* motFecReset - reset the `motFec' interface
*
* This routine resets the chip by setting the Reset bit in the Ethernet
* Control Register. The ETHER_EN bit i
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -