1 /** @file 2 * SMSC LAN91x series Network Controller Driver. 3 * 4 * Copyright (c) 2013 Linaro.org 5 * 6 * Derived from the LAN9118 driver. Original sources 7 * Copyright (c) 2012-2013, ARM Limited. All rights reserved. 8 * 9 * This program and the accompanying materials are licensed and 10 * made available under the terms and conditions of the BSD License 11 * which accompanies this distribution. The full text of the license 12 * may be found at: http://opensource.org/licenses/bsd-license.php 13 * 14 * THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 15 * WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 16 * 17 **/ 18 19 #include <Uefi.h> 20 #include <Uefi/UefiSpec.h> 21 #include <Base.h> 22 23 // Protocols used by this driver 24 #include <Protocol/SimpleNetwork.h> 25 #include <Protocol/ComponentName2.h> 26 #include <Protocol/PxeBaseCode.h> 27 #include <Protocol/DevicePath.h> 28 29 // Libraries used by this driver 30 #include <Library/UefiLib.h> 31 #include <Library/DebugLib.h> 32 #include <Library/UefiBootServicesTableLib.h> 33 #include <Library/MemoryAllocationLib.h> 34 #include <Library/IoLib.h> 35 #include <Library/PcdLib.h> 36 #include <Library/NetLib.h> 37 #include <Library/DevicePathLib.h> 38 39 // Hardware register definitions 40 #include "Lan91xDxeHw.h" 41 42 // Debugging output options 43 //#define LAN91X_PRINT_REGISTERS 1 44 //#define LAN91X_PRINT_PACKET_HEADERS 1 45 //#define LAN91X_PRINT_RECEIVE_FILTERS 1 46 47 // Chip power-down option -- UNTESTED 48 //#define LAN91X_POWER_DOWN 1 49 50 /*--------------------------------------------------------------------------------------------------------------------- 51 52 LAN91x Information Structure 53 54 ---------------------------------------------------------------------------------------------------------------------*/ 55 typedef struct _LAN91X_DRIVER { 56 // Driver signature 57 UINT32 Signature; 58 EFI_HANDLE ControllerHandle; 59 60 // EFI SNP protocol instances 61 EFI_SIMPLE_NETWORK_PROTOCOL Snp; 62 EFI_SIMPLE_NETWORK_MODE SnpMode; 63 64 // EFI Snp statistics instance 65 EFI_NETWORK_STATISTICS Stats; 66 67 // Transmit Buffer recycle queue 68 #define TX_QUEUE_DEPTH 16 69 VOID *TxQueue[TX_QUEUE_DEPTH]; 70 UINTN TxQueHead; 71 UINTN TxQueTail; 72 73 // Register access variables 74 UINTN IoBase; // I/O Base Address 75 UINT8 Revision; // Chip Revision Number 76 INT8 PhyAd; // Phy Address 77 UINT8 BankSel; // Currently selected register bank 78 79 } LAN91X_DRIVER; 80 81 #define LAN91X_NO_PHY (-1) // PhyAd value if PHY not detected 82 83 #define LAN91X_SIGNATURE SIGNATURE_32('S', 'M', '9', '1') 84 #define INSTANCE_FROM_SNP_THIS(a) CR(a, LAN91X_DRIVER, Snp, LAN91X_SIGNATURE) 85 86 #define LAN91X_STALL 2 87 #define LAN91X_MEMORY_ALLOC_POLLS 100 // Max times to poll for memory allocation 88 #define LAN91X_PKT_OVERHEAD 6 // Overhead bytes in packet buffer 89 90 // Synchronization TPLs 91 #define LAN91X_TPL TPL_CALLBACK 92 93 // Most common CRC32 Polynomial for little endian machines 94 #define CRC_POLYNOMIAL 0xEDB88320 95 96 97 typedef struct { 98 MAC_ADDR_DEVICE_PATH Lan91x; 99 EFI_DEVICE_PATH_PROTOCOL End; 100 } LAN91X_DEVICE_PATH; 101 102 LAN91X_DEVICE_PATH Lan91xPathTemplate = { 103 { 104 { 105 MESSAGING_DEVICE_PATH, MSG_MAC_ADDR_DP, 106 { (UINT8) (sizeof(MAC_ADDR_DEVICE_PATH)), (UINT8) ((sizeof(MAC_ADDR_DEVICE_PATH)) >> 8) } 107 }, 108 { { 0 } }, 109 0 110 }, 111 { 112 END_DEVICE_PATH_TYPE, 113 END_ENTIRE_DEVICE_PATH_SUBTYPE, 114 { sizeof(EFI_DEVICE_PATH_PROTOCOL), 0 } 115 } 116 }; 117 118 // Chip ID numbers and name strings 119 #define CHIP_9192 3 120 #define CHIP_9194 4 121 #define CHIP_9195 5 122 #define CHIP_9196 6 123 #define CHIP_91100 7 124 #define CHIP_91100FD 8 125 #define CHIP_91111FD 9 126 127 STATIC CHAR16 CONST * CONST ChipIds[ 16 ] = { 128 NULL, NULL, NULL, 129 /* 3 */ L"SMC91C90/91C92", 130 /* 4 */ L"SMC91C94", 131 /* 5 */ L"SMC91C95", 132 /* 6 */ L"SMC91C96", 133 /* 7 */ L"SMC91C100", 134 /* 8 */ L"SMC91C100FD", 135 /* 9 */ L"SMC91C11xFD", 136 NULL, NULL, NULL, 137 NULL, NULL, NULL 138 }; 139 140 141 /* ------------------ TxBuffer Queue functions ------------------- */ 142 143 #define TxQueNext(off) ((((off) + 1) >= TX_QUEUE_DEPTH) ? 0 : ((off) + 1)) 144 145 STATIC 146 BOOLEAN 147 TxQueInsert ( 148 IN LAN91X_DRIVER *LanDriver, 149 IN VOID *Buffer 150 ) 151 { 152 153 if (TxQueNext (LanDriver->TxQueTail) == LanDriver->TxQueHead) { 154 return FALSE; 155 } 156 157 LanDriver->TxQueue[LanDriver->TxQueTail] = Buffer; 158 LanDriver->TxQueTail = TxQueNext (LanDriver->TxQueTail); 159 160 return TRUE; 161 } 162 163 STATIC 164 VOID 165 *TxQueRemove ( 166 IN LAN91X_DRIVER *LanDriver 167 ) 168 { 169 VOID *Buffer; 170 171 if (LanDriver->TxQueTail == LanDriver->TxQueHead) { 172 return NULL; 173 } 174 175 Buffer = LanDriver->TxQueue[LanDriver->TxQueHead]; 176 LanDriver->TxQueue[LanDriver->TxQueHead] = NULL; 177 LanDriver->TxQueHead = TxQueNext (LanDriver->TxQueHead); 178 179 return Buffer; 180 } 181 182 /* ------------------ MAC Address Hash Calculations ------------------- */ 183 184 /* 185 ** Generate a hash value from a multicast address 186 ** 187 ** This uses the Ethernet standard CRC32 algorithm 188 ** 189 ** INFO USED: 190 ** 1: http://en.wikipedia.org/wiki/Cyclic_redundancy_check 191 ** 192 ** 2: http://www.erg.abdn.ac.uk/~gorry/eg3567/dl-pages/crc.html 193 ** 194 ** 3: http://en.wikipedia.org/wiki/Computation_of_CRC 195 */ 196 STATIC 197 UINT32 198 MulticastHash ( 199 IN EFI_MAC_ADDRESS *Mac, 200 IN UINT32 AddrLen 201 ) 202 { 203 UINT32 Iter; 204 UINT32 Remainder; 205 UINT32 Crc32; 206 UINT8 *Addr; 207 208 // 0xFFFFFFFF is standard seed for Ethernet 209 Remainder = 0xFFFFFFFF; 210 211 // Generate the remainder byte-by-byte (LSB first) 212 Addr = &Mac->Addr[0]; 213 while (AddrLen-- > 0) { 214 Remainder ^= *Addr++; 215 for (Iter = 0; Iter < 8; ++Iter) { 216 // Check if exponent is set 217 if ((Remainder & 1) != 0) { 218 Remainder = (Remainder >> 1) ^ CRC_POLYNOMIAL; 219 } else { 220 Remainder = (Remainder >> 1) ^ 0; 221 } 222 } 223 } 224 225 // Reverse the bits of the remainder 226 Crc32 = 0; 227 for (Iter = 0; Iter < 32; ++Iter) { 228 Crc32 <<= 1; 229 Crc32 |= Remainder & 1; 230 Remainder >>= 1; 231 } 232 return Crc32; 233 } 234 235 236 /* ---------------- Banked Register Operations ------------------ */ 237 238 // Select the proper I/O bank 239 STATIC 240 VOID 241 SelectIoBank ( 242 LAN91X_DRIVER *LanDriver, 243 UINTN Register 244 ) 245 { 246 UINT8 Bank; 247 248 Bank = RegisterToBank (Register); 249 250 // Select the proper I/O bank 251 if (LanDriver->BankSel != Bank) { 252 MmioWrite16 (LanDriver->IoBase + LAN91X_BANK_OFFSET, Bank); 253 LanDriver->BankSel = Bank; 254 } 255 } 256 257 // Read a 16-bit I/O-space register 258 STATIC 259 UINT16 260 ReadIoReg16 ( 261 LAN91X_DRIVER *LanDriver, 262 UINTN Register 263 ) 264 { 265 UINT8 Offset; 266 267 // Select the proper I/O bank 268 SelectIoBank (LanDriver, Register); 269 270 // Read the requested register 271 Offset = RegisterToOffset (Register); 272 return MmioRead16 (LanDriver->IoBase + Offset); 273 } 274 275 // Write a 16-bit I/O-space register 276 STATIC 277 UINT16 278 WriteIoReg16 ( 279 LAN91X_DRIVER *LanDriver, 280 UINTN Register, 281 UINT16 Value 282 ) 283 { 284 UINT8 Offset; 285 286 // Select the proper I/O bank 287 SelectIoBank (LanDriver, Register); 288 289 // Write the requested register 290 Offset = RegisterToOffset (Register); 291 return MmioWrite16 (LanDriver->IoBase + Offset, Value); 292 } 293 294 // Read an 8-bit I/O-space register 295 STATIC 296 UINT8 297 ReadIoReg8 ( 298 LAN91X_DRIVER *LanDriver, 299 UINTN Register 300 ) 301 { 302 UINT8 Offset; 303 304 // Select the proper I/O bank 305 SelectIoBank (LanDriver, Register); 306 307 // Read the requested register 308 Offset = RegisterToOffset (Register); 309 return MmioRead8 (LanDriver->IoBase + Offset); 310 } 311 312 // Write an 8-bit I/O-space register 313 STATIC 314 UINT8 315 WriteIoReg8 ( 316 LAN91X_DRIVER *LanDriver, 317 UINTN Register, 318 UINT8 Value 319 ) 320 { 321 UINT8 Offset; 322 323 // Select the proper I/O bank 324 SelectIoBank (LanDriver, Register); 325 326 // Write the requested register 327 Offset = RegisterToOffset (Register); 328 return MmioWrite8 (LanDriver->IoBase + Offset, Value); 329 } 330 331 332 /* ---------------- MII/PHY Access Operations ------------------ */ 333 334 #define LAN91X_MDIO_STALL 1 335 336 STATIC 337 VOID 338 MdioOutput ( 339 LAN91X_DRIVER *LanDriver, 340 UINTN Bits, 341 UINT32 Value 342 ) 343 { 344 UINT16 MgmtReg; 345 UINT32 Mask; 346 347 MgmtReg = ReadIoReg16 (LanDriver, LAN91X_MGMT); 348 MgmtReg &= ~MGMT_MCLK; 349 MgmtReg |= MGMT_MDOE; 350 351 for (Mask = (1 << (Bits - 1)); Mask != 0; Mask >>= 1) { 352 if ((Value & Mask) != 0) { 353 MgmtReg |= MGMT_MDO; 354 } else { 355 MgmtReg &= ~MGMT_MDO; 356 } 357 358 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg); 359 gBS->Stall (LAN91X_MDIO_STALL); 360 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg | MGMT_MCLK); 361 gBS->Stall (LAN91X_MDIO_STALL); 362 } 363 } 364 #define PHY_OUTPUT_TIME (2 * LAN91X_MDIO_STALL) 365 366 STATIC 367 UINT32 368 MdioInput ( 369 LAN91X_DRIVER *LanDriver, 370 UINTN Bits 371 ) 372 { 373 UINT16 MgmtReg; 374 UINT32 Mask; 375 UINT32 Value; 376 377 MgmtReg = ReadIoReg16 (LanDriver, LAN91X_MGMT); 378 MgmtReg &= ~(MGMT_MDOE | MGMT_MCLK | MGMT_MDO); 379 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg); 380 381 Value = 0; 382 for (Mask = (1 << (Bits - 1)); Mask != 0; Mask >>= 1) { 383 if ((ReadIoReg16 (LanDriver, LAN91X_MGMT) & MGMT_MDI) != 0) { 384 Value |= Mask; 385 } 386 387 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg); 388 gBS->Stall (LAN91X_MDIO_STALL); 389 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg | MGMT_MCLK); 390 gBS->Stall (LAN91X_MDIO_STALL); 391 } 392 393 return Value; 394 } 395 #define PHY_INPUT_TIME (2 * LAN91X_MDIO_STALL) 396 397 STATIC 398 VOID 399 MdioIdle ( 400 LAN91X_DRIVER *LanDriver 401 ) 402 { 403 UINT16 MgmtReg; 404 405 MgmtReg = ReadIoReg16 (LanDriver, LAN91X_MGMT); 406 MgmtReg &= ~(MGMT_MDOE | MGMT_MCLK | MGMT_MDO); 407 WriteIoReg16 (LanDriver, LAN91X_MGMT, MgmtReg); 408 } 409 410 // Write to a PHY register 411 STATIC 412 VOID 413 WritePhyReg16 ( 414 LAN91X_DRIVER *LanDriver, 415 UINTN RegAd, 416 UINT16 Value 417 ) 418 { 419 // Bit-bang the MII Serial Frame write operation 420 MdioOutput (LanDriver, 32, 0xffffffff); // Send 32 Ones as a preamble 421 MdioOutput (LanDriver, 2, 0x01); // Send Start (01) 422 MdioOutput (LanDriver, 2, 0x01); // Send Write (01) 423 MdioOutput (LanDriver, 5, LanDriver->PhyAd); // Send PHYAD[4:0] 424 MdioOutput (LanDriver, 5, RegAd); // Send REGAD[4:0] 425 MdioOutput (LanDriver, 2, 0x02); // Send TurnAround (10) 426 MdioOutput (LanDriver, 16, Value); // Write 16 data bits 427 428 // Idle the MDIO bus 429 MdioIdle (LanDriver); 430 } 431 // Calculate approximate time to write a PHY register in microseconds 432 #define PHY_WRITE_TIME ((32 + 2 + 2 + 5 + 5 + 2 + 16) * PHY_OUTPUT_TIME) 433 434 // Read from a PHY register 435 STATIC 436 UINT16 437 ReadPhyReg16 ( 438 LAN91X_DRIVER *LanDriver, 439 UINTN RegAd 440 ) 441 { 442 UINT32 Value; 443 444 // Bit-bang the MII Serial Frame read operation 445 MdioOutput (LanDriver, 32, 0xffffffff); // Send 32 Ones as a preamble 446 MdioOutput (LanDriver, 2, 0x01); // Send Start (01) 447 MdioOutput (LanDriver, 2, 0x02); // Send Read (10) 448 MdioOutput (LanDriver, 5, LanDriver->PhyAd); // Send PHYAD[4:0] 449 MdioOutput (LanDriver, 5, RegAd); // Send REGAD[4:0] 450 451 (VOID) MdioInput (LanDriver, 2); // Discard TurnAround bits 452 Value = MdioInput (LanDriver, 16); // Read 16 data bits 453 454 // Idle the MDIO bus 455 MdioIdle (LanDriver); 456 457 return (Value & 0xffff); 458 } 459 // Calculate approximate time to read a PHY register in microseconds 460 #define PHY_READ_TIME (((32 + 2 + 2 + 5 + 5) * PHY_OUTPUT_TIME) + \ 461 ((2 + 16) * PHY_INPUT_TIME)) 462 463 464 /* ---------------- Debug Functions ------------------ */ 465 466 #ifdef LAN91X_PRINT_REGISTERS 467 STATIC 468 VOID 469 PrintIoRegisters ( 470 IN LAN91X_DRIVER *LanDriver 471 ) 472 { 473 UINTN Bank; 474 UINTN Offset; 475 UINT16 Value; 476 477 DEBUG((EFI_D_ERROR, "\nLAN91x I/O Register Dump:\n")); 478 479 // Print currrent bank select register 480 Value = MmioRead16 (LanDriver->IoBase + LAN91X_BANK_OFFSET); 481 DEBUG((EFI_D_ERROR, " BankSel: %d Bank Register %04x (%d)\n", 482 LanDriver->BankSel, Value, Value & 0x0007)); 483 484 // Print all I/O registers 485 for (Offset = 0; Offset < 0x0e; Offset += 2) { 486 DEBUG((EFI_D_ERROR, " %02x:", Offset)); 487 for (Bank = 0; Bank <= 3; ++Bank) { 488 DEBUG((EFI_D_ERROR, " %04x", ReadIoReg16 (LanDriver, MakeRegister (Bank, Offset)))); 489 } 490 DEBUG((EFI_D_ERROR, "\n")); 491 } 492 } 493 494 STATIC 495 VOID 496 PrintPhyRegisters ( 497 IN LAN91X_DRIVER *LanDriver 498 ) 499 { 500 UINTN RegNum; 501 502 DEBUG((EFI_D_ERROR, "\nLAN91x Phy %d Register Dump:\n", LanDriver->PhyAd)); 503 504 // Print all Phy registers 505 for (RegNum = 0; RegNum <= 5; ++RegNum) { 506 DEBUG((EFI_D_ERROR, " %2d: %04x\n", 507 RegNum, 508 ReadPhyReg16 (LanDriver, RegNum) 509 )); 510 } 511 for (RegNum = 16; RegNum <= 20; ++RegNum) { 512 DEBUG((EFI_D_ERROR, " %2d: %04x\n", 513 RegNum, 514 ReadPhyReg16 (LanDriver, RegNum) 515 )); 516 } 517 } 518 #endif 519 520 #if LAN91X_PRINT_PACKET_HEADERS 521 STATIC 522 VOID 523 PrintIpDgram ( 524 IN CONST VOID *DstMac, 525 IN CONST VOID *SrcMac, 526 IN CONST VOID *Proto, 527 IN CONST VOID *IpDgram 528 ) 529 { 530 CONST UINT8 *Ptr; 531 UINT16 SrcPort; 532 UINT16 DstPort; 533 534 Ptr = DstMac; 535 DEBUG((EFI_D_ERROR, " Dst: %02x-%02x-%02x", 536 Ptr[0], Ptr[1], Ptr[2])); 537 DEBUG((EFI_D_ERROR, "-%02x-%02x-%02x", 538 Ptr[3], Ptr[4], Ptr[5])); 539 540 Ptr = SrcMac; 541 DEBUG((EFI_D_ERROR, " Src: %02x-%02x-%02x", 542 Ptr[0], Ptr[1], Ptr[2])); 543 DEBUG((EFI_D_ERROR, "-%02x-%02x-%02x", 544 Ptr[3], Ptr[4], Ptr[5])); 545 546 Ptr = Proto; 547 DEBUG((EFI_D_ERROR, " Proto: %02x%02x\n", 548 Ptr[0], Ptr[1])); 549 550 Ptr = IpDgram; 551 switch (Ptr[9]) { 552 case EFI_IP_PROTO_ICMP: 553 DEBUG((EFI_D_ERROR, " ICMP")); 554 break; 555 case EFI_IP_PROTO_TCP: 556 DEBUG((EFI_D_ERROR, " TCP")); 557 break; 558 case EFI_IP_PROTO_UDP: 559 DEBUG((EFI_D_ERROR, " UDP")); 560 break; 561 default: 562 DEBUG((EFI_D_ERROR, " IpProto %d\n", Ptr[9])); 563 return; 564 } 565 566 DEBUG((EFI_D_ERROR, " SrcIp: %d.%d.%d.%d", 567 Ptr[12], Ptr[13], Ptr[14], Ptr[15])); 568 DEBUG((EFI_D_ERROR, " DstIp: %d.%d.%d.%d", 569 Ptr[16], Ptr[17], Ptr[18], Ptr[19])); 570 571 SrcPort = (Ptr[20] << 8) | Ptr[21]; 572 DstPort = (Ptr[22] << 8) | Ptr[23]; 573 DEBUG((EFI_D_ERROR, " SrcPort: %d DstPort: %d\n", SrcPort, DstPort)); 574 } 575 #endif 576 577 578 /* ---------------- PHY Management Operations ----------------- */ 579 580 STATIC 581 EFI_STATUS 582 PhyDetect ( 583 IN LAN91X_DRIVER *LanDriver 584 ) 585 { 586 UINT16 PhyId1; 587 UINT16 PhyId2; 588 589 for (LanDriver->PhyAd = 0x1f; LanDriver->PhyAd >= 0 ; --LanDriver->PhyAd) { 590 PhyId1 = ReadPhyReg16 (LanDriver, PHY_INDEX_ID1); 591 PhyId2 = ReadPhyReg16 (LanDriver, PHY_INDEX_ID2); 592 593 if ((PhyId1 != 0x0000) && (PhyId1 != 0xffff) && 594 (PhyId2 != 0x0000) && (PhyId2 != 0xffff)) { 595 if ((PhyId1 == 0x0016) && ((PhyId2 & 0xfff0) == 0xf840)) { 596 DEBUG((EFI_D_ERROR, "LAN91x: PHY type LAN83C183 (LAN91C111 Internal)\n")); 597 } else if ((PhyId1 == 0x0282) && ((PhyId2 & 0xfff0) == 0x1c50)) { 598 DEBUG((EFI_D_ERROR, "LAN91x: PHY type LAN83C180\n")); 599 } else { 600 DEBUG((EFI_D_ERROR, "LAN91x: PHY id %04x:%04x\n", PhyId1, PhyId2)); 601 } 602 return EFI_SUCCESS; 603 } 604 } 605 606 DEBUG((EFI_D_ERROR, "LAN91x: PHY detection failed\n")); 607 return EFI_NO_MEDIA; 608 } 609 610 611 // Check the Link Status and take appropriate action 612 STATIC 613 BOOLEAN 614 CheckLinkStatus ( 615 IN LAN91X_DRIVER *LanDriver 616 ) 617 { 618 UINT16 PhyStatus; 619 620 // Get the PHY Status 621 PhyStatus = ReadPhyReg16 (LanDriver, PHY_INDEX_BASIC_STATUS); 622 623 return (PhyStatus & PHYSTS_LINK_STS) != 0; 624 } 625 626 627 // Do auto-negotiation 628 STATIC 629 EFI_STATUS 630 PhyAutoNegotiate ( 631 IN LAN91X_DRIVER *LanDriver 632 ) 633 { 634 UINTN Retries; 635 UINT16 PhyControl; 636 UINT16 PhyStatus; 637 UINT16 PhyAdvert; 638 639 // If there isn't a PHY, don't try to reset it 640 if (LanDriver->PhyAd == LAN91X_NO_PHY) { 641 return EFI_SUCCESS; 642 } 643 644 // Next check that auto-negotiation is supported 645 PhyStatus = ReadPhyReg16 (LanDriver, PHY_INDEX_BASIC_STATUS); 646 if ((PhyStatus & PHYSTS_AUTO_CAP) == 0) { 647 return EFI_SUCCESS; 648 } 649 650 // Translate capabilities to advertise 651 PhyAdvert = PHYANA_CSMA; 652 653 if ((PhyStatus & PHYSTS_10BASET_HDPLX) != 0) { 654 PhyAdvert |= PHYANA_10BASET; 655 } 656 if ((PhyStatus & PHYSTS_10BASET_FDPLX) != 0) { 657 PhyAdvert |= PHYANA_10BASETFD; 658 } 659 if ((PhyStatus & PHYSTS_100BASETX_HDPLX) != 0) { 660 PhyAdvert |= PHYANA_100BASETX; 661 } 662 if ((PhyStatus & PHYSTS_100BASETX_FDPLX) != 0) { 663 PhyAdvert |= PHYANA_100BASETXFD; 664 } 665 if ((PhyStatus & PHYSTS_100BASE_T4) != 0) { 666 PhyAdvert |= PHYANA_100BASET4; 667 } 668 669 // Set the capabilities to advertise 670 WritePhyReg16 (LanDriver, PHY_INDEX_AUTO_NEG_ADVERT, PhyAdvert); 671 (VOID) ReadPhyReg16 (LanDriver, PHY_INDEX_AUTO_NEG_ADVERT); 672 673 // Restart Auto-Negotiation 674 PhyControl = ReadPhyReg16 (LanDriver, PHY_INDEX_BASIC_CTRL); 675 PhyControl &= ~(PHYCR_SPEED_SEL | PHYCR_DUPLEX_MODE); 676 PhyControl |= PHYCR_AUTO_EN | PHYCR_RST_AUTO; 677 WritePhyReg16 (LanDriver, PHY_INDEX_BASIC_CTRL, PhyControl); 678 679 // Wait up to 2 seconds for the process to complete 680 Retries = 2000000 / (PHY_READ_TIME + 100); 681 while ((ReadPhyReg16 (LanDriver, PHY_INDEX_BASIC_STATUS) & PHYSTS_AUTO_COMP) == 0) { 682 if (--Retries == 0) { 683 DEBUG((EFI_D_ERROR, "LAN91x: PHY auto-negotiation timed-out\n")); 684 return EFI_TIMEOUT; 685 } 686 gBS->Stall (100); 687 } 688 689 return EFI_SUCCESS; 690 } 691 692 693 // Perform PHY software reset 694 STATIC 695 EFI_STATUS 696 PhySoftReset ( 697 IN LAN91X_DRIVER *LanDriver 698 ) 699 { 700 UINTN Retries; 701 702 // If there isn't a PHY, don't try to reset it 703 if (LanDriver->PhyAd == LAN91X_NO_PHY) { 704 return EFI_SUCCESS; 705 } 706 707 // Request a PHY reset 708 WritePhyReg16 (LanDriver, PHY_INDEX_BASIC_CTRL, PHYCR_RESET); 709 710 // The internal PHY will reset within 50ms. Allow 100ms. 711 Retries = 100000 / (PHY_READ_TIME + 100); 712 while (ReadPhyReg16 (LanDriver, PHY_INDEX_BASIC_CTRL) & PHYCR_RESET) { 713 if (--Retries == 0) { 714 DEBUG((EFI_D_ERROR, "LAN91x: PHY reset timed-out\n")); 715 return EFI_TIMEOUT; 716 } 717 gBS->Stall (100); 718 } 719 720 return EFI_SUCCESS; 721 } 722 723 724 /* ---------------- General Operations ----------------- */ 725 726 STATIC 727 EFI_MAC_ADDRESS 728 GetCurrentMacAddress ( 729 IN LAN91X_DRIVER *LanDriver 730 ) 731 { 732 UINTN RegNum; 733 UINT8 *Addr; 734 EFI_MAC_ADDRESS MacAddress; 735 736 SetMem (&MacAddress, sizeof(MacAddress), 0); 737 738 Addr = &MacAddress.Addr[0]; 739 for (RegNum = LAN91X_IAR0; RegNum <= LAN91X_IAR5; ++RegNum) { 740 *Addr = ReadIoReg8 (LanDriver, RegNum); 741 ++Addr; 742 } 743 744 return MacAddress; 745 } 746 747 STATIC 748 EFI_STATUS 749 SetCurrentMacAddress ( 750 IN LAN91X_DRIVER *LanDriver, 751 IN EFI_MAC_ADDRESS *MacAddress 752 ) 753 { 754 UINTN RegNum; 755 UINT8 *Addr; 756 757 Addr = &MacAddress->Addr[0]; 758 for (RegNum = LAN91X_IAR0; RegNum <= LAN91X_IAR5; ++RegNum) { 759 WriteIoReg8 (LanDriver, RegNum, *Addr); 760 ++Addr; 761 } 762 763 return EFI_SUCCESS; 764 } 765 766 STATIC 767 EFI_STATUS 768 MmuOperation ( 769 IN LAN91X_DRIVER *LanDriver, 770 IN UINTN MmuOp 771 ) 772 { 773 UINTN Polls; 774 775 WriteIoReg16 (LanDriver, LAN91X_MMUCR, MmuOp); 776 Polls = 100; 777 while ((ReadIoReg16 (LanDriver, LAN91X_MMUCR) & MMUCR_BUSY) != 0) { 778 if (--Polls == 0) { 779 DEBUG((EFI_D_ERROR, "LAN91x: MMU operation %04x timed-out\n", MmuOp)); 780 return EFI_TIMEOUT; 781 } 782 gBS->Stall (LAN91X_STALL); 783 } 784 785 return EFI_SUCCESS; 786 } 787 788 // Read bytes from the DATA register 789 STATIC 790 EFI_STATUS 791 ReadIoData ( 792 IN LAN91X_DRIVER *LanDriver, 793 IN VOID *Buffer, 794 IN UINTN BufLen 795 ) 796 { 797 UINT8 *Ptr; 798 799 Ptr = Buffer; 800 for (; BufLen > 0; --BufLen) { 801 *Ptr = ReadIoReg8 (LanDriver, LAN91X_DATA0); 802 ++Ptr; 803 } 804 805 return EFI_SUCCESS; 806 } 807 808 // Write bytes to the DATA register 809 STATIC 810 EFI_STATUS 811 WriteIoData ( 812 IN LAN91X_DRIVER *LanDriver, 813 IN VOID *Buffer, 814 IN UINTN BufLen 815 ) 816 { 817 UINT8 *Ptr; 818 819 Ptr = Buffer; 820 for (; BufLen > 0; --BufLen) { 821 WriteIoReg8 (LanDriver, LAN91X_DATA0, *Ptr); 822 ++Ptr; 823 } 824 825 return EFI_SUCCESS; 826 } 827 828 // Disable the interface 829 STATIC 830 EFI_STATUS 831 ChipDisable ( 832 IN LAN91X_DRIVER *LanDriver 833 ) 834 { 835 #ifdef LAN91X_POWER_DOWN 836 UINT16 Val16; 837 #endif 838 839 // Stop Rx and Tx operations 840 WriteIoReg16 (LanDriver, LAN91X_RCR, RCR_CLEAR); 841 WriteIoReg16 (LanDriver, LAN91X_TCR, TCR_CLEAR); 842 843 #ifdef LAN91X_POWER_DOWN 844 // Power-down the chip 845 Val16 = ReadIoReg16 (LanDriver, LAN91X_CR); 846 Val16 &= ~CR_EPH_POWER_EN; 847 WriteIoReg16 (LanDriver, LAN91X_CR, Val16); 848 #endif 849 850 return EFI_SUCCESS; 851 } 852 853 // Enable the interface 854 STATIC 855 EFI_STATUS 856 ChipEnable ( 857 IN LAN91X_DRIVER *LanDriver 858 ) 859 { 860 #ifdef LAN91X_POWER_DOWN 861 UINT16 Val16; 862 863 // Power-up the chip 864 Val16 = ReadIoReg16 (LanDriver, LAN91X_CR); 865 Val16 |= CR_EPH_POWER_EN; 866 WriteIoReg16 (LanDriver, LAN91X_CR, Val16); 867 gBS->Stall (LAN91X_STALL); 868 #endif 869 870 // Start Rx and Tx operations 871 WriteIoReg16 (LanDriver, LAN91X_TCR, TCR_DEFAULT); 872 WriteIoReg16 (LanDriver, LAN91X_RCR, RCR_DEFAULT); 873 874 return EFI_SUCCESS; 875 } 876 877 878 // Perform software reset on the LAN91x 879 STATIC 880 EFI_STATUS 881 SoftReset ( 882 IN LAN91X_DRIVER *LanDriver 883 ) 884 { 885 UINT16 Val16; 886 887 // Issue the reset 888 WriteIoReg16 (LanDriver, LAN91X_RCR, RCR_SOFT_RST); 889 gBS->Stall (LAN91X_STALL); 890 WriteIoReg16 (LanDriver, LAN91X_RCR, RCR_CLEAR); 891 892 // Set the configuration register 893 WriteIoReg16 (LanDriver, LAN91X_CR, CR_DEFAULT); 894 gBS->Stall (LAN91X_STALL); 895 896 // Stop Rx and Tx 897 WriteIoReg16 (LanDriver, LAN91X_RCR, RCR_CLEAR); 898 WriteIoReg16 (LanDriver, LAN91X_TCR, TCR_CLEAR); 899 900 // Initialize the Control Register 901 Val16 = ReadIoReg16 (LanDriver, LAN91X_CTR); 902 Val16 |= CTR_AUTO_REL; 903 WriteIoReg16 (LanDriver, LAN91X_CTR, Val16); 904 905 // Reset the MMU 906 MmuOperation (LanDriver, MMUCR_OP_RESET_MMU); 907 908 return EFI_SUCCESS; 909 } 910 911 /* 912 ** Probe() 913 ** 914 ** Validate that there is a LAN91x device. 915 ** 916 */ 917 STATIC 918 EFI_STATUS 919 Probe ( 920 IN LAN91X_DRIVER *LanDriver 921 ) 922 { 923 UINT16 Bank; 924 UINT16 Val16; 925 CHAR16 CONST *ChipId; 926 UINTN ResetTime; 927 928 // First check that the Bank Select register is valid 929 Bank = MmioRead16 (LanDriver->IoBase + LAN91X_BANK_OFFSET); 930 if ((Bank & 0xff00) != 0x3300) { 931 DEBUG((EFI_D_ERROR, "LAN91x: signature error: expecting 33xx, read %04x\n", Bank)); 932 return EFI_DEVICE_ERROR; 933 } 934 935 // Try reading the revision register next 936 LanDriver->BankSel = 0xff; 937 Val16 = ReadIoReg16 (LanDriver, LAN91X_REV); 938 939 Bank = MmioRead16 (LanDriver->IoBase + LAN91X_BANK_OFFSET); 940 if ((Bank & 0xff03) != 0x3303) { 941 DEBUG((EFI_D_ERROR, "LAN91x: signature error: expecting 33x3, read %04x\n", Bank)); 942 return EFI_DEVICE_ERROR; 943 } 944 945 // Validate the revision register 946 if ((Val16 & 0xff00) != 0x3300) { 947 DEBUG((EFI_D_ERROR, "LAN91x: revision error: expecting 33xx, read %04x\n", Val16)); 948 return EFI_DEVICE_ERROR; 949 } 950 951 ChipId = ChipIds[(Val16 >> 4) & 0x0f]; 952 if (ChipId == NULL) { 953 DEBUG((EFI_D_ERROR, "LAN91x: unrecognized revision: %04x\n", Val16)); 954 return EFI_DEVICE_ERROR; 955 } 956 DEBUG((EFI_D_ERROR, "LAN91x: detected chip %s rev %d\n", ChipId, Val16 & 0xf)); 957 LanDriver->Revision = Val16 & 0xff; 958 959 // Reload from EEPROM to get the hardware MAC address 960 WriteIoReg16 (LanDriver, LAN91X_CTR, CTR_RESERVED | CTR_RELOAD); 961 ResetTime = 1000; 962 while ((ReadIoReg16 (LanDriver, LAN91X_CTR) & CTR_RELOAD) != 0) { 963 if (--ResetTime == 0) { 964 DEBUG((EFI_D_ERROR, "LAN91x: reload from EEPROM timed-out\n")); 965 WriteIoReg16 (LanDriver, LAN91X_CTR, CTR_RESERVED); 966 return EFI_DEVICE_ERROR; 967 } 968 gBS->Stall (LAN91X_STALL); 969 } 970 971 // Read and save the Permanent MAC Address 972 LanDriver->SnpMode.PermanentAddress = GetCurrentMacAddress (LanDriver); 973 LanDriver->SnpMode.CurrentAddress = LanDriver->SnpMode.PermanentAddress; 974 DEBUG((EFI_D_ERROR, //EFI_D_NET | EFI_D_INFO, 975 "LAN91x: HW MAC Address: %02x-%02x-%02x-%02x-%02x-%02x\n", 976 LanDriver->SnpMode.PermanentAddress.Addr[0], 977 LanDriver->SnpMode.PermanentAddress.Addr[1], 978 LanDriver->SnpMode.PermanentAddress.Addr[2], 979 LanDriver->SnpMode.PermanentAddress.Addr[3], 980 LanDriver->SnpMode.PermanentAddress.Addr[4], 981 LanDriver->SnpMode.PermanentAddress.Addr[5] 982 )); 983 984 // Reset the device 985 SoftReset (LanDriver); 986 987 // Try to detect a PHY 988 if (LanDriver->Revision > (CHIP_91100 << 4)) { 989 PhyDetect (LanDriver); 990 } else { 991 LanDriver->PhyAd = LAN91X_NO_PHY; 992 } 993 994 return EFI_SUCCESS; 995 } 996 997 998 999 1000 /*------------------ Simple Network Driver entry point functions ------------------*/ 1001 1002 // Refer to the Simple Network Protocol section (21.1) 1003 // in the UEFI 2.3.1 Specification for documentation. 1004 1005 #define ReturnUnlock(s) do { Status = (s); goto exit_unlock; } while(0) 1006 1007 1008 /* 1009 ** UEFI Start() function 1010 ** 1011 */ 1012 EFI_STATUS 1013 EFIAPI 1014 SnpStart ( 1015 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp 1016 ) 1017 { 1018 EFI_SIMPLE_NETWORK_MODE *Mode; 1019 EFI_TPL SavedTpl; 1020 EFI_STATUS Status; 1021 1022 // Check Snp instance 1023 if (Snp == NULL) { 1024 return EFI_INVALID_PARAMETER; 1025 } 1026 1027 // Serialize access to data and registers 1028 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1029 Mode = Snp->Mode; 1030 1031 // Check state of the driver 1032 switch (Mode->State) { 1033 case EfiSimpleNetworkStopped: 1034 break; 1035 case EfiSimpleNetworkStarted: 1036 case EfiSimpleNetworkInitialized: 1037 DEBUG((EFI_D_WARN, "LAN91x: Driver already started\n")); 1038 ReturnUnlock (EFI_ALREADY_STARTED); 1039 default: 1040 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1041 (UINTN)Snp->Mode->State)); 1042 ReturnUnlock (EFI_DEVICE_ERROR); 1043 } 1044 1045 1046 // Change state 1047 Mode->State = EfiSimpleNetworkStarted; 1048 Status = EFI_SUCCESS; 1049 1050 // Restore TPL and return 1051 exit_unlock: 1052 gBS->RestoreTPL (SavedTpl); 1053 return Status; 1054 } 1055 1056 /* 1057 ** UEFI Stop() function 1058 ** 1059 */ 1060 EFI_STATUS 1061 EFIAPI 1062 SnpStop ( 1063 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp 1064 ) 1065 { 1066 LAN91X_DRIVER *LanDriver; 1067 EFI_TPL SavedTpl; 1068 EFI_STATUS Status; 1069 1070 // Check Snp Instance 1071 if (Snp == NULL) { 1072 return EFI_INVALID_PARAMETER; 1073 } 1074 1075 // Serialize access to data and registers 1076 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1077 1078 // Check state of the driver 1079 switch (Snp->Mode->State) { 1080 case EfiSimpleNetworkStarted: 1081 case EfiSimpleNetworkInitialized: 1082 break; 1083 case EfiSimpleNetworkStopped: 1084 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1085 ReturnUnlock (EFI_NOT_STARTED); 1086 default: 1087 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1088 (UINTN)Snp->Mode->State)); 1089 ReturnUnlock (EFI_DEVICE_ERROR); 1090 } 1091 1092 // Find the LanDriver structure 1093 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1094 1095 // Stop the Tx and Rx 1096 ChipDisable (LanDriver); 1097 1098 // Change the state 1099 Snp->Mode->State = EfiSimpleNetworkStopped; 1100 Status = EFI_SUCCESS; 1101 1102 // Restore TPL and return 1103 exit_unlock: 1104 gBS->RestoreTPL (SavedTpl); 1105 return Status; 1106 } 1107 1108 /* 1109 ** UEFI Initialize() function 1110 ** 1111 */ 1112 EFI_STATUS 1113 EFIAPI 1114 SnpInitialize ( 1115 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp, 1116 IN UINTN RxBufferSize OPTIONAL, 1117 IN UINTN TxBufferSize OPTIONAL 1118 ) 1119 { 1120 LAN91X_DRIVER *LanDriver; 1121 EFI_TPL SavedTpl; 1122 EFI_STATUS Status; 1123 1124 // Check Snp Instance 1125 if (Snp == NULL) { 1126 return EFI_INVALID_PARAMETER; 1127 } 1128 1129 // Serialize access to data and registers 1130 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1131 1132 // Check that driver was started but not initialised 1133 switch (Snp->Mode->State) { 1134 case EfiSimpleNetworkStarted: 1135 break; 1136 case EfiSimpleNetworkInitialized: 1137 DEBUG((EFI_D_WARN, "LAN91x: Driver already initialized\n")); 1138 ReturnUnlock (EFI_SUCCESS); 1139 case EfiSimpleNetworkStopped: 1140 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1141 ReturnUnlock (EFI_NOT_STARTED); 1142 default: 1143 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1144 (UINTN)Snp->Mode->State)); 1145 ReturnUnlock (EFI_DEVICE_ERROR); 1146 } 1147 1148 // Find the LanDriver structure 1149 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1150 1151 // Initiate a software reset 1152 Status = SoftReset (LanDriver); 1153 if (EFI_ERROR(Status)) { 1154 DEBUG((EFI_D_WARN, "LAN91x: Soft reset failed\n")); 1155 ReturnUnlock (EFI_DEVICE_ERROR); 1156 } 1157 1158 // Initiate a PHY reset 1159 if (PhySoftReset (LanDriver) < 0) { 1160 Snp->Mode->State = EfiSimpleNetworkStopped; 1161 DEBUG((EFI_D_WARN, "LAN91x: PHY soft reset timeout\n")); 1162 ReturnUnlock (EFI_NOT_STARTED); 1163 } 1164 1165 // Do auto-negotiation 1166 Status = PhyAutoNegotiate (LanDriver); 1167 if (EFI_ERROR(Status)) { 1168 DEBUG((EFI_D_WARN, "LAN91x: PHY auto-negotiation failed\n")); 1169 } 1170 1171 // Enable the receiver and transmitter 1172 ChipEnable (LanDriver); 1173 1174 // Now acknowledge all interrupts 1175 WriteIoReg8 (LanDriver, LAN91X_IST, 0xFF); 1176 1177 // Declare the driver as initialized 1178 Snp->Mode->State = EfiSimpleNetworkInitialized; 1179 Status = EFI_SUCCESS; 1180 1181 // Restore TPL and return 1182 exit_unlock: 1183 gBS->RestoreTPL (SavedTpl); 1184 return Status; 1185 } 1186 1187 /* 1188 ** UEFI Reset () function 1189 ** 1190 */ 1191 EFI_STATUS 1192 EFIAPI 1193 SnpReset ( 1194 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp, 1195 IN BOOLEAN Verification 1196 ) 1197 { 1198 LAN91X_DRIVER *LanDriver; 1199 EFI_TPL SavedTpl; 1200 EFI_STATUS Status; 1201 1202 // Check Snp Instance 1203 if (Snp == NULL) { 1204 return EFI_INVALID_PARAMETER; 1205 } 1206 1207 // Serialize access to data and registers 1208 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1209 1210 // Check that driver was started and initialised 1211 switch (Snp->Mode->State) { 1212 case EfiSimpleNetworkInitialized: 1213 break; 1214 case EfiSimpleNetworkStarted: 1215 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1216 ReturnUnlock (EFI_DEVICE_ERROR); 1217 case EfiSimpleNetworkStopped: 1218 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1219 ReturnUnlock (EFI_NOT_STARTED); 1220 default: 1221 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1222 (UINTN)Snp->Mode->State)); 1223 ReturnUnlock (EFI_DEVICE_ERROR); 1224 } 1225 1226 // Find the LanDriver structure 1227 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1228 1229 // Initiate a software reset 1230 if (EFI_ERROR (SoftReset (LanDriver))) { 1231 DEBUG((EFI_D_WARN, "LAN91x: Soft reset failed\n")); 1232 ReturnUnlock (EFI_DEVICE_ERROR); 1233 } 1234 1235 // Initiate a PHY reset 1236 if (EFI_ERROR (PhySoftReset (LanDriver))) { 1237 DEBUG((EFI_D_WARN, "LAN91x: PHY soft reset failed\n")); 1238 ReturnUnlock (EFI_DEVICE_ERROR); 1239 } 1240 1241 // Enable the receiver and transmitter 1242 Status = ChipEnable (LanDriver); 1243 1244 // Restore TPL and return 1245 exit_unlock: 1246 gBS->RestoreTPL (SavedTpl); 1247 return Status; 1248 } 1249 1250 /* 1251 ** UEFI Shutdown () function 1252 ** 1253 */ 1254 EFI_STATUS 1255 EFIAPI 1256 SnpShutdown ( 1257 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp 1258 ) 1259 { 1260 LAN91X_DRIVER *LanDriver; 1261 EFI_TPL SavedTpl; 1262 EFI_STATUS Status; 1263 1264 // Check Snp Instance 1265 if (Snp == NULL) { 1266 return EFI_INVALID_PARAMETER; 1267 } 1268 1269 // Serialize access to data and registers 1270 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1271 1272 // First check that driver has already been initialized 1273 switch (Snp->Mode->State) { 1274 case EfiSimpleNetworkInitialized: 1275 break; 1276 case EfiSimpleNetworkStarted: 1277 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1278 ReturnUnlock (EFI_DEVICE_ERROR); 1279 case EfiSimpleNetworkStopped: 1280 DEBUG((EFI_D_WARN, "LAN91x: Driver in stopped state\n")); 1281 ReturnUnlock (EFI_NOT_STARTED); 1282 default: 1283 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1284 (UINTN)Snp->Mode->State)); 1285 ReturnUnlock (EFI_DEVICE_ERROR); 1286 } 1287 1288 // Find the LanDriver structure 1289 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1290 1291 // Disable the interface 1292 Status = ChipDisable (LanDriver); 1293 1294 // Restore TPL and return 1295 exit_unlock: 1296 gBS->RestoreTPL (SavedTpl); 1297 return Status; 1298 } 1299 1300 1301 /* 1302 ** UEFI ReceiveFilters() function 1303 ** 1304 */ 1305 EFI_STATUS 1306 EFIAPI 1307 SnpReceiveFilters ( 1308 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp, 1309 IN UINT32 Enable, 1310 IN UINT32 Disable, 1311 IN BOOLEAN Reset, 1312 IN UINTN NumMfilter OPTIONAL, 1313 IN EFI_MAC_ADDRESS *Mfilter OPTIONAL 1314 ) 1315 { 1316 #define MCAST_HASH_BYTES 8 1317 1318 LAN91X_DRIVER *LanDriver; 1319 EFI_SIMPLE_NETWORK_MODE *SnpMode; 1320 EFI_TPL SavedTpl; 1321 EFI_STATUS Status; 1322 UINTN i; 1323 UINT32 Crc; 1324 UINT16 RcvCtrl; 1325 UINT8 McastHash[MCAST_HASH_BYTES]; 1326 1327 // Check Snp Instance 1328 if (Snp == NULL) { 1329 return EFI_INVALID_PARAMETER; 1330 } 1331 1332 // Serialize access to data and registers 1333 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1334 1335 // First check that driver has already been initialized 1336 switch (Snp->Mode->State) { 1337 case EfiSimpleNetworkInitialized: 1338 break; 1339 case EfiSimpleNetworkStarted: 1340 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1341 ReturnUnlock (EFI_DEVICE_ERROR); 1342 case EfiSimpleNetworkStopped: 1343 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1344 ReturnUnlock (EFI_NOT_STARTED); 1345 default: 1346 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1347 (UINTN)Snp->Mode->State)); 1348 ReturnUnlock (EFI_DEVICE_ERROR); 1349 } 1350 1351 // Find the LanDriver structure 1352 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1353 SnpMode = Snp->Mode; 1354 1355 #ifdef LAN91X_PRINT_RECEIVE_FILTERS 1356 DEBUG((EFI_D_ERROR, "LAN91x:SnpReceiveFilters()\n")); 1357 DEBUG((EFI_D_ERROR, " Enable = %08x\n", Enable)); 1358 DEBUG((EFI_D_ERROR, " Disable = %08x\n", Disable)); 1359 DEBUG((EFI_D_ERROR, " Reset = %d\n", Reset)); 1360 DEBUG((EFI_D_ERROR, " NumMfilter = %d\n", NumMfilter)); 1361 for (i = 0; i < NumMfilter; ++i) { 1362 DEBUG((EFI_D_ERROR, 1363 " [%2d] = %02x-%02x-%02x-%02x-%02x-%02x\n", 1364 i, 1365 Mfilter[i].Addr[0], 1366 Mfilter[i].Addr[1], 1367 Mfilter[i].Addr[2], 1368 Mfilter[i].Addr[3], 1369 Mfilter[i].Addr[4], 1370 Mfilter[i].Addr[5])); 1371 } 1372 #endif 1373 1374 // Update the Multicast Hash registers 1375 if (Reset) { 1376 // Clear the hash table 1377 SetMem (McastHash, MCAST_HASH_BYTES, 0); 1378 SnpMode->MCastFilterCount = 0; 1379 } else { 1380 // Read the current hash table 1381 for (i = 0; i < MCAST_HASH_BYTES; ++i) { 1382 McastHash[i] = ReadIoReg8 (LanDriver, LAN91X_MT0 + i); 1383 } 1384 // Set the new additions 1385 for (i = 0; i < NumMfilter; ++i) { 1386 Crc = MulticastHash (&Mfilter[i], NET_ETHER_ADDR_LEN); 1387 McastHash[(Crc >> 29) & 0x3] |= 1 << ((Crc >> 26) & 0x3); 1388 } 1389 SnpMode->MCastFilterCount = NumMfilter; 1390 } 1391 // If the hash registers need updating, write them 1392 if (Reset || NumMfilter > 0) { 1393 for (i = 0; i < MCAST_HASH_BYTES; ++i) { 1394 WriteIoReg8 (LanDriver, LAN91X_MT0 + i, McastHash[i]); 1395 } 1396 } 1397 1398 RcvCtrl = ReadIoReg16 (LanDriver, LAN91X_RCR); 1399 if ((Enable & EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS) != 0) { 1400 RcvCtrl |= RCR_PRMS; 1401 SnpMode->ReceiveFilterSetting |= EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS; 1402 } 1403 if ((Disable & EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS) != 0) { 1404 RcvCtrl &= ~RCR_PRMS; 1405 SnpMode->ReceiveFilterSetting &= ~EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS; 1406 } 1407 1408 if ((Enable & EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST) != 0) { 1409 RcvCtrl |= RCR_ALMUL; 1410 SnpMode->ReceiveFilterSetting |= EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST; 1411 } 1412 if ((Disable & EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST) != 0) { 1413 RcvCtrl &= ~RCR_ALMUL; 1414 SnpMode->ReceiveFilterSetting &= ~EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST; 1415 } 1416 WriteIoReg16 (LanDriver, LAN91X_RCR, RcvCtrl); 1417 1418 Status = SetCurrentMacAddress (LanDriver, &SnpMode->CurrentAddress); 1419 1420 // Restore TPL and return 1421 exit_unlock: 1422 gBS->RestoreTPL (SavedTpl); 1423 return Status; 1424 } 1425 1426 /* 1427 ** UEFI StationAddress() function 1428 ** 1429 */ 1430 EFI_STATUS 1431 EFIAPI 1432 SnpStationAddress ( 1433 IN EFI_SIMPLE_NETWORK_PROTOCOL *Snp, 1434 IN BOOLEAN Reset, 1435 IN EFI_MAC_ADDRESS *NewMac 1436 ) 1437 { 1438 LAN91X_DRIVER *LanDriver; 1439 EFI_TPL SavedTpl; 1440 EFI_STATUS Status; 1441 1442 // Check Snp instance 1443 if (Snp == NULL) { 1444 return EFI_INVALID_PARAMETER; 1445 } 1446 1447 // Serialize access to data and registers 1448 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1449 1450 // Check that driver was started and initialised 1451 switch (Snp->Mode->State) { 1452 case EfiSimpleNetworkInitialized: 1453 break; 1454 case EfiSimpleNetworkStarted: 1455 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1456 ReturnUnlock (EFI_DEVICE_ERROR); 1457 case EfiSimpleNetworkStopped: 1458 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1459 ReturnUnlock (EFI_NOT_STARTED); 1460 default: 1461 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1462 (UINTN)Snp->Mode->State)); 1463 ReturnUnlock (EFI_DEVICE_ERROR); 1464 } 1465 1466 // Find the LanDriver structure 1467 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1468 1469 if (Reset) { 1470 Snp->Mode->CurrentAddress = Snp->Mode->PermanentAddress; 1471 } else { 1472 if (NewMac == NULL) { 1473 ReturnUnlock (EFI_INVALID_PARAMETER); 1474 } 1475 Snp->Mode->CurrentAddress = *NewMac; 1476 } 1477 1478 Status = SetCurrentMacAddress (LanDriver, &Snp->Mode->CurrentAddress); 1479 1480 // Restore TPL and return 1481 exit_unlock: 1482 gBS->RestoreTPL (SavedTpl); 1483 return Status; 1484 } 1485 1486 /* 1487 ** UEFI Statistics() function 1488 ** 1489 */ 1490 EFI_STATUS 1491 EFIAPI 1492 SnpStatistics ( 1493 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp, 1494 IN BOOLEAN Reset, 1495 IN OUT UINTN *StatSize, 1496 OUT EFI_NETWORK_STATISTICS *Statistics 1497 ) 1498 { 1499 LAN91X_DRIVER *LanDriver; 1500 EFI_TPL SavedTpl; 1501 EFI_STATUS Status; 1502 1503 // Check Snp instance 1504 if (Snp == NULL) { 1505 return EFI_INVALID_PARAMETER; 1506 } 1507 1508 // Check pointless condition 1509 if ((!Reset) && (StatSize == NULL) && (Statistics == NULL)) { 1510 return EFI_SUCCESS; 1511 } 1512 1513 // Check the parameters 1514 if ((StatSize == NULL) && (Statistics != NULL)) { 1515 return EFI_INVALID_PARAMETER; 1516 } 1517 1518 // Serialize access to data and registers 1519 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1520 1521 // Check that driver was started and initialised 1522 switch (Snp->Mode->State) { 1523 case EfiSimpleNetworkInitialized: 1524 break; 1525 case EfiSimpleNetworkStarted: 1526 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1527 ReturnUnlock (EFI_DEVICE_ERROR); 1528 case EfiSimpleNetworkStopped: 1529 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1530 ReturnUnlock (EFI_NOT_STARTED); 1531 default: 1532 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1533 (UINTN)Snp->Mode->State)); 1534 ReturnUnlock (EFI_DEVICE_ERROR); 1535 } 1536 1537 // Find the LanDriver structure 1538 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1539 1540 // Do a reset if required 1541 if (Reset) { 1542 ZeroMem (&LanDriver->Stats, sizeof(EFI_NETWORK_STATISTICS)); 1543 } 1544 1545 // Check buffer size 1546 if (*StatSize < sizeof(EFI_NETWORK_STATISTICS)) { 1547 *StatSize = sizeof(EFI_NETWORK_STATISTICS); 1548 ReturnUnlock (EFI_BUFFER_TOO_SMALL); 1549 goto exit_unlock; 1550 } 1551 1552 // Fill in the statistics 1553 CopyMem(&Statistics, &LanDriver->Stats, sizeof(EFI_NETWORK_STATISTICS)); 1554 Status = EFI_SUCCESS; 1555 1556 // Restore TPL and return 1557 exit_unlock: 1558 gBS->RestoreTPL (SavedTpl); 1559 return Status; 1560 } 1561 1562 /* 1563 ** UEFI MCastIPtoMAC() function 1564 ** 1565 */ 1566 EFI_STATUS 1567 EFIAPI 1568 SnpMcastIptoMac ( 1569 IN EFI_SIMPLE_NETWORK_PROTOCOL* Snp, 1570 IN BOOLEAN IsIpv6, 1571 IN EFI_IP_ADDRESS *Ip, 1572 OUT EFI_MAC_ADDRESS *McastMac 1573 ) 1574 { 1575 // Check Snp instance 1576 if (Snp == NULL) { 1577 return EFI_INVALID_PARAMETER; 1578 } 1579 1580 // Check parameters 1581 if ((McastMac == NULL) || (Ip == NULL)) { 1582 return EFI_INVALID_PARAMETER; 1583 } 1584 1585 // Make sure MAC address is empty 1586 ZeroMem (McastMac, sizeof(EFI_MAC_ADDRESS)); 1587 1588 // If we need ipv4 address 1589 if (!IsIpv6) { 1590 // Most significant 25 bits of a multicast HW address are set 1591 McastMac->Addr[0] = 0x01; 1592 McastMac->Addr[1] = 0x00; 1593 McastMac->Addr[2] = 0x5E; 1594 1595 // Lower 23 bits from ipv4 address 1596 McastMac->Addr[3] = (Ip->v4.Addr[1] & 0x7F); // Clear the ms bit (25th bit of MAC must be 0) 1597 McastMac->Addr[4] = Ip->v4.Addr[2]; 1598 McastMac->Addr[5] = Ip->v4.Addr[3]; 1599 } else { 1600 // Most significant 16 bits of multicast v6 HW address are set 1601 McastMac->Addr[0] = 0x33; 1602 McastMac->Addr[1] = 0x33; 1603 1604 // lower four octets are taken from ipv6 address 1605 McastMac->Addr[2] = Ip->v6.Addr[8]; 1606 McastMac->Addr[3] = Ip->v6.Addr[9]; 1607 McastMac->Addr[4] = Ip->v6.Addr[10]; 1608 McastMac->Addr[5] = Ip->v6.Addr[11]; 1609 } 1610 1611 return EFI_SUCCESS; 1612 } 1613 1614 /* 1615 ** UEFI NvData() function 1616 ** 1617 */ 1618 EFI_STATUS 1619 EFIAPI 1620 SnpNvData ( 1621 IN EFI_SIMPLE_NETWORK_PROTOCOL* pobj, 1622 IN BOOLEAN read_write, 1623 IN UINTN offset, 1624 IN UINTN buff_size, 1625 IN OUT VOID *data 1626 ) 1627 { 1628 DEBUG((EFI_D_ERROR, "LAN91x: Non-volatile storage not supported\n")); 1629 1630 return EFI_UNSUPPORTED; 1631 } 1632 1633 1634 /* 1635 ** UEFI GetStatus () function 1636 ** 1637 */ 1638 EFI_STATUS 1639 EFIAPI 1640 SnpGetStatus ( 1641 IN EFI_SIMPLE_NETWORK_PROTOCOL *Snp, 1642 OUT UINT32 *IrqStat OPTIONAL, 1643 OUT VOID **TxBuff OPTIONAL 1644 ) 1645 { 1646 LAN91X_DRIVER *LanDriver; 1647 EFI_TPL SavedTpl; 1648 EFI_STATUS Status; 1649 BOOLEAN MediaPresent; 1650 UINT8 IstReg; 1651 1652 // Check preliminaries 1653 if (Snp == NULL) { 1654 return EFI_INVALID_PARAMETER; 1655 } 1656 1657 // Serialize access to data and registers 1658 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1659 1660 // Check that driver was started and initialised 1661 switch (Snp->Mode->State) { 1662 case EfiSimpleNetworkInitialized: 1663 break; 1664 case EfiSimpleNetworkStarted: 1665 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1666 ReturnUnlock (EFI_DEVICE_ERROR); 1667 case EfiSimpleNetworkStopped: 1668 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1669 ReturnUnlock (EFI_NOT_STARTED); 1670 default: 1671 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1672 (UINTN)Snp->Mode->State)); 1673 ReturnUnlock (EFI_DEVICE_ERROR); 1674 } 1675 1676 // Find the LanDriver structure 1677 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1678 1679 // Arbitrarily set the interrupt status to 0 1680 if (IrqStat != NULL) { 1681 *IrqStat = 0; 1682 IstReg = ReadIoReg8 (LanDriver, LAN91X_IST); 1683 if ((IstReg & IST_RCV) != 0) { 1684 *IrqStat |= EFI_SIMPLE_NETWORK_RECEIVE_INTERRUPT; 1685 } 1686 if ((IstReg & IST_TX) != 0) { 1687 *IrqStat |= EFI_SIMPLE_NETWORK_TRANSMIT_INTERRUPT; 1688 } 1689 } 1690 1691 // Pass back the completed buffer address 1692 if (TxBuff != NULL) { 1693 *TxBuff = TxQueRemove (LanDriver); 1694 } 1695 1696 // Update the media status 1697 MediaPresent = CheckLinkStatus (LanDriver); 1698 if (MediaPresent != Snp->Mode->MediaPresent) { 1699 DEBUG((EFI_D_WARN, "LAN91x: Link %s\n", MediaPresent ? L"up" : L"down")); 1700 } 1701 Snp->Mode->MediaPresent = MediaPresent; 1702 Status = EFI_SUCCESS; 1703 1704 // Restore TPL and return 1705 exit_unlock: 1706 gBS->RestoreTPL (SavedTpl); 1707 return Status; 1708 } 1709 1710 1711 /* 1712 ** UEFI Transmit() function 1713 ** 1714 */ 1715 EFI_STATUS 1716 EFIAPI 1717 SnpTransmit ( 1718 IN EFI_SIMPLE_NETWORK_PROTOCOL *Snp, 1719 IN UINTN HdrSize, 1720 IN UINTN BufSize, 1721 IN VOID *BufAddr, 1722 IN EFI_MAC_ADDRESS *SrcAddr OPTIONAL, 1723 IN EFI_MAC_ADDRESS *DstAddr OPTIONAL, 1724 IN UINT16 *Protocol OPTIONAL 1725 ) 1726 { 1727 LAN91X_DRIVER *LanDriver; 1728 EFI_TPL SavedTpl; 1729 EFI_STATUS Status; 1730 UINT8 *Ptr; 1731 UINTN Len; 1732 UINTN MmuPages; 1733 UINTN Retries; 1734 UINT16 Proto; 1735 UINT8 PktNum; 1736 1737 // Check preliminaries 1738 if ((Snp == NULL) || (BufAddr == NULL)) { 1739 DEBUG((EFI_D_ERROR, "LAN91x: SnpTransmit(): NULL Snp (%p) or BufAddr (%p)\n", 1740 Snp, BufAddr)); 1741 return EFI_INVALID_PARAMETER; 1742 } 1743 1744 // Serialize access to data and registers 1745 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1746 1747 // Check that driver was started and initialised 1748 switch (Snp->Mode->State) { 1749 case EfiSimpleNetworkInitialized: 1750 break; 1751 case EfiSimpleNetworkStarted: 1752 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1753 ReturnUnlock (EFI_DEVICE_ERROR); 1754 case EfiSimpleNetworkStopped: 1755 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1756 ReturnUnlock (EFI_NOT_STARTED); 1757 default: 1758 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1759 (UINTN)Snp->Mode->State)); 1760 ReturnUnlock (EFI_DEVICE_ERROR); 1761 } 1762 1763 // Find the LanDriver structure 1764 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1765 1766 // Ensure header is correct size if non-zero 1767 if (HdrSize != 0) { 1768 if (HdrSize != Snp->Mode->MediaHeaderSize) { 1769 DEBUG((EFI_D_ERROR, "LAN91x: SnpTransmit(): Invalid HdrSize %d\n", HdrSize)); 1770 ReturnUnlock (EFI_INVALID_PARAMETER); 1771 } 1772 1773 if ((DstAddr == NULL) || (Protocol == NULL)) { 1774 DEBUG((EFI_D_ERROR, "LAN91x: SnpTransmit(): NULL DstAddr %p or Protocol %p\n", 1775 DstAddr, Protocol)); 1776 ReturnUnlock (EFI_INVALID_PARAMETER); 1777 } 1778 } 1779 1780 // Before transmitting check the link status 1781 if (!Snp->Mode->MediaPresent) { 1782 DEBUG((EFI_D_WARN, "LAN91x: SnpTransmit(): Link not ready\n")); 1783 ReturnUnlock (EFI_NOT_READY); 1784 } 1785 1786 // Calculate the request size in 256-byte "pages" minus 1 1787 // The 91C111 ignores this, but some older devices need it. 1788 MmuPages = ((BufSize & ~1) + LAN91X_PKT_OVERHEAD - 1) >> 8; 1789 if (MmuPages > 7) { 1790 DEBUG((EFI_D_WARN, "LAN91x: Tx buffer too large (%d bytes)\n", BufSize)); 1791 LanDriver->Stats.TxOversizeFrames += 1; 1792 LanDriver->Stats.TxDroppedFrames += 1; 1793 ReturnUnlock (EFI_BAD_BUFFER_SIZE); 1794 } 1795 1796 // Request allocation of a transmit buffer 1797 Status = MmuOperation (LanDriver, MMUCR_OP_TX_ALLOC | MmuPages); 1798 if (EFI_ERROR (Status)) { 1799 DEBUG((EFI_D_ERROR, "LAN91x: Tx buffer request failure: %d\n", Status)); 1800 ReturnUnlock (EFI_DEVICE_ERROR); 1801 } 1802 1803 // Wait for allocation request completion 1804 Retries = LAN91X_MEMORY_ALLOC_POLLS; 1805 while ((ReadIoReg8 (LanDriver, LAN91X_IST) & IST_ALLOC) == 0) { 1806 if (--Retries == 0) { 1807 DEBUG((EFI_D_ERROR, "LAN91x: Tx buffer allocation timeout\n")); 1808 ReturnUnlock (EFI_TIMEOUT); 1809 } 1810 } 1811 1812 // Check for successful allocation 1813 PktNum = ReadIoReg8 (LanDriver, LAN91X_ARR); 1814 if ((PktNum & ARR_FAILED) != 0) { 1815 DEBUG((EFI_D_ERROR, "LAN91x: Tx buffer allocation failure: %02x\n", PktNum)); 1816 ReturnUnlock (EFI_NOT_READY); 1817 } 1818 PktNum &= ARR_PACKET; 1819 1820 // Check for the nature of the frame 1821 if (DstAddr->Addr[0] == 0xFF) { 1822 LanDriver->Stats.TxBroadcastFrames += 1; 1823 } else if ((DstAddr->Addr[0] & 0x1) == 1) { 1824 LanDriver->Stats.TxMulticastFrames += 1; 1825 } else { 1826 LanDriver->Stats.TxUnicastFrames += 1; 1827 } 1828 1829 // Set the Packet Number and Pointer registers 1830 WriteIoReg8 (LanDriver, LAN91X_PNR, PktNum); 1831 WriteIoReg16 (LanDriver, LAN91X_PTR, PTR_AUTO_INCR); 1832 1833 // Set up mutable buffer information variables 1834 Ptr = BufAddr; 1835 Len = BufSize; 1836 1837 // Write Status and Byte Count first 1838 WriteIoReg16 (LanDriver, LAN91X_DATA0, 0); 1839 WriteIoReg16 (LanDriver, LAN91X_DATA0, (Len + LAN91X_PKT_OVERHEAD) & BCW_COUNT); 1840 1841 // This packet may come with a preconfigured Ethernet header. 1842 // If not, we need to construct one from optional parameters. 1843 if (HdrSize) { 1844 1845 // Write the destination address 1846 WriteIoData (LanDriver, DstAddr, NET_ETHER_ADDR_LEN); 1847 1848 // Write the Source Address 1849 if (SrcAddr != NULL) { 1850 WriteIoData (LanDriver, SrcAddr, NET_ETHER_ADDR_LEN); 1851 } else { 1852 WriteIoData (LanDriver, &LanDriver->SnpMode.CurrentAddress, NET_ETHER_ADDR_LEN); 1853 } 1854 1855 // Write the Protocol word 1856 Proto = HTONS (*Protocol); 1857 WriteIoReg16 (LanDriver, LAN91X_DATA0, Proto); 1858 1859 // Adjust the data start and length 1860 Ptr += sizeof(ETHER_HEAD); 1861 Len -= sizeof(ETHER_HEAD); 1862 } 1863 1864 // Copy the remainder data buffer, except the odd byte 1865 WriteIoData (LanDriver, Ptr, Len & ~1); 1866 Ptr += Len & ~1; 1867 Len &= 1; 1868 1869 // Write the Packet Control Word and odd byte 1870 WriteIoReg16 (LanDriver, LAN91X_DATA0, 1871 (Len != 0) ? (PCW_ODD | PCW_CRC | *Ptr) : PCW_CRC); 1872 1873 // Release the packet for transmission 1874 Status = MmuOperation (LanDriver, MMUCR_OP_TX_PUSH); 1875 if (EFI_ERROR (Status)) { 1876 DEBUG((EFI_D_ERROR, "LAN91x: Tx buffer release failure: %d\n", Status)); 1877 ReturnUnlock (EFI_DEVICE_ERROR); 1878 } 1879 1880 // Update the Rx statistics 1881 LanDriver->Stats.TxTotalBytes += BufSize; 1882 LanDriver->Stats.TxGoodFrames += 1; 1883 1884 // Update the Tx Buffer cache 1885 if (!TxQueInsert (LanDriver, BufAddr)) { 1886 DEBUG((EFI_D_WARN, "LAN91x: SnpTransmit(): TxQueue insert failure.\n")); 1887 } 1888 Status = EFI_SUCCESS; 1889 1890 // Dump the packet header 1891 #if LAN91X_PRINT_PACKET_HEADERS 1892 Ptr = BufAddr; 1893 DEBUG((EFI_D_ERROR, "LAN91X:SnpTransmit()\n")); 1894 DEBUG((EFI_D_ERROR, " HdrSize: %d, SrcAddr: %p, Length: %d, Last byte: %02x\n", 1895 HdrSize, SrcAddr, BufSize, Ptr[BufSize - 1])); 1896 PrintIpDgram ( 1897 (HdrSize == 0) ? (EFI_MAC_ADDRESS *)&Ptr[0] : DstAddr, 1898 (HdrSize == 0) ? (EFI_MAC_ADDRESS *)&Ptr[6] : (SrcAddr != NULL) ? SrcAddr : &LanDriver->SnpMode.CurrentAddress, 1899 (HdrSize == 0) ? (UINT16 *)&Ptr[12] : &Proto, 1900 &Ptr[14] 1901 ); 1902 #endif 1903 1904 // Restore TPL and return 1905 exit_unlock: 1906 gBS->RestoreTPL (SavedTpl); 1907 return Status; 1908 } 1909 1910 1911 /* 1912 ** UEFI Receive() function 1913 ** 1914 */ 1915 EFI_STATUS 1916 EFIAPI 1917 SnpReceive ( 1918 IN EFI_SIMPLE_NETWORK_PROTOCOL *Snp, 1919 OUT UINTN *HdrSize OPTIONAL, 1920 IN OUT UINTN *BuffSize, 1921 OUT VOID *Data, 1922 OUT EFI_MAC_ADDRESS *SrcAddr OPTIONAL, 1923 OUT EFI_MAC_ADDRESS *DstAddr OPTIONAL, 1924 OUT UINT16 *Protocol OPTIONAL 1925 ) 1926 { 1927 EFI_TPL SavedTpl; 1928 EFI_STATUS Status; 1929 LAN91X_DRIVER *LanDriver; 1930 UINT8 *DataPtr; 1931 UINT16 PktStatus; 1932 UINT16 PktLength; 1933 UINT16 PktControl; 1934 UINT8 IstReg; 1935 1936 // Check preliminaries 1937 if ((Snp == NULL) || (Data == NULL)) { 1938 return EFI_INVALID_PARAMETER; 1939 } 1940 1941 // Serialize access to data and registers 1942 SavedTpl = gBS->RaiseTPL (LAN91X_TPL); 1943 1944 // Check that driver was started and initialised 1945 switch (Snp->Mode->State) { 1946 case EfiSimpleNetworkInitialized: 1947 break; 1948 case EfiSimpleNetworkStarted: 1949 DEBUG((EFI_D_WARN, "LAN91x: Driver not yet initialized\n")); 1950 ReturnUnlock (EFI_DEVICE_ERROR); 1951 case EfiSimpleNetworkStopped: 1952 DEBUG((EFI_D_WARN, "LAN91x: Driver not started\n")); 1953 ReturnUnlock (EFI_NOT_STARTED); 1954 default: 1955 DEBUG((EFI_D_ERROR, "LAN91x: Driver in an invalid state: %u\n", 1956 (UINTN)Snp->Mode->State)); 1957 ReturnUnlock (EFI_DEVICE_ERROR); 1958 } 1959 1960 // Find the LanDriver structure 1961 LanDriver = INSTANCE_FROM_SNP_THIS(Snp); 1962 1963 // Check for Rx Overrun 1964 IstReg = ReadIoReg8 (LanDriver, LAN91X_IST); 1965 if ((IstReg & IST_RX_OVRN) != 0) { 1966 LanDriver->Stats.RxTotalFrames += 1; 1967 LanDriver->Stats.RxDroppedFrames += 1; 1968 WriteIoReg8 (LanDriver, LAN91X_IST, IST_RX_OVRN); 1969 DEBUG((EFI_D_WARN, "LAN91x: Receiver overrun\n")); 1970 } 1971 1972 // Check for Rx data available 1973 if ((IstReg & IST_RCV) == 0) { 1974 ReturnUnlock (EFI_NOT_READY); 1975 } 1976 1977 // Configure the PTR register for reading 1978 WriteIoReg16 (LanDriver, LAN91X_PTR, PTR_RCV | PTR_AUTO_INCR | PTR_READ); 1979 1980 // Read the Packet Status and Packet Length words 1981 PktStatus = ReadIoReg16 (LanDriver, LAN91X_DATA0); 1982 PktLength = ReadIoReg16 (LanDriver, LAN91X_DATA0) & BCW_COUNT; 1983 1984 // Check for valid received packet 1985 if ((PktStatus == 0) && (PktLength == 0)) { 1986 DEBUG((EFI_D_WARN, "LAN91x: Received zero-length packet. IST=%04x\n", IstReg)); 1987 ReturnUnlock (EFI_NOT_READY); 1988 } 1989 LanDriver->Stats.RxTotalFrames += 1; 1990 1991 // Check if we got a CRC error 1992 if ((PktStatus & RX_BAD_CRC) != 0) { 1993 DEBUG((EFI_D_WARN, "LAN91x: Received frame CRC error\n")); 1994 LanDriver->Stats.RxCrcErrorFrames += 1; 1995 LanDriver->Stats.RxDroppedFrames += 1; 1996 Status = EFI_DEVICE_ERROR; 1997 goto exit_release; 1998 } 1999 2000 // Check if we got a too-short frame 2001 if ((PktStatus & RX_TOO_SHORT) != 0) { 2002 DEBUG((EFI_D_WARN, "LAN91x: Received frame too short (%d bytes)\n", PktLength)); 2003 LanDriver->Stats.RxUndersizeFrames += 1; 2004 LanDriver->Stats.RxDroppedFrames += 1; 2005 Status = EFI_DEVICE_ERROR; 2006 goto exit_release; 2007 } 2008 2009 // Check if we got a too-long frame 2010 if ((PktStatus & RX_TOO_LONG) != 0) { 2011 DEBUG((EFI_D_WARN, "LAN91x: Received frame too long (%d bytes)\n", PktLength)); 2012 LanDriver->Stats.RxOversizeFrames += 1; 2013 LanDriver->Stats.RxDroppedFrames += 1; 2014 Status = EFI_DEVICE_ERROR; 2015 goto exit_release; 2016 } 2017 2018 // Check if we got an alignment error 2019 if ((PktStatus & RX_ALGN_ERR) != 0) { 2020 DEBUG((EFI_D_WARN, "LAN91x: Received frame alignment error\n")); 2021 // Don't seem to keep track of these specifically 2022 LanDriver->Stats.RxDroppedFrames += 1; 2023 Status = EFI_DEVICE_ERROR; 2024 goto exit_release; 2025 } 2026 2027 // Classify the received fram 2028 if ((PktStatus & RX_MULTICAST) != 0) { 2029 LanDriver->Stats.RxMulticastFrames += 1; 2030 } else if ((PktStatus & RX_BROADCAST) != 0) { 2031 LanDriver->Stats.RxBroadcastFrames += 1; 2032 } else { 2033 LanDriver->Stats.RxUnicastFrames += 1; 2034 } 2035 2036 // Calculate the received packet data length 2037 PktLength -= LAN91X_PKT_OVERHEAD; 2038 if ((PktStatus & RX_ODD_FRAME) != 0) { 2039 PktLength += 1; 2040 } 2041 2042 // Check buffer size 2043 if (*BuffSize < PktLength) { 2044 DEBUG((EFI_D_WARN, "LAN91x: Receive buffer too small for packet (%d < %d)\n", 2045 *BuffSize, PktLength)); 2046 *BuffSize = PktLength; 2047 Status = EFI_BUFFER_TOO_SMALL; 2048 goto exit_release; 2049 } 2050 2051 // Transfer the data bytes 2052 DataPtr = Data; 2053 ReadIoData (LanDriver, DataPtr, PktLength & ~0x0001); 2054 2055 // Read the PktControl and Odd Byte from the FIFO 2056 PktControl = ReadIoReg16 (LanDriver, LAN91X_DATA0); 2057 if ((PktControl & PCW_ODD) != 0) { 2058 DataPtr[PktLength - 1] = PktControl & PCW_ODD_BYTE; 2059 } 2060 2061 // Update buffer size 2062 *BuffSize = PktLength; 2063 2064 if (HdrSize != NULL) { 2065 *HdrSize = LanDriver->SnpMode.MediaHeaderSize; 2066 } 2067 2068 // Extract the destination address 2069 if (DstAddr != NULL) { 2070 CopyMem (DstAddr, &DataPtr[0], NET_ETHER_ADDR_LEN); 2071 } 2072 2073 // Get the source address 2074 if (SrcAddr != NULL) { 2075 CopyMem (SrcAddr, &DataPtr[6], NET_ETHER_ADDR_LEN); 2076 } 2077 2078 // Get the protocol 2079 if (Protocol != NULL) { 2080 *Protocol = NTOHS (*(UINT16*)(&DataPtr[12])); 2081 } 2082 2083 // Update the Rx statistics 2084 LanDriver->Stats.RxTotalBytes += PktLength; 2085 LanDriver->Stats.RxGoodFrames += 1; 2086 Status = EFI_SUCCESS; 2087 2088 #if LAN91X_PRINT_PACKET_HEADERS 2089 // Dump the packet header 2090 DEBUG((EFI_D_ERROR, "LAN91X:SnpReceive()\n")); 2091 DEBUG((EFI_D_ERROR, " HdrSize: %p, SrcAddr: %p, DstAddr: %p, Protocol: %p\n", 2092 HdrSize, SrcAddr, DstAddr, Protocol)); 2093 DEBUG((EFI_D_ERROR, " Length: %d, Last byte: %02x\n", PktLength, DataPtr[PktLength - 1])); 2094 PrintIpDgram (&DataPtr[0], &DataPtr[6], &DataPtr[12], &DataPtr[14]); 2095 #endif 2096 2097 // Release the FIFO buffer 2098 exit_release: 2099 MmuOperation (LanDriver, MMUCR_OP_RX_POP_REL); 2100 2101 // Restore TPL and return 2102 exit_unlock: 2103 gBS->RestoreTPL (SavedTpl); 2104 return Status; 2105 } 2106 2107 2108 /*------------------ Driver Execution Environment main entry point ------------------*/ 2109 2110 /* 2111 ** Entry point for the LAN91x driver 2112 ** 2113 */ 2114 EFI_STATUS 2115 Lan91xDxeEntry ( 2116 IN EFI_HANDLE Handle, 2117 IN EFI_SYSTEM_TABLE *SystemTable 2118 ) 2119 { 2120 EFI_STATUS Status; 2121 LAN91X_DRIVER *LanDriver; 2122 EFI_SIMPLE_NETWORK_PROTOCOL *Snp; 2123 EFI_SIMPLE_NETWORK_MODE *SnpMode; 2124 LAN91X_DEVICE_PATH *Lan91xPath; 2125 2126 // The PcdLan91xDxeBaseAddress PCD must be defined 2127 ASSERT(PcdGet32 (PcdLan91xDxeBaseAddress) != 0); 2128 2129 // Allocate Resources 2130 LanDriver = AllocateZeroPool (sizeof(LAN91X_DRIVER)); 2131 Lan91xPath = AllocateCopyPool (sizeof(LAN91X_DEVICE_PATH), &Lan91xPathTemplate); 2132 2133 // Initialize I/O Space access info 2134 LanDriver->IoBase = PcdGet32 (PcdLan91xDxeBaseAddress); 2135 LanDriver->PhyAd = LAN91X_NO_PHY; 2136 LanDriver->BankSel = 0xff; 2137 2138 // Initialize pointers 2139 Snp = &(LanDriver->Snp); 2140 SnpMode = &(LanDriver->SnpMode); 2141 Snp->Mode = SnpMode; 2142 2143 // Set the signature of the LAN Driver structure 2144 LanDriver->Signature = LAN91X_SIGNATURE; 2145 2146 // Probe the device 2147 Status = Probe (LanDriver); 2148 if (EFI_ERROR(Status)) { 2149 DEBUG((EFI_D_ERROR, "LAN91x:Lan91xDxeEntry(): Probe failed with status %d\n", Status)); 2150 return Status; 2151 } 2152 2153 #ifdef LAN91X_PRINT_REGISTERS 2154 PrintIoRegisters (LanDriver); 2155 PrintPhyRegisters (LanDriver); 2156 #endif 2157 2158 // Assign fields and func pointers 2159 Snp->Revision = EFI_SIMPLE_NETWORK_PROTOCOL_REVISION; 2160 Snp->WaitForPacket = NULL; 2161 Snp->Initialize = SnpInitialize; 2162 Snp->Start = SnpStart; 2163 Snp->Stop = SnpStop; 2164 Snp->Reset = SnpReset; 2165 Snp->Shutdown = SnpShutdown; 2166 Snp->ReceiveFilters = SnpReceiveFilters; 2167 Snp->StationAddress = SnpStationAddress; 2168 Snp->Statistics = SnpStatistics; 2169 Snp->MCastIpToMac = SnpMcastIptoMac; 2170 Snp->NvData = SnpNvData; 2171 Snp->GetStatus = SnpGetStatus; 2172 Snp->Transmit = SnpTransmit; 2173 Snp->Receive = SnpReceive; 2174 2175 // Fill in simple network mode structure 2176 SnpMode->State = EfiSimpleNetworkStopped; 2177 SnpMode->HwAddressSize = NET_ETHER_ADDR_LEN; // HW address is 6 bytes 2178 SnpMode->MediaHeaderSize = sizeof(ETHER_HEAD); // Size of an Ethernet header 2179 SnpMode->MaxPacketSize = EFI_PAGE_SIZE; // Ethernet Frame (with VLAN tag +4 bytes) 2180 2181 // Supported receive filters 2182 SnpMode->ReceiveFilterMask = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST | 2183 EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST | 2184 EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST | 2185 EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS | 2186 EFI_SIMPLE_NETWORK_RECEIVE_PROMISCUOUS_MULTICAST; 2187 2188 // Initially-enabled receive filters 2189 SnpMode->ReceiveFilterSetting = EFI_SIMPLE_NETWORK_RECEIVE_UNICAST | 2190 EFI_SIMPLE_NETWORK_RECEIVE_MULTICAST | 2191 EFI_SIMPLE_NETWORK_RECEIVE_BROADCAST; 2192 2193 // LAN91x has 64bit hash table. We can filter an infinite MACs, but 2194 // higher-level software must filter out any hash collisions. 2195 SnpMode->MaxMCastFilterCount = MAX_MCAST_FILTER_CNT; 2196 SnpMode->MCastFilterCount = 0; 2197 ZeroMem (&SnpMode->MCastFilter, MAX_MCAST_FILTER_CNT * sizeof(EFI_MAC_ADDRESS)); 2198 2199 // Set the interface type (1: Ethernet or 6: IEEE 802 Networks) 2200 SnpMode->IfType = NET_IFTYPE_ETHERNET; 2201 2202 // Mac address is changeable 2203 SnpMode->MacAddressChangeable = TRUE; 2204 2205 // We can only transmit one packet at a time 2206 SnpMode->MultipleTxSupported = FALSE; 2207 2208 // MediaPresent checks for cable connection and partner link 2209 SnpMode->MediaPresentSupported = TRUE; 2210 SnpMode->MediaPresent = FALSE; 2211 2212 // Set broadcast address 2213 SetMem (&SnpMode->BroadcastAddress, sizeof (EFI_MAC_ADDRESS), 0xFF); 2214 2215 // Assign fields for device path 2216 Lan91xPath->Lan91x.MacAddress = SnpMode->PermanentAddress; 2217 Lan91xPath->Lan91x.IfType = SnpMode->IfType; 2218 2219 // Initialise the protocol 2220 Status = gBS->InstallMultipleProtocolInterfaces ( 2221 &LanDriver->ControllerHandle, 2222 &gEfiSimpleNetworkProtocolGuid, Snp, 2223 &gEfiDevicePathProtocolGuid, Lan91xPath, 2224 NULL 2225 ); 2226 2227 // Say what the status of loading the protocol structure is 2228 if (EFI_ERROR(Status)) { 2229 FreePool (LanDriver); 2230 } 2231 2232 return Status; 2233 } 2234