Skip to content

Commit

Permalink
NetworkPkg/UefiPxeBcDxe: Configure the ARP Instance/RouteTable with n…
Browse files Browse the repository at this point in the history
…ew address

After completed a DHCP D.O.R.A process and got the new address, the ARP Instance
and RouteTable should be configured so as to avoid the later Pxe.Arp failure.

Cc: Fu Siyuan <[email protected]>
Cc: Ye Ting <[email protected]>
Contributed-under: TianoCore Contribution Agreement 1.0
Signed-off-by: Jiaxin Wu <[email protected]>
Reviewed-by: Fu Siyuan <[email protected]>
  • Loading branch information
jiaxinwu committed Mar 22, 2018
1 parent 07bd82d commit 2f1b849
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 40 deletions.
26 changes: 4 additions & 22 deletions NetworkPkg/UefiPxeBcDxe/PxeBcImpl.c
Original file line number Diff line number Diff line change
Expand Up @@ -2003,7 +2003,6 @@ EfiPxeBcSetStationIP (
EFI_STATUS Status;
PXEBC_PRIVATE_DATA *Private;
EFI_PXE_BASE_CODE_MODE *Mode;
EFI_ARP_CONFIG_DATA ArpConfigData;

if (This == NULL) {
return EFI_INVALID_PARAMETER;
Expand Down Expand Up @@ -2043,27 +2042,6 @@ EfiPxeBcSetStationIP (
if (EFI_ERROR (Status)) {
goto ON_EXIT;
}
} else if (!Mode->UsingIpv6 && NewStationIp != NULL) {
//
// Configure the corresponding ARP with the IPv4 address.
//
ZeroMem (&ArpConfigData, sizeof (EFI_ARP_CONFIG_DATA));

ArpConfigData.SwAddressType = 0x0800;
ArpConfigData.SwAddressLength = (UINT8) sizeof (EFI_IPv4_ADDRESS);
ArpConfigData.StationAddress = &NewStationIp->v4;

Private->Arp->Configure (Private->Arp, NULL);
Private->Arp->Configure (Private->Arp, &ArpConfigData);

if (NewSubnetMask != NULL) {
Mode->RouteTableEntries = 1;
Mode->RouteTable[0].IpAddr.Addr[0] = NewStationIp->Addr[0] & NewSubnetMask->Addr[0];
Mode->RouteTable[0].SubnetMask.Addr[0] = NewSubnetMask->Addr[0];
Mode->RouteTable[0].GwAddr.Addr[0] = 0;
}

Private->IsAddressOk = TRUE;
}

if (NewStationIp != NULL) {
Expand All @@ -2077,6 +2055,10 @@ EfiPxeBcSetStationIP (
}

Status = PxeBcFlushStationIp (Private, NewStationIp, NewSubnetMask);
if (!EFI_ERROR (Status)) {
Private->IsAddressOk = TRUE;
}

ON_EXIT:
return Status;
}
Expand Down
66 changes: 48 additions & 18 deletions NetworkPkg/UefiPxeBcDxe/PxeBcSupport.c
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
/** @file
Support functions implementation for UefiPxeBc Driver.
Copyright (c) 2007 - 2017, Intel Corporation. All rights reserved.<BR>
Copyright (c) 2007 - 2018, Intel Corporation. All rights reserved.<BR>
This program and the accompanying materials
are licensed and made available under the terms and conditions of the BSD License
Expand Down Expand Up @@ -36,17 +36,19 @@ PxeBcFlushStationIp (
{
EFI_PXE_BASE_CODE_MODE *Mode;
EFI_STATUS Status;
EFI_ARP_CONFIG_DATA ArpConfigData;

Mode = Private->PxeBc.Mode;
Status = EFI_SUCCESS;
ZeroMem (&ArpConfigData, sizeof (EFI_ARP_CONFIG_DATA));

if (Mode->UsingIpv6) {

if (StationIp != NULL) {
CopyMem (&Private->Udp6CfgData.StationAddress, StationIp, sizeof (EFI_IPv6_ADDRESS));
CopyMem (&Private->Ip6CfgData.StationAddress, StationIp, sizeof (EFI_IPv6_ADDRESS));
}

if (Mode->UsingIpv6 && StationIp != NULL) {
//
// Overwrite Udp6CfgData/Ip6CfgData StationAddress.
//
CopyMem (&Private->Udp6CfgData.StationAddress, StationIp, sizeof (EFI_IPv6_ADDRESS));
CopyMem (&Private->Ip6CfgData.StationAddress, StationIp, sizeof (EFI_IPv6_ADDRESS));
//
// Reconfigure the Ip6 instance to capture background ICMP6 packets with new station Ip address.
//
Expand All @@ -61,27 +63,55 @@ PxeBcFlushStationIp (
Status = Private->Ip6->Receive (Private->Ip6, &Private->Icmp6Token);
} else {
if (StationIp != NULL) {
//
// Reconfigure the ARP instance with station Ip address.
//
ArpConfigData.SwAddressType = 0x0800;
ArpConfigData.SwAddressLength = (UINT8) sizeof (EFI_IPv4_ADDRESS);
ArpConfigData.StationAddress = StationIp;

Private->Arp->Configure (Private->Arp, NULL);
Private->Arp->Configure (Private->Arp, &ArpConfigData);

//
// Overwrite Udp4CfgData/Ip4CfgData StationAddress.
//
CopyMem (&Private->Udp4CfgData.StationAddress, StationIp, sizeof (EFI_IPv4_ADDRESS));
CopyMem (&Private->Ip4CfgData.StationAddress, StationIp, sizeof (EFI_IPv4_ADDRESS));
}

if (SubnetMask != NULL) {
//
// Overwrite Udp4CfgData/Ip4CfgData SubnetMask.
//
CopyMem (&Private->Udp4CfgData.SubnetMask, SubnetMask, sizeof (EFI_IPv4_ADDRESS));
CopyMem (&Private->Ip4CfgData.SubnetMask, SubnetMask, sizeof (EFI_IPv4_ADDRESS));
}

//
// Reconfigure the Ip4 instance to capture background ICMP packets with new station Ip address.
//
Private->Ip4->Cancel (Private->Ip4, &Private->IcmpToken);
Private->Ip4->Configure (Private->Ip4, NULL);

Status = Private->Ip4->Configure (Private->Ip4, &Private->Ip4CfgData);
if (EFI_ERROR (Status)) {
goto ON_EXIT;
if (StationIp != NULL && SubnetMask != NULL) {
//
// Updated the route table.
//
Mode->RouteTableEntries = 1;
Mode->RouteTable[0].IpAddr.Addr[0] = StationIp->Addr[0] & SubnetMask->Addr[0];
Mode->RouteTable[0].SubnetMask.Addr[0] = SubnetMask->Addr[0];
Mode->RouteTable[0].GwAddr.Addr[0] = 0;
}

if (StationIp != NULL || SubnetMask != NULL) {
//
// Reconfigure the Ip4 instance to capture background ICMP packets with new station Ip address.
//
Private->Ip4->Cancel (Private->Ip4, &Private->IcmpToken);
Private->Ip4->Configure (Private->Ip4, NULL);

Status = Private->Ip4->Receive (Private->Ip4, &Private->IcmpToken);
Status = Private->Ip4->Configure (Private->Ip4, &Private->Ip4CfgData);
if (EFI_ERROR (Status)) {
goto ON_EXIT;
}

Status = Private->Ip4->Receive (Private->Ip4, &Private->IcmpToken);
}
}

ON_EXIT:
Expand Down

0 comments on commit 2f1b849

Please sign in to comment.