?? lan91c96.c
字號:
data = ReadWord(&ioRegsP[LAN91C96_DATA_HIGH]); // Save the data. *dataP++ = data; } // Now check the status word for an odd byte in the data packet. if (statusWord & LAN91C96_ODD_FRM) { // Now read the Control word to get the last data byte. controlWord = ReadWord(&ioRegsP[LAN91C96_DATA_HIGH]); // Store the last byte. *dataP = (UCHAR)controlWord; // Update the receive count. count += 1; } // Now deallocate the page. DeallocateRxPacket(ctxP); // Check for errors. if (statusWord & LAN91C96_TOO_SHORT) { /*LOGERROR(ctxP->loggedError, ERR_L_LAN91C96, ERR_LAN91C96_RECEIVE, ERR_T_WRONG_STATE, statusWord, 0, 0);*/ //printf("LAN91C96: rx error frame too short\n"); } if (statusWord & LAN91C96_TOO_LONG) { //printf("LAN91C96: rx error frame too long\n"); } if (statusWord & LAN91C96_BAD_CRC) { //printf("LAN91C96: rx error bad CRC\n"); } if (statusWord & LAN91C96_ALGN_ERR) { //printf("LAN91C96: rx error, alignment error\n"); } // Check dump flag. if (ctxP->dumpFlag) { if (statusWord & LAN91C96_BROD_CAST) { //printf("LAN91C96: rx broadcast\n"); } } // Check dump flag. if (ctxP->dumpFlag) { // Display received frame. /*DM_Printf("Receive Packet:");*/ LAN91C96DumpFrame(ctxP, 0, (PUCHAR)bufferP, count - CRC_LEN); } // Return the receive count. *rxCountP = count - CRC_LEN; } // Get delta time reference. GetDeltaTimeStamp(ctxP, "Rx"); return (0);}/********************************************************************************** FUNCTION:* LAN91C96HWSetup** DESCRIPTION:* Initialize the LAN91C96 and set the MAC address.** INPUT PARAMETERS:* LAN91C96_ContextT *ctxP - Pointer to the LAN91C96 Device Context Structure* BOOL resetFlag - Reset the LAN91C96 even if previously setup.** RETURNS:* 0 - Success* non-zero - Error** GLOBAL EFFECTS:* Sets up the initial state of the LAN91C96 Ethernet controller.** ASSUMPTIONS:* None.** CALLS:* WriteByte - To write a byte to either the attribute or I/O space.* WriteWord - To write a word to either the attribute or I/O space.* ReadByte - Read a byte from either the attribute or I/O space.* ReadWord - Read a word from either the attribute or I/O space.* WriteEEPROM - Write the word into the specified location within the EEPROM.* ReadEEPROM - Read the work from the specified location within the EEPROM.** CALLED BY:* Application or test code.** PROTOTYPE:* UINT LAN91C96HWSetup(LAN91C96_ContextT *ctxP, BOOL resetFlag);*********************************************************************************/UINT LAN91C96HWSetup(LAN91C96_ContextT *ctxP, BOOL resetFlag){ PVUINT32 ioRegsP = ctxP->LAN91C96IoP; // Get pointer to I/O space PVUINT32 attRegsP = ctxP->LAN91C96AttP; // Get pointer to attribute space volatile UINT32 lanReg; // Copy of LAN91C96 register volatile UINT16 MACAddress[3]; // Used to check the MAC address volatile UINT16 CfgReg; // Contents of Config Register UINT16 frameHandle = 0; // Page number of allocated frame volatile UINT32 randomNumber, i; char tempChar ; // Check if we should override the default and do a hard reset. if (resetFlag) { // Clear the setup flag and do a hard reset. ctxP->setupFlag = FALSE; } // Check if we've already reset the LAN91C96 if (ctxP->setupFlag) { // Already setup, just return. return (0); } // When an EEPROM acess is in progress the STORE and RELOAD bits will be // read back as high. The remaining 14 bits of this register will be // invalid. During this time, attempted read/write operations, other than // polling the EEPROM status, will NOT have any effect on the internal // registers. The CPU can resume accessess to the LAN91C96 after both bits // are low. A worst case RELOAD operation initiated by RESET or by software // takes less than 750 us in either mode. // // SRESET: This bit when set will clear all internal registers // associated with the Ethernet function except itself and it will also // lower the nIREQ/READY pin. When this bit is cleared, nIREQ/READY pin // will be raised. // // Enable Function: This bit enables (1) or disables (0) the Ethernet // function. While the Ethernet function is disabled it remains in power // down mode, no access to the Ethernet I/O space (i.e. The bank register // are not accessible) is allowed. IREQ is not generated for this function // and INPACK* is not returned for accessess to the Ethernet registers. // // Note: Magic packet bit setting is ignored if the function is disabled. // Access the attribute space to set the SRESET bit to reset the LAN91C96 lanReg = ReadByte(&attRegsP[LAN91C96_ECOR]); lanReg |= LAN91C96_ECOR_SRESET; WriteByte(lanReg, &attRegsP[LAN91C96_ECOR]); hal_delay_us(750) ; // Access the attribute space to enable the LAN91C96. // First clear the SRESET bit. lanReg = ReadByte(&attRegsP[LAN91C96_ECOR]); lanReg &= ~LAN91C96_ECOR_SRESET; WriteByte(lanReg, &attRegsP[LAN91C96_ECOR]); hal_delay_us(750); // Now set the Enable Function bit. lanReg = ReadByte(&attRegsP[LAN91C96_ECOR]); lanReg |= LAN91C96_ECOR_ENABLE; WriteByte(lanReg, &attRegsP[LAN91C96_ECOR]); hal_delay_us(750); // Force byte mode (not required) lanReg = ReadByte(&attRegsP[LAN91C96_ECSR]); lanReg |= LAN91C96_ECSR_IOIS8; WriteByte(lanReg, &attRegsP[LAN91C96_ECSR]); hal_delay_us(750) ; lanReg = ReadWord(&ioRegsP[LAN91C96_BANK_SELECT]) ; if((lanReg & 0xFF00) != 0x3300) { printf("LAN91C96: Unable to detect device - upper 8 bits = %x\n", lanReg); return (-1); } // Read the MAC address from the 91C96. This gets read from the EEPROM // by the 91C96 during reset. This assumes Bank 1 is selected. /* Need to copy the MAC address into the ioRegs space in a different order than which it is stored in EEPROM. It is stored in EEPROM with the most significant octet in the highest memory location octet and down from there. So what I need to so is read EEPROM_MAC_OFSSET_3 amd store the uooer 8 bits in the first 8 bits of &ioRegs[LAN91C96_IA0], and ...*/ WriteByte(BANK1, &ioRegsP[LAN91C96_BANK_SELECT]);/* MACAddress[0] = ReadWord(&ioRegsP[LAN91C96_IA0]); MACAddress[1] = ReadWord(&ioRegsP[LAN91C96_IA2]); MACAddress[2] = ReadWord(&ioRegsP[LAN91C96_IA4]);*/ /* MACAddress[0] = ReadEEPROM(ctxP, EEPROM_MAC_OFFSET_1); MACAddress[1] = ReadEEPROM(ctxP, EEPROM_MAC_OFFSET_2); MACAddress[2] = ReadEEPROM(ctxP, EEPROM_MAC_OFFSET_3); */ MACAddress[0] = ReadWord(&ioRegsP[LAN91C96_IA0]); MACAddress[1] = ReadWord(&ioRegsP[LAN91C96_IA2]); MACAddress[2] = ReadWord(&ioRegsP[LAN91C96_IA4]); // Convert the MAC address to ASCII so it prints out consistently printf("LAN91C96: The current MAC address is ") ; for(i=0;i<3;i++) { tempChar = (char)(0x30 + (MACAddress[i]>>4 & 0x000F)) ; if((short)tempChar>0x39) { (short)tempChar = (short)tempChar + 7 ; } printf("%c", tempChar) ; tempChar = (char)(0x30 + (MACAddress[i]>>0 & 0x000F)) ; if((short)tempChar>0x39) { (short)tempChar = (short)tempChar + 7 ; } printf("%c", tempChar) ; printf("%c", ' ') ; tempChar = (char)(0x30 + (MACAddress[i]>>12 & 0x000F)) ; if((short)tempChar>0x39) { (short)tempChar = (short)tempChar + 7 ; } printf("%c", tempChar) ; tempChar = (char)(0x30 + (MACAddress[i]>>8 & 0x000F)) ; if((short)tempChar>0x39) { (short)tempChar = (short)tempChar + 7 ; } printf("%c", tempChar) ; printf("%c", ' ') ; } printf("\n") ; // copy the MAC address to the configuration structure ctxP->MACAddress[0] = MACAddress[0] ; ctxP->MACAddress[1] = MACAddress[1] ; ctxP->MACAddress[2] = MACAddress[2] ; // Read the Configuration Register. This assumes Bank 1 is selected. ctxP->configRegister = ReadWord(&ioRegsP[LAN91C96_CONFIG]); // Read the Base Address Register. // Access the I/O space to select Bank 3 and read the IOS bits. WriteByte(BANK3, &ioRegsP[LAN91C96_BANK_SELECT]); ctxP->switches = ReadWord(&ioRegsP[LAN91C96_MGMT]); // Read the LAN91C96 revision. This assumes Bank 3 is selected. ctxP->revision = ReadWord(&ioRegsP[LAN91C96_REVISION]); // Give the LAN91C96 time to settle down. hal_delay_us(750) ; // Set the SQUELCH bit - this changes the threshold for a valid signal // from 300mV to 180mV. This is to attempt to fix problems we have seen // with some (usually 8 port) hubs. // Select Bank 1 WriteByte(BANK1, &ioRegsP[LAN91C96_BANK_SELECT]); // Set the squelch and no wait bits. CfgReg = ReadWord(&ioRegsP[LAN91C96_CONFIG]); CfgReg |= (LAN91C96_CR_SET_SQLCH | LAN91C96_CR_NO_WAIT); CfgReg &= ~(LAN91C96_CR_AUI_SELECT | LAN91C96_CR_INT_SEL0 | LAN91C96_CR_DIS_LINK); WriteWord(CfgReg, &ioRegsP[LAN91C96_CONFIG]); // Initialize the Control Register - set Transmit Enable and Auto Release. // Bit 8 is always set? This assumes Bank 1 is selected. WriteWord((LAN91C96_CTR_TE_ENABLE | LAN91C96_CTR_BIT_8 | LAN91C96_CTR_AUTO_RELEASE), &ioRegsP[LAN91C96_CONTROL]); // Select Bank 0 WriteByte(BANK0, &ioRegsP[LAN91C96_BANK_SELECT]); // Initialize the Memory Configuration Register. See page 49 of the // LAN91C96 data sheet for details. We reserve enough memory for one // maximum sized transmit frame. This will prevent deadlock conditions // if we receive multiple frames that can't be handled because of the // lack of memory. The amount of memory reserved for transmit is calculated // as LAN91C96_MCR_TRANSMIT_PAGES * 256 * M, where M is 1 for the 91C96. // For a 1500 byte frame, we'll need 1500 / 256 = 6 memory pages. WriteWord(LAN91C96_MCR_TRANSMIT_PAGES, &ioRegsP[LAN91C96_MCR]); // Initialize the Transmit Control Register - Set the Transmit enable and // Pad bit, which will pad transmit packets less than 64 bytes with zeroes. // This assumes Bank 0 is selected. WriteWord((LAN91C96_TCR_TXENA | LAN91C96_TCR_PAD_EN), &ioRegsP[LAN91C96_TCR]); // Select Bank 2 WriteByte(BANK2, &ioRegsP[LAN91C96_BANK_SELECT]); // Disable all interrupts. WriteByte(0, &ioRegsP[LAN91C96_INT_MASK]); // Select Bank 0 WriteByte(BANK0, &ioRegsP[LAN91C96_BANK_SELECT]); // The receive register should be the last thing initialized to avoid // receiving packets before we're ready. Now set the Receive Enable bit. WriteWord((LAN91C96_RCR_RXEN | LAN91C96_RCR_ALMUL | LAN91C96_RCR_PRMS), &ioRegsP[LAN91C96_RCR]); // Select Bank 2 WriteByte(BANK2, &ioRegsP[LAN91C96_BANK_SELECT]); // Now perform a quick test to determine if the LAN91C96 is working. // Allocate a transmit frame from the LAN91C96. if (AllocateTxPacket(ctxP, ETHERNET_MAX_LENGTH, &frameHandle)) { printf("In LAN91C96HWSetup - AllocateTxPacket failed\n") ; return (ctxP->loggedError); } // Now deallocate the page. if (DeallocateTxPacket(ctxP)) { printf("In LAN91C96HWSetup - DeallocateTxPacket failed\n") ; return (ctxP->loggedError); } // Set setup flag. ctxP->setupFlag = TRUE; LAN91C96LoopBack(ctxP, 0) ; // Let the LAN91C96 settle before attempting the first transmit. hal_delay_us(LAN91C96_TIME_DELAY) ; return (0);}/********************************************************************************** FUNCTION:* LAN91C96HWShutdown** DESCRIPTION:* This routine disables the LAN91C96 and turns it off.** INPUT PARAMETERS:* LAN91C96_ContextT *ctxP - Pointer to the LAN91C96 Device Context Structure** RETURNS:* None.** GLOBAL EFFECTS:* Disables the LAN91C96 from transmitting or receiving packets from the* Ethernet.** ASSUMPTIONS:* None.** CALLS:* None.** CALLED BY:* None.** PROTOTYPE:* VOID LAN91C96HWShutdown(LAN91C96_ContextT *ctxP);*********************************************************************************/VOID LAN91C96HWShutdown(LAN91C96_ContextT *ctxP){ PVUINT32 attRegsP = ctxP->LAN91C96AttP; // Get pointer to attribute space UINT16 lanReg; // Copy of LAN91C96 register // SRESET: This bit when set will clear all internal registers // associated with the Ethernet function except itself and it will also // lower the nIREQ/READY pin. When this bit is cleared, nIREQ/READY pin // will be raised. // Access the attribute space to set the SRESET bit to reset the LAN91C96. lanReg = ReadByte(&attRegsP[LAN91C96_ECOR]); lanReg |= LAN91C96_ECOR_SRESET; WriteByte(lanReg, &attRegsP[LAN91C96_ECOR]); hal_delay_us(750) ;//DM_WaitUs(750); // Save the default interrupt mask. ctxP->intMask = LAN91C96_MSK_RCV_INT; // Clear setup flag. ctxP->setupFlag = FALSE; // Zero the MAC address. memset(&ctxP->MACAddress[0], 0, sizeof(ctxP->MACAddress)); // Clear ramdom MAC flag. ctxP->randomMACFlag = 0;}/********************************************************************************** FUNCTION:* LAN91C96SetMACAddress** DESCRIPTION:* This routine will set the specified MAC address.** INPUT PARAMETERS:* LAN91C96_ContextT *ctxP - Pointer to the LAN91C96 Device Context Structure* PUCHAR MACP - Pointer to the MAC address.* UINT randomFlag = 0 = MAC address supplied, 1 = generate a MAC address.** RETURNS:* 0 - Success* non-zero - Error** GLOBAL EFFECTS:* The LAN91C96 MAC address is changed.
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -