]> git.proxmox.com Git - mirror_edk2.git/blobdiff - MdeModulePkg/Universal/Network/PxeBcDxe/Pxe_bc_ip.c
remove EFI 1.10 network stack.
[mirror_edk2.git] / MdeModulePkg / Universal / Network / PxeBcDxe / Pxe_bc_ip.c
diff --git a/MdeModulePkg/Universal/Network/PxeBcDxe/Pxe_bc_ip.c b/MdeModulePkg/Universal/Network/PxeBcDxe/Pxe_bc_ip.c
deleted file mode 100644 (file)
index e05440d..0000000
+++ /dev/null
@@ -1,844 +0,0 @@
-/** @file\r
-\r
-Copyright (c) 2004, Intel Corporation\r
-All rights reserved. This program and the accompanying materials\r
-are licensed and made available under the terms and conditions of the BSD License\r
-which accompanies this distribution.  The full text of the license may be found at\r
-http://opensource.org/licenses/bsd-license.php\r
-\r
-THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
-WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
-\r
-Module Name:\r
-  pxe_bc_ip.c\r
-\r
-Abstract:\r
-\r
-\r
-**/\r
-\r
-#include "Bc.h"\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-/**\r
-  Check if two IP addresses are on the same subnet.\r
-\r
-  @param  IpLength     Length of IP address in bytes.\r
-  @param  Ip1          IP address to check.\r
-  @param  Ip2          IP address to check.\r
-  @param  SubnetMask   Subnet mask to check with.\r
-\r
-  @retval TRUE         IP addresses are on the same subnet.\r
-  @retval FALSE        IP addresses are on different subnets.\r
-\r
-**/\r
-BOOLEAN\r
-OnSameSubnet (\r
-  IN UINTN           IpLength,\r
-  IN EFI_IP_ADDRESS  *Ip1,\r
-  IN EFI_IP_ADDRESS  *Ip2,\r
-  IN EFI_IP_ADDRESS  *SubnetMask\r
-  )\r
-{\r
-  if (IpLength == 0 || Ip1 == NULL || Ip2 == NULL || SubnetMask == NULL) {\r
-    return FALSE;\r
-  }\r
-\r
-  while (IpLength-- != 0) {\r
-    if ((Ip1->v6.Addr[IpLength] ^ Ip2->v6.Addr[IpLength]) & SubnetMask->v6.Addr[IpLength]) {\r
-      return FALSE;\r
-    }\r
-  }\r
-\r
-  return TRUE;\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-/**\r
-  Add router to router table.\r
-\r
-  @param  Private      Pointer PxeBc instance data.\r
-  @param  RouterIpPtr  Pointer to router IP address.\r
-\r
-  @return Nothing\r
-\r
-**/\r
-VOID\r
-IpAddRouter (\r
-  IN PXE_BASECODE_DEVICE *Private,\r
-  IN EFI_IP_ADDRESS      *RouterIpPtr\r
-  )\r
-{\r
-  EFI_PXE_BASE_CODE_MODE  *PxeBcMode;\r
-  UINTN                   Index;\r
-\r
-  if (Private == NULL || RouterIpPtr == NULL) {\r
-    return ;\r
-  }\r
-\r
-  PxeBcMode = Private->EfiBc.Mode;\r
-\r
-  //\r
-  // if we are filled up or this is not on the same subnet, forget it\r
-  //\r
-  if ((PxeBcMode->RouteTableEntries == PXE_ROUTER_TABLE_SIZE) ||\r
-    !OnSameSubnet(Private->IpLength, &PxeBcMode->StationIp, RouterIpPtr, &PxeBcMode->SubnetMask)) {\r
-    return ;\r
-  }\r
-  //\r
-  // make sure we don't already have it\r
-  //\r
-  for (Index = 0; Index < PxeBcMode->RouteTableEntries; ++Index) {\r
-    if (!CompareMem (\r
-          &PxeBcMode->RouteTable[Index].GwAddr,\r
-          RouterIpPtr,\r
-          Private->IpLength\r
-          )) {\r
-      return ;\r
-    }\r
-  }\r
-  //\r
-  // keep it\r
-  //\r
-  ZeroMem (\r
-    &PxeBcMode->RouteTable[PxeBcMode->RouteTableEntries],\r
-    sizeof (EFI_PXE_BASE_CODE_ROUTE_ENTRY)\r
-    );\r
-\r
-  CopyMem (\r
-    &PxeBcMode->RouteTable[PxeBcMode->RouteTableEntries++].GwAddr,\r
-    RouterIpPtr,\r
-    Private->IpLength\r
-    );\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// return router ip to use for DestIp (0 if none)\r
-//\r
-EFI_IP_ADDRESS *\r
-GetRouterIp (\r
-  PXE_BASECODE_DEVICE *Private,\r
-  EFI_IP_ADDRESS      *DestIpPtr\r
-  )\r
-{\r
-  EFI_PXE_BASE_CODE_MODE  *PxeBcMode;\r
-  UINTN                   Index;\r
-\r
-  if (Private == NULL || DestIpPtr == NULL) {\r
-    return NULL;\r
-  }\r
-\r
-  PxeBcMode = Private->EfiBc.Mode;\r
-\r
-  for (Index = 0; Index < PxeBcMode->RouteTableEntries; ++Index) {\r
-    if (OnSameSubnet (\r
-          Private->IpLength,\r
-          &PxeBcMode->RouteTable[Index].IpAddr,\r
-          DestIpPtr,\r
-          &PxeBcMode->RouteTable[Index].SubnetMask\r
-          )) {\r
-      return &PxeBcMode->RouteTable[Index].GwAddr;\r
-    }\r
-  }\r
-\r
-  return NULL;\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// routine to send ipv4 packet\r
-// ipv4 header of length HdrLth in TransmitBufferPtr\r
-// routine fills in ipv4hdr Ver_Hdl, TotalLength, and Checksum, moves in Data\r
-// and gets dest MAC address\r
-//\r
-#define IP_TX_BUFFER  ((IPV4_BUFFER *) Private->TransmitBufferPtr)\r
-#define IP_TX_HEADER  IP_TX_BUFFER->IpHeader\r
-\r
-EFI_STATUS\r
-Ipv4Xmt (\r
-  PXE_BASECODE_DEVICE         *Private,\r
-  UINT32                      GatewayIp,\r
-  UINTN                       IpHeaderLength,\r
-  UINTN                       TotalHeaderLength,\r
-  VOID                        *Data,\r
-  UINTN                       DataLength,\r
-  EFI_PXE_BASE_CODE_FUNCTION  Function\r
-  )\r
-{\r
-  EFI_MAC_ADDRESS             DestMac;\r
-  EFI_SIMPLE_NETWORK_PROTOCOL *Snp;\r
-  EFI_PXE_BASE_CODE_MODE      *PxeBcMode;\r
-  EFI_STATUS                  StatCode;\r
-  UINTN                       PacketLength;\r
-\r
-  Snp           = Private->SimpleNetwork;\r
-  PxeBcMode     = Private->EfiBc.Mode;\r
-  StatCode      = EFI_SUCCESS;\r
-  PacketLength  = TotalHeaderLength + DataLength;\r
-\r
-  //\r
-  // get dest MAC address\r
-  // multicast - convert to hw equiv\r
-  // unicast on same net, use arp\r
-  // on different net, arp for router\r
-  //\r
-  if (IP_TX_HEADER.DestAddr.L == BROADCAST_IPv4) {\r
-    CopyMem (&DestMac, &Snp->Mode->BroadcastAddress, sizeof (DestMac));\r
-  } else if (IS_MULTICAST (&IP_TX_HEADER.DestAddr)) {\r
-    StatCode = (*Snp->MCastIpToMac) (Snp, PxeBcMode->UsingIpv6, (EFI_IP_ADDRESS *) &IP_TX_HEADER.DestAddr, &DestMac);\r
-  } else {\r
-    UINT32  Ip;\r
-\r
-    if (OnSameSubnet (\r
-          Private->IpLength,\r
-          &PxeBcMode->StationIp,\r
-          (EFI_IP_ADDRESS *) &IP_TX_HEADER.DestAddr,\r
-          &PxeBcMode->SubnetMask\r
-          )) {\r
-      Ip = IP_TX_HEADER.DestAddr.L;\r
-    } else if (GatewayIp != 0) {\r
-      Ip = GatewayIp;\r
-    } else {\r
-      EFI_IP_ADDRESS  *TmpIp;\r
-\r
-      TmpIp = GetRouterIp (Private, (EFI_IP_ADDRESS *) &IP_TX_HEADER.DestAddr);\r
-\r
-      if (TmpIp == NULL) {\r
-        DEBUG (\r
-          (DEBUG_WARN,\r
-          "\nIpv4Xmit()  Exit #1  %xh (%r)",\r
-          EFI_NO_RESPONSE,\r
-          EFI_NO_RESPONSE)\r
-          );\r
-\r
-        return EFI_NO_RESPONSE;\r
-        //\r
-        // no router\r
-        //\r
-      }\r
-\r
-      Ip = TmpIp->Addr[0];\r
-    }\r
-\r
-    if (!GetHwAddr (\r
-          Private,\r
-          (EFI_IP_ADDRESS *) &Ip,\r
-          (EFI_MAC_ADDRESS *) &DestMac\r
-          )) {\r
-      if (!PxeBcMode->AutoArp) {\r
-        DEBUG (\r
-          (DEBUG_WARN,\r
-          "\nIpv4Xmit()  Exit #2  %xh (%r)",\r
-          EFI_DEVICE_ERROR,\r
-          EFI_DEVICE_ERROR)\r
-          );\r
-\r
-        return EFI_DEVICE_ERROR;\r
-      } else {\r
-        StatCode = DoArp (\r
-                    Private,\r
-                    (EFI_IP_ADDRESS *) &Ip,\r
-                    (EFI_MAC_ADDRESS *) &DestMac\r
-                    );\r
-      }\r
-    }\r
-  }\r
-\r
-  if (EFI_ERROR (StatCode)) {\r
-    DEBUG ((DEBUG_WARN, "\nIpv4Xmit()  Exit #3  %xh (%r)", StatCode, StatCode));\r
-    return StatCode;\r
-  }\r
-  //\r
-  // fill in packet info\r
-  //\r
-  SET_IPV4_VER_HDL (&IP_TX_HEADER, IpHeaderLength);\r
-  IP_TX_HEADER.TotalLength    = HTONS (PacketLength);\r
-  IP_TX_HEADER.HeaderChecksum = IpChecksum ((UINT16 *) &IP_TX_HEADER, IpHeaderLength);\r
-  CopyMem (((UINT8 *) &IP_TX_HEADER) + TotalHeaderLength, Data, DataLength);\r
-\r
-  //\r
-  // send it\r
-  //\r
-  return SendPacket (\r
-          Private,\r
-          (UINT8 *) &IP_TX_HEADER - Snp->Mode->MediaHeaderSize,\r
-          &IP_TX_HEADER,\r
-          PacketLength,\r
-          &DestMac,\r
-          PXE_PROTOCOL_ETHERNET_IP,\r
-          Function\r
-          );\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// send ipv4 packet with option\r
-//\r
-EFI_STATUS\r
-Ipv4SendWOp (\r
-  PXE_BASECODE_DEVICE         *Private,\r
-  UINT32                      GatewayIp,\r
-  UINT8                       *Msg,\r
-  UINTN                       MessageLength,\r
-  UINT8                       Prot,\r
-  UINT8                       *Option,\r
-  UINTN                       OptionLength,\r
-  UINT32                      DestIp,\r
-  EFI_PXE_BASE_CODE_FUNCTION  Function\r
-  )\r
-{\r
-  EFI_PXE_BASE_CODE_MODE  *PxeBcMode;\r
-  UINTN                   HdrLth;\r
-\r
-  PxeBcMode = Private->EfiBc.Mode;\r
-  HdrLth    = sizeof (IPV4_HEADER) + OptionLength;\r
-\r
-  ZeroMem ((VOID *) &IP_TX_HEADER, sizeof (IPV4_HEADER));\r
-  IP_TX_HEADER.TimeToLive     = PxeBcMode->TTL;\r
-  IP_TX_HEADER.TypeOfService  = PxeBcMode->ToS;\r
-  IP_TX_HEADER.Protocol       = Prot;\r
-  IP_TX_HEADER.SrcAddr.L      = *(UINT32 *) &PxeBcMode->StationIp;\r
-  IP_TX_HEADER.DestAddr.L     = DestIp;\r
-  IP_TX_HEADER.Id             = Random (Private);\r
-  CopyMem (IP_TX_BUFFER->u.Data, Option, OptionLength);\r
-  return Ipv4Xmt (\r
-          Private,\r
-          GatewayIp,\r
-          HdrLth,\r
-          HdrLth,\r
-          Msg,\r
-          MessageLength,\r
-          Function\r
-          );\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// send MessageLength message at MessagePtr - higher level protocol header already in TransmitBufferPtr, length HdrSize\r
-//\r
-EFI_STATUS\r
-Ip4Send (\r
-  PXE_BASECODE_DEVICE                          *Private,  // pointer to instance data\r
-  UINTN               MayFrag,                            //\r
-  UINT8                                    Prot,          // protocol\r
-  UINT32                          SrcIp,                  // Source IP address\r
-  UINT32                 DestIp,                          // Destination IP address\r
-  UINT32              GatewayIp,                          // used if not NULL and needed\r
-  UINTN               HdrSize,                            // protocol header byte length\r
-  UINT8               *MessagePtr,                        // pointer to data\r
-  UINTN               MessageLength                       // data byte length\r
-  )\r
-{\r
-  EFI_STATUS  StatCode;\r
-  UINTN       TotDataLength;\r
-\r
-  TotDataLength = HdrSize + MessageLength;\r
-\r
-  if (TotDataLength > MAX_IPV4_DATA_SIZE) {\r
-    DEBUG (\r
-      (DEBUG_WARN,\r
-      "\nIp4Send()  Exit #1  %xh (%r)",\r
-      EFI_BAD_BUFFER_SIZE,\r
-      EFI_BAD_BUFFER_SIZE)\r
-      );\r
-\r
-    return EFI_BAD_BUFFER_SIZE;\r
-  }\r
-\r
-  ZeroMem ((VOID *) &IP_TX_HEADER, sizeof (IPV4_HEADER));\r
-  IP_TX_HEADER.TimeToLive = DEFAULT_TTL;\r
-  IP_TX_HEADER.Protocol   = Prot;\r
-  IP_TX_HEADER.SrcAddr.L  = SrcIp;\r
-  IP_TX_HEADER.DestAddr.L = DestIp;\r
-  IP_TX_HEADER.Id         = Random (Private);\r
-\r
-  if (!MayFrag) {\r
-    *(UINT8 *) (&IP_TX_HEADER.FragmentFields) = IP_NO_FRAG >> 8;\r
-  }\r
-  //\r
-  // check for need to fragment\r
-  //\r
-  if (TotDataLength > MAX_IPV4_FRAME_DATA_SIZE) {\r
-    UINTN   DataLengthSent;\r
-    UINT16  FragmentOffset;\r
-\r
-    FragmentOffset = IP_MORE_FRAG;\r
-    //\r
-    // frag offset field\r
-    //\r
-    if (!MayFrag) {\r
-      DEBUG (\r
-        (DEBUG_WARN,\r
-        "\nIp4Send()  Exit #2  %xh (%r)",\r
-        EFI_BAD_BUFFER_SIZE,\r
-        EFI_BAD_BUFFER_SIZE)\r
-        );\r
-\r
-      return EFI_BAD_BUFFER_SIZE;\r
-    }\r
-    //\r
-    // send out in fragments - first includes upper level header\r
-    // all are max and include more frag bit except last\r
-    //\r
-    * (UINT8 *) (&IP_TX_HEADER.FragmentFields) = IP_MORE_FRAG >> 8;\r
-\r
-#define IPV4_FRAG_SIZE    (MAX_IPV4_FRAME_DATA_SIZE & 0xfff8)\r
-#define IPV4_FRAG_OFF_INC (IPV4_FRAG_SIZE >> 3)\r
-\r
-    DataLengthSent = IPV4_FRAG_SIZE - HdrSize;\r
-\r
-    StatCode = Ipv4Xmt (\r
-                Private,\r
-                GatewayIp,\r
-                sizeof (IPV4_HEADER),\r
-                sizeof (IPV4_HEADER) + HdrSize,\r
-                MessagePtr,\r
-                DataLengthSent,\r
-                Private->Function\r
-                );\r
-\r
-    if (EFI_ERROR (StatCode)) {\r
-      DEBUG (\r
-        (DEBUG_WARN,\r
-        "\nIp4Send()  Exit #3  %xh (%r)",\r
-        StatCode,\r
-        StatCode)\r
-        );\r
-\r
-      return StatCode;\r
-    }\r
-\r
-    MessagePtr += DataLengthSent;\r
-    MessageLength -= DataLengthSent;\r
-    FragmentOffset += IPV4_FRAG_OFF_INC;\r
-    IP_TX_HEADER.FragmentFields = HTONS (FragmentOffset);\r
-\r
-    while (MessageLength > IPV4_FRAG_SIZE) {\r
-      StatCode = Ipv4Xmt (\r
-                  Private,\r
-                  GatewayIp,\r
-                  sizeof (IPV4_HEADER),\r
-                  sizeof (IPV4_HEADER),\r
-                  MessagePtr,\r
-                  IPV4_FRAG_SIZE,\r
-                  Private->Function\r
-                  );\r
-\r
-      if (EFI_ERROR (StatCode)) {\r
-        DEBUG (\r
-          (DEBUG_WARN,\r
-          "\nIp4Send()  Exit #3  %xh (%r)",\r
-          StatCode,\r
-          StatCode)\r
-          );\r
-\r
-        return StatCode;\r
-      }\r
-\r
-      MessagePtr += IPV4_FRAG_SIZE;\r
-      MessageLength -= IPV4_FRAG_SIZE;\r
-      FragmentOffset += IPV4_FRAG_OFF_INC;\r
-      IP_TX_HEADER.FragmentFields = HTONS (FragmentOffset);\r
-    }\r
-\r
-    * (UINT8 *) (&IP_TX_HEADER.FragmentFields) &= ~(IP_MORE_FRAG >> 8);\r
-    HdrSize = 0;\r
-  }\r
-  //\r
-  // transmit\r
-  //\r
-  return Ipv4Xmt (\r
-          Private,\r
-          GatewayIp,\r
-          sizeof (IPV4_HEADER),\r
-          sizeof (IPV4_HEADER) + HdrSize,\r
-          MessagePtr,\r
-          MessageLength,\r
-          Private->Function\r
-          );\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// return true if dst IP in receive header matched with what's enabled\r
-//\r
-BOOLEAN\r
-IPgood (\r
-  PXE_BASECODE_DEVICE *Private,\r
-  IPV4_HEADER         *IpHeader\r
-  )\r
-{\r
-  EFI_PXE_BASE_CODE_MODE  *PxeBcMode;\r
-  UINTN                   Index;\r
-\r
-  PxeBcMode = Private->EfiBc.Mode;\r
-\r
-  if (PxeBcMode->IpFilter.Filters & EFI_PXE_BASE_CODE_IP_FILTER_PROMISCUOUS) {\r
-    return TRUE;\r
-  }\r
-\r
-  if ((PxeBcMode->IpFilter.Filters & EFI_PXE_BASE_CODE_IP_FILTER_PROMISCUOUS_MULTICAST) &&\r
-      IS_MULTICAST (&IpHeader->DestAddr)\r
-        ) {\r
-    return TRUE;\r
-  }\r
-\r
-  if ((PxeBcMode->IpFilter.Filters & EFI_PXE_BASE_CODE_IP_FILTER_STATION_IP) &&\r
-      PxeBcMode->StationIp.Addr[0] == IpHeader->DestAddr.L\r
-      ) {\r
-    return TRUE;\r
-  }\r
-\r
-  if ((PxeBcMode->IpFilter.Filters & EFI_PXE_BASE_CODE_IP_FILTER_BROADCAST) && IpHeader->DestAddr.L == BROADCAST_IPv4) {\r
-    return TRUE;\r
-  }\r
-\r
-  for (Index = 0; Index < PxeBcMode->IpFilter.IpCnt; ++Index) {\r
-    if (IpHeader->DestAddr.L == PxeBcMode->IpFilter.IpList[Index].Addr[0]) {\r
-      return TRUE;\r
-    }\r
-  }\r
-\r
-  return FALSE;\r
-}\r
-\r
-/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */\r
-\r
-//\r
-// receive up to MessageLength message into MessagePtr for protocol Prot\r
-// return message length, src/dest ips if select any, and pointer to protocol\r
-// header routine will filter based on source and/or dest ip if OpFlags set.\r
-//\r
-EFI_STATUS\r
-IpReceive (\r
-  PXE_BASECODE_DEVICE *Private,\r
-  PXE_OPFLAGS         OpFlags,\r
-  EFI_IP_ADDRESS      *SrcIpPtr,\r
-  EFI_IP_ADDRESS      *DestIpPtr,\r
-  UINT8               Prot,\r
-  VOID                *HeaderPtr,\r
-  UINTN               HdrSize,\r
-  UINT8               *MessagePtr,\r
-  UINTN               *MessageLengthPtr,\r
-  EFI_EVENT           TimeoutEvent\r
-  )\r
-{\r
-  EFI_PXE_BASE_CODE_MODE  *PxeBcMode;\r
-  EFI_STATUS              StatCode;\r
-  UINTN                   ByteCount;\r
-  UINTN                   FragmentCount;\r
-  UINTN                   ExpectedPacketLength;\r
-  UINTN                   Id;\r
-  BOOLEAN                 GotFirstFragment;\r
-  BOOLEAN                 GotLastFragment;\r
-\r
-  DEBUG (\r
-    (DEBUG_NET,\r
-    "\nIpReceive()  Hdr=%Xh  HdrSz=%d  Data=%Xh  DataSz=%d",\r
-    HeaderPtr,\r
-    HdrSize,\r
-    MessagePtr,\r
-    *MessageLengthPtr)\r
-    );\r
-\r
-  PxeBcMode                     = Private->EfiBc.Mode;\r
-  PxeBcMode->IcmpErrorReceived  = FALSE;\r
-\r
-  ExpectedPacketLength          = 0;\r
-  GotFirstFragment              = FALSE;\r
-  GotLastFragment               = FALSE;\r
-  FragmentCount                 = 0;\r
-  ByteCount                     = 0;\r
-  Id = 0;\r
-\r
-  for (;;) {\r
-    IPV4_HEADER IpHdr;\r
-    UINTN       FFlds;\r
-    UINTN       TotalLength;\r
-    UINTN       FragmentOffset;\r
-    UINTN       HeaderSize;\r
-    UINTN       BufferSize;\r
-    UINTN       IpHeaderLength;\r
-    UINTN       DataLength;\r
-    UINT16      Protocol;\r
-    UINT8       *NextHdrPtr;\r
-    UINT8       *PacketPtr;\r
-\r
-    StatCode = WaitForReceive (\r
-                Private,\r
-                Private->Function,\r
-                TimeoutEvent,\r
-                &HeaderSize,\r
-                &BufferSize,\r
-                &Protocol\r
-                );\r
-\r
-    if (EFI_ERROR (StatCode)) {\r
-      return StatCode;\r
-    }\r
-\r
-    PacketPtr = Private->ReceiveBufferPtr + HeaderSize;\r
-\r
-    if (Protocol == PXE_PROTOCOL_ETHERNET_ARP) {\r
-      HandleArpReceive (\r
-        Private,\r
-        (ARP_PACKET *) PacketPtr,\r
-        Private->ReceiveBufferPtr\r
-        );\r
-\r
-      continue;\r
-    }\r
-\r
-    if (Protocol != PXE_PROTOCOL_ETHERNET_IP) {\r
-      continue;\r
-    }\r
-\r
-#define IpRxHeader  ((IPV4_HEADER *) PacketPtr)\r
-\r
-    //\r
-    // filter for version & check sum\r
-    //\r
-    IpHeaderLength = IPV4_HEADER_LENGTH (IpRxHeader);\r
-\r
-    if ((IpRxHeader->VersionIhl >> 4) != IPVER4) {\r
-      continue;\r
-    }\r
-\r
-    if (IpChecksum ((UINT16 *) IpRxHeader, IpHeaderLength)) {\r
-      continue;\r
-    }\r
-\r
-    CopyMem (&IpHdr, IpRxHeader, sizeof (IpHdr));\r
-    TotalLength = NTOHS (IpHdr.TotalLength);\r
-\r
-    if (IpHdr.Protocol == PROT_TCP) {\r
-      //\r
-      // The NextHdrPtr is used to seed the header buffer we are passing back.\r
-      // That being the case, we want to see everything in pPkt which contains\r
-      // everything but the ethernet (or whatever) frame.  IP + TCP in this case.\r
-      //\r
-      DataLength  = TotalLength;\r
-      NextHdrPtr  = PacketPtr;\r
-    } else {\r
-      DataLength  = TotalLength - IpHeaderLength;\r
-      NextHdrPtr  = PacketPtr + IpHeaderLength;\r
-    }\r
-    //\r
-    // If this is an ICMP, it might not be for us.\r
-    // Double check the state of the IP stack and the\r
-    // packet fields before assuming it is an ICMP\r
-    // error.  ICMP requests are not supported by the\r
-    // PxeBc IP stack and should be ignored.\r
-    //\r
-    if (IpHdr.Protocol == PROT_ICMP) {\r
-      ICMPV4_HEADER *Icmpv4;\r
-\r
-      Icmpv4 = (ICMPV4_HEADER *) NextHdrPtr;\r
-\r
-      //\r
-      // For now only obvious ICMP error replies will be accepted by\r
-      // this stack.  This still makes us vulnerable to DoS attacks.\r
-      // But at least we will not be killed by DHCP daemons.\r
-      //\r
-      switch (Icmpv4->Type) {\r
-      case ICMP_REDIRECT:\r
-      case ICMP_ECHO:\r
-      case ICMP_ROUTER_ADV:\r
-      case ICMP_ROUTER_SOLICIT:\r
-      case ICMP_TIMESTAMP:\r
-      case ICMP_TIMESTAMP_REPLY:\r
-      case ICMP_INFO_REQ:\r
-      case ICMP_INFO_REQ_REPLY:\r
-      case ICMP_SUBNET_MASK_REQ:\r
-      case ICMP_SUBNET_MASK_REPLY:\r
-      default:\r
-        continue;\r
-\r
-      //\r
-      // %%TBD - This should be implemented.\r
-      //\r
-      case ICMP_ECHO_REPLY:\r
-        continue;\r
-\r
-      case ICMP_DEST_UNREACHABLE:\r
-      case ICMP_TIME_EXCEEDED:\r
-      case ICMP_PARAMETER_PROBLEM:\r
-      case ICMP_SOURCE_QUENCH:\r
-        PxeBcMode->IcmpErrorReceived = TRUE;\r
-\r
-        CopyMem (\r
-          &PxeBcMode->IcmpError,\r
-          NextHdrPtr,\r
-          sizeof (EFI_PXE_BASE_CODE_ICMP_ERROR)\r
-          );\r
-\r
-        DEBUG (\r
-          (DEBUG_NET,\r
-          "\nIpReceive()  Exit #1  %Xh (%r)",\r
-          EFI_ICMP_ERROR,\r
-          EFI_ICMP_ERROR)\r
-          );\r
-      }\r
-\r
-      return EFI_ICMP_ERROR;\r
-    }\r
-\r
-    if (IpHdr.Protocol == PROT_IGMP) {\r
-      HandleIgmp (Private, (IGMPV2_MESSAGE *) NextHdrPtr, DataLength);\r
-\r
-      DEBUG ((DEBUG_NET, "\n  IGMP"));\r
-      continue;\r
-    }\r
-    //\r
-    // check for protocol\r
-    //\r
-    if (IpHdr.Protocol != Prot) {\r
-      continue;\r
-    }\r
-    //\r
-    // do filtering\r
-    //\r
-    if (!(OpFlags & EFI_PXE_BASE_CODE_UDP_OPFLAGS_ANY_SRC_IP) && SrcIpPtr && SrcIpPtr->Addr[0] != IpHdr.SrcAddr.L) {\r
-      DEBUG ((DEBUG_NET, "\n  Not expected source IP address."));\r
-      continue;\r
-    }\r
-\r
-    if (OpFlags & EFI_PXE_BASE_CODE_UDP_OPFLAGS_USE_FILTER) {\r
-      if (!IPgood (Private, &IpHdr)) {\r
-        continue;\r
-      }\r
-    } else if (!(OpFlags & EFI_PXE_BASE_CODE_UDP_OPFLAGS_ANY_DEST_IP)) {\r
-      if (DestIpPtr == NULL) {\r
-        if (PxeBcMode->StationIp.Addr[0] != IpHdr.DestAddr.L) {\r
-          continue;\r
-        }\r
-      } else if (DestIpPtr->Addr[0] != IpHdr.DestAddr.L) {\r
-        continue;\r
-      }\r
-    }\r
-    //\r
-    // get some data we need\r
-    //\r
-    FFlds           = NTOHS (IpHdr.FragmentFields);\r
-    FragmentOffset  = ((FFlds & IP_FRAG_OFF_MSK) << 3);\r
-\r
-    /* Keep count of fragments that belong to this session.\r
-     * If we get packets with a different IP ID number,\r
-     * ignore them.  Ignored packets should be handled\r
-     * by the upper level protocol.\r
-     */\r
-    if (FragmentCount == 0) {\r
-      Id = IpHdr.Id;\r
-\r
-      if (DestIpPtr != NULL) {\r
-        DestIpPtr->Addr[0] = IpHdr.DestAddr.L;\r
-      }\r
-\r
-      if (SrcIpPtr != NULL) {\r
-        SrcIpPtr->Addr[0] = IpHdr.SrcAddr.L;\r
-      }\r
-    } else {\r
-      if (IpHdr.Id != Id) {\r
-        continue;\r
-      }\r
-    }\r
-\r
-    ++FragmentCount;\r
-\r
-    /* Fragment management.\r
-     */\r
-    if (FragmentOffset == 0) {\r
-      /* This is the first fragment (may also be the\r
-       * only fragment).\r
-       */\r
-      GotFirstFragment = TRUE;\r
-\r
-      /* If there is a separate protocol header buffer,\r
-       * copy the header, adjust the data pointer and\r
-       * the data length.\r
-       */\r
-      if (HdrSize != 0) {\r
-        CopyMem (HeaderPtr, NextHdrPtr, HdrSize);\r
-\r
-        NextHdrPtr += HdrSize;\r
-        DataLength -= HdrSize;\r
-      }\r
-    } else {\r
-      /* If there is a separate protocol header buffer,\r
-       * adjust the fragment offset.\r
-       */\r
-      FragmentOffset -= HdrSize;\r
-    }\r
-\r
-    /* See if this is the last fragment.\r
-     */\r
-    if (!(FFlds & IP_MORE_FRAG)) {\r
-      //\r
-      // This is the last fragment (may also be the only fragment).\r
-      //\r
-      GotLastFragment = TRUE;\r
-\r
-      /* Compute the expected length of the assembled\r
-       * packet.  This will be used to decide if we\r
-       * have gotten all of the fragments.\r
-       */\r
-      ExpectedPacketLength = FragmentOffset + DataLength;\r
-    }\r
-\r
-    DEBUG (\r
-      (DEBUG_NET,\r
-      "\n  ID = %Xh  Off = %d  Len = %d",\r
-      Id,\r
-      FragmentOffset,\r
-      DataLength)\r
-      );\r
-\r
-    /* Check for receive buffer overflow.\r
-     */\r
-    if (FragmentOffset + DataLength > *MessageLengthPtr) {\r
-      /* There is not enough space in the receive\r
-       * buffer for the fragment.\r
-       */\r
-      DEBUG (\r
-        (DEBUG_NET,\r
-        "\nIpReceive()  Exit #3  %Xh (%r)",\r
-        EFI_BUFFER_TOO_SMALL,\r
-        EFI_BUFFER_TOO_SMALL)\r
-        );\r
-\r
-      return EFI_BUFFER_TOO_SMALL;\r
-    }\r
-\r
-    /* Copy data into receive buffer.\r
-     */\r
-    if (DataLength != 0) {\r
-      DEBUG ((DEBUG_NET, "  To = %Xh", MessagePtr + FragmentOffset));\r
-\r
-      CopyMem (MessagePtr + FragmentOffset, NextHdrPtr, DataLength);\r
-      ByteCount += DataLength;\r
-    }\r
-\r
-    /* If we have seen the first and last fragments and\r
-     * the receive byte count is at least as large as the\r
-     * expected byte count, return SUCCESS.\r
-     *\r
-     * We could be tricked by receiving a fragment twice\r
-     * but the upper level protocol should figure this\r
-     * out.\r
-     */\r
-    if (GotFirstFragment && GotLastFragment && ByteCount >= ExpectedPacketLength) {\r
-      *MessageLengthPtr = ExpectedPacketLength;\r
-      return EFI_SUCCESS;\r
-    }\r
-  }\r
-}\r
-\r
-/* eof - pxe_bc_ip.c */\r