/** @file\r
Driver Binding Protocol for IPsec Driver.\r
\r
- Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>\r
+ Copyright (c) 2009 - 2018, Intel Corporation. All rights reserved.<BR>\r
\r
This program and the accompanying materials\r
are licensed and made available under the terms and conditions of the BSD License\r
#include "IpSecDebug.h"\r
\r
/**\r
- Test to see if this driver supports ControllerHandle.\r
+ Test to see if this driver supports ControllerHandle. This is the worker function\r
+ for IpSec4(6)DriverbindingSupported.\r
\r
@param[in] This Protocol instance pointer.\r
@param[in] ControllerHandle Handle of device to test.\r
@param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
device to start.\r
+ @param[in] IpVersion IP_VERSION_4 or IP_VERSION_6.\r
\r
@retval EFI_SUCCES This driver supports this device.\r
@retval EFI_ALREADY_STARTED This driver is already running on this device.\r
**/\r
EFI_STATUS\r
EFIAPI\r
-IpSecDriverBindingSupported (\r
+IpSecSupported (\r
IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
IN EFI_HANDLE ControllerHandle,\r
- IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL,\r
+ IN UINT8 IpVersion\r
)\r
{\r
- EFI_STATUS Udp4Status;\r
- EFI_STATUS Udp6Status;\r
-\r
- Udp4Status = gBS->OpenProtocol (\r
- ControllerHandle,\r
- &gEfiUdp4ServiceBindingProtocolGuid,\r
- NULL,\r
- This->DriverBindingHandle,\r
- ControllerHandle,\r
- EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
- );\r
-\r
- Udp6Status = gBS->OpenProtocol (\r
- ControllerHandle,\r
- &gEfiUdp6ServiceBindingProtocolGuid,\r
- NULL,\r
- This->DriverBindingHandle,\r
- ControllerHandle,\r
- EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
- );\r
+ EFI_STATUS Status;\r
+ EFI_GUID *UdpServiceBindingGuid;\r
\r
- //\r
- // The controller with either Udp4Sb or Udp6Sb is supported.\r
- //\r
- if (!EFI_ERROR (Udp4Status) || !EFI_ERROR (Udp6Status)) {\r
- return EFI_SUCCESS;\r
+ if (IpVersion == IP_VERSION_4) {\r
+ UdpServiceBindingGuid = &gEfiUdp4ServiceBindingProtocolGuid;\r
+ } else {\r
+ UdpServiceBindingGuid = &gEfiUdp6ServiceBindingProtocolGuid;\r
}\r
\r
- return EFI_UNSUPPORTED;\r
+ Status = gBS->OpenProtocol (\r
+ ControllerHandle,\r
+ UdpServiceBindingGuid,\r
+ NULL,\r
+ This->DriverBindingHandle,\r
+ ControllerHandle,\r
+ EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
+ );\r
+ if (EFI_ERROR (Status)) {\r
+ return EFI_UNSUPPORTED;\r
+ }\r
+ return EFI_SUCCESS;\r
}\r
\r
/**\r
- Start this driver on ControllerHandle.\r
+ Start this driver on ControllerHandle. This is the worker function\r
+ for IpSec4(6)DriverbindingStart.\r
\r
@param[in] This Protocol instance pointer.\r
@param[in] ControllerHandle Handle of device to bind driver to.\r
@param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
device to start.\r
+ @param[in] IpVersion IP_VERSION_4 or IP_VERSION_6.\r
\r
@retval EFI_SUCCES This driver is added to ControllerHandle\r
@retval EFI_ALREADY_STARTED This driver is already running on ControllerHandle\r
**/\r
EFI_STATUS\r
EFIAPI\r
-IpSecDriverBindingStart (\r
+IpSecStart (\r
IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
IN EFI_HANDLE ControllerHandle,\r
- IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL,\r
+ IN UINT8 IpVersion\r
)\r
{\r
EFI_IPSEC2_PROTOCOL *IpSec;\r
EFI_STATUS Status;\r
- EFI_STATUS Udp4Status;\r
- EFI_STATUS Udp6Status;\r
IPSEC_PRIVATE_DATA *Private;\r
\r
//\r
\r
Private = IPSEC_PRIVATE_DATA_FROM_IPSEC (IpSec);\r
\r
- //\r
- // If udp4 sb is on the controller, try to open a udp4 io for input.\r
- //\r
- Udp4Status = gBS->OpenProtocol (\r
- ControllerHandle,\r
- &gEfiUdp4ServiceBindingProtocolGuid,\r
- NULL,\r
- This->DriverBindingHandle,\r
- ControllerHandle,\r
- EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
- );\r
-\r
- if (!EFI_ERROR (Udp4Status)) {\r
- Udp4Status = IkeOpenInputUdp4 (Private, ControllerHandle);\r
- }\r
- //\r
- // If udp6 sb is on the controller, try to open a udp6 io for input.\r
- //\r
- Udp6Status = gBS->OpenProtocol (\r
- ControllerHandle,\r
- &gEfiUdp6ServiceBindingProtocolGuid,\r
- NULL,\r
- This->DriverBindingHandle,\r
- ControllerHandle,\r
- EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
- );\r
-\r
- if (!EFI_ERROR (Udp6Status)) {\r
- Udp6Status = IkeOpenInputUdp6 (Private, ControllerHandle);\r
+ if (IpVersion == IP_VERSION_4) {\r
+ //\r
+ // Try to open a udp4 io for input.\r
+ //\r
+ Status = gBS->OpenProtocol (\r
+ ControllerHandle,\r
+ &gEfiUdp4ServiceBindingProtocolGuid,\r
+ NULL,\r
+ This->DriverBindingHandle,\r
+ ControllerHandle,\r
+ EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
+ );\r
+\r
+ if (!EFI_ERROR (Status)) {\r
+ Status = IkeOpenInputUdp4 (Private, ControllerHandle, This->DriverBindingHandle);\r
+ }\r
+ } else {\r
+ //\r
+ // Try to open a udp6 io for input.\r
+ //\r
+ Status = gBS->OpenProtocol (\r
+ ControllerHandle,\r
+ &gEfiUdp6ServiceBindingProtocolGuid,\r
+ NULL,\r
+ This->DriverBindingHandle,\r
+ ControllerHandle,\r
+ EFI_OPEN_PROTOCOL_TEST_PROTOCOL\r
+ );\r
+\r
+ if (!EFI_ERROR (Status)) {\r
+ Status = IkeOpenInputUdp6 (Private, ControllerHandle, This->DriverBindingHandle);\r
+ }\r
}\r
\r
- if (!EFI_ERROR (Udp4Status) || !EFI_ERROR (Udp6Status)) {\r
- return EFI_SUCCESS;\r
+ if (EFI_ERROR (Status)) {\r
+ return EFI_DEVICE_ERROR;\r
}\r
-\r
- return EFI_DEVICE_ERROR;\r
+ return EFI_SUCCESS;\r
}\r
\r
/**\r
- Stop this driver on ControllerHandle.\r
+ Stop this driver on ControllerHandle. This is the worker function\r
+ for IpSec4(6)DriverbindingStop.\r
\r
@param[in] This Protocol instance pointer.\r
@param[in] ControllerHandle Handle of a device to stop the driver on.\r
@param[in] NumberOfChildren Number of Handles in ChildHandleBuffer. If the number of\r
children is zero, stop the entire bus driver.\r
@param[in] ChildHandleBuffer List of Child Handles to Stop.\r
+ @param[in] IpVersion IP_VERSION_4 or IP_VERSION_6.\r
\r
@retval EFI_SUCCES This driver removed ControllerHandle.\r
@retval other This driver was not removed from this device.\r
**/\r
EFI_STATUS\r
EFIAPI\r
-IpSecDriverBindingStop (\r
+IpSecStop (\r
IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
IN EFI_HANDLE ControllerHandle,\r
IN UINTN NumberOfChildren,\r
- IN EFI_HANDLE *ChildHandleBuffer\r
+ IN EFI_HANDLE *ChildHandleBuffer,\r
+ IN UINT8 IpVersion\r
)\r
{\r
EFI_IPSEC2_PROTOCOL *IpSec;\r
IKE_UDP_SERVICE *UdpSrv;\r
LIST_ENTRY *Entry;\r
LIST_ENTRY *Next;\r
+ IKEV2_SA_SESSION *Ikev2SaSession;\r
\r
//\r
// Locate ipsec protocol to get private data.\r
Private = IPSEC_PRIVATE_DATA_FROM_IPSEC (IpSec);\r
\r
//\r
- // Delete all SAs before stop Ipsec.\r
- //\r
- IkeDeleteAllSas (Private, FALSE);\r
- //\r
- // If has udp4 io opened on the controller, close and free it.\r
+ // The SAs are shared by both IP4 and IP6 stack. So we skip the cleanup\r
+ // and leave the SAs unchanged if the other IP stack is still running.\r
//\r
- NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Udp4List) {\r
-\r
- UdpSrv = IPSEC_UDP_SERVICE_FROM_LIST (Entry);\r
+ if ((IpVersion == IP_VERSION_4 && Private->Udp6Num ==0) ||\r
+ (IpVersion == IP_VERSION_6 && Private->Udp4Num ==0)) {\r
//\r
- // Find the right udp service which installed on the appointed nic handle.\r
+ // If IKEv2 SAs are under establishing, delete it directly.\r
//\r
- if (UdpSrv->Input != NULL && ControllerHandle == UdpSrv->Input->UdpHandle) {\r
- UdpIoFreeIo (UdpSrv->Input);\r
- UdpSrv->Input = NULL;\r
- }\r
-\r
- if (UdpSrv->Output != NULL && ControllerHandle == UdpSrv->Output->UdpHandle) {\r
- UdpIoFreeIo (UdpSrv->Output);\r
- UdpSrv->Output = NULL;\r
+ if (!IsListEmpty (&Private->Ikev2SessionList)) {\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Ikev2SessionList) {\r
+ Ikev2SaSession = IKEV2_SA_SESSION_BY_SESSION (Entry);\r
+ RemoveEntryList (&Ikev2SaSession->BySessionTable);\r
+ Ikev2SaSessionFree (Ikev2SaSession);\r
+ }\r
}\r
\r
- if (UdpSrv->Input == NULL && UdpSrv->Output == NULL) {\r
- RemoveEntryList (&UdpSrv->List);\r
- FreePool (UdpSrv);\r
- ASSERT (Private->Udp4Num > 0);\r
- Private->Udp4Num--;\r
+ //\r
+ // Delete established IKEv2 SAs.\r
+ //\r
+ if (!IsListEmpty (&Private->Ikev2EstablishedList)) {\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Ikev2EstablishedList) {\r
+ Ikev2SaSession = IKEV2_SA_SESSION_BY_SESSION (Entry);\r
+ RemoveEntryList (&Ikev2SaSession->BySessionTable);\r
+ Ikev2SaSessionFree (Ikev2SaSession);\r
+ }\r
}\r
}\r
- //\r
- // If has udp6 io opened on the controller, close and free it.\r
- //\r
- NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Udp6List) {\r
\r
- UdpSrv = IPSEC_UDP_SERVICE_FROM_LIST (Entry);\r
+ if (IpVersion == IP_VERSION_4) {\r
//\r
- // Find the right udp service which installed on the appointed nic handle.\r
+ // If has udp4 io opened on the controller, close and free it.\r
//\r
- if (UdpSrv->Input != NULL && ControllerHandle == UdpSrv->Input->UdpHandle) {\r
- UdpIoFreeIo (UdpSrv->Input);\r
- UdpSrv->Input = NULL;\r
- }\r
-\r
- if (UdpSrv->Output != NULL && ControllerHandle == UdpSrv->Output->UdpHandle) {\r
- UdpIoFreeIo (UdpSrv->Output);\r
- UdpSrv->Output = NULL;\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Udp4List) {\r
+\r
+ UdpSrv = IPSEC_UDP_SERVICE_FROM_LIST (Entry);\r
+ //\r
+ // Find the right udp service which installed on the appointed nic handle.\r
+ //\r
+ if (UdpSrv->Input != NULL && ControllerHandle == UdpSrv->Input->UdpHandle) {\r
+ UdpIoFreeIo (UdpSrv->Input);\r
+ UdpSrv->Input = NULL;\r
+ }\r
+\r
+ if (UdpSrv->Output != NULL && ControllerHandle == UdpSrv->Output->UdpHandle) {\r
+ UdpIoFreeIo (UdpSrv->Output);\r
+ UdpSrv->Output = NULL;\r
+ }\r
+\r
+ if (UdpSrv->Input == NULL && UdpSrv->Output == NULL) {\r
+ RemoveEntryList (&UdpSrv->List);\r
+ FreePool (UdpSrv);\r
+ ASSERT (Private->Udp4Num > 0);\r
+ Private->Udp4Num--;\r
+ }\r
}\r
-\r
- if (UdpSrv->Input == NULL && UdpSrv->Output == NULL) {\r
- RemoveEntryList (&UdpSrv->List);\r
- FreePool (UdpSrv);\r
- ASSERT (Private->Udp6Num > 0);\r
- Private->Udp6Num--;\r
+ } else {\r
+ //\r
+ // If has udp6 io opened on the controller, close and free it.\r
+ //\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &Private->Udp6List) {\r
+\r
+ UdpSrv = IPSEC_UDP_SERVICE_FROM_LIST (Entry);\r
+ //\r
+ // Find the right udp service which installed on the appointed nic handle.\r
+ //\r
+ if (UdpSrv->Input != NULL && ControllerHandle == UdpSrv->Input->UdpHandle) {\r
+ UdpIoFreeIo (UdpSrv->Input);\r
+ UdpSrv->Input = NULL;\r
+ }\r
+\r
+ if (UdpSrv->Output != NULL && ControllerHandle == UdpSrv->Output->UdpHandle) {\r
+ UdpIoFreeIo (UdpSrv->Output);\r
+ UdpSrv->Output = NULL;\r
+ }\r
+\r
+ if (UdpSrv->Input == NULL && UdpSrv->Output == NULL) {\r
+ RemoveEntryList (&UdpSrv->List);\r
+ FreePool (UdpSrv);\r
+ ASSERT (Private->Udp6Num > 0);\r
+ Private->Udp6Num--;\r
+ }\r
}\r
}\r
\r
return EFI_SUCCESS;\r
}\r
\r
-EFI_DRIVER_BINDING_PROTOCOL gIpSecDriverBinding = {\r
- IpSecDriverBindingSupported,\r
- IpSecDriverBindingStart,\r
- IpSecDriverBindingStop,\r
+/**\r
+ Test to see if this driver supports ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of device to test.\r
+ @param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
+ device to start.\r
+\r
+ @retval EFI_SUCCES This driver supports this device.\r
+ @retval EFI_ALREADY_STARTED This driver is already running on this device.\r
+ @retval other This driver does not support this device.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec4DriverBindingSupported (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ )\r
+{\r
+ return IpSecSupported (\r
+ This,\r
+ ControllerHandle,\r
+ RemainingDevicePath,\r
+ IP_VERSION_4\r
+ );\r
+}\r
+\r
+/**\r
+ Start this driver on ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of device to bind driver to.\r
+ @param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
+ device to start.\r
+\r
+ @retval EFI_SUCCES This driver is added to ControllerHandle\r
+ @retval EFI_ALREADY_STARTED This driver is already running on ControllerHandle\r
+ @retval EFI_DEVICE_ERROR The device could not be started due to a device error.\r
+ Currently not implemented.\r
+ @retval other This driver does not support this device\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec4DriverBindingStart (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ )\r
+{\r
+ return IpSecStart (\r
+ This,\r
+ ControllerHandle,\r
+ RemainingDevicePath,\r
+ IP_VERSION_4\r
+ );\r
+}\r
+\r
+/**\r
+ Stop this driver on ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of a device to stop the driver on.\r
+ @param[in] NumberOfChildren Number of Handles in ChildHandleBuffer. If the number of\r
+ children is zero, stop the entire bus driver.\r
+ @param[in] ChildHandleBuffer List of Child Handles to Stop.\r
+\r
+ @retval EFI_SUCCES This driver removed ControllerHandle.\r
+ @retval other This driver was not removed from this device.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec4DriverBindingStop (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN UINTN NumberOfChildren,\r
+ IN EFI_HANDLE *ChildHandleBuffer\r
+ )\r
+{\r
+ return IpSecStop (\r
+ This,\r
+ ControllerHandle,\r
+ NumberOfChildren,\r
+ ChildHandleBuffer,\r
+ IP_VERSION_4\r
+ );\r
+}\r
+\r
+/**\r
+ Test to see if this driver supports ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of device to test.\r
+ @param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
+ device to start.\r
+\r
+ @retval EFI_SUCCES This driver supports this device.\r
+ @retval EFI_ALREADY_STARTED This driver is already running on this device.\r
+ @retval other This driver does not support this device.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec6DriverBindingSupported (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ )\r
+{\r
+ return IpSecSupported (\r
+ This,\r
+ ControllerHandle,\r
+ RemainingDevicePath,\r
+ IP_VERSION_6\r
+ );\r
+}\r
+\r
+/**\r
+ Start this driver on ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of device to bind driver to.\r
+ @param[in] RemainingDevicePath Optional parameter used to pick a specific child\r
+ device to start.\r
+\r
+ @retval EFI_SUCCES This driver is added to ControllerHandle\r
+ @retval EFI_ALREADY_STARTED This driver is already running on ControllerHandle\r
+ @retval EFI_DEVICE_ERROR The device could not be started due to a device error.\r
+ Currently not implemented.\r
+ @retval other This driver does not support this device\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec6DriverBindingStart (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath OPTIONAL\r
+ )\r
+{\r
+ return IpSecStart (\r
+ This,\r
+ ControllerHandle,\r
+ RemainingDevicePath,\r
+ IP_VERSION_6\r
+ );\r
+}\r
+\r
+/**\r
+ Stop this driver on ControllerHandle.\r
+\r
+ @param[in] This Protocol instance pointer.\r
+ @param[in] ControllerHandle Handle of a device to stop the driver on.\r
+ @param[in] NumberOfChildren Number of Handles in ChildHandleBuffer. If the number of\r
+ children is zero, stop the entire bus driver.\r
+ @param[in] ChildHandleBuffer List of Child Handles to Stop.\r
+\r
+ @retval EFI_SUCCES This driver removed ControllerHandle.\r
+ @retval other This driver was not removed from this device.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+IpSec6DriverBindingStop (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE ControllerHandle,\r
+ IN UINTN NumberOfChildren,\r
+ IN EFI_HANDLE *ChildHandleBuffer\r
+ )\r
+{\r
+ return IpSecStop (\r
+ This,\r
+ ControllerHandle,\r
+ NumberOfChildren,\r
+ ChildHandleBuffer,\r
+ IP_VERSION_6\r
+ );\r
+}\r
+\r
+EFI_DRIVER_BINDING_PROTOCOL gIpSec4DriverBinding = {\r
+ IpSec4DriverBindingSupported,\r
+ IpSec4DriverBindingStart,\r
+ IpSec4DriverBindingStop,\r
+ 0xa,\r
+ NULL,\r
+ NULL\r
+};\r
+\r
+EFI_DRIVER_BINDING_PROTOCOL gIpSec6DriverBinding = {\r
+ IpSec6DriverBindingSupported,\r
+ IpSec6DriverBindingStart,\r
+ IpSec6DriverBindingStop,\r
0xa,\r
NULL,\r
NULL\r
Status = EfiLibInstallDriverBindingComponentName2 (\r
ImageHandle,\r
SystemTable,\r
- &gIpSecDriverBinding,\r
+ &gIpSec4DriverBinding,\r
ImageHandle,\r
&gIpSecComponentName,\r
&gIpSecComponentName2\r
goto ON_UNINSTALL_IPSEC;\r
}\r
\r
+ Status = EfiLibInstallDriverBindingComponentName2 (\r
+ ImageHandle,\r
+ SystemTable,\r
+ &gIpSec6DriverBinding,\r
+ NULL,\r
+ &gIpSecComponentName,\r
+ &gIpSecComponentName2\r
+ );\r
+ if (EFI_ERROR (Status)) {\r
+ goto ON_UNINSTALL_IPSEC4_DB;\r
+ }\r
+\r
return Status;\r
\r
+ON_UNINSTALL_IPSEC4_DB:\r
+ EfiLibUninstallDriverBindingComponentName2 (\r
+ &gIpSec4DriverBinding,\r
+ &gIpSecComponentName,\r
+ &gIpSecComponentName2\r
+ );\r
+\r
ON_UNINSTALL_IPSEC:\r
gBS->UninstallProtocolInterface (\r
Private->Handle,\r