X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=NetworkPkg%2FUefiPxeBcDxe%2FPxeBcDriver.c;h=09c5753ad9e79938f1c129b350c3ad39aa9d8b2f;hb=26a7ece72189cb83b1be4bf529253ca1e7b9cb57;hp=92fd1f19df64bc9ebbf972a58dcc96adb7a5b306;hpb=8f586b85c3f617ba802e663b4b3b303e06140863;p=mirror_edk2.git
diff --git a/NetworkPkg/UefiPxeBcDxe/PxeBcDriver.c b/NetworkPkg/UefiPxeBcDxe/PxeBcDriver.c
index 92fd1f19df..09c5753ad9 100644
--- a/NetworkPkg/UefiPxeBcDxe/PxeBcDriver.c
+++ b/NetworkPkg/UefiPxeBcDxe/PxeBcDriver.c
@@ -2,7 +2,7 @@
Driver Binding functions implementationfor for UefiPxeBc Driver.
(C) Copyright 2014 Hewlett-Packard Development Company, L.P.
- Copyright (c) 2007 - 2013, Intel Corporation. All rights reserved.
+ Copyright (c) 2007 - 2016, Intel Corporation. All rights reserved.
This program and the accompanying materials
are licensed and made available under the terms and conditions of the BSD License
@@ -442,6 +442,103 @@ PxeBcDestroyIp6Children (
Private->Mode.Ipv6Available = FALSE;
}
+/**
+ Check whether UNDI protocol supports IPv6.
+
+ @param[in] ControllerHandle Controller handle.
+ @param[in] Private Pointer to PXEBC_PRIVATE_DATA.
+ @param[out] Ipv6Support TRUE if UNDI supports IPv6.
+
+ @retval EFI_SUCCESS Get the result whether UNDI supports IPv6 by NII or AIP protocol successfully.
+ @retval EFI_NOT_FOUND Don't know whether UNDI supports IPv6 since NII or AIP is not available.
+
+**/
+EFI_STATUS
+PxeBcCheckIpv6Support (
+ IN EFI_HANDLE ControllerHandle,
+ IN PXEBC_PRIVATE_DATA *Private,
+ OUT BOOLEAN *Ipv6Support
+ )
+{
+ EFI_HANDLE Handle;
+ EFI_ADAPTER_INFORMATION_PROTOCOL *Aip;
+ EFI_STATUS Status;
+ EFI_GUID *InfoTypesBuffer;
+ UINTN InfoTypeBufferCount;
+ UINTN TypeIndex;
+ BOOLEAN Supported;
+ VOID *InfoBlock;
+ UINTN InfoBlockSize;
+
+ ASSERT (Private != NULL && Ipv6Support != NULL);
+
+ //
+ // Check whether the UNDI supports IPv6 by NII protocol.
+ //
+ if (Private->Nii != NULL) {
+ *Ipv6Support = Private->Nii->Ipv6Supported;
+ return EFI_SUCCESS;
+ }
+
+ //
+ // Check whether the UNDI supports IPv6 by AIP protocol.
+ //
+
+ //
+ // Get the NIC handle by SNP protocol.
+ //
+ Handle = NetLibGetSnpHandle (ControllerHandle, NULL);
+ if (Handle == NULL) {
+ return EFI_NOT_FOUND;
+ }
+
+ Aip = NULL;
+ Status = gBS->HandleProtocol (
+ Handle,
+ &gEfiAdapterInformationProtocolGuid,
+ (VOID *) &Aip
+ );
+ if (EFI_ERROR (Status) || Aip == NULL) {
+ return EFI_NOT_FOUND;
+ }
+
+ InfoTypesBuffer = NULL;
+ InfoTypeBufferCount = 0;
+ Status = Aip->GetSupportedTypes (Aip, &InfoTypesBuffer, &InfoTypeBufferCount);
+ if (EFI_ERROR (Status) || InfoTypesBuffer == NULL) {
+ FreePool (InfoTypesBuffer);
+ return EFI_NOT_FOUND;
+ }
+
+ Supported = FALSE;
+ for (TypeIndex = 0; TypeIndex < InfoTypeBufferCount; TypeIndex++) {
+ if (CompareGuid (&InfoTypesBuffer[TypeIndex], &gEfiAdapterInfoUndiIpv6SupportGuid)) {
+ Supported = TRUE;
+ break;
+ }
+ }
+
+ FreePool (InfoTypesBuffer);
+ if (!Supported) {
+ return EFI_NOT_FOUND;
+ }
+
+ //
+ // We now have adapter information block.
+ //
+ InfoBlock = NULL;
+ InfoBlockSize = 0;
+ Status = Aip->GetInformation (Aip, &gEfiAdapterInfoUndiIpv6SupportGuid, &InfoBlock, &InfoBlockSize);
+ if (EFI_ERROR (Status) || InfoBlock == NULL) {
+ FreePool (InfoBlock);
+ return EFI_NOT_FOUND;
+ }
+
+ *Ipv6Support = ((EFI_ADAPTER_INFO_UNDI_IPV6_SUPPORT *) InfoBlock)->Ipv6Support;
+ FreePool (InfoBlock);
+ return EFI_SUCCESS;
+
+}
/**
Create the opened instances based on IPv4.
@@ -645,6 +742,18 @@ PxeBcCreateIp4Children (
Private->Ip4Nic->Private = Private;
Private->Ip4Nic->Signature = PXEBC_VIRTUAL_NIC_SIGNATURE;
+ //
+ // Locate Ip4->Ip4Config2 and store it for set IPv4 Policy.
+ //
+ Status = gBS->HandleProtocol (
+ ControllerHandle,
+ &gEfiIp4Config2ProtocolGuid,
+ (VOID **) &Private->Ip4Config2
+ );
+ if (EFI_ERROR (Status)) {
+ goto ON_ERROR;
+ }
+
//
// Create a device path node for Ipv4 virtual nic, and append it.
//
@@ -952,6 +1061,30 @@ PxeBcCreateIp6Children (
Private->Ip6MaxPacketSize = Ip6ModeData.MaxPacketSize;
+ if (Ip6ModeData.AddressList != NULL) {
+ FreePool (Ip6ModeData.AddressList);
+ }
+
+ if (Ip6ModeData.GroupTable != NULL) {
+ FreePool (Ip6ModeData.GroupTable);
+ }
+
+ if (Ip6ModeData.RouteTable != NULL) {
+ FreePool (Ip6ModeData.RouteTable);
+ }
+
+ if (Ip6ModeData.NeighborCache != NULL) {
+ FreePool (Ip6ModeData.NeighborCache);
+ }
+
+ if (Ip6ModeData.PrefixTable != NULL) {
+ FreePool (Ip6ModeData.PrefixTable);
+ }
+
+ if (Ip6ModeData.IcmpTypeList != NULL) {
+ FreePool (Ip6ModeData.IcmpTypeList);
+ }
+
//
// Locate Ip6->Ip6Config and store it for set IPv6 address.
//
@@ -1057,7 +1190,18 @@ PxeBcCreateIp6Children (
// Set IPv6 avaiable flag and set default configure data for
// Udp6Read and Ip6 instance.
//
- Private->Mode.Ipv6Available = TRUE;
+ Status = PxeBcCheckIpv6Support (ControllerHandle, Private, &Private->Mode.Ipv6Available);
+ if (EFI_ERROR (Status)) {
+ //
+ // Fail to get the data whether UNDI supports IPv6. Set default value.
+ //
+ Private->Mode.Ipv6Available = TRUE;
+ }
+
+ if (!Private->Mode.Ipv6Available) {
+ goto ON_ERROR;
+ }
+
Udp6CfgData = &Private->Udp6CfgData;
Ip6CfgData = &Private->Ip6CfgData;