2 The implementation of IPSEC_CONFIG_PROTOCOL.
4 Copyright (c) 2009 - 2011, Intel Corporation. All rights reserved.<BR>
6 This program and the accompanying materials
7 are licensed and made available under the terms and conditions of the BSD License
8 which accompanies this distribution. The full text of the license may be found at
9 http://opensource.org/licenses/bsd-license.php.
11 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
12 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
16 #include "IpSecConfigImpl.h"
17 #include "IpSecDebug.h"
19 LIST_ENTRY mConfigData
[IPsecConfigDataTypeMaximum
];
20 BOOLEAN mSetBySelf
= FALSE
;
23 // Common CompareSelector routine entry for SPD/SAD/PAD.
25 IPSEC_COMPARE_SELECTOR mCompareSelector
[] = {
26 (IPSEC_COMPARE_SELECTOR
) CompareSpdSelector
,
27 (IPSEC_COMPARE_SELECTOR
) CompareSaId
,
28 (IPSEC_COMPARE_SELECTOR
) ComparePadId
32 // Common IsZeroSelector routine entry for SPD/SAD/PAD.
34 IPSEC_IS_ZERO_SELECTOR mIsZeroSelector
[] = {
35 (IPSEC_IS_ZERO_SELECTOR
) IsZeroSpdSelector
,
36 (IPSEC_IS_ZERO_SELECTOR
) IsZeroSaId
,
37 (IPSEC_IS_ZERO_SELECTOR
) IsZeroPadId
41 // Common DuplicateSelector routine entry for SPD/SAD/PAD.
43 IPSEC_DUPLICATE_SELECTOR mDuplicateSelector
[] = {
44 (IPSEC_DUPLICATE_SELECTOR
) DuplicateSpdSelector
,
45 (IPSEC_DUPLICATE_SELECTOR
) DuplicateSaId
,
46 (IPSEC_DUPLICATE_SELECTOR
) DuplicatePadId
50 // Common FixPolicyEntry routine entry for SPD/SAD/PAD.
52 IPSEC_FIX_POLICY_ENTRY mFixPolicyEntry
[] = {
53 (IPSEC_FIX_POLICY_ENTRY
) FixSpdEntry
,
54 (IPSEC_FIX_POLICY_ENTRY
) FixSadEntry
,
55 (IPSEC_FIX_POLICY_ENTRY
) FixPadEntry
59 // Common UnfixPolicyEntry routine entry for SPD/SAD/PAD.
61 IPSEC_FIX_POLICY_ENTRY mUnfixPolicyEntry
[] = {
62 (IPSEC_FIX_POLICY_ENTRY
) UnfixSpdEntry
,
63 (IPSEC_FIX_POLICY_ENTRY
) UnfixSadEntry
,
64 (IPSEC_FIX_POLICY_ENTRY
) UnfixPadEntry
68 // Common SetPolicyEntry routine entry for SPD/SAD/PAD.
70 IPSEC_SET_POLICY_ENTRY mSetPolicyEntry
[] = {
71 (IPSEC_SET_POLICY_ENTRY
) SetSpdEntry
,
72 (IPSEC_SET_POLICY_ENTRY
) SetSadEntry
,
73 (IPSEC_SET_POLICY_ENTRY
) SetPadEntry
77 // Common GetPolicyEntry routine entry for SPD/SAD/PAD.
79 IPSEC_GET_POLICY_ENTRY mGetPolicyEntry
[] = {
80 (IPSEC_GET_POLICY_ENTRY
) GetSpdEntry
,
81 (IPSEC_GET_POLICY_ENTRY
) GetSadEntry
,
82 (IPSEC_GET_POLICY_ENTRY
) GetPadEntry
86 // Routine entry for IpSecConfig protocol.
88 EFI_IPSEC_CONFIG_PROTOCOL mIpSecConfigInstance
= {
89 EfiIpSecConfigSetData
,
90 EfiIpSecConfigGetData
,
91 EfiIpSecConfigGetNextSelector
,
92 EfiIpSecConfigRegisterNotify
,
93 EfiIpSecConfigUnregisterNotify
97 Get the all IPSec configuration variables and store those variables
98 to the internal data structure.
100 This founction is called by IpSecConfigInitialize() that is to intialize the
101 IPsecConfiguration Protocol.
103 @param[in] Private Point to IPSEC_PRIVATE_DATA.
105 @retval EFI_OUT_OF_RESOURCES The required system resource could not be allocated.
106 @retval EFI_SUCCESS Restore the IPsec Configuration successfully.
107 @retval others Other errors is found during the variable getting.
112 IN IPSEC_PRIVATE_DATA
*Private
116 Check if the specified EFI_IP_ADDRESS_INFO is in EFI_IP_ADDRESS_INFO list.
118 @param[in] AddressInfo Pointer of IP_ADDRESS_INFO to be search in AddressInfo list.
119 @param[in] AddressInfoList A list that contains IP_ADDRESS_INFOs.
120 @param[in] AddressCount Point out how many IP_ADDRESS_INFO in the list.
122 @retval TRUE The specified AddressInfo is in the AddressInfoList.
123 @retval FALSE The specified AddressInfo is not in the AddressInfoList.
128 IN EFI_IP_ADDRESS_INFO
*AddressInfo
,
129 IN EFI_IP_ADDRESS_INFO
*AddressInfoList
,
130 IN UINT32 AddressCount
134 EFI_IP_ADDRESS ZeroAddress
;
136 ZeroMem(&ZeroAddress
, sizeof (EFI_IP_ADDRESS
));
139 // Zero Address means any address is matched.
141 if (AddressCount
== 1) {
143 &AddressInfoList
[0].Address
,
145 sizeof (EFI_IP_ADDRESS
)
150 for (Index
= 0; Index
< AddressCount
; Index
++) {
153 &AddressInfoList
[Index
].Address
,
154 sizeof (EFI_IP_ADDRESS
)
156 AddressInfo
->PrefixLength
== AddressInfoList
[Index
].PrefixLength
165 Compare two SPD Selectors.
167 Compare two SPD Selector by the fields of LocalAddressCount/RemoteAddressCount/
168 NextLayerProtocol/LocalPort/LocalPortRange/RemotePort/RemotePortRange and the
169 Local Addresses and remote Addresses.
171 @param[in] Selector1 Pointer of first SPD Selector.
172 @param[in] Selector2 Pointer of second SPD Selector.
174 @retval TRUE This two Selector have the same value in above fields.
175 @retval FALSE Not all above fields have the same value in these two Selectors.
180 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector1
,
181 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector2
184 EFI_IPSEC_SPD_SELECTOR
*SpdSel1
;
185 EFI_IPSEC_SPD_SELECTOR
*SpdSel2
;
189 SpdSel1
= &Selector1
->SpdSelector
;
190 SpdSel2
= &Selector2
->SpdSelector
;
194 // Compare the LocalAddressCount/RemoteAddressCount/NextLayerProtocol/
195 // LocalPort/LocalPortRange/RemotePort/RemotePortRange fields in the
196 // two Spdselectors. Since the SPD supports two directions, it needs to
197 // compare two directions.
199 if ((SpdSel1
->LocalAddressCount
!= SpdSel2
->LocalAddressCount
&&
200 SpdSel1
->LocalAddressCount
!= SpdSel2
->RemoteAddressCount
) ||
201 (SpdSel1
->RemoteAddressCount
!= SpdSel2
->RemoteAddressCount
&&
202 SpdSel1
->RemoteAddressCount
!= SpdSel2
->LocalAddressCount
) ||
203 SpdSel1
->NextLayerProtocol
!= SpdSel2
->NextLayerProtocol
||
204 SpdSel1
->LocalPort
!= SpdSel2
->LocalPort
||
205 SpdSel1
->LocalPortRange
!= SpdSel2
->LocalPortRange
||
206 SpdSel1
->RemotePort
!= SpdSel2
->RemotePort
||
207 SpdSel1
->RemotePortRange
!= SpdSel2
->RemotePortRange
214 // Compare the all LocalAddress fields in the two Spdselectors.
215 // First, SpdSel1->LocalAddress to SpdSel2->LocalAddress && Compare
216 // SpdSel1->RemoteAddress to SpdSel2->RemoteAddress. If all match, return
219 for (Index
= 0; Index
< SpdSel1
->LocalAddressCount
; Index
++) {
220 if (!IsInAddressInfoList (
221 &SpdSel1
->LocalAddress
[Index
],
222 SpdSel2
->LocalAddress
,
223 SpdSel2
->LocalAddressCount
230 for (Index
= 0; Index
< SpdSel2
->LocalAddressCount
; Index
++) {
231 if (!IsInAddressInfoList (
232 &SpdSel2
->LocalAddress
[Index
],
233 SpdSel1
->LocalAddress
,
234 SpdSel1
->LocalAddressCount
242 for (Index
= 0; Index
< SpdSel1
->RemoteAddressCount
; Index
++) {
243 if (!IsInAddressInfoList (
244 &SpdSel1
->RemoteAddress
[Index
],
245 SpdSel2
->RemoteAddress
,
246 SpdSel2
->RemoteAddressCount
254 for (Index
= 0; Index
< SpdSel2
->RemoteAddressCount
; Index
++) {
255 if (!IsInAddressInfoList (
256 &SpdSel2
->RemoteAddress
[Index
],
257 SpdSel1
->RemoteAddress
,
258 SpdSel1
->RemoteAddressCount
266 // Finish the one direction compare. If it is matched, return; otherwise,
267 // compare the other direction.
273 // Secondly, the SpdSel1->LocalAddress doesn't equal to SpdSel2->LocalAddress and
274 // SpdSel1->RemoteAddress doesn't equal to SpdSel2->RemoteAddress. Try to compare
275 // the RemoteAddress to LocalAddress.
278 for (Index
= 0; Index
< SpdSel1
->RemoteAddressCount
; Index
++) {
279 if (!IsInAddressInfoList (
280 &SpdSel1
->RemoteAddress
[Index
],
281 SpdSel2
->LocalAddress
,
282 SpdSel2
->LocalAddressCount
289 for (Index
= 0; Index
< SpdSel2
->RemoteAddressCount
; Index
++) {
290 if (!IsInAddressInfoList (
291 &SpdSel2
->RemoteAddress
[Index
],
292 SpdSel1
->LocalAddress
,
293 SpdSel1
->LocalAddressCount
301 for (Index
= 0; Index
< SpdSel1
->LocalAddressCount
; Index
++) {
302 if (!IsInAddressInfoList (
303 &SpdSel1
->LocalAddress
[Index
],
304 SpdSel2
->RemoteAddress
,
305 SpdSel2
->RemoteAddressCount
313 for (Index
= 0; Index
< SpdSel2
->LocalAddressCount
; Index
++) {
314 if (!IsInAddressInfoList (
315 &SpdSel2
->LocalAddress
[Index
],
316 SpdSel1
->RemoteAddress
,
317 SpdSel1
->RemoteAddressCount
328 Find if the two SPD Selectors has subordinative.
330 Compare two SPD Selector by the fields of LocalAddressCount/RemoteAddressCount/
331 NextLayerProtocol/LocalPort/LocalPortRange/RemotePort/RemotePortRange and the
332 Local Addresses and remote Addresses.
334 @param[in] Selector1 Pointer of first SPD Selector.
335 @param[in] Selector2 Pointer of second SPD Selector.
337 @retval TRUE The first SPD Selector is subordinate Selector of second SPD Selector.
338 @retval FALSE The first SPD Selector is not subordinate Selector of second
344 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector1
,
345 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector2
348 EFI_IPSEC_SPD_SELECTOR
*SpdSel1
;
349 EFI_IPSEC_SPD_SELECTOR
*SpdSel2
;
353 SpdSel1
= &Selector1
->SpdSelector
;
354 SpdSel2
= &Selector2
->SpdSelector
;
358 // Compare the LocalAddressCount/RemoteAddressCount/NextLayerProtocol/
359 // LocalPort/LocalPortRange/RemotePort/RemotePortRange fields in the
360 // two Spdselectors. Since the SPD supports two directions, it needs to
361 // compare two directions.
363 if (SpdSel1
->LocalAddressCount
> SpdSel2
->LocalAddressCount
||
364 SpdSel1
->RemoteAddressCount
> SpdSel2
->RemoteAddressCount
||
365 (SpdSel1
->NextLayerProtocol
!= SpdSel2
->NextLayerProtocol
&& SpdSel2
->NextLayerProtocol
!= 0xffff) ||
366 (SpdSel1
->LocalPort
> SpdSel2
->LocalPort
&& SpdSel2
->LocalPort
!= 0)||
367 (SpdSel1
->LocalPortRange
> SpdSel2
->LocalPortRange
&& SpdSel1
->LocalPort
!= 0)||
368 (SpdSel1
->RemotePort
> SpdSel2
->RemotePort
&& SpdSel2
->RemotePort
!= 0) ||
369 (SpdSel1
->RemotePortRange
> SpdSel2
->RemotePortRange
&& SpdSel2
->RemotePort
!= 0)
375 // Compare the all LocalAddress fields in the two Spdselectors.
376 // First, SpdSel1->LocalAddress to SpdSel2->LocalAddress && Compare
377 // SpdSel1->RemoteAddress to SpdSel2->RemoteAddress. If all match, return
381 for (Index
= 0; Index
< SpdSel1
->LocalAddressCount
; Index
++) {
382 if (!IsInAddressInfoList (
383 &SpdSel1
->LocalAddress
[Index
],
384 SpdSel2
->LocalAddress
,
385 SpdSel2
->LocalAddressCount
393 for (Index
= 0; Index
< SpdSel1
->RemoteAddressCount
; Index
++) {
394 if (!IsInAddressInfoList (
395 &SpdSel1
->RemoteAddress
[Index
],
396 SpdSel2
->RemoteAddress
,
397 SpdSel2
->RemoteAddressCount
411 // The SPD selector in SPD entry is two way.
413 // Compare the LocalAddressCount/RemoteAddressCount/NextLayerProtocol/
414 // LocalPort/LocalPortRange/RemotePort/RemotePortRange fields in the
415 // two Spdselectors. Since the SPD supports two directions, it needs to
416 // compare two directions.
419 if (SpdSel1
->LocalAddressCount
> SpdSel2
->RemoteAddressCount
||
420 SpdSel1
->RemoteAddressCount
> SpdSel2
->LocalAddressCount
||
421 (SpdSel1
->NextLayerProtocol
!= SpdSel2
->NextLayerProtocol
&& SpdSel2
->NextLayerProtocol
!= 0xffff) ||
422 (SpdSel1
->LocalPort
> SpdSel2
->RemotePort
&& SpdSel2
->RemotePort
!= 0)||
423 (SpdSel1
->LocalPortRange
> SpdSel2
->RemotePortRange
&& SpdSel1
->RemotePort
!= 0)||
424 (SpdSel1
->RemotePort
> SpdSel2
->LocalPort
&& SpdSel2
->LocalPort
!= 0) ||
425 (SpdSel1
->RemotePortRange
> SpdSel2
->LocalPortRange
&& SpdSel2
->LocalPort
!= 0)
432 // Compare the all LocalAddress fields in the two Spdselectors.
433 // First, SpdSel1->LocalAddress to SpdSel2->LocalAddress && Compare
434 // SpdSel1->RemoteAddress to SpdSel2->RemoteAddress. If all match, return
437 for (Index
= 0; Index
< SpdSel1
->LocalAddressCount
; Index
++) {
438 if (!IsInAddressInfoList (
439 &SpdSel1
->LocalAddress
[Index
],
440 SpdSel2
->RemoteAddress
,
441 SpdSel2
->RemoteAddressCount
449 for (Index
= 0; Index
< SpdSel1
->RemoteAddressCount
; Index
++) {
450 if (!IsInAddressInfoList (
451 &SpdSel1
->RemoteAddress
[Index
],
452 SpdSel2
->LocalAddress
,
453 SpdSel2
->LocalAddressCount
467 @param[in] Selector1 Pointer of first SA ID.
468 @param[in] Selector2 Pointer of second SA ID.
470 @retval TRUE This two Selectors have the same SA ID.
471 @retval FALSE This two Selecotrs don't have the same SA ID.
476 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector1
,
477 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector2
480 EFI_IPSEC_SA_ID
*SaId1
;
481 EFI_IPSEC_SA_ID
*SaId2
;
484 SaId1
= &Selector1
->SaId
;
485 SaId2
= &Selector2
->SaId
;
488 if (CompareMem (SaId1
, SaId2
, sizeof (EFI_IPSEC_SA_ID
)) != 0) {
498 @param[in] Selector1 Pointer of first PAD ID.
499 @param[in] Selector2 Pointer of second PAD ID.
501 @retval TRUE This two Selectors have the same PAD ID.
502 @retval FALSE This two Selecotrs don't have the same PAD ID.
507 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector1
,
508 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector2
511 EFI_IPSEC_PAD_ID
*PadId1
;
512 EFI_IPSEC_PAD_ID
*PadId2
;
515 PadId1
= &Selector1
->PadId
;
516 PadId2
= &Selector2
->PadId
;
520 // Compare the PeerIdValid fields in PadId.
522 if (PadId1
->PeerIdValid
!= PadId2
->PeerIdValid
) {
526 // Compare the PeerId fields in PadId if PeerIdValid is true.
529 PadId1
->PeerIdValid
&&
530 AsciiStriCmp ((CONST CHAR8
*) PadId1
->Id
.PeerId
, (CONST CHAR8
*) PadId2
->Id
.PeerId
) != 0
535 // Compare the IpAddress fields in PadId if PeerIdValid is false.
538 !PadId1
->PeerIdValid
&&
539 (PadId1
->Id
.IpAddress
.PrefixLength
!= PadId2
->Id
.IpAddress
.PrefixLength
||
540 CompareMem (&PadId1
->Id
.IpAddress
.Address
, &PadId2
->Id
.IpAddress
.Address
, sizeof (EFI_IP_ADDRESS
)) != 0)
549 Check if the SPD Selector is Zero by its LocalAddressCount and RemoteAddressCount
552 @param[in] Selector Pointer of the SPD Selector.
554 @retval TRUE If the SPD Selector is Zero.
555 @retval FALSE If the SPD Selector is not Zero.
560 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
563 EFI_IPSEC_SPD_SELECTOR
*SpdSel
;
566 SpdSel
= &Selector
->SpdSelector
;
569 if (SpdSel
->LocalAddressCount
== 0 && SpdSel
->RemoteAddressCount
== 0) {
577 Check if the SA ID is Zero by its DestAddress.
579 @param[in] Selector Pointer of the SA ID.
581 @retval TRUE If the SA ID is Zero.
582 @retval FALSE If the SA ID is not Zero.
587 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
591 EFI_IPSEC_CONFIG_SELECTOR ZeroSelector
;
595 ZeroMem (&ZeroSelector
, sizeof (EFI_IPSEC_CONFIG_SELECTOR
));
597 if (CompareMem (&ZeroSelector
, Selector
, sizeof (EFI_IPSEC_CONFIG_SELECTOR
)) == 0) {
605 Check if the PAD ID is Zero.
607 @param[in] Selector Pointer of the PAD ID.
609 @retval TRUE If the PAD ID is Zero.
610 @retval FALSE If the PAD ID is not Zero.
615 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
618 EFI_IPSEC_PAD_ID
*PadId
;
619 EFI_IPSEC_PAD_ID ZeroId
;
622 PadId
= &Selector
->PadId
;
625 ZeroMem (&ZeroId
, sizeof (EFI_IPSEC_PAD_ID
));
627 if (CompareMem (PadId
, &ZeroId
, sizeof (EFI_IPSEC_PAD_ID
)) == 0) {
635 Copy Source SPD Selector to the Destination SPD Selector.
637 @param[in, out] DstSel Pointer of Destination SPD Selector.
638 @param[in] SrcSel Pointer of Source SPD Selector.
639 @param[in, out] Size The size of the Destination SPD Selector. If it
640 not NULL and its value less than the size of
641 Source SPD Selector, the value of Source SPD
642 Selector's size will be passed to caller by this
645 @retval EFI_INVALID_PARAMETER If the Destination or Source SPD Selector is NULL
646 @retval EFI_BUFFER_TOO_SMALL If the input Size is less than size of the Source SPD Selector.
647 @retval EFI_SUCCESS Copy Source SPD Selector to the Destination SPD
648 Selector successfully.
652 DuplicateSpdSelector (
653 IN OUT EFI_IPSEC_CONFIG_SELECTOR
*DstSel
,
654 IN EFI_IPSEC_CONFIG_SELECTOR
*SrcSel
,
658 EFI_IPSEC_SPD_SELECTOR
*Dst
;
659 EFI_IPSEC_SPD_SELECTOR
*Src
;
661 Dst
= &DstSel
->SpdSelector
;
662 Src
= &SrcSel
->SpdSelector
;
664 if (Dst
== NULL
|| Src
== NULL
) {
665 return EFI_INVALID_PARAMETER
;
668 if (Size
!= NULL
&& (*Size
) < SIZE_OF_SPD_SELECTOR (Src
)) {
669 *Size
= SIZE_OF_SPD_SELECTOR (Src
);
670 return EFI_BUFFER_TOO_SMALL
;
673 // Copy the base structure of SPD selector.
675 CopyMem (Dst
, Src
, sizeof (EFI_IPSEC_SPD_SELECTOR
));
678 // Copy the local address array of SPD selector.
680 Dst
->LocalAddress
= (EFI_IP_ADDRESS_INFO
*) (Dst
+ 1);
684 sizeof (EFI_IP_ADDRESS_INFO
) * Dst
->LocalAddressCount
688 // Copy the remote address array of SPD selector.
690 Dst
->RemoteAddress
= Dst
->LocalAddress
+ Dst
->LocalAddressCount
;
694 sizeof (EFI_IP_ADDRESS_INFO
) * Dst
->RemoteAddressCount
701 Copy Source SA ID to the Destination SA ID.
703 @param[in, out] DstSel Pointer of Destination SA ID.
704 @param[in] SrcSel Pointer of Source SA ID.
705 @param[in, out] Size The size of the Destination SA ID. If it
706 not NULL and its value less than the size of
707 Source SA ID, the value of Source SA ID's size
708 will be passed to caller by this parameter.
710 @retval EFI_INVALID_PARAMETER If the Destination or Source SA ID is NULL.
711 @retval EFI_BUFFER_TOO_SMALL If the input Size less than size of source SA ID.
712 @retval EFI_SUCCESS Copy Source SA ID to the Destination SA ID successfully.
717 IN OUT EFI_IPSEC_CONFIG_SELECTOR
*DstSel
,
718 IN EFI_IPSEC_CONFIG_SELECTOR
*SrcSel
,
722 EFI_IPSEC_SA_ID
*Dst
;
723 EFI_IPSEC_SA_ID
*Src
;
728 if (Dst
== NULL
|| Src
== NULL
) {
729 return EFI_INVALID_PARAMETER
;
732 if (Size
!= NULL
&& *Size
< sizeof (EFI_IPSEC_SA_ID
)) {
733 *Size
= sizeof (EFI_IPSEC_SA_ID
);
734 return EFI_BUFFER_TOO_SMALL
;
737 CopyMem (Dst
, Src
, sizeof (EFI_IPSEC_SA_ID
));
743 Copy Source PAD ID to the Destination PAD ID.
745 @param[in, out] DstSel Pointer of Destination PAD ID.
746 @param[in] SrcSel Pointer of Source PAD ID.
747 @param[in, out] Size The size of the Destination PAD ID. If it
748 not NULL and its value less than the size of
749 Source PAD ID, the value of Source PAD ID's size
750 will be passed to caller by this parameter.
752 @retval EFI_INVALID_PARAMETER If the Destination or Source PAD ID is NULL.
753 @retval EFI_BUFFER_TOO_SMALL If the input Size less than size of source PAD ID .
754 @retval EFI_SUCCESS Copy Source PAD ID to the Destination PAD ID successfully.
759 IN OUT EFI_IPSEC_CONFIG_SELECTOR
*DstSel
,
760 IN EFI_IPSEC_CONFIG_SELECTOR
*SrcSel
,
764 EFI_IPSEC_PAD_ID
*Dst
;
765 EFI_IPSEC_PAD_ID
*Src
;
767 Dst
= &DstSel
->PadId
;
768 Src
= &SrcSel
->PadId
;
770 if (Dst
== NULL
|| Src
== NULL
) {
771 return EFI_INVALID_PARAMETER
;
774 if (Size
!= NULL
&& *Size
< sizeof (EFI_IPSEC_PAD_ID
)) {
775 *Size
= sizeof (EFI_IPSEC_PAD_ID
);
776 return EFI_BUFFER_TOO_SMALL
;
779 CopyMem (Dst
, Src
, sizeof (EFI_IPSEC_PAD_ID
));
785 Fix the value of some members of SPD Selector.
787 This function is called by IpSecCopyPolicyEntry()which copy the Policy
788 Entry into the Variable. Since some members in SPD Selector are pointers,
789 a physical address to relative address convertion is required before copying
790 this SPD entry into the variable.
792 @param[in] Selector Pointer of SPD Selector.
793 @param[in, out] Data Pointer of SPD Data.
798 IN EFI_IPSEC_SPD_SELECTOR
*Selector
,
799 IN OUT EFI_IPSEC_SPD_DATA
*Data
803 // It assumes that all ref buffers in SPD selector and data are
804 // stored in the continous memory and close to the base structure.
806 FIX_REF_BUF_ADDR (Selector
->LocalAddress
, Selector
);
807 FIX_REF_BUF_ADDR (Selector
->RemoteAddress
, Selector
);
809 if (Data
->ProcessingPolicy
!= NULL
) {
810 if (Data
->ProcessingPolicy
->TunnelOption
!= NULL
) {
811 FIX_REF_BUF_ADDR (Data
->ProcessingPolicy
->TunnelOption
, Data
);
814 FIX_REF_BUF_ADDR (Data
->ProcessingPolicy
, Data
);
820 Fix the value of some members of SA ID.
822 This function is called by IpSecCopyPolicyEntry()which copy the Policy
823 Entry into the Variable. Since some members in SA ID are pointers,
824 a physical address to relative address conversion is required before copying
825 this SAD into the variable.
827 @param[in] SaId Pointer of SA ID
828 @param[in, out] Data Pointer of SA Data.
833 IN EFI_IPSEC_SA_ID
*SaId
,
834 IN OUT EFI_IPSEC_SA_DATA2
*Data
838 // It assumes that all ref buffers in SAD selector and data are
839 // stored in the continous memory and close to the base structure.
841 if (Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
!= NULL
) {
842 FIX_REF_BUF_ADDR (Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
, Data
);
845 if (SaId
->Proto
== EfiIPsecESP
&& Data
->AlgoInfo
.EspAlgoInfo
.EncKey
!= NULL
) {
846 FIX_REF_BUF_ADDR (Data
->AlgoInfo
.EspAlgoInfo
.EncKey
, Data
);
849 if (Data
->SpdSelector
!= NULL
) {
850 if (Data
->SpdSelector
->LocalAddress
!= NULL
) {
851 FIX_REF_BUF_ADDR (Data
->SpdSelector
->LocalAddress
, Data
);
854 FIX_REF_BUF_ADDR (Data
->SpdSelector
->RemoteAddress
, Data
);
855 FIX_REF_BUF_ADDR (Data
->SpdSelector
, Data
);
861 Fix the value of some members of PAD ID.
863 This function is called by IpSecCopyPolicyEntry()which copy the Policy
864 Entry into the Variable. Since some members in PAD ID are pointers,
865 a physical address to relative address conversion is required before copying
866 this PAD into the variable.
868 @param[in] PadId Pointer of PAD ID.
869 @param[in, out] Data Pointer of PAD Data.
874 IN EFI_IPSEC_PAD_ID
*PadId
,
875 IN OUT EFI_IPSEC_PAD_DATA
*Data
879 // It assumes that all ref buffers in pad selector and data are
880 // stored in the continous memory and close to the base structure.
882 if (Data
->AuthData
!= NULL
) {
883 FIX_REF_BUF_ADDR (Data
->AuthData
, Data
);
886 if (Data
->RevocationData
!= NULL
) {
887 FIX_REF_BUF_ADDR (Data
->RevocationData
, Data
);
893 Recover the value of some members of SPD Selector.
895 This function is corresponding to FixSpdEntry(). It recovers the value of members
896 of SPD Selector that are fixed by FixSpdEntry().
898 @param[in, out] Selector Pointer of SPD Selector.
899 @param[in, out] Data Pointer of SPD Data.
904 IN OUT EFI_IPSEC_SPD_SELECTOR
*Selector
,
905 IN OUT EFI_IPSEC_SPD_DATA
*Data
909 // It assumes that all ref buffers in SPD selector and data are
910 // stored in the continous memory and close to the base structure.
912 UNFIX_REF_BUF_ADDR (Selector
->LocalAddress
, Selector
);
913 UNFIX_REF_BUF_ADDR (Selector
->RemoteAddress
, Selector
);
915 if (Data
->ProcessingPolicy
!= NULL
) {
916 UNFIX_REF_BUF_ADDR (Data
->ProcessingPolicy
, Data
);
917 if (Data
->ProcessingPolicy
->TunnelOption
!= NULL
) {
918 UNFIX_REF_BUF_ADDR (Data
->ProcessingPolicy
->TunnelOption
, Data
);
925 Recover the value of some members of SA ID.
927 This function is corresponding to FixSadEntry(). It recovers the value of members
928 of SAD ID that are fixed by FixSadEntry().
930 @param[in, out] SaId Pointer of SAD ID.
931 @param[in, out] Data Pointer of SAD Data.
936 IN OUT EFI_IPSEC_SA_ID
*SaId
,
937 IN OUT EFI_IPSEC_SA_DATA2
*Data
941 // It assumes that all ref buffers in SAD selector and data are
942 // stored in the continous memory and close to the base structure.
944 if (Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
!= NULL
) {
945 UNFIX_REF_BUF_ADDR (Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
, Data
);
948 if (SaId
->Proto
== EfiIPsecESP
&& Data
->AlgoInfo
.EspAlgoInfo
.EncKey
!= NULL
) {
949 UNFIX_REF_BUF_ADDR (Data
->AlgoInfo
.EspAlgoInfo
.EncKey
, Data
);
952 if (Data
->SpdSelector
!= NULL
) {
953 UNFIX_REF_BUF_ADDR (Data
->SpdSelector
, Data
);
954 if (Data
->SpdSelector
->LocalAddress
!= NULL
) {
955 UNFIX_REF_BUF_ADDR (Data
->SpdSelector
->LocalAddress
, Data
);
958 UNFIX_REF_BUF_ADDR (Data
->SpdSelector
->RemoteAddress
, Data
);
964 Recover the value of some members of PAD ID.
966 This function is corresponding to FixPadEntry(). It recovers the value of members
967 of PAD ID that are fixed by FixPadEntry().
969 @param[in] PadId Pointer of PAD ID.
970 @param[in, out] Data Pointer of PAD Data.
975 IN EFI_IPSEC_PAD_ID
*PadId
,
976 IN OUT EFI_IPSEC_PAD_DATA
*Data
980 // It assumes that all ref buffers in pad selector and data are
981 // stored in the continous memory and close to the base structure.
983 if (Data
->AuthData
!= NULL
) {
984 UNFIX_REF_BUF_ADDR (Data
->AuthData
, Data
);
987 if (Data
->RevocationData
!= NULL
) {
988 UNFIX_REF_BUF_ADDR (Data
->RevocationData
, Data
);
994 Set the security policy information for the EFI IPsec driver.
996 The IPsec configuration data has a unique selector/identifier separately to
997 identify a data entry.
999 @param[in] Selector Pointer to an entry selector on operated
1000 configuration data specified by DataType.
1001 A NULL Selector causes the entire specified-type
1002 configuration information to be flushed.
1003 @param[in] Data The data buffer to be set. The structure
1004 of the data buffer should be EFI_IPSEC_SPD_DATA.
1005 @param[in] Context Pointer to one entry selector that describes
1006 the expected position the new data entry will
1007 be added. If Context is NULL, the new entry will
1008 be appended the end of database.
1010 @retval EFI_INVALID_PARAMETER One or more of the following are TRUE:
1011 - Selector is not NULL and its LocalAddress
1012 is NULL or its RemoteAddress is NULL.
1013 - Data is not NULL and its Action is Protected
1014 and its plolicy is NULL.
1015 - Data is not NULL, its Action is not protected,
1016 and its policy is not NULL.
1017 - The Action of Data is Protected, its policy
1018 mode is Tunnel, and its tunnel option is NULL.
1019 - The Action of Data is protected and its policy
1020 mode is not Tunnel and it tunnel option is not NULL.
1021 @retval EFI_OUT_OF_RESOURCED The required system resource could not be allocated.
1022 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1027 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1029 IN VOID
*Context OPTIONAL
1032 EFI_IPSEC_SPD_SELECTOR
*SpdSel
;
1033 EFI_IPSEC_SPD_DATA
*SpdData
;
1034 EFI_IPSEC_SPD_SELECTOR
*InsertBefore
;
1035 LIST_ENTRY
*SpdList
;
1036 LIST_ENTRY
*SadList
;
1038 LIST_ENTRY
*EntryInsertBefore
;
1041 LIST_ENTRY
*NextEntry
;
1042 IPSEC_SPD_ENTRY
*SpdEntry
;
1043 IPSEC_SAD_ENTRY
*SadEntry
;
1047 SpdSel
= (Selector
== NULL
) ? NULL
: &Selector
->SpdSelector
;
1048 SpdData
= (Data
== NULL
) ? NULL
: (EFI_IPSEC_SPD_DATA
*) Data
;
1049 InsertBefore
= (Context
== NULL
) ? NULL
: &((EFI_IPSEC_CONFIG_SELECTOR
*) Context
)->SpdSelector
;
1050 SpdList
= &mConfigData
[IPsecConfigDataTypeSpd
];
1052 if (SpdSel
!= NULL
) {
1053 if (SpdSel
->LocalAddress
== NULL
|| SpdSel
->RemoteAddress
== NULL
) {
1054 return EFI_INVALID_PARAMETER
;
1058 if (SpdData
!= NULL
) {
1059 if ((SpdData
->Action
== EfiIPsecActionProtect
&& SpdData
->ProcessingPolicy
== NULL
) ||
1060 (SpdData
->Action
!= EfiIPsecActionProtect
&& SpdData
->ProcessingPolicy
!= NULL
)
1062 return EFI_INVALID_PARAMETER
;
1065 if (SpdData
->Action
== EfiIPsecActionProtect
) {
1066 if ((SpdData
->ProcessingPolicy
->Mode
== EfiIPsecTunnel
&& SpdData
->ProcessingPolicy
->TunnelOption
== NULL
) ||
1067 (SpdData
->ProcessingPolicy
->Mode
!= EfiIPsecTunnel
&& SpdData
->ProcessingPolicy
->TunnelOption
!= NULL
)
1069 return EFI_INVALID_PARAMETER
;
1074 // The default behavior is to insert the node ahead of the header.
1076 EntryInsertBefore
= SpdList
;
1079 // Remove the existed SPD entry.
1081 NET_LIST_FOR_EACH_SAFE (Entry
, NextEntry
, SpdList
) {
1083 SpdEntry
= IPSEC_SPD_ENTRY_FROM_LIST (Entry
);
1085 if (SpdSel
== NULL
||
1086 CompareSpdSelector ((EFI_IPSEC_CONFIG_SELECTOR
*) SpdEntry
->Selector
, (EFI_IPSEC_CONFIG_SELECTOR
*) SpdSel
)
1089 // Record the existed entry position to keep the original order.
1091 EntryInsertBefore
= SpdEntry
->List
.ForwardLink
;
1092 RemoveEntryList (&SpdEntry
->List
);
1095 // Update the reverse ref of SAD entry in the SPD.sas list.
1097 SpdSas
= &SpdEntry
->Data
->Sas
;
1100 // TODO: Deleted the related SAs.
1102 NET_LIST_FOR_EACH (Entry2
, SpdSas
) {
1103 SadEntry
= IPSEC_SAD_ENTRY_FROM_SPD (Entry2
);
1104 SadEntry
->Data
->SpdEntry
= NULL
;
1108 // Free the existed SPD entry
1110 FreePool (SpdEntry
);
1114 // Return success here if only want to remove the SPD entry.
1116 if (SpdData
== NULL
|| SpdSel
== NULL
) {
1120 // Search the appointed entry position if InsertBefore is not NULL.
1122 if (InsertBefore
!= NULL
) {
1124 NET_LIST_FOR_EACH (Entry
, SpdList
) {
1125 SpdEntry
= IPSEC_SPD_ENTRY_FROM_LIST (Entry
);
1127 if (CompareSpdSelector (
1128 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdEntry
->Selector
,
1129 (EFI_IPSEC_CONFIG_SELECTOR
*) InsertBefore
1131 EntryInsertBefore
= Entry
;
1138 // Do Padding for the different Arch.
1140 SpdEntrySize
= ALIGN_VARIABLE (sizeof (IPSEC_SPD_ENTRY
));
1141 SpdEntrySize
= ALIGN_VARIABLE (SpdEntrySize
+ (UINTN
)SIZE_OF_SPD_SELECTOR (SpdSel
));
1142 SpdEntrySize
+= IpSecGetSizeOfEfiSpdData (SpdData
);
1144 SpdEntry
= AllocateZeroPool (SpdEntrySize
);
1146 if (SpdEntry
== NULL
) {
1147 return EFI_OUT_OF_RESOURCES
;
1150 // Fix the address of Selector and Data buffer and copy them, which is
1151 // continous memory and close to the base structure of SPD entry.
1153 SpdEntry
->Selector
= (EFI_IPSEC_SPD_SELECTOR
*) ALIGN_POINTER ((SpdEntry
+ 1), sizeof (UINTN
));
1154 SpdEntry
->Data
= (IPSEC_SPD_DATA
*) ALIGN_POINTER (
1155 ((UINT8
*) SpdEntry
->Selector
+ SIZE_OF_SPD_SELECTOR (SpdSel
)),
1159 DuplicateSpdSelector (
1160 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdEntry
->Selector
,
1161 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdSel
,
1166 SpdEntry
->Data
->Name
,
1168 sizeof (SpdData
->Name
)
1170 SpdEntry
->Data
->PackageFlag
= SpdData
->PackageFlag
;
1171 SpdEntry
->Data
->Action
= SpdData
->Action
;
1174 // Fix the address of ProcessingPolicy and copy it if need, which is continous
1175 // memory and close to the base structure of SAD data.
1177 if (SpdData
->Action
!= EfiIPsecActionProtect
) {
1178 SpdEntry
->Data
->ProcessingPolicy
= NULL
;
1180 SpdEntry
->Data
->ProcessingPolicy
= (EFI_IPSEC_PROCESS_POLICY
*) ALIGN_POINTER (
1184 IpSecDuplicateProcessPolicy (SpdEntry
->Data
->ProcessingPolicy
, SpdData
->ProcessingPolicy
);
1187 // Update the sas list of the new SPD entry.
1189 InitializeListHead (&SpdEntry
->Data
->Sas
);
1191 SadList
= &mConfigData
[IPsecConfigDataTypeSad
];
1193 NET_LIST_FOR_EACH (Entry
, SadList
) {
1194 SadEntry
= IPSEC_SAD_ENTRY_FROM_LIST (Entry
);
1196 for (Index
= 0; Index
< SpdData
->SaIdCount
; Index
++) {
1199 (EFI_IPSEC_CONFIG_SELECTOR
*) &SpdData
->SaId
[Index
],
1200 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Id
1202 InsertTailList (&SpdEntry
->Data
->Sas
, &SadEntry
->BySpd
);
1203 SadEntry
->Data
->SpdEntry
= SpdEntry
;
1204 DuplicateSpdSelector (
1205 (EFI_IPSEC_CONFIG_SELECTOR
*)SadEntry
->Data
->SpdSelector
,
1206 (EFI_IPSEC_CONFIG_SELECTOR
*)SpdEntry
->Selector
,
1213 // Insert the new SPD entry.
1215 InsertTailList (EntryInsertBefore
, &SpdEntry
->List
);
1221 Set the security association information for the EFI IPsec driver.
1223 The IPsec configuration data has a unique selector/identifier separately to
1224 identify a data entry.
1226 @param[in] Selector Pointer to an entry selector on operated
1227 configuration data specified by DataType.
1228 A NULL Selector causes the entire specified-type
1229 configuration information to be flushed.
1230 @param[in] Data The data buffer to be set. The structure
1231 of the data buffer should be EFI_IPSEC_SA_DATA.
1232 @param[in] Context Pointer to one entry selector which describes
1233 the expected position the new data entry will
1234 be added. If Context is NULL,the new entry will
1235 be appended the end of database.
1237 @retval EFI_OUT_OF_RESOURCED The required system resource could not be allocated.
1238 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1243 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1245 IN VOID
*Context OPTIONAL
1248 IPSEC_SAD_ENTRY
*SadEntry
;
1249 IPSEC_SPD_ENTRY
*SpdEntry
;
1251 LIST_ENTRY
*NextEntry
;
1252 LIST_ENTRY
*SadList
;
1253 LIST_ENTRY
*SpdList
;
1254 EFI_IPSEC_SA_ID
*SaId
;
1255 EFI_IPSEC_SA_DATA2
*SaData
;
1256 EFI_IPSEC_SA_ID
*InsertBefore
;
1257 LIST_ENTRY
*EntryInsertBefore
;
1260 SaId
= (Selector
== NULL
) ? NULL
: &Selector
->SaId
;
1261 SaData
= (Data
== NULL
) ? NULL
: (EFI_IPSEC_SA_DATA2
*) Data
;
1262 InsertBefore
= (Context
== NULL
) ? NULL
: &((EFI_IPSEC_CONFIG_SELECTOR
*) Context
)->SaId
;
1263 SadList
= &mConfigData
[IPsecConfigDataTypeSad
];
1266 // The default behavior is to insert the node ahead of the header.
1268 EntryInsertBefore
= SadList
;
1271 // Remove the existed SAD entry.
1273 NET_LIST_FOR_EACH_SAFE (Entry
, NextEntry
, SadList
) {
1275 SadEntry
= IPSEC_SAD_ENTRY_FROM_LIST (Entry
);
1279 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Id
,
1280 (EFI_IPSEC_CONFIG_SELECTOR
*) SaId
1283 // Record the existed entry position to keep the original order.
1285 EntryInsertBefore
= SadEntry
->List
.ForwardLink
;
1288 // Update the related SAD.byspd field.
1290 if (SadEntry
->Data
->SpdEntry
!= NULL
) {
1291 RemoveEntryList (&SadEntry
->BySpd
);
1294 RemoveEntryList (&SadEntry
->List
);
1295 FreePool (SadEntry
);
1299 // Return success here if only want to remove the SAD entry
1301 if (SaData
== NULL
|| SaId
== NULL
) {
1305 // Search the appointed entry position if InsertBefore is not NULL.
1307 if (InsertBefore
!= NULL
) {
1309 NET_LIST_FOR_EACH (Entry
, SadList
) {
1310 SadEntry
= IPSEC_SAD_ENTRY_FROM_LIST (Entry
);
1313 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Id
,
1314 (EFI_IPSEC_CONFIG_SELECTOR
*) InsertBefore
1316 EntryInsertBefore
= Entry
;
1323 // Do Padding for different Arch.
1325 SadEntrySize
= ALIGN_VARIABLE (sizeof (IPSEC_SAD_ENTRY
));
1326 SadEntrySize
= ALIGN_VARIABLE (SadEntrySize
+ sizeof (EFI_IPSEC_SA_ID
));
1327 SadEntrySize
= ALIGN_VARIABLE (SadEntrySize
+ sizeof (IPSEC_SAD_DATA
));
1329 if (SaId
->Proto
== EfiIPsecAH
) {
1330 SadEntrySize
+= SaData
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
;
1332 SadEntrySize
= ALIGN_VARIABLE (SadEntrySize
+ SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
);
1333 SadEntrySize
+= ALIGN_VARIABLE (SaData
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
);
1336 if (SaData
->SpdSelector
!= NULL
) {
1337 SadEntrySize
+= SadEntrySize
+ (UINTN
)SIZE_OF_SPD_SELECTOR (SaData
->SpdSelector
);
1339 SadEntry
= AllocateZeroPool (SadEntrySize
);
1341 if (SadEntry
== NULL
) {
1342 return EFI_OUT_OF_RESOURCES
;
1345 // Fix the address of Id and Data buffer and copy them, which is
1346 // continous memory and close to the base structure of SAD entry.
1348 SadEntry
->Id
= (EFI_IPSEC_SA_ID
*) ALIGN_POINTER ((SadEntry
+ 1), sizeof (UINTN
));
1349 SadEntry
->Data
= (IPSEC_SAD_DATA
*) ALIGN_POINTER ((SadEntry
->Id
+ 1), sizeof (UINTN
));
1351 CopyMem (SadEntry
->Id
, SaId
, sizeof (EFI_IPSEC_SA_ID
));
1353 SadEntry
->Data
->Mode
= SaData
->Mode
;
1354 SadEntry
->Data
->SequenceNumber
= SaData
->SNCount
;
1355 SadEntry
->Data
->AntiReplayWindowSize
= SaData
->AntiReplayWindows
;
1358 &SadEntry
->Data
->AntiReplayBitmap
,
1359 sizeof (SadEntry
->Data
->AntiReplayBitmap
)
1363 &SadEntry
->Data
->AlgoInfo
,
1364 sizeof (EFI_IPSEC_ALGO_INFO
)
1367 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthAlgoId
= SaData
->AlgoInfo
.EspAlgoInfo
.AuthAlgoId
;
1368 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
= SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
;
1370 if (SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
!= 0) {
1371 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
= (VOID
*) ALIGN_POINTER ((SadEntry
->Data
+ 1), sizeof (UINTN
));
1373 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
,
1374 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKey
,
1375 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
1379 if (SaId
->Proto
== EfiIPsecESP
) {
1380 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncAlgoId
= SaData
->AlgoInfo
.EspAlgoInfo
.EncAlgoId
;
1381 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
= SaData
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
;
1383 if (SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
!= 0) {
1384 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKey
= (VOID
*) ALIGN_POINTER (
1385 ((UINT8
*) (SadEntry
->Data
+ 1) +
1386 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
),
1390 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKey
,
1391 SaData
->AlgoInfo
.EspAlgoInfo
.EncKey
,
1392 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
1398 &SadEntry
->Data
->SaLifetime
,
1399 &SaData
->SaLifetime
,
1400 sizeof (EFI_IPSEC_SA_LIFETIME
)
1403 SadEntry
->Data
->PathMTU
= SaData
->PathMTU
;
1404 SadEntry
->Data
->SpdSelector
= NULL
;
1405 SadEntry
->Data
->ESNEnabled
= FALSE
;
1406 SadEntry
->Data
->ManualSet
= SaData
->ManualSet
;
1409 // Copy Tunnel Source/Destination Address
1411 if (SaData
->Mode
== EfiIPsecTunnel
) {
1413 &SadEntry
->Data
->TunnelDestAddress
,
1414 &SaData
->TunnelDestinationAddress
,
1415 sizeof (EFI_IP_ADDRESS
)
1418 &SadEntry
->Data
->TunnelSourceAddress
,
1419 &SaData
->TunnelSourceAddress
,
1420 sizeof (EFI_IP_ADDRESS
)
1424 // Update the spd.sas list of the spd entry specified by SAD selector
1426 SpdList
= &mConfigData
[IPsecConfigDataTypeSpd
];
1428 for (Entry
= SpdList
->ForwardLink
; Entry
!= SpdList
&& SaData
->SpdSelector
!= NULL
; Entry
= Entry
->ForwardLink
) {
1430 SpdEntry
= IPSEC_SPD_ENTRY_FROM_LIST (Entry
);
1431 if (IsSubSpdSelector (
1432 (EFI_IPSEC_CONFIG_SELECTOR
*) SaData
->SpdSelector
,
1433 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdEntry
->Selector
1434 ) && SpdEntry
->Data
->Action
== EfiIPsecActionProtect
) {
1435 SadEntry
->Data
->SpdEntry
= SpdEntry
;
1436 SadEntry
->Data
->SpdSelector
= (EFI_IPSEC_SPD_SELECTOR
*)((UINT8
*)SadEntry
+
1438 (UINTN
)SIZE_OF_SPD_SELECTOR (SaData
->SpdSelector
)
1440 DuplicateSpdSelector (
1441 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Data
->SpdSelector
,
1442 (EFI_IPSEC_CONFIG_SELECTOR
*) SaData
->SpdSelector
,
1445 InsertTailList (&SpdEntry
->Data
->Sas
, &SadEntry
->BySpd
);
1449 // Insert the new SAD entry.
1451 InsertTailList (EntryInsertBefore
, &SadEntry
->List
);
1457 Set the peer authorization configuration information for the EFI IPsec driver.
1459 The IPsec configuration data has a unique selector/identifier separately to
1460 identify a data entry.
1462 @param[in] Selector Pointer to an entry selector on operated
1463 configuration data specified by DataType.
1464 A NULL Selector causes the entire specified-type
1465 configuration information to be flushed.
1466 @param[in] Data The data buffer to be set. The structure
1467 of the data buffer should be EFI_IPSEC_PAD_DATA.
1468 @param[in] Context Pointer to one entry selector that describes
1469 the expected position the new data entry will
1470 be added. If Context is NULL, the new entry will
1471 be appended the end of database.
1473 @retval EFI_OUT_OF_RESOURCES The required system resources could not be allocated.
1474 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1479 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1481 IN VOID
*Context OPTIONAL
1484 IPSEC_PAD_ENTRY
*PadEntry
;
1485 EFI_IPSEC_PAD_ID
*PadId
;
1486 EFI_IPSEC_PAD_DATA
*PadData
;
1487 LIST_ENTRY
*PadList
;
1489 LIST_ENTRY
*NextEntry
;
1490 EFI_IPSEC_PAD_ID
*InsertBefore
;
1491 LIST_ENTRY
*EntryInsertBefore
;
1494 PadId
= (Selector
== NULL
) ? NULL
: &Selector
->PadId
;
1495 PadData
= (Data
== NULL
) ? NULL
: (EFI_IPSEC_PAD_DATA
*) Data
;
1496 InsertBefore
= (Context
== NULL
) ? NULL
: &((EFI_IPSEC_CONFIG_SELECTOR
*) Context
)->PadId
;
1497 PadList
= &mConfigData
[IPsecConfigDataTypePad
];
1500 // The default behavior is to insert the node ahead of the header.
1502 EntryInsertBefore
= PadList
;
1505 // Remove the existed pad entry.
1507 NET_LIST_FOR_EACH_SAFE (Entry
, NextEntry
, PadList
) {
1509 PadEntry
= IPSEC_PAD_ENTRY_FROM_LIST (Entry
);
1511 if (PadId
== NULL
||
1512 ComparePadId ((EFI_IPSEC_CONFIG_SELECTOR
*) PadEntry
->Id
, (EFI_IPSEC_CONFIG_SELECTOR
*) PadId
)
1515 // Record the existed entry position to keep the original order.
1517 EntryInsertBefore
= PadEntry
->List
.ForwardLink
;
1518 RemoveEntryList (&PadEntry
->List
);
1520 FreePool (PadEntry
);
1524 // Return success here if only want to remove the pad entry
1526 if (PadData
== NULL
|| PadId
== NULL
) {
1530 // Search the appointed entry position if InsertBefore is not NULL.
1532 if (InsertBefore
!= NULL
) {
1534 NET_LIST_FOR_EACH (Entry
, PadList
) {
1535 PadEntry
= IPSEC_PAD_ENTRY_FROM_LIST (Entry
);
1538 (EFI_IPSEC_CONFIG_SELECTOR
*) PadEntry
->Id
,
1539 (EFI_IPSEC_CONFIG_SELECTOR
*) InsertBefore
1541 EntryInsertBefore
= Entry
;
1548 // Do PADDING for different arch.
1550 PadEntrySize
= ALIGN_VARIABLE (sizeof (IPSEC_PAD_ENTRY
));
1551 PadEntrySize
= ALIGN_VARIABLE (PadEntrySize
+ sizeof (EFI_IPSEC_PAD_ID
));
1552 PadEntrySize
= ALIGN_VARIABLE (PadEntrySize
+ sizeof (EFI_IPSEC_PAD_DATA
));
1553 PadEntrySize
= ALIGN_VARIABLE (PadEntrySize
+ (PadData
->AuthData
!= NULL
? PadData
->AuthDataSize
: 0));
1554 PadEntrySize
+= PadData
->RevocationData
!= NULL
? PadData
->RevocationDataSize
: 0;
1556 PadEntry
= AllocateZeroPool (PadEntrySize
);
1558 if (PadEntry
== NULL
) {
1559 return EFI_OUT_OF_RESOURCES
;
1562 // Fix the address of Id and Data buffer and copy them, which is
1563 // continous memory and close to the base structure of pad entry.
1565 PadEntry
->Id
= (EFI_IPSEC_PAD_ID
*) ALIGN_POINTER ((PadEntry
+ 1), sizeof (UINTN
));
1566 PadEntry
->Data
= (EFI_IPSEC_PAD_DATA
*) ALIGN_POINTER ((PadEntry
->Id
+ 1), sizeof (UINTN
));
1568 CopyMem (PadEntry
->Id
, PadId
, sizeof (EFI_IPSEC_PAD_ID
));
1570 PadEntry
->Data
->AuthProtocol
= PadData
->AuthProtocol
;
1571 PadEntry
->Data
->AuthMethod
= PadData
->AuthMethod
;
1572 PadEntry
->Data
->IkeIdFlag
= PadData
->IkeIdFlag
;
1574 if (PadData
->AuthData
!= NULL
) {
1575 PadEntry
->Data
->AuthDataSize
= PadData
->AuthDataSize
;
1576 PadEntry
->Data
->AuthData
= (VOID
*) ALIGN_POINTER (PadEntry
->Data
+ 1, sizeof (UINTN
));
1578 PadEntry
->Data
->AuthData
,
1580 PadData
->AuthDataSize
1583 PadEntry
->Data
->AuthDataSize
= 0;
1584 PadEntry
->Data
->AuthData
= NULL
;
1587 if (PadData
->RevocationData
!= NULL
) {
1588 PadEntry
->Data
->RevocationDataSize
= PadData
->RevocationDataSize
;
1589 PadEntry
->Data
->RevocationData
= (VOID
*) ALIGN_POINTER (
1590 ((UINT8
*) (PadEntry
->Data
+ 1) + PadData
->AuthDataSize
),
1594 PadEntry
->Data
->RevocationData
,
1595 PadData
->RevocationData
,
1596 PadData
->RevocationDataSize
1599 PadEntry
->Data
->RevocationDataSize
= 0;
1600 PadEntry
->Data
->RevocationData
= NULL
;
1603 // Insert the new pad entry.
1605 InsertTailList (EntryInsertBefore
, &PadEntry
->List
);
1611 This function lookup the data entry from IPsec SPD. Return the configuration
1612 value of the specified SPD Entry.
1614 @param[in] Selector Pointer to an entry selector which is an identifier
1616 @param[in, out] DataSize On output the size of data returned in Data.
1617 @param[out] Data The buffer to return the contents of the IPsec
1618 configuration data. The type of the data buffer
1619 is associated with the DataType.
1621 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1622 @retval EFI_INVALID_PARAMETER Data is NULL and *DataSize is not zero.
1623 @retval EFI_NOT_FOUND The configuration data specified by Selector is not found.
1624 @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the result. DataSize has been
1625 updated with the size needed to complete the request.
1630 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1631 IN OUT UINTN
*DataSize
,
1635 IPSEC_SPD_ENTRY
*SpdEntry
;
1636 IPSEC_SAD_ENTRY
*SadEntry
;
1637 EFI_IPSEC_SPD_SELECTOR
*SpdSel
;
1638 EFI_IPSEC_SPD_DATA
*SpdData
;
1639 LIST_ENTRY
*SpdList
;
1644 SpdSel
= &Selector
->SpdSelector
;
1645 SpdData
= (EFI_IPSEC_SPD_DATA
*) Data
;
1646 SpdList
= &mConfigData
[IPsecConfigDataTypeSpd
];
1648 NET_LIST_FOR_EACH (Entry
, SpdList
) {
1649 SpdEntry
= IPSEC_SPD_ENTRY_FROM_LIST (Entry
);
1652 // Find the required SPD entry
1654 if (CompareSpdSelector (
1655 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdSel
,
1656 (EFI_IPSEC_CONFIG_SELECTOR
*) SpdEntry
->Selector
1659 RequiredSize
= IpSecGetSizeOfSpdData (SpdEntry
->Data
);
1660 if (*DataSize
< RequiredSize
) {
1661 *DataSize
= RequiredSize
;
1662 return EFI_BUFFER_TOO_SMALL
;
1665 if (SpdData
== NULL
) {
1666 return EFI_INVALID_PARAMETER
;
1669 *DataSize
= RequiredSize
;
1672 // Extract and fill all SaId array from the SPD.sas list
1674 SpdSas
= &SpdEntry
->Data
->Sas
;
1675 SpdData
->SaIdCount
= 0;
1677 NET_LIST_FOR_EACH (Entry
, SpdSas
) {
1678 SadEntry
= IPSEC_SAD_ENTRY_FROM_SPD (Entry
);
1680 &SpdData
->SaId
[SpdData
->SaIdCount
++],
1682 sizeof (EFI_IPSEC_SA_ID
)
1686 // Fill the other fields in SPD data.
1688 CopyMem (SpdData
->Name
, SpdEntry
->Data
->Name
, sizeof (SpdData
->Name
));
1690 SpdData
->PackageFlag
= SpdEntry
->Data
->PackageFlag
;
1691 SpdData
->Action
= SpdEntry
->Data
->Action
;
1693 if (SpdData
->Action
!= EfiIPsecActionProtect
) {
1694 SpdData
->ProcessingPolicy
= NULL
;
1696 SpdData
->ProcessingPolicy
= (EFI_IPSEC_PROCESS_POLICY
*) ((UINT8
*) SpdData
+ sizeof (EFI_IPSEC_SPD_DATA
) + (SpdData
->SaIdCount
- 1) * sizeof (EFI_IPSEC_SA_ID
));
1698 IpSecDuplicateProcessPolicy (
1699 SpdData
->ProcessingPolicy
,
1700 SpdEntry
->Data
->ProcessingPolicy
1708 return EFI_NOT_FOUND
;
1712 This function lookup the data entry from IPsec SAD. Return the configuration
1713 value of the specified SAD Entry.
1715 @param[in] Selector Pointer to an entry selector which is an identifier
1717 @param[in, out] DataSize On output, the size of data returned in Data.
1718 @param[out] Data The buffer to return the contents of the IPsec
1719 configuration data. The type of the data buffer
1720 is associated with the DataType.
1722 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1723 @retval EFI_NOT_FOUND The configuration data specified by Selector is not found.
1724 @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the result. DataSize has been
1725 updated with the size needed to complete the request.
1730 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1731 IN OUT UINTN
*DataSize
,
1735 IPSEC_SAD_ENTRY
*SadEntry
;
1737 LIST_ENTRY
*SadList
;
1738 EFI_IPSEC_SA_ID
*SaId
;
1739 EFI_IPSEC_SA_DATA2
*SaData
;
1742 SaId
= &Selector
->SaId
;
1743 SaData
= (EFI_IPSEC_SA_DATA2
*) Data
;
1744 SadList
= &mConfigData
[IPsecConfigDataTypeSad
];
1746 NET_LIST_FOR_EACH (Entry
, SadList
) {
1747 SadEntry
= IPSEC_SAD_ENTRY_FROM_LIST (Entry
);
1750 // Find the required SAD entry.
1753 (EFI_IPSEC_CONFIG_SELECTOR
*) SaId
,
1754 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Id
1757 // Calculate the required size of the SAD entry.
1758 // Data Layout is follows:
1759 // |EFI_IPSEC_SA_DATA
1761 // |EncryptKey (Optional)
1762 // |SpdSelector (Optional)
1764 RequiredSize
= ALIGN_VARIABLE (sizeof (EFI_IPSEC_SA_DATA2
));
1766 if (SaId
->Proto
== EfiIPsecAH
) {
1767 RequiredSize
= ALIGN_VARIABLE (RequiredSize
+ SadEntry
->Data
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
);
1769 RequiredSize
= ALIGN_VARIABLE (RequiredSize
+ SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
);
1770 RequiredSize
= ALIGN_VARIABLE (RequiredSize
+ SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
);
1773 if (SadEntry
->Data
->SpdSelector
!= NULL
) {
1774 RequiredSize
+= SIZE_OF_SPD_SELECTOR (SadEntry
->Data
->SpdSelector
);
1777 if (*DataSize
< RequiredSize
) {
1778 *DataSize
= RequiredSize
;
1779 return EFI_BUFFER_TOO_SMALL
;
1783 // Fill the data fields of SAD entry.
1785 *DataSize
= RequiredSize
;
1786 SaData
->Mode
= SadEntry
->Data
->Mode
;
1787 SaData
->SNCount
= SadEntry
->Data
->SequenceNumber
;
1788 SaData
->AntiReplayWindows
= SadEntry
->Data
->AntiReplayWindowSize
;
1791 &SaData
->SaLifetime
,
1792 &SadEntry
->Data
->SaLifetime
,
1793 sizeof (EFI_IPSEC_SA_LIFETIME
)
1798 sizeof (EFI_IPSEC_ALGO_INFO
)
1801 if (SaId
->Proto
== EfiIPsecAH
) {
1803 // Copy AH alogrithm INFO to SaData
1805 SaData
->AlgoInfo
.AhAlgoInfo
.AuthAlgoId
= SadEntry
->Data
->AlgoInfo
.AhAlgoInfo
.AuthAlgoId
;
1806 SaData
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
= SadEntry
->Data
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
;
1807 if (SaData
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
!= 0) {
1808 SaData
->AlgoInfo
.AhAlgoInfo
.AuthKey
= (VOID
*) ALIGN_POINTER ((SaData
+ 1), sizeof (UINTN
));
1810 SaData
->AlgoInfo
.AhAlgoInfo
.AuthKey
,
1811 SadEntry
->Data
->AlgoInfo
.AhAlgoInfo
.AuthKey
,
1812 SaData
->AlgoInfo
.AhAlgoInfo
.AuthKeyLength
1815 } else if (SaId
->Proto
== EfiIPsecESP
) {
1817 // Copy ESP alogrithem INFO to SaData
1819 SaData
->AlgoInfo
.EspAlgoInfo
.AuthAlgoId
= SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthAlgoId
;
1820 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
= SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
;
1821 if (SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
!= 0) {
1822 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKey
= (VOID
*) ALIGN_POINTER ((SaData
+ 1), sizeof (UINTN
));
1824 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKey
,
1825 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.AuthKey
,
1826 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
1830 SaData
->AlgoInfo
.EspAlgoInfo
.EncAlgoId
= SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncAlgoId
;
1831 SaData
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
= SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
;
1833 if (SaData
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
!= 0) {
1834 SaData
->AlgoInfo
.EspAlgoInfo
.EncKey
= (VOID
*) ALIGN_POINTER (
1835 ((UINT8
*) (SaData
+ 1) +
1836 SaData
->AlgoInfo
.EspAlgoInfo
.AuthKeyLength
),
1840 SaData
->AlgoInfo
.EspAlgoInfo
.EncKey
,
1841 SadEntry
->Data
->AlgoInfo
.EspAlgoInfo
.EncKey
,
1842 SaData
->AlgoInfo
.EspAlgoInfo
.EncKeyLength
1847 SaData
->PathMTU
= SadEntry
->Data
->PathMTU
;
1850 // Fill Tunnel Address if it is Tunnel Mode
1852 if (SadEntry
->Data
->Mode
== EfiIPsecTunnel
) {
1854 &SaData
->TunnelDestinationAddress
,
1855 &SadEntry
->Data
->TunnelDestAddress
,
1856 sizeof (EFI_IP_ADDRESS
)
1859 &SaData
->TunnelSourceAddress
,
1860 &SadEntry
->Data
->TunnelSourceAddress
,
1861 sizeof (EFI_IP_ADDRESS
)
1865 // Fill the spd selector field of SAD data
1867 if (SadEntry
->Data
->SpdSelector
!= NULL
) {
1869 SaData
->SpdSelector
= (EFI_IPSEC_SPD_SELECTOR
*) (
1872 SIZE_OF_SPD_SELECTOR (SadEntry
->Data
->SpdSelector
)
1875 DuplicateSpdSelector (
1876 (EFI_IPSEC_CONFIG_SELECTOR
*) SaData
->SpdSelector
,
1877 (EFI_IPSEC_CONFIG_SELECTOR
*) SadEntry
->Data
->SpdSelector
,
1883 SaData
->SpdSelector
= NULL
;
1886 SaData
->ManualSet
= SadEntry
->Data
->ManualSet
;
1892 return EFI_NOT_FOUND
;
1896 This function lookup the data entry from IPsec PAD. Return the configuration
1897 value of the specified PAD Entry.
1899 @param[in] Selector Pointer to an entry selector which is an identifier
1901 @param[in, out] DataSize On output the size of data returned in Data.
1902 @param[out] Data The buffer to return the contents of the IPsec
1903 configuration data. The type of the data buffer
1904 is associated with the DataType.
1906 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
1907 @retval EFI_NOT_FOUND The configuration data specified by Selector is not found.
1908 @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the result. DataSize has been
1909 updated with the size needed to complete the request.
1914 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
1915 IN OUT UINTN
*DataSize
,
1919 IPSEC_PAD_ENTRY
*PadEntry
;
1920 LIST_ENTRY
*PadList
;
1922 EFI_IPSEC_PAD_ID
*PadId
;
1923 EFI_IPSEC_PAD_DATA
*PadData
;
1926 PadId
= &Selector
->PadId
;
1927 PadData
= (EFI_IPSEC_PAD_DATA
*) Data
;
1928 PadList
= &mConfigData
[IPsecConfigDataTypePad
];
1930 NET_LIST_FOR_EACH (Entry
, PadList
) {
1931 PadEntry
= IPSEC_PAD_ENTRY_FROM_LIST (Entry
);
1934 // Find the required pad entry.
1937 (EFI_IPSEC_CONFIG_SELECTOR
*) PadId
,
1938 (EFI_IPSEC_CONFIG_SELECTOR
*) PadEntry
->Id
1941 // Calculate the required size of the pad entry.
1943 RequiredSize
= ALIGN_VARIABLE (sizeof (EFI_IPSEC_PAD_DATA
));
1944 RequiredSize
= ALIGN_VARIABLE (RequiredSize
+ PadEntry
->Data
->AuthDataSize
);
1945 RequiredSize
+= PadEntry
->Data
->RevocationDataSize
;
1947 if (*DataSize
< RequiredSize
) {
1948 *DataSize
= RequiredSize
;
1949 return EFI_BUFFER_TOO_SMALL
;
1952 // Fill the data fields of pad entry
1954 *DataSize
= RequiredSize
;
1955 PadData
->AuthProtocol
= PadEntry
->Data
->AuthProtocol
;
1956 PadData
->AuthMethod
= PadEntry
->Data
->AuthMethod
;
1957 PadData
->IkeIdFlag
= PadEntry
->Data
->IkeIdFlag
;
1960 // Copy Authentication data.
1962 if (PadEntry
->Data
->AuthData
!= NULL
) {
1964 PadData
->AuthDataSize
= PadEntry
->Data
->AuthDataSize
;
1965 PadData
->AuthData
= (VOID
*) ALIGN_POINTER ((PadData
+ 1), sizeof (UINTN
));
1968 PadEntry
->Data
->AuthData
,
1969 PadData
->AuthDataSize
1973 PadData
->AuthDataSize
= 0;
1974 PadData
->AuthData
= NULL
;
1977 // Copy Revocation Data.
1979 if (PadEntry
->Data
->RevocationData
!= NULL
) {
1981 PadData
->RevocationDataSize
= PadEntry
->Data
->RevocationDataSize
;
1982 PadData
->RevocationData
= (VOID
*) ALIGN_POINTER (
1983 ((UINT8
*) (PadData
+ 1) + PadData
->AuthDataSize
),
1987 PadData
->RevocationData
,
1988 PadEntry
->Data
->RevocationData
,
1989 PadData
->RevocationDataSize
1993 PadData
->RevocationDataSize
= 0;
1994 PadData
->RevocationData
= NULL
;
2001 return EFI_NOT_FOUND
;
2005 Copy Source Process Policy to the Destination Process Policy.
2007 @param[in] Dst Pointer to the Source Process Policy.
2008 @param[in] Src Pointer to the Destination Process Policy.
2012 IpSecDuplicateProcessPolicy (
2013 IN EFI_IPSEC_PROCESS_POLICY
*Dst
,
2014 IN EFI_IPSEC_PROCESS_POLICY
*Src
2018 // Firstly copy the structure content itself.
2020 CopyMem (Dst
, Src
, sizeof (EFI_IPSEC_PROCESS_POLICY
));
2023 // Recursively copy the tunnel option if needed.
2025 if (Dst
->Mode
!= EfiIPsecTunnel
) {
2026 ASSERT (Dst
->TunnelOption
== NULL
);
2028 Dst
->TunnelOption
= (EFI_IPSEC_TUNNEL_OPTION
*) ALIGN_POINTER ((Dst
+ 1), sizeof (UINTN
));
2032 sizeof (EFI_IPSEC_TUNNEL_OPTION
)
2038 Calculate the a whole size of EFI_IPSEC_SPD_DATA, which includes the buffer size pointed
2039 to by the pointer members.
2041 @param[in] SpdData Pointer to a specified EFI_IPSEC_SPD_DATA.
2043 @return the whole size the specified EFI_IPSEC_SPD_DATA.
2047 IpSecGetSizeOfEfiSpdData (
2048 IN EFI_IPSEC_SPD_DATA
*SpdData
2053 Size
= ALIGN_VARIABLE (sizeof (IPSEC_SPD_DATA
));
2055 if (SpdData
->Action
== EfiIPsecActionProtect
) {
2056 Size
= ALIGN_VARIABLE (Size
+ sizeof (EFI_IPSEC_PROCESS_POLICY
));
2058 if (SpdData
->ProcessingPolicy
->Mode
== EfiIPsecTunnel
) {
2059 Size
= ALIGN_VARIABLE (Size
+ sizeof (EFI_IPSEC_TUNNEL_OPTION
));
2067 Calculate the a whole size of IPSEC_SPD_DATA which includes the buffer size pointed
2068 to by the pointer members and the buffer size used by the Sa List.
2070 @param[in] SpdData Pointer to the specified IPSEC_SPD_DATA.
2072 @return the whole size of IPSEC_SPD_DATA.
2076 IpSecGetSizeOfSpdData (
2077 IN IPSEC_SPD_DATA
*SpdData
2083 Size
= sizeof (EFI_IPSEC_SPD_DATA
) - sizeof (EFI_IPSEC_SA_ID
);
2085 if (SpdData
->Action
== EfiIPsecActionProtect
) {
2086 Size
+= sizeof (EFI_IPSEC_PROCESS_POLICY
);
2088 if (SpdData
->ProcessingPolicy
->Mode
== EfiIPsecTunnel
) {
2089 Size
+= sizeof (EFI_IPSEC_TUNNEL_OPTION
);
2093 NET_LIST_FOR_EACH (Link
, &SpdData
->Sas
) {
2094 Size
+= sizeof (EFI_IPSEC_SA_ID
);
2101 Get the IPsec Variable.
2103 Get the all variables which start with the string contained in VaraiableName.
2104 Since all IPsec related variable store in continual space, those kinds of
2105 variable can be searched by the EfiGetNextVariableName. Those variables also are
2106 returned in a continual buffer.
2108 @param[in] VariableName Pointer to a specified Variable Name.
2109 @param[in] VendorGuid Pointer to a specified Vendor Guid.
2110 @param[in] Attributes Point to memory location to return the attributes
2111 of variable. If the point is NULL, the parameter
2113 @param[in, out] DataSize As input, point to the maximum size of return
2114 Data-Buffer. As output, point to the actual
2115 size of the returned Data-Buffer.
2116 @param[in] Data Point to return Data-Buffer.
2118 @retval EFI_ABORTED If the Variable size which contained in the variable
2119 structure doesn't match the variable size obtained
2120 from the EFIGetVariable.
2121 @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the result. DataSize has
2122 been updated with the size needed to complete the request.
2123 @retval EFI_SUCCESS The function completed successfully.
2124 @retval others Other errors found during the variable getting.
2128 IN CHAR16
*VariableName
,
2129 IN EFI_GUID
*VendorGuid
,
2130 IN UINT32
*Attributes
, OPTIONAL
2131 IN OUT UINTN
*DataSize
,
2136 EFI_GUID VendorGuidI
;
2137 UINTN VariableNameLength
;
2138 CHAR16
*VariableNameI
;
2139 UINTN VariableNameISize
;
2140 UINTN VariableNameISizeNew
;
2141 UINTN VariableIndex
;
2142 UINTN VariableCount
;
2143 IP_SEC_VARIABLE_INFO IpSecVariableInfo
;
2147 // The variable name constructor is "VariableName + Info/0001/0002/... + NULL".
2148 // So the varialbe name is like "VariableNameInfo", "VariableName0001", ...
2149 // "VariableNameNULL".
2151 VariableNameLength
= StrLen (VariableName
);
2152 VariableNameISize
= (VariableNameLength
+ 5) * sizeof (CHAR16
);
2153 VariableNameI
= AllocateZeroPool (VariableNameISize
);
2154 ASSERT (VariableNameI
!= NULL
);
2157 // Construct the varible name of ipsecconfig meta data.
2159 UnicodeSPrint (VariableNameI
, VariableNameISize
, L
"%s%s", VariableName
, L
"Info");
2161 DataSizeI
= sizeof (IpSecVariableInfo
);
2163 Status
= gRT
->GetVariable (
2170 if (EFI_ERROR (Status
)) {
2174 if (*DataSize
< IpSecVariableInfo
.VariableSize
) {
2175 *DataSize
= IpSecVariableInfo
.VariableSize
;
2176 Status
= EFI_BUFFER_TOO_SMALL
;
2180 VariableCount
= IpSecVariableInfo
.VariableCount
;
2181 VariableNameI
[0] = L
'\0';
2183 while (VariableCount
!= 0) {
2185 // Get the variable name one by one in the variable database.
2187 VariableNameISizeNew
= VariableNameISize
;
2188 Status
= gRT
->GetNextVariableName (
2189 &VariableNameISizeNew
,
2193 if (Status
== EFI_BUFFER_TOO_SMALL
) {
2194 VariableNameI
= ReallocatePool (
2196 VariableNameISizeNew
,
2199 if (VariableNameI
== NULL
) {
2200 Status
= EFI_OUT_OF_RESOURCES
;
2203 VariableNameISize
= VariableNameISizeNew
;
2205 Status
= gRT
->GetNextVariableName (
2206 &VariableNameISizeNew
,
2212 if (EFI_ERROR (Status
)) {
2216 // Check whether the current variable is the required "ipsecconfig".
2218 if (StrnCmp (VariableNameI
, VariableName
, VariableNameLength
) == 0 ||
2219 CompareGuid (VendorGuid
, &VendorGuidI
)
2222 // Parse the variable count of the current ipsecconfig data.
2224 VariableIndex
= StrDecimalToUintn (VariableNameI
+ VariableNameLength
);
2225 if (VariableIndex
!= 0 && VariableIndex
<= IpSecVariableInfo
.VariableCount
) {
2227 // Get the variable size of the current ipsecconfig data.
2230 Status
= gRT
->GetVariable (
2237 ASSERT (Status
== EFI_BUFFER_TOO_SMALL
);
2239 // Validate the variable count and variable size.
2241 if (VariableIndex
!= IpSecVariableInfo
.VariableCount
) {
2243 // If the varaibe is not the last one, its size should be the max
2244 // size of the single variable.
2246 if (DataSizeI
!= IpSecVariableInfo
.SingleVariableSize
) {
2250 if (DataSizeI
!= IpSecVariableInfo
.VariableSize
% IpSecVariableInfo
.SingleVariableSize
) {
2255 // Get the variable data of the current ipsecconfig data and
2256 // store it into user buffer continously.
2258 Status
= gRT
->GetVariable (
2263 (UINT8
*) Data
+ (VariableIndex
- 1) * IpSecVariableInfo
.SingleVariableSize
2265 ASSERT_EFI_ERROR (Status
);
2271 // The VariableCount in "VariableNameInfo" varaible should have the correct
2272 // numbers of variables which name starts with VariableName.
2274 if (VariableCount
!= 0) {
2275 Status
= EFI_ABORTED
;
2279 if (VariableNameI
!= NULL
) {
2280 FreePool (VariableNameI
);
2286 Set the IPsec variables.
2288 Set all IPsec variables which start with the specified variable name. Those variables
2291 @param[in] VariableName The name of the vendor's variable. It is a
2292 Null-Terminated Unicode String.
2293 @param[in] VendorGuid Unify identifier for vendor.
2294 @param[in] Attributes Point to memory location to return the attributes of
2295 variable. If the point is NULL, the parameter would be ignored.
2296 @param[in] DataSize The size in bytes of Data-Buffer.
2297 @param[in] Data Points to the content of the variable.
2299 @retval EFI_SUCCESS The firmware successfully stored the variable and its data, as
2300 defined by the Attributes.
2301 @retval others Storing the variables failed.
2306 IN CHAR16
*VariableName
,
2307 IN EFI_GUID
*VendorGuid
,
2308 IN UINT32 Attributes
,
2314 CHAR16
*VariableNameI
;
2315 UINTN VariableNameSize
;
2316 UINTN VariableIndex
;
2317 IP_SEC_VARIABLE_INFO IpSecVariableInfo
;
2318 UINT64 MaximumVariableStorageSize
;
2319 UINT64 RemainingVariableStorageSize
;
2320 UINT64 MaximumVariableSize
;
2322 Status
= gRT
->QueryVariableInfo (
2324 &MaximumVariableStorageSize
,
2325 &RemainingVariableStorageSize
,
2326 &MaximumVariableSize
2328 if (EFI_ERROR (Status
)) {
2333 // "VariableName + Info/0001/0002/... + NULL"
2335 VariableNameSize
= (StrLen (VariableName
) + 5) * sizeof (CHAR16
);
2336 VariableNameI
= AllocateZeroPool (VariableNameSize
);
2338 if (VariableNameI
== NULL
) {
2339 Status
= EFI_OUT_OF_RESOURCES
;
2343 // Construct the variable of ipsecconfig general information. Like the total
2344 // numbers of the Ipsecconfig variables, the total size of all ipsecconfig variables.
2346 UnicodeSPrint (VariableNameI
, VariableNameSize
, L
"%s%s", VariableName
, L
"Info");
2347 MaximumVariableSize
-= VariableNameSize
;
2349 IpSecVariableInfo
.VariableCount
= (UINT32
) ((DataSize
+ (UINTN
) MaximumVariableSize
- 1) / (UINTN
) MaximumVariableSize
);
2350 IpSecVariableInfo
.VariableSize
= (UINT32
) DataSize
;
2351 IpSecVariableInfo
.SingleVariableSize
= (UINT32
) MaximumVariableSize
;
2354 // Set the variable of ipsecconfig general information.
2356 Status
= gRT
->SetVariable (
2360 sizeof (IpSecVariableInfo
),
2363 if (EFI_ERROR (Status
)) {
2364 DEBUG ((DEBUG_ERROR
, "Error set ipsecconfig meta data with %r\n", Status
));
2368 for (VariableIndex
= 0; VariableIndex
< IpSecVariableInfo
.VariableCount
; VariableIndex
++) {
2370 // Construct and set the variable of ipsecconfig data one by one.
2371 // The index of variable name begin from 0001, and the varaible name
2372 // likes "VariableName0001", "VaraiableName0002"....
2374 UnicodeSPrint (VariableNameI
, VariableNameSize
, L
"%s%04d", VariableName
, VariableIndex
+ 1);
2375 Status
= gRT
->SetVariable (
2379 (VariableIndex
== IpSecVariableInfo
.VariableCount
- 1) ?
2380 (DataSize
% (UINTN
) MaximumVariableSize
) :
2381 (UINTN
) MaximumVariableSize
,
2382 (UINT8
*) Data
+ VariableIndex
* (UINTN
) MaximumVariableSize
2385 if (EFI_ERROR (Status
)) {
2386 DEBUG ((DEBUG_ERROR
, "Error set ipsecconfig variable data with %r\n", Status
));
2392 if (VariableNameI
!= NULL
) {
2393 FreePool (VariableNameI
);
2400 Return the configuration value for the EFI IPsec driver.
2402 This function lookup the data entry from IPsec database or IKEv2 configuration
2403 information. The expected data type and unique identification are described in
2404 DataType and Selector parameters.
2406 @param[in] This Pointer to the EFI_IPSEC_CONFIG_PROTOCOL instance.
2407 @param[in] DataType The type of data to retrieve.
2408 @param[in] Selector Pointer to an entry selector that is an identifier of the IPsec
2409 configuration data entry.
2410 @param[in, out] DataSize On output the size of data returned in Data.
2411 @param[out] Data The buffer to return the contents of the IPsec configuration data.
2412 The type of the data buffer associated with the DataType.
2414 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
2415 @retval EFI_INVALID_PARAMETER One or more of the followings are TRUE:
2419 - Data is NULL and *DataSize is not zero
2420 @retval EFI_NOT_FOUND The configuration data specified by Selector is not found.
2421 @retval EFI_UNSUPPORTED The specified DataType is not supported.
2422 @retval EFI_BUFFER_TOO_SMALL The DataSize is too small for the result. DataSize has been
2423 updated with the size needed to complete the request.
2428 EfiIpSecConfigGetData (
2429 IN EFI_IPSEC_CONFIG_PROTOCOL
*This
,
2430 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2431 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
2432 IN OUT UINTN
*DataSize
,
2436 if (This
== NULL
|| Selector
== NULL
|| DataSize
== NULL
) {
2437 return EFI_INVALID_PARAMETER
;
2440 if (*DataSize
!= 0 && Data
== NULL
) {
2441 return EFI_INVALID_PARAMETER
;
2444 if (DataType
>= IPsecConfigDataTypeMaximum
) {
2445 return EFI_UNSUPPORTED
;
2448 return mGetPolicyEntry
[DataType
](Selector
, DataSize
, Data
);
2452 Set the security association, security policy and peer authorization configuration
2453 information for the EFI IPsec driver.
2455 This function is used to set the IPsec configuration information of type DataType for
2456 the EFI IPsec driver.
2457 The IPsec configuration data has a unique selector/identifier separately to identify
2458 a data entry. The selector structure depends on DataType's definition.
2459 Using SetData() with a Data of NULL causes the IPsec configuration data entry identified
2460 by DataType and Selector to be deleted.
2462 @param[in] This Pointer to the EFI_IPSEC_CONFIG_PROTOCOL instance.
2463 @param[in] DataType The type of data to be set.
2464 @param[in] Selector Pointer to an entry selector on operated configuration data
2465 specified by DataType. A NULL Selector causes the entire
2466 specified-type configuration information to be flushed.
2467 @param[in] Data The data buffer to be set. The structure of the data buffer is
2468 associated with the DataType.
2469 @param[in] InsertBefore Pointer to one entry selector which describes the expected
2470 position the new data entry will be added. If InsertBefore is NULL,
2471 the new entry will be appended to the end of the database.
2473 @retval EFI_SUCCESS The specified configuration entry data was set successfully.
2474 @retval EFI_INVALID_PARAMETER One or more of the following are TRUE:
2476 @retval EFI_UNSUPPORTED The specified DataType is not supported.
2477 @retval EFI_OUT_OF_RESOURCED The required system resource could not be allocated.
2482 EfiIpSecConfigSetData (
2483 IN EFI_IPSEC_CONFIG_PROTOCOL
*This
,
2484 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2485 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
2487 IN EFI_IPSEC_CONFIG_SELECTOR
*InsertBefore OPTIONAL
2493 return EFI_INVALID_PARAMETER
;
2496 if (DataType
>= IPsecConfigDataTypeMaximum
) {
2497 return EFI_UNSUPPORTED
;
2500 Status
= mSetPolicyEntry
[DataType
](Selector
, Data
, InsertBefore
);
2502 if (!EFI_ERROR (Status
) && !mSetBySelf
) {
2504 // Save the updated config data into variable.
2513 Enumerates the current selector for IPsec configuration data entry.
2515 This function is called multiple times to retrieve the entry Selector in IPsec
2516 configuration database. On each call to GetNextSelector(), the next entry
2517 Selector are retrieved into the output interface.
2519 If the entire IPsec configuration database has been iterated, the error
2520 EFI_NOT_FOUND is returned.
2521 If the Selector buffer is too small for the next Selector copy, an
2522 EFI_BUFFER_TOO_SMALL error is returned, and SelectorSize is updated to reflect
2523 the size of buffer needed.
2525 On the initial call to GetNextSelector() to start the IPsec configuration database
2526 search, a pointer to the buffer with all zero value is passed in Selector. Calls
2527 to SetData() between calls to GetNextSelector may produce unpredictable results.
2529 @param[in] This Pointer to the EFI_IPSEC_CONFIG_PROTOCOL instance.
2530 @param[in] DataType The type of IPsec configuration data to retrieve.
2531 @param[in, out] SelectorSize The size of the Selector buffer.
2532 @param[in, out] Selector On input, supplies the pointer to last Selector that was
2533 returned by GetNextSelector().
2534 On output, returns one copy of the current entry Selector
2535 of a given DataType.
2537 @retval EFI_SUCCESS The specified configuration data was obtained successfully.
2538 @retval EFI_INVALID_PARAMETER One or more of the followings are TRUE:
2540 - SelectorSize is NULL.
2542 @retval EFI_NOT_FOUND The next configuration data entry was not found.
2543 @retval EFI_UNSUPPORTED The specified DataType is not supported.
2544 @retval EFI_BUFFER_TOO_SMALL The SelectorSize is too small for the result. This parameter
2545 has been updated with the size needed to complete the search
2551 EfiIpSecConfigGetNextSelector (
2552 IN EFI_IPSEC_CONFIG_PROTOCOL
*This
,
2553 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2554 IN OUT UINTN
*SelectorSize
,
2555 IN OUT EFI_IPSEC_CONFIG_SELECTOR
*Selector
2559 IPSEC_COMMON_POLICY_ENTRY
*CommonEntry
;
2562 if (This
== NULL
|| Selector
== NULL
|| SelectorSize
== NULL
) {
2563 return EFI_INVALID_PARAMETER
;
2566 if (DataType
>= IPsecConfigDataTypeMaximum
) {
2567 return EFI_UNSUPPORTED
;
2572 NET_LIST_FOR_EACH (Link
, &mConfigData
[DataType
]) {
2573 CommonEntry
= BASE_CR (Link
, IPSEC_COMMON_POLICY_ENTRY
, List
);
2575 if (IsFound
|| (BOOLEAN
)(mIsZeroSelector
[DataType
](Selector
))) {
2577 // If found the appointed entry, then duplicate the next one and return,
2578 // or if the appointed entry is zero, then return the first one directly.
2580 return mDuplicateSelector
[DataType
](Selector
, CommonEntry
->Selector
, SelectorSize
);
2583 // Set the flag if find the appointed entry.
2585 IsFound
= mCompareSelector
[DataType
](Selector
, CommonEntry
->Selector
);
2589 return EFI_NOT_FOUND
;
2593 Register an event that is to be signaled whenever a configuration process on the
2594 specified IPsec configuration information is done.
2596 The register function is not surpport now and always returns EFI_UNSUPPORTED.
2598 @param[in] This Pointer to the EFI_IPSEC_CONFIG_PROTOCOL instance.
2599 @param[in] DataType The type of data to be registered the event for.
2600 @param[in] Event The event to be registered.
2602 @retval EFI_SUCCESS The event is registered successfully.
2603 @retval EFI_INVALID_PARAMETER This is NULL or Event is NULL.
2604 @retval EFI_ACCESS_DENIED The Event is already registered for the DataType.
2605 @retval EFI_UNSUPPORTED The notify registration is unsupported, or the specified
2606 DataType is not supported.
2611 EfiIpSecConfigRegisterNotify (
2612 IN EFI_IPSEC_CONFIG_PROTOCOL
*This
,
2613 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2617 return EFI_UNSUPPORTED
;
2621 Remove the specified event that was previously registered on the specified IPsec
2624 This function is not support now and alwasy return EFI_UNSUPPORTED.
2626 @param[in] This Pointer to the EFI_IPSEC_CONFIG_PROTOCOL instance.
2627 @param[in] DataType The configuration data type to remove the registered event for.
2628 @param[in] Event The event to be unregistered.
2630 @retval EFI_SUCCESS The event was removed successfully.
2631 @retval EFI_NOT_FOUND The Event specified by DataType could not be found in the
2633 @retval EFI_INVALID_PARAMETER This is NULL or Event is NULL.
2634 @retval EFI_UNSUPPORTED The notify registration is unsupported, or the specified
2635 DataType is not supported.
2640 EfiIpSecConfigUnregisterNotify (
2641 IN EFI_IPSEC_CONFIG_PROTOCOL
*This
,
2642 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2646 return EFI_UNSUPPORTED
;
2650 Copy whole data in specified EFI_SIPEC_CONFIG_SELECTOR and the Data to a buffer.
2652 This function is a caller defined function, and it is called by the IpSecVisitConfigData().
2653 The orignal caller is IpSecConfigSave(), which calls the IpsecVisitConfigData() to
2654 copy all types of IPsec Config datas into one buffer and store this buffer into firmware in
2655 the form of several variables.
2657 @param[in] Type A specified IPSEC_CONFIG_DATA_TYPE.
2658 @param[in] Selector Points to a EFI_IPSEC_CONFIG_SELECTOR to be copied
2660 @param[in] Data Points to data to be copied to the buffer. The
2661 Data type is related to the Type.
2662 @param[in] SelectorSize The size of the Selector.
2663 @param[in] DataSize The size of the Data.
2664 @param[in, out] Buffer The buffer to store the Selector and Data.
2666 @retval EFI_SUCCESS Copy the Selector and Data to a buffer successfully.
2667 @retval EFI_OUT_OF_RESOURCES The required system resource could not be allocated.
2671 IpSecCopyPolicyEntry (
2672 IN EFI_IPSEC_CONFIG_DATA_TYPE Type
,
2673 IN EFI_IPSEC_CONFIG_SELECTOR
*Selector
,
2675 IN UINTN SelectorSize
,
2677 IN OUT IPSEC_VARIABLE_BUFFER
*Buffer
2680 IPSEC_VAR_ITEM_HEADER SelectorHeader
;
2681 IPSEC_VAR_ITEM_HEADER DataHeader
;
2685 if (Type
== IPsecConfigDataTypeSad
) {
2687 // Don't save automatically-generated SA entry into variable.
2689 if (((EFI_IPSEC_SA_DATA2
*) Data
)->ManualSet
== FALSE
) {
2694 // Increase the capacity size of the buffer if needed.
2696 EntrySize
= ALIGN_VARIABLE (sizeof (SelectorHeader
));
2697 EntrySize
= ALIGN_VARIABLE (EntrySize
+ SelectorSize
);
2698 EntrySize
= ALIGN_VARIABLE (EntrySize
+ sizeof (SelectorHeader
));
2699 EntrySize
= ALIGN_VARIABLE (EntrySize
+ DataSize
);
2701 //EntrySize = SelectorSize + DataSize + 2 * sizeof (SelectorHeader);
2702 if (Buffer
->Capacity
- Buffer
->Size
< EntrySize
) {
2704 // Calculate the required buffer
2706 Buffer
->Capacity
+= EntrySize
;
2707 TempPoint
= AllocatePool (Buffer
->Capacity
);
2709 if (TempPoint
== NULL
) {
2710 return EFI_OUT_OF_RESOURCES
;
2713 // Copy the old Buffer to new buffer and free the old one.
2715 CopyMem (TempPoint
, Buffer
->Ptr
, Buffer
->Size
);
2716 FreePool (Buffer
->Ptr
);
2718 Buffer
->Ptr
= TempPoint
;
2721 mFixPolicyEntry
[Type
](Selector
, Data
);
2724 // Fill the selector header and copy it into buffer.
2726 SelectorHeader
.Type
= (UINT8
) (Type
| IPSEC_VAR_ITEM_HEADER_LOGO_BIT
);
2727 SelectorHeader
.Size
= (UINT16
) SelectorSize
;
2730 Buffer
->Ptr
+ Buffer
->Size
,
2732 sizeof (SelectorHeader
)
2734 Buffer
->Size
= ALIGN_VARIABLE (Buffer
->Size
+ sizeof (SelectorHeader
));
2737 // Copy the selector into buffer.
2740 Buffer
->Ptr
+ Buffer
->Size
,
2744 Buffer
->Size
= ALIGN_VARIABLE (Buffer
->Size
+ SelectorSize
);
2747 // Fill the data header and copy it into buffer.
2749 DataHeader
.Type
= (UINT8
) Type
;
2750 DataHeader
.Size
= (UINT16
) DataSize
;
2753 Buffer
->Ptr
+ Buffer
->Size
,
2757 Buffer
->Size
= ALIGN_VARIABLE (Buffer
->Size
+ sizeof (DataHeader
));
2759 // Copy the data into buffer.
2762 Buffer
->Ptr
+ Buffer
->Size
,
2766 Buffer
->Size
= ALIGN_VARIABLE (Buffer
->Size
+ DataSize
);
2768 mUnfixPolicyEntry
[Type
](Selector
, Data
);
2774 Visit all IPsec Configurations of specified Type and call the caller defined
2777 @param[in] DataType The specified IPsec Config Data Type.
2778 @param[in] Routine The function defined by the caller.
2779 @param[in] Context The data passed to the Routine.
2781 @retval EFI_OUT_OF_RESOURCES The required system resource could not be allocated
2782 @retval EFI_SUCCESS This function completed successfully.
2786 IpSecVisitConfigData (
2787 IN EFI_IPSEC_CONFIG_DATA_TYPE DataType
,
2788 IN IPSEC_COPY_POLICY_ENTRY Routine
,
2792 EFI_STATUS GetNextStatus
;
2793 EFI_STATUS GetDataStatus
;
2794 EFI_STATUS RoutineStatus
;
2795 EFI_IPSEC_CONFIG_SELECTOR
*Selector
;
2799 UINTN SelectorBufferSize
;
2800 UINTN DataBufferSize
;
2801 BOOLEAN FirstGetNext
;
2803 FirstGetNext
= TRUE
;
2806 SelectorBufferSize
= sizeof (EFI_IPSEC_CONFIG_SELECTOR
);
2807 Selector
= AllocateZeroPool (SelectorBufferSize
);
2809 if (Selector
== NULL
) {
2810 return EFI_OUT_OF_RESOURCES
;
2815 // Get the real size of the selector.
2817 SelectorSize
= SelectorBufferSize
;
2818 GetNextStatus
= EfiIpSecConfigGetNextSelector (
2819 &mIpSecConfigInstance
,
2824 if (GetNextStatus
== EFI_BUFFER_TOO_SMALL
) {
2825 FreePool (Selector
);
2826 SelectorBufferSize
= SelectorSize
;
2828 // Allocate zero pool for the first selector, while store the last
2829 // selector content for the other selectors.
2832 Selector
= AllocateZeroPool (SelectorBufferSize
);
2834 Selector
= AllocateCopyPool (SelectorBufferSize
, Selector
);
2837 if (Selector
== NULL
) {
2838 return EFI_OUT_OF_RESOURCES
;
2841 // Get the content of the selector.
2843 GetNextStatus
= EfiIpSecConfigGetNextSelector (
2844 &mIpSecConfigInstance
,
2851 if (EFI_ERROR (GetNextStatus
)) {
2855 FirstGetNext
= FALSE
;
2858 // Get the real size of the policy entry according to the selector.
2860 DataSize
= DataBufferSize
;
2861 GetDataStatus
= EfiIpSecConfigGetData (
2862 &mIpSecConfigInstance
,
2868 if (GetDataStatus
== EFI_BUFFER_TOO_SMALL
) {
2873 DataBufferSize
= DataSize
;
2874 Data
= AllocateZeroPool (DataBufferSize
);
2877 return EFI_OUT_OF_RESOURCES
;
2880 // Get the content of the policy entry according to the selector.
2882 GetDataStatus
= EfiIpSecConfigGetData (
2883 &mIpSecConfigInstance
,
2891 if (EFI_ERROR (GetDataStatus
)) {
2895 // Prepare the buffer of updated policy entry, which is stored in
2896 // the continous memory, and then save into variable later.
2898 RoutineStatus
= Routine (
2906 if (EFI_ERROR (RoutineStatus
)) {
2915 if (Selector
!= NULL
) {
2916 FreePool (Selector
);
2923 This function is the subfunction of EFIIpSecConfigSetData.
2925 This function call IpSecSetVaraible to set the IPsec Configuration into the firmware.
2927 @retval EFI_OUT_OF_RESOURCES The required system resource could not be allocated.
2928 @retval EFI_SUCCESS Saved the configration successfully.
2929 @retval Others Other errors were found while obtaining the variable.
2937 IPSEC_VARIABLE_BUFFER Buffer
;
2939 EFI_IPSEC_CONFIG_DATA_TYPE Type
;
2942 Buffer
.Capacity
= IPSEC_DEFAULT_VARIABLE_SIZE
;
2943 Buffer
.Ptr
= AllocateZeroPool (Buffer
.Capacity
);
2945 if (Buffer
.Ptr
== NULL
) {
2946 return EFI_OUT_OF_RESOURCES
;
2949 // For each policy database, prepare the contious buffer to save into variable.
2951 for (Type
= IPsecConfigDataTypeSpd
; Type
< IPsecConfigDataTypeMaximum
; Type
++) {
2952 IpSecVisitConfigData (
2954 (IPSEC_COPY_POLICY_ENTRY
) IpSecCopyPolicyEntry
,
2959 // Save the updated policy database into variable.
2961 Status
= IpSecSetVariable (
2962 IPSECCONFIG_VARIABLE_NAME
,
2963 &gEfiIpSecConfigProtocolGuid
,
2964 EFI_VARIABLE_BOOTSERVICE_ACCESS
| EFI_VARIABLE_NON_VOLATILE
,
2969 FreePool (Buffer
.Ptr
);
2975 Get the all IPSec configuration variables and store those variables
2976 to the internal data structure.
2978 This founction is called by IpSecConfigInitialize() which is to intialize the
2979 IPsecConfiguration Protocol.
2981 @param[in] Private Point to IPSEC_PRIVATE_DATA.
2983 @retval EFI_OUT_OF_RESOURCES The required system resource could not be allocated
2984 @retval EFI_SUCCESS Restore the IPsec Configuration successfully.
2985 @retval others Other errors is found while obtaining the variable.
2989 IpSecConfigRestore (
2990 IN IPSEC_PRIVATE_DATA
*Private
2996 IPSEC_VAR_ITEM_HEADER
*Header
;
2998 EFI_IPSEC_CONFIG_SELECTOR
*Selector
;
2999 EFI_IPSEC_CONFIG_DATA_TYPE Type
;
3005 Size
= sizeof (Value
);
3009 Status
= gRT
->GetVariable (
3010 IPSECCONFIG_STATUS_NAME
,
3011 &gEfiIpSecConfigProtocolGuid
,
3017 if (!EFI_ERROR (Status
) && Value
== IPSEC_STATUS_ENABLED
) {
3018 Private
->IpSec
.DisabledFlag
= FALSE
;
3021 // Get the real size of policy database in variable.
3023 Status
= IpSecGetVariable (
3024 IPSECCONFIG_VARIABLE_NAME
,
3025 &gEfiIpSecConfigProtocolGuid
,
3030 if (Status
== EFI_BUFFER_TOO_SMALL
) {
3032 Buffer
= AllocateZeroPool (BufferSize
);
3033 if (Buffer
== NULL
) {
3034 return EFI_OUT_OF_RESOURCES
;
3037 // Get the content of policy database in variable.
3039 Status
= IpSecGetVariable (
3040 IPSECCONFIG_VARIABLE_NAME
,
3041 &gEfiIpSecConfigProtocolGuid
,
3046 if (EFI_ERROR (Status
)) {
3051 for (Ptr
= Buffer
; Ptr
< Buffer
+ BufferSize
;) {
3053 Header
= (IPSEC_VAR_ITEM_HEADER
*) Ptr
;
3054 Type
= (EFI_IPSEC_CONFIG_DATA_TYPE
) (Header
->Type
& IPSEC_VAR_ITEM_HEADER_CONTENT_BIT
);
3055 ASSERT (((Header
->Type
& 0x80) == IPSEC_VAR_ITEM_HEADER_LOGO_BIT
) && (Type
< IPsecConfigDataTypeMaximum
));
3057 Selector
= (EFI_IPSEC_CONFIG_SELECTOR
*) ALIGN_POINTER (Header
+ 1, sizeof (UINTN
));
3058 Header
= (IPSEC_VAR_ITEM_HEADER
*) ALIGN_POINTER (
3059 (UINT8
*) Selector
+ Header
->Size
,
3062 ASSERT (Header
->Type
== Type
);
3064 Data
= ALIGN_POINTER (Header
+ 1, sizeof (UINTN
));
3066 mUnfixPolicyEntry
[Type
](Selector
, Data
);
3069 // Update each policy entry according to the content in variable.
3072 Status
= EfiIpSecConfigSetData (
3073 &Private
->IpSecConfig
,
3081 if (EFI_ERROR (Status
)) {
3086 Ptr
= ALIGN_POINTER ((UINT8
*) Data
+ Header
->Size
, sizeof (UINTN
));
3096 Install and Initialize IPsecConfig protocol
3098 @param[in, out] Private Pointer to IPSEC_PRIVATE_DATA. After this function finish,
3099 the pointer of IPsecConfig Protocol implementation will copy
3100 into its IPsecConfig member.
3102 @retval EFI_SUCCESS Initialized the IPsecConfig Protocol successfully.
3103 @retval Others Initializing the IPsecConfig Protocol failed.
3106 IpSecConfigInitialize (
3107 IN OUT IPSEC_PRIVATE_DATA
*Private
3110 EFI_IPSEC_CONFIG_DATA_TYPE Type
;
3113 &Private
->IpSecConfig
,
3114 &mIpSecConfigInstance
,
3115 sizeof (EFI_IPSEC_CONFIG_PROTOCOL
)
3119 // Initialize the list head of policy database.
3121 for (Type
= IPsecConfigDataTypeSpd
; Type
< IPsecConfigDataTypeMaximum
; Type
++) {
3122 InitializeListHead (&mConfigData
[Type
]);
3125 // Restore the content of policy database according to the variable.
3127 IpSecConfigRestore (Private
);
3129 return gBS
->InstallMultipleProtocolInterfaces (
3131 &gEfiIpSecConfigProtocolGuid
,
3132 &Private
->IpSecConfig
,