/** @file\r
Common operation of the IKE\r
- \r
- Copyright (c) 2010 - 2015, 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
- which accompanies this distribution. The full text of the license may be found at\r
- http://opensource.org/licenses/bsd-license.php.\r
+ Copyright (c) 2010 - 2018, Intel Corporation. All rights reserved.<BR>\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
+ SPDX-License-Identifier: BSD-2-Clause-Patent\r
\r
**/\r
\r
#include "IpSecConfigImpl.h"\r
#include "IpSecDebug.h"\r
\r
-//\r
-// Initial the SPI\r
-//\r
-UINT32 mNextSpi = IKE_SPI_BASE;\r
+/**\r
+ Check whether the new generated Spi has existed.\r
+\r
+ @param[in] IkeSaSession Pointer to the Child SA Session.\r
+ @param[in] SpiValue SPI Value.\r
+\r
+ @retval TRUE This SpiValue has existed in the Child SA Session\r
+ @retval FALSE This SpiValue doesn't exist in the Child SA Session.\r
+\r
+**/\r
+BOOLEAN\r
+IkeSpiValueExisted (\r
+ IN IKEV2_SA_SESSION *IkeSaSession,\r
+ IN UINT32 SpiValue\r
+ )\r
+{\r
+ LIST_ENTRY *Entry;\r
+ LIST_ENTRY *Next;\r
+ IKEV2_CHILD_SA_SESSION *SaSession;\r
+\r
+ Entry = NULL;\r
+ Next = NULL;\r
+ SaSession = NULL;\r
+\r
+ //\r
+ // Check whether the SPI value has existed in ChildSaEstablishSessionList.\r
+ //\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &IkeSaSession->ChildSaEstablishSessionList) {\r
+ SaSession= IKEV2_CHILD_SA_SESSION_BY_IKE_SA (Entry);\r
+ if (SaSession->LocalPeerSpi == SpiValue) {\r
+ return TRUE;\r
+ }\r
+ }\r
+\r
+ //\r
+ // Check whether the SPI value has existed in ChildSaSessionList.\r
+ //\r
+ NET_LIST_FOR_EACH_SAFE (Entry, Next, &IkeSaSession->ChildSaSessionList) {\r
+ SaSession= IKEV2_CHILD_SA_SESSION_BY_IKE_SA (Entry);\r
+ if (SaSession->LocalPeerSpi == SpiValue) {\r
+ return TRUE;\r
+ }\r
+ }\r
+\r
+ return FALSE;\r
+}\r
\r
/**\r
Call Crypto Lib to generate a random value with eight-octet length.\r
- \r
+\r
@return the 64 byte vaule.\r
\r
**/\r
Generate the random data for Nonce payload.\r
\r
@param[in] NonceSize Size of the data in bytes.\r
- \r
- @return Buffer which contains the random data of the spcified size. \r
+\r
+ @return Buffer which contains the random data of the spcified size.\r
\r
**/\r
UINT8 *\r
if (IkePayload == NULL) {\r
return NULL;\r
}\r
- \r
+\r
IkePayload->Signature = IKE_PAYLOAD_SIGNATURE;\r
\r
return IkePayload;\r
/**\r
Generate an new SPI.\r
\r
- @return a SPI in 4 bytes.\r
+ @param[in] IkeSaSession Pointer to IKEV2_SA_SESSION related to this Child SA\r
+ Session.\r
+ @param[in, out] SpiValue Pointer to the new generated SPI value.\r
+\r
+ @retval EFI_SUCCESS The operation performs successfully.\r
+ @retval Otherwise The operation is failed.\r
\r
**/\r
-UINT32\r
+EFI_STATUS\r
IkeGenerateSpi (\r
- VOID\r
+ IN IKEV2_SA_SESSION *IkeSaSession,\r
+ IN OUT UINT32 *SpiValue\r
)\r
{\r
- //\r
- // TODO: should generate SPI randomly to avoid security issue\r
- //\r
- return mNextSpi++;\r
+ EFI_STATUS Status;\r
+\r
+ Status = EFI_SUCCESS;\r
+\r
+ while (TRUE) {\r
+ //\r
+ // Generate SPI randomly\r
+ //\r
+ Status = IpSecCryptoIoGenerateRandomBytes ((UINT8 *)SpiValue, sizeof (UINT32));\r
+ if (EFI_ERROR (Status)) {\r
+ break;\r
+ }\r
+\r
+ //\r
+ // The set of SPI values in the range 1 through 255 are reserved by the\r
+ // Internet Assigned Numbers Authority (IANA) for future use; a reserved\r
+ // SPI value will not normally be assigned by IANA unless the use of the\r
+ // assigned SPI value is specified in an RFC.\r
+ //\r
+ if (*SpiValue < IKE_SPI_BASE) {\r
+ *SpiValue += IKE_SPI_BASE;\r
+ }\r
+\r
+ //\r
+ // Check whether the new generated SPI has existed.\r
+ //\r
+ if (!IkeSpiValueExisted (IkeSaSession, *SpiValue)) {\r
+ break;\r
+ }\r
+ }\r
+\r
+ return Status;\r
}\r
\r
/**\r