📄 dec21x40end.c
字号:
* dec21x40InitMem - initialize memory** RETURNS: OK or ERROR.*/LOCAL STATUS dec21x40InitMem ( DRV_CTRL * pDrvCtrl ) { DEC_RD * pRxD = pDrvCtrl->rxRing; DEC_TD * pTxD = pDrvCtrl->txRing; M_CL_CONFIG dcMclBlkConfig; CL_DESC clDesc; /* cluster description */ char * pBuf; int ix; int sz; char * pShMem; /* Establish size of shared memory region we require */ DRV_LOG (DRV_DEBUG_LOAD, "InitMem\n", 0, 0, 0, 0, 0, 0); if ((int)pDrvCtrl->memBase != NONE) /* specified memory pool */ { sz = ((pDrvCtrl->memSize - (RD_SIZ + TD_SIZ)) / (((2 + NUM_LOAN) * DEC_BUFSIZ) + RD_SIZ + TD_SIZ)); pDrvCtrl->numRds = max (sz, MIN_RDS); pDrvCtrl->numTds = max (sz, MIN_TDS); } /* Establish a region of shared memory */ /* OK. We now know how much shared memory we need. If the caller * provides a specific memory region, we check to see if the provided * region is large enough for our needs. If the caller did not * provide a specific region, then we attempt to allocate the memory * from the system, using the cache aware allocation system call. */ switch ((int)pDrvCtrl->memBase) { default : /* caller provided memory */ sz = ((pDrvCtrl->numRds * (DEC_BUFSIZ + RD_SIZ + 8)) + 4 + (pDrvCtrl->numTds * (DEC_BUFSIZ + TD_SIZ + 8)) + 4 + (NUM_LOAN * (DEC_BUFSIZ + 8)) + 4); if ( pDrvCtrl->memSize < sz ) /* not enough space */ { DRV_LOG ( DRV_DEBUG_LOAD, "%s%d: not enough memory provided\n", (int)DRV_NAME, pDrvCtrl->unit,0,0,0,0); return ( ERROR ); } pShMem = pDrvCtrl->memBase; /* set the beginning of pool */ /* assume pool is cache coherent, copy null structure */ pDrvCtrl->cacheFuncs = cacheNullFuncs; break; case NONE : /* get our own memory */ /* Because the structures that are shared between the device * and the driver may share cache lines, the possibility exists * that the driver could flush a cache line for a structure and * wipe out an asynchronous change by the device to a neighboring * structure. Therefore, this driver cannot operate with memory * that is not write coherent. We check for the availability of * such memory here, and abort if the system did not give us what * we need. */ if (!CACHE_DMA_IS_WRITE_COHERENT ()) { DRV_LOG ( DRV_DEBUG_LOAD, "dc: device requires cache coherent memory\n", 0,0,0,0,0,0); return (ERROR); } sz = (((pDrvCtrl->numRds + 1) * RD_SIZ) + ((pDrvCtrl->numTds + 1) * TD_SIZ)); pDrvCtrl->memBase = pShMem = (char *) cacheDmaMalloc ( sz ); if (pShMem == NULL) { DRV_LOG ( DRV_DEBUG_LOAD, "%s%d - system memory unavailable\n", (int)DRV_NAME, pDrvCtrl->unit, 0,0,0,0); return (ERROR); } pDrvCtrl->memSize = sz; DRV_FLAGS_SET (DEC_MEMOWN); /* copy the DMA structure */ pDrvCtrl->cacheFuncs = cacheDmaFuncs; break; } /* zero the shared memory */ bzero (pShMem, (int) sz); /* carve Rx memory structure */ pRxD = pDrvCtrl->rxRing = (DEC_RD *) (((int)pShMem + 0x03) & ~0x03); /* carve Tx memory structure */ pTxD = pDrvCtrl->txRing = (DEC_TD *) (pDrvCtrl->rxRing + pDrvCtrl->numRds); /* Initialize net buffer pool for tx/rx buffers */ bzero ((char *)&dcMclBlkConfig, sizeof(dcMclBlkConfig)); bzero ((char *)&clDesc, sizeof(clDesc)); dcMclBlkConfig.mBlkNum = pDrvCtrl->numRds * 4; clDesc.clNum = pDrvCtrl->numRds + pDrvCtrl->numTds + NUM_LOAN; dcMclBlkConfig.clBlkNum = clDesc.clNum; /* * mBlk and cluster configuration memory size initialization * memory size adjusted to hold the netPool pointer at the head. */ dcMclBlkConfig.memSize = ((dcMclBlkConfig.mBlkNum * (MSIZE + sizeof (long))) + (dcMclBlkConfig.clBlkNum * (CL_BLK_SZ + sizeof (long)))); if ((dcMclBlkConfig.memArea = (char *)memalign(sizeof (long), dcMclBlkConfig.memSize)) == NULL) return (ERROR); clDesc.clSize = DEC_BUFSIZ; clDesc.memSize = ((clDesc.clNum * (clDesc.clSize + 4)) + 4); if (DRV_FLAGS_ISSET(DEC_MEMOWN)) { clDesc.memArea = (char *) cacheDmaMalloc (clDesc.memSize); if (clDesc.memArea == NULL) { DRV_LOG (DRV_DEBUG_LOAD, "%s%d - system memory unavailable\n", (int)DRV_NAME, pDrvCtrl->unit, 0,0,0,0); return (ERROR); } } else clDesc.memArea = (char *) (pDrvCtrl->txRing + pDrvCtrl->numTds); if ((pDrvCtrl->endObj.pNetPool = malloc (sizeof(NET_POOL))) == NULL) return (ERROR); /* Initialize the net buffer pool with transmit buffers */ if (netPoolInit (pDrvCtrl->endObj.pNetPool, &dcMclBlkConfig, &clDesc, 1, NULL) == ERROR) { DRV_LOG (DRV_DEBUG_LOAD, "%s%d - netPoolInit failed\n", (int)DRV_NAME, pDrvCtrl->unit,0,0,0,0); return (ERROR); } /* Save the cluster pool id */ pDrvCtrl->clPoolId = clPoolIdGet (pDrvCtrl->endObj.pNetPool, DEC_BUFSIZ, FALSE); /* Clear all indices */ pDrvCtrl->rxIndex=0; pDrvCtrl->txIndex=0; pDrvCtrl->txDiIndex=0; /* Setup the receive ring */ for (ix = 0; ix < pDrvCtrl->numRds; ix++, pRxD++) { pBuf = (char *) NET_BUF_ALLOC(); if (pBuf == NULL) { DRV_LOG (DRV_DEBUG_LOAD, "%s%d - netClusterGet failed\n", (int)DRV_NAME, pDrvCtrl->unit,0,0,0,0); return (ERROR); } pRxD->rDesc2 = PCISWAP (DEC_VIRT_TO_PCI (pBuf)); /* buffer 1 */ pRxD->rDesc3 = 0; /* no second buffer */ /* buffer size */ pRxD->rDesc1 = PCISWAP (RDESC1_RBS1_VAL (DEC_BUFSIZ) | RDESC1_RBS2_VAL (0)); if (ix == (pDrvCtrl->numRds - 1)) /* if its is last one */ pRxD->rDesc1 |= PCISWAP (RDESC1_RER); /* end of receive ring */ pRxD->rDesc0 = PCISWAP (RDESC0_OWN); /* give ownership to chip */ } /* Setup the transmit ring */ for (ix = 0; ix < pDrvCtrl->numTds; ix++, pTxD++) { /* empty -- no buffers at this time */ pTxD->tDesc2 = 0; pTxD->tDesc3 = 0; pTxD->tDesc1 = PCISWAP ((TDESC1_TBS1_PUT(0) | /* buffer1 size */ TDESC1_TBS2_PUT(0) | /* buffer2 size */ TDESC1_IC | /* intrpt on xmit */ TDESC1_LS | /* last segment */ TDESC1_FS)); /* first segment */ if (ix == (pDrvCtrl->numTds - 1)) /* if its is last one */ pTxD->tDesc1 |= PCISWAP (TDESC1_TER); /* end of Xmit ring */ pTxD->tDesc0 = 0; /* owner is host */ } /* Flush the write pipe */ CACHE_PIPE_FLUSH (); return (OK); }/********************************************************************************* dec21x40Start - start the device** This function initializes the device and calls BSP functions to connect* interrupts and start the device running in interrupt mode.** The complement of this routine is dec21x40Stop. Once a unit is reset by* dec21x40Stop, it may be re-initialized to a running state by this routine.** RETURNS: OK if successful, otherwise ERROR*/LOCAL STATUS dec21x40Start ( DRV_CTRL * pDrvCtrl /* device to start */ ) { int retVal; UINT csr6Val = 0; UINT usrFlags = pDrvCtrl->usrFlags; UINT tries = 0; DRV_LOG (DRV_DEBUG_LOAD, "Start, IO base addr: 0x%x ivec %d, ilevel %d, mempool base addr: 0x%x\n", pDrvCtrl->devAdrs, pDrvCtrl->ivec, pDrvCtrl->ilevel, (int)(pDrvCtrl->memBase), 0, 0); DRV_LOG (DRV_DEBUG_LOAD, " pciMemBase=0x%x flags=0x%x usrFlags=0x%x\n", (int)pDrvCtrl->pciMemBase, pDrvCtrl->flags, pDrvCtrl->usrFlags, 0, 0, 0);restart: /* Reset the device */ DEC_CSR_WRITE (CSR6, 0); dec21x40ChipReset (pDrvCtrl); /* Clear all indices */ pDrvCtrl->rxIndex=0; pDrvCtrl->txIndex=0; pDrvCtrl->txDiIndex=0; pDrvCtrl->txCleaning = FALSE; pDrvCtrl->rxHandling = FALSE; pDrvCtrl->txBlocked = FALSE; if (! DRV_FLAGS_ISSET (DEC_21040)) { if (_func_dec21x40MediaSelect != NULL) retVal = (* _func_dec21x40MediaSelect) (pDrvCtrl, &csr6Val); else if (DRV_FLAGS_ISSET (DEC_21140)) retVal = dec21140MediaSelect (pDrvCtrl, &csr6Val); else retVal = dec21143MediaSelect (pDrvCtrl, &csr6Val); if (retVal == ERROR) return (ERROR); if (csr6Val & CSR6_21140_PS) { /* changing PS requires a software reset */ DEC_CSR_UPDATE (CSR6, CSR6_21140_PS); DEC_CSR_WRITE (CSR0, CSR0_SWR); csr6Val |= CSR6_21140_HBD; /* clear CSR13 and 14 if 21143 - Appendix D, Port Selection */ if (usrFlags & DEC_USR_21143) { DEC_CSR_WRITE (CSR13, 0); DEC_CSR_WRITE (CSR14, 0); } } csr6Val &= DEC_USR_CSR6_MSK; csr6Val |= CSR6_21140_MB1; /* decode CSR6 specific options from userFlags */ if (usrFlags & DEC_USR_SF) csr6Val |= CSR6_21140_SF; if (usrFlags & DEC_USR_THR_MSK) csr6Val |= (usrFlags & DEC_USR_THR_MSK) >> DEC_USR_THR_SHF; if (usrFlags & DEC_USR_SB) csr6Val |= CSR6_SB; if (usrFlags & DEC_USR_PB) csr6Val |= CSR6_PB; if (usrFlags & DEC_USR_SC) csr6Val |= CSR6_21140_SC; if (usrFlags & DEC_USR_CA) csr6Val |= CSR6_CAE; } else dec21040AuiTpInit (pDrvCtrl); /* Write start of receive ring */ DEC_CSR_WRITE (CSR3, DEC_VIRT_TO_PCI(pDrvCtrl->rxRing)); /* Write start of transmit ring */ DEC_CSR_WRITE (CSR4, DEC_VIRT_TO_PCI(pDrvCtrl->txRing)); /* clear the status register */ DEC_CSR_WRITE (CSR5, 0xffffffff); /* setup CSR6 - start transmitter */ DEC_CSR_WRITE (CSR6, csr6Val | CSR6_ST); DRV_LOG (DRV_DEBUG_LOAD, "Writing CSR6 = %#08x\nCSR7 = %#08x\n", csr6Val | CSR6_ST, DEC_CSR_READ (CSR7), 0,0,0,0); taskDelay (sysClkRateGet() * 2); /* Check status of link */ tries++; /* Increment the number of attempts to find media */ if ((csr6Val & CSR6_21140_PS) && (csr6Val & CSR6_21140_PCS)) { /* 100 Mbps non-MII mode */ if (DEC_CSR_READ (CSR12) & CSR12_21143_LS100) { /* LS100 indicates link state down */ if (tries < pDrvCtrl->mediaCount) { DRV_LOG (DRV_DEBUG_LOAD, "100Mbps link failed - restarting\n", 0,0,0,0,0,0); goto restart; } else { DRV_LOG (DRV_DEBUG_LOAD, "100Mbps link failed - aborting\n", 0,0,0,0,0,0); return ERROR; } } } else if ((csr6Val & CSR6_21140_PS) == 0) { /* 10 Mbps mode */ if (DEC_CSR_READ (CSR12) & (CSR12_21143_LS10 | CSR12_21040_LKF)) { /* Link down */ if (tries < pDrvCtrl->mediaCount) { DRV_LOG (DRV_DEBUG_LOAD, "10Mbps link failed - restarting\n", 0,0,0,0,0,0);
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -