//------------------------------------------------------------------------------------------------- // Close the interface //------------------------------------------------------------------------------------------------- void MDrv_EMAC_close(struct eth_device *nic) { u32 uRegVal; //Disable Receiver and Transmitter // uRegVal = MHal_EMAC_Read_CTL(); //uRegVal &= ~(EMAC_TE | EMAC_RE); MHal_EMAC_Write_CTL(uRegVal); // Disable PHY interrupt // MHal_EMAC_disable_phyirq (); //Disable MAC interrupts // uRegVal = EMAC_INT_RCOM | EMAC_INT_RBNA | EMAC_INT_TUND | EMAC_INT_RTRY | EMAC_INT_TCOM | EMAC_INT_ROVR | EMAC_INT_HRESP; MHal_EMAC_Write_IDR(uRegVal); netif_stop_queue (nic); }
//------------------------------------------------------------------------------------------------- //Initialize and start the Receiver and Transmit subsystems //------------------------------------------------------------------------------------------------- static void MDrv_EMAC_start (const struct eth_device *nic) { struct emac_hw *hw = (struct emac_hw *) nic->priv; u32 uRegVal; #ifdef SOFTWARE_DESCRIPTOR u32 i; #endif // Initialize Receive Buffer Descriptors memset((u8*)(RBQP_BASE+RAM_ADDR_BASE),0x00,RBQP_SIZE); #ifdef SOFTWARE_DESCRIPTOR for(i=0; i<RBQP_LENG;i++) { if(i<(RBQP_LENG-1)) MHal_EMAC_WritRam32((RBQP_BASE+RAM_ADDR_BASE), i*16, (RX_BUFFER_BASE+0x600*i)); else MHal_EMAC_WritRam32((RBQP_BASE+RAM_ADDR_BASE), i*16, (RX_BUFFER_BASE+0x600*i+EMAC_DESC_WRAP)); } #else MHal_EMAC_WritRam32((RBQP_BASE+RAM_ADDR_BASE),(RBQP_SIZE-0x08),0x00000002); #endif Chip_Flush_Memory(); // set offset of read and write pointers in the receive circular buffer // uRegVal = MHal_EMAC_Read_BUFF(); uRegVal = (RX_BUFFER_BASE|RX_BUFFER_SEL); MHal_EMAC_Write_BUFF(uRegVal); MHal_EMAC_Write_RDPTR(0); MHal_EMAC_Write_WRPTR(0); // Program address of descriptor list in Rx Buffer Queue register // MHal_EMAC_Write_RBQP(RBQP_BASE); //Reset buffer index// hw->rxBuffIndex = 0; // Enable Receive and Transmit // uRegVal = MHal_EMAC_Read_CTL(); uRegVal |= (EMAC_RE | EMAC_TE); MHal_EMAC_Write_CTL(uRegVal); }
//------------------------------------------------------------------------------------------------- // Open the ethernet interface //------------------------------------------------------------------------------------------------- static int MDrv_EMAC_open (struct eth_device *nic, bd_t * bis) { // struct emac_hw *hw = (struct emac_hw *) nic->priv; u32 uRegVal; //ato EMAC_SYS->PMC_PCER = 1 << EMAC_ID_EMAC; //Re-enable Peripheral clock // uRegVal = MHal_EMAC_Read_CTL(); uRegVal |= EMAC_CSR; MHal_EMAC_Write_CTL(uRegVal); // Enable PHY interrupt // MHal_EMAC_enable_phyirq (); // Enable MAC interrupts // uRegVal = EMAC_INT_RCOM |EMAC_INT_RBNA | EMAC_INT_TUND | EMAC_INT_RTRY | EMAC_INT_TCOM | EMAC_INT_ROVR | EMAC_INT_HRESP; MHal_EMAC_Write_IER(uRegVal); MDrv_EMAC_start (nic); return 0; }
//------------------------------------------------------------------------------------------------- // EMAC Negotiation PHY //------------------------------------------------------------------------------------------------- u32 MHal_EMAC_NegotiationPHY(void) { // Set PHY -------------------------------------------------------------- u32 i; u32 word_PHY = 0x00000000; u32 retValue = 0; // IMPORTANT: Get real duplex by negotiation with peer. u32 word_ETH_CTL = MHal_EMAC_Read_CTL(); MHal_EMAC_Write_CTL(0x0000001C | word_ETH_CTL); MHalThisUVE.cntChkINTCounter=0; word_PHY = 0x50822100; MHal_EMAC_Write_MAN(word_PHY); while(MHal_EMAC_CheckINTDone()!=1); MHalThisUVE.flagISR_INT_DONE = 0x00; MHalThisUVE.cntChkINTCounter=0; word_PHY = 0x509201E1; MHal_EMAC_Write_MAN(word_PHY); while(MHal_EMAC_CheckINTDone()!=1); MHalThisUVE.flagISR_INT_DONE = 0x00; MHalThisUVE.cntChkINTCounter=0; word_PHY = 0x50821200; MHal_EMAC_Write_MAN(word_PHY); while(MHal_EMAC_CheckINTDone()!=1); MHalThisUVE.flagISR_INT_DONE = 0x00; MHalThisUVE.cntChkINTCounter=0; // IMPORTANT: (20070906) There must be some delay (about 2 ~ 3 seconds) between writing 0x57821200 and 0x67FE0000. // Otherwise, the later EMAC_WritReg32(REG_ETH_MAN,word_PHY) has no effect. MHalThisBCE.duplex = 1; // Set default as Half-duplex if negotiation fails. retValue = 1; MHal_EMAC_CableConnection(); word_PHY = 0x60FE0000; // Read for 32th reg MHal_EMAC_Write_MAN(word_PHY); MHalThisUVE.cntChkINTCounter=0; while(MHal_EMAC_CheckINTDone()!=1); MHalThisUVE.flagISR_INT_DONE = 0x00; MHalThisUVE.cntChkINTCounter=0; MHalThisUVE.cntChkCableConnect = 0; for(i=0;i<100;i++) // (20071026_CHARLES) No check connection here, if no connect, also init here. { word_PHY = MHal_EMAC_Read_MAN(); word_PHY &= 0x0000FFFF; if(word_PHY & 0x00001000) { u32 test1 = (word_PHY & 0x0000001C) >> 2; if(test1 == 0x001 || test1 == 0x002) { MHalThisBCE.duplex = 1; retValue = 1; } else { MHalThisBCE.duplex = 2; retValue = 2; } // else //retValue = 1; break; } // if mdelay(1); MHalThisUVE.cntChkCableConnect++; if(MHalThisUVE.cntChkCableConnect==MAX_INT_COUNTER) break; } // for