static int bfin_EMAC_init(struct eth_device *dev, bd_t *bd) { u32 opmode; int dat; int i; debug("Eth_init: ......\n"); txIdx = 0; rxIdx = 0; /* Initialize System Register */ if (bfin_miiphy_init(dev, &dat) < 0) return -1; /* Initialize EMAC address */ bfin_EMAC_setup_addr(dev); /* Initialize TX and RX buffer */ for (i = 0; i < PKTBUFSRX; i++) { rxbuf[i] = SetupRxBuffer(i); if (i > 0) { rxbuf[i - 1]->Dma[1].NEXT_DESC_PTR = rxbuf[i]->Dma; if (i == (PKTBUFSRX - 1)) rxbuf[i]->Dma[1].NEXT_DESC_PTR = rxbuf[0]->Dma; } } for (i = 0; i < TX_BUF_CNT; i++) { txbuf[i] = SetupTxBuffer(i); if (i > 0) { txbuf[i - 1]->Dma[1].NEXT_DESC_PTR = txbuf[i]->Dma; if (i == (TX_BUF_CNT - 1)) txbuf[i]->Dma[1].NEXT_DESC_PTR = txbuf[0]->Dma; } } /* Set RX DMA */ bfin_write_DMA1_NEXT_DESC_PTR(rxbuf[0]->Dma); bfin_write_DMA1_CONFIG(rxbuf[0]->Dma[0].CONFIG_DATA); /* Wait MII done */ bfin_miiphy_wait(); /* We enable only RX here */ /* ASTP : Enable Automatic Pad Stripping PR : Promiscuous Mode for test PSF : Receive frames with total length less than 64 bytes. FDMODE : Full Duplex Mode LB : Internal Loopback for test RE : Receiver Enable */ if (dat == FDMODE) opmode = ASTP | FDMODE | PSF; else opmode = ASTP | PSF; opmode |= RE; #ifdef CONFIG_RMII opmode |= TE | RMII; #endif /* Turn on the EMAC */ bfin_write_EMAC_OPMODE(opmode); return 0; }
int LanTest() { int iResult = 1; //unsigned long ulEndTime; unsigned int nTimer; ADI_ETHER_BUFFER *txbuf = NULL; ADI_ETHER_BUFFER *txfst = NULL; ADI_ETHER_BUFFER *txlst = NULL; ADI_ETHER_BUFFER *rxfst = NULL; ADI_ETHER_BUFFER *rxbuf = NULL; ADI_ETHER_BUFFER *rxlst = NULL; int ib; int irxh; int itxh; int RxCounter = 0; u32 txstatus; u32 rxstatus; // first, we setup various non-EMAC stuff SetupSystemRegs(); // next, we set up a MAC ADDRESS SetupMacAddr(g_SrcAddr); // initialize the TX DMA channel registers *pDMA2_X_COUNT = 0; *pDMA2_X_MODIFY = 4; // initialize the RX DMA channel registers *pDMA1_X_COUNT = 0; *pDMA1_X_MODIFY = 4; // set up a transmit frames and form a chain of them txlst = NULL; txfst = NULL; for( ib = 0; ib < NO_TX_BUFS; ib++ ) { txbuf = SetupTxBuffer(TXFRM_SIZE,ib); if( NULL == txbuf ) { // memory allocation failed return 0; } if (txfst==NULL) txfst = txbuf; if (txlst != NULL) { txlst->pNext = txbuf; // chain this buffer on txlst->Dma[1].NEXT_DESC_PTR = &txbuf->Dma[0]; // chain the descriptors txlst->Dma[1].CONFIG.b_NDSIZE = 5; // five elements txlst->Dma[1].CONFIG.b_FLOW = 7; // large descriptors } txlst = txbuf; } // loop the transmit chain txlst->Dma[1].NEXT_DESC_PTR = &txfst->Dma[0]; txlst->Dma[1].CONFIG.b_NDSIZE = 5; // five elements txlst->Dma[1].CONFIG.b_FLOW = 7; // large descriptors txlst->pNext = txfst; // set up a receive frames and form a chain of them rxlst = NULL; rxfst = NULL; for (ib=0;ib<NO_RX_BUFS;ib++) { rxbuf = SetupRxBuffer(); if( NULL == rxbuf ) { // memory allocation failed return 0; } if (rxfst==NULL) rxfst = rxbuf; if (rxlst != NULL) { rxlst->pNext = rxbuf; // chain this buffer on rxlst->Dma[1].NEXT_DESC_PTR = &rxbuf->Dma[0]; // chain the descriptors rxlst->Dma[1].CONFIG.b_NDSIZE = 5; // five elements rxlst->Dma[1].CONFIG.b_FLOW = 7; // large descriptors } rxlst = rxbuf; } // loop the receive chain rxlst->Dma[1].NEXT_DESC_PTR = &rxfst->Dma[0]; rxlst->Dma[1].CONFIG.b_NDSIZE = 5; // five elements rxlst->Dma[1].CONFIG.b_FLOW = 7; // large descriptors rxlst->pNext = rxfst; // start the TX DMA channel before enabling the MAC txbuf = txfst; if (txfst != NULL) { *pDMA2_NEXT_DESC_PTR = &txfst->Dma[0]; *pDMA2_CONFIG = *((u16*)&txfst->Dma[0].CONFIG); } // start the RX DMA channel before enabling the MAC rxbuf = rxfst; if (rxfst != NULL) { *pDMA1_NEXT_DESC_PTR = &rxfst->Dma[0]; *pDMA1_CONFIG = *((u16*)&rxfst->Dma[0].CONFIG); } // reset counters, allow rollover, enable counters *pEMAC_MMC_CTL = RSTC | CROLL | MMCE; // finally enable sending/receiving at the mac PollMdcDone(); // enable RX, TX, and full duplex *pEMAC_OPMODE = (TE | RE | FDMODE); // now poll for completion on the tx and rx buffers txbuf = txfst; itxh = 0; rxbuf = rxfst; irxh = 0; // ulEndTime = (GetTickCount() + 0x200000); nTimer = SetTimeout(0x200000); while ( ((rxbuf!=NULL) || (txbuf!=NULL)) ) { if( IsTimedout(nTimer) ) { iResult = 0; break; } else { if ((txbuf != NULL) && ((txbuf->StatusWord & TX_COMP) !=0)) { // enable the transmit DMA for the sending the next packets PollMdcDone(); if( NO_TX_BUFS > 0 ) { *pEMAC_OPMODE &= (~TE); } // frame marked as transmitted txstatus = txbuf->StatusWord; // save the status txbuf->StatusWord = 0; if(TX_OK != (txstatus & TX_OK) ) { iResult = 0; break; } txbuf = txbuf->pNext; // store current status in history list if (++itxh >= NO_TX_BUFS) { itxh = 0; } // enable the transmit DMA for the sending the next packets // start the TX DMA channel before enabling the MAC txbuf = txfst; if (txfst != NULL) { *pDMA2_NEXT_DESC_PTR = &txfst->Dma[0]; *pDMA2_CONFIG = *((u16*)&txfst->Dma[0].CONFIG); } PollMdcDone(); if( NO_TX_BUFS > 0 ) { *pEMAC_OPMODE |= TE; } } if ((rxbuf != NULL) && ((rxbuf->StatusWord & RX_COMP) !=0)) { // frame marked as received rxstatus = rxbuf->StatusWord; // save the status rxbuf->StatusWord = 0; if( rxstatus & RX_OK ) { // recvved OK memcpy(g_rx_src_addr,rxbuf->Data->Srce,6); RxCounter++; if ((RxCounter % 1000000) == 0x0) { iResult = 1; break; } memset(g_rx_src_addr,0x0,6); } else { iResult = 0; break; } rxbuf = rxbuf->pNext; if (++irxh >= NO_RX_BUFS) { irxh = 0; } } }// end else(tickcount) } ClearTimeout(nTimer); *pEMAC_OPMODE = 0; if( iResult ) { // this will verify that the correct PHY address is being used if( 0xFFFF == RdPHYReg(BR_BUB_PHYADD, 31) ) { iResult = 0; } } // delete the tx & rx buffers { ADI_ETHER_BUFFER *pHead; ADI_ETHER_BUFFER *pTemp = txfst; do{ pHead = pTemp; pTemp = pHead->pNext; pHead->pNext = NULL; memset(pHead, 0x00, sizeof(ADI_ETHER_BUFFER) ); free(pHead); }while( NULL != pTemp->pNext ); pTemp = rxfst; do{ pHead = pTemp; pTemp = pHead->pNext; pHead->pNext = NULL; memset(pHead, 0x00, sizeof(ADI_ETHER_BUFFER) ); free(pHead); }while( NULL != pTemp->pNext ); } return iResult; }