2 PCD DXE driver manage all PCD entry initialized in PEI phase and DXE phase, and
3 produce the implementation of native PCD protocol and EFI_PCD_PROTOCOL defined in
6 Copyright (c) 2006 - 2018, Intel Corporation. All rights reserved.<BR>
7 SPDX-License-Identifier: BSD-2-Clause-Patent
14 /// PCD database lock.
16 EFI_LOCK mPcdDatabaseLock
= EFI_INITIALIZE_LOCK_VARIABLE (TPL_NOTIFY
);
19 /// PCD_PROTOCOL the EDKII native implementation which support dynamic
20 /// type and dynamicEx type PCDs.
22 PCD_PROTOCOL mPcdInstance
= {
55 DxeRegisterCallBackOnSet
,
56 DxeUnRegisterCallBackOnSet
,
58 DxePcdGetNextTokenSpace
62 /// EFI_PCD_PROTOCOL is defined in PI 1.2 Vol 3 which only support dynamicEx type
65 EFI_PCD_PROTOCOL mEfiPcdInstance
= {
80 (EFI_PCD_PROTOCOL_CALLBACK_ON_SET
)DxeRegisterCallBackOnSet
,
81 (EFI_PCD_PROTOCOL_CANCEL_CALLBACK
)DxeUnRegisterCallBackOnSet
,
83 DxePcdGetNextTokenSpace
87 /// Instance of GET_PCD_INFO_PROTOCOL protocol is EDKII native implementation.
88 /// This protocol instance support dynamic and dynamicEx type PCDs.
90 GET_PCD_INFO_PROTOCOL mGetPcdInfoInstance
= {
92 DxeGetPcdInfoGetInfoEx
,
97 /// Instance of EFI_GET_PCD_INFO_PROTOCOL which is defined in PI 1.2.1 Vol 3.
98 /// This PPI instance only support dyanmicEx type PCD.
100 EFI_GET_PCD_INFO_PROTOCOL mEfiGetPcdInfoInstance
= {
101 DxeGetPcdInfoGetInfoEx
,
105 EFI_HANDLE mPcdHandle
= NULL
;
106 UINTN mVpdBaseAddress
= 0;
109 Main entry for PCD DXE driver.
111 This routine initialize the PCD database and install PCD_PROTOCOL.
113 @param ImageHandle Image handle for PCD DXE driver.
114 @param SystemTable Pointer to SystemTable.
116 @return Status of gBS->InstallProtocolInterface()
122 IN EFI_HANDLE ImageHandle
,
123 IN EFI_SYSTEM_TABLE
*SystemTable
130 // Make sure the Pcd Protocol is not already installed in the system
133 ASSERT_PROTOCOL_ALREADY_INSTALLED (NULL
, &gPcdProtocolGuid
);
135 BuildPcdDxeDataBase ();
138 // Install PCD_PROTOCOL to handle dynamic type PCD
139 // Install EFI_PCD_PROTOCOL to handle dynamicEx type PCD
141 Status
= gBS
->InstallMultipleProtocolInterfaces (
145 &gEfiPcdProtocolGuid
,
149 ASSERT_EFI_ERROR (Status
);
152 // Install GET_PCD_INFO_PROTOCOL to handle dynamic type PCD
153 // Install EFI_GET_PCD_INFO_PROTOCOL to handle dynamicEx type PCD
155 Status
= gBS
->InstallMultipleProtocolInterfaces (
157 &gGetPcdInfoProtocolGuid
,
158 &mGetPcdInfoInstance
,
159 &gEfiGetPcdInfoProtocolGuid
,
160 &mEfiGetPcdInfoInstance
,
163 ASSERT_EFI_ERROR (Status
);
166 // Register callback function upon VariableLockProtocol
167 // to lock the variables referenced by DynamicHii PCDs with RO property set in *.dsc.
169 EfiCreateProtocolNotifyEvent (
170 &gEdkiiVariableLockProtocolGuid
,
172 VariableLockCallBack
,
178 // Cache VpdBaseAddress in entry point for the following usage.
182 // PcdVpdBaseAddress64 is DynamicEx PCD only. So, DxePcdGet64Ex() is used to get its value.
184 mVpdBaseAddress
= (UINTN
)DxePcdGet64Ex (&gEfiMdeModulePkgTokenSpaceGuid
, PcdToken (PcdVpdBaseAddress64
));
185 if (mVpdBaseAddress
== 0) {
187 // PcdVpdBaseAddress64 is not set, get value from PcdVpdBaseAddress.
189 mVpdBaseAddress
= (UINTN
)PcdGet32 (PcdVpdBaseAddress
);
196 Retrieve additional information associated with a PCD token in the default token space.
198 This includes information such as the type of value the TokenNumber is associated with as well as possible
199 human readable name that is associated with the token.
201 @param[in] TokenNumber The PCD token number.
202 @param[out] PcdInfo The returned information associated with the requested TokenNumber.
203 The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
205 @retval EFI_SUCCESS The PCD information was returned successfully.
206 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
210 DxeGetPcdInfoGetInfo (
211 IN UINTN TokenNumber
,
212 OUT EFI_PCD_INFO
*PcdInfo
215 return DxeGetPcdInfo (NULL
, TokenNumber
, PcdInfo
);
219 Retrieve additional information associated with a PCD token.
221 This includes information such as the type of value the TokenNumber is associated with as well as possible
222 human readable name that is associated with the token.
224 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
225 @param[in] TokenNumber The PCD token number.
226 @param[out] PcdInfo The returned information associated with the requested TokenNumber.
227 The caller is responsible for freeing the buffer that is allocated by callee for PcdInfo->PcdName.
229 @retval EFI_SUCCESS The PCD information was returned successfully.
230 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
234 DxeGetPcdInfoGetInfoEx (
235 IN CONST EFI_GUID
*Guid
,
236 IN UINTN TokenNumber
,
237 OUT EFI_PCD_INFO
*PcdInfo
240 return DxeGetPcdInfo (Guid
, TokenNumber
, PcdInfo
);
244 Retrieve the currently set SKU Id.
246 @return The currently set SKU Id. If the platform has not set at a SKU Id, then the
247 default SKU Id value of 0 is returned. If the platform has set a SKU Id, then the currently set SKU
252 DxeGetPcdInfoGetSku (
256 return (UINTN
)mPcdDatabase
.DxeDb
->SystemSkuId
;
260 Sets the SKU value for subsequent calls to set or get PCD token values.
262 SetSku() sets the SKU Id to be used for subsequent calls to set or get PCD values.
263 SetSku() is normally called only once by the system.
265 For each item (token), the database can hold a single value that applies to all SKUs,
266 or multiple values, where each value is associated with a specific SKU Id. Items with multiple,
267 SKU-specific values are called SKU enabled.
269 The SKU Id of zero is reserved as a default.
270 For tokens that are not SKU enabled, the system ignores any set SKU Id and works with the
271 single value for that token. For SKU-enabled tokens, the system will use the SKU Id set by the
272 last call to SetSku(). If no SKU Id is set or the currently set SKU Id isn't valid for the specified token,
273 the system uses the default SKU Id. If the system attempts to use the default SKU Id and no value has been
274 set for that Id, the results are unpredictable.
276 @param[in] SkuId The SKU value that will be used when the PCD service will retrieve and
277 set values associated with a PCD token.
290 DEBUG ((DEBUG_INFO
, "PcdDxe - SkuId 0x%lx is to be set.\n", (SKU_ID
)SkuId
));
292 if (SkuId
== mPcdDatabase
.DxeDb
->SystemSkuId
) {
294 // The input SKU Id is equal to current SKU Id, return directly.
296 DEBUG ((DEBUG_INFO
, "PcdDxe - SkuId is same to current system Sku.\n"));
300 if (mPcdDatabase
.DxeDb
->SystemSkuId
!= (SKU_ID
)0) {
301 DEBUG ((DEBUG_ERROR
, "PcdDxe - The SKU Id could be changed only once."));
304 "PcdDxe - The SKU Id was set to 0x%lx already, it could not be set to 0x%lx any more.",
305 mPcdDatabase
.DxeDb
->SystemSkuId
,
312 SkuIdTable
= (SKU_ID
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->SkuIdTableOffset
);
313 for (Index
= 0; Index
< SkuIdTable
[0]; Index
++) {
314 if (SkuId
== SkuIdTable
[Index
+ 1]) {
315 DEBUG ((DEBUG_INFO
, "PcdDxe - SkuId is found in SkuId table.\n"));
316 Status
= UpdatePcdDatabase (SkuId
, TRUE
);
317 if (!EFI_ERROR (Status
)) {
318 mPcdDatabase
.DxeDb
->SystemSkuId
= (SKU_ID
)SkuId
;
319 DEBUG ((DEBUG_INFO
, "PcdDxe - Set current SKU Id to 0x%lx.\n", (SKU_ID
)SkuId
));
326 // Invalid input SkuId, the default SKU Id will be still used for the system.
328 DEBUG ((DEBUG_ERROR
, "PcdDxe - Invalid input SkuId, the default SKU Id will be still used.\n"));
333 Retrieves an 8-bit value for a given PCD token.
335 Retrieves the current byte-sized value for a PCD token number.
336 If the TokenNumber is invalid, the results are unpredictable.
338 @param[in] TokenNumber The PCD token number.
340 @return The UINT8 value.
349 return *((UINT8
*)GetWorker (TokenNumber
, sizeof (UINT8
)));
353 Retrieves an 16-bit value for a given PCD token.
355 Retrieves the current 16-bits value for a PCD token number.
356 If the TokenNumber is invalid, the results are unpredictable.
358 @param[in] TokenNumber The PCD token number.
360 @return The UINT16 value.
369 return ReadUnaligned16 (GetWorker (TokenNumber
, sizeof (UINT16
)));
373 Retrieves an 32-bit value for a given PCD token.
375 Retrieves the current 32-bits value for a PCD token number.
376 If the TokenNumber is invalid, the results are unpredictable.
378 @param[in] TokenNumber The PCD token number.
380 @return The UINT32 value.
389 return ReadUnaligned32 (GetWorker (TokenNumber
, sizeof (UINT32
)));
393 Retrieves an 64-bit value for a given PCD token.
395 Retrieves the current 64-bits value for a PCD token number.
396 If the TokenNumber is invalid, the results are unpredictable.
398 @param[in] TokenNumber The PCD token number.
400 @return The UINT64 value.
409 return ReadUnaligned64 (GetWorker (TokenNumber
, sizeof (UINT64
)));
413 Retrieves a pointer to a value for a given PCD token.
415 Retrieves the current pointer to the buffer for a PCD token number.
416 Do not make any assumptions about the alignment of the pointer that
417 is returned by this function call. If the TokenNumber is invalid,
418 the results are unpredictable.
420 @param[in] TokenNumber The PCD token number.
422 @return The pointer to the buffer to be retrived.
431 return GetWorker (TokenNumber
, 0);
435 Retrieves a Boolean value for a given PCD token.
437 Retrieves the current boolean value for a PCD token number.
438 Do not make any assumptions about the alignment of the pointer that
439 is returned by this function call. If the TokenNumber is invalid,
440 the results are unpredictable.
442 @param[in] TokenNumber The PCD token number.
444 @return The Boolean value.
453 return *((BOOLEAN
*)GetWorker (TokenNumber
, sizeof (BOOLEAN
)));
457 Retrieves the size of the value for a given PCD token.
459 Retrieves the current size of a particular PCD token.
460 If the TokenNumber is invalid, the results are unpredictable.
462 @param[in] TokenNumber The PCD token number.
464 @return The size of the value for the PCD token.
474 UINT32
*LocalTokenNumberTable
;
477 UINTN TmpTokenNumber
;
480 // TokenNumber Zero is reserved as PCD_INVALID_TOKEN_NUMBER.
481 // We have to decrement TokenNumber by 1 to make it usable
482 // as the array index.
487 // Backup the TokenNumber passed in as GetPtrTypeSize need the original TokenNumber
489 TmpTokenNumber
= TokenNumber
;
491 // EBC compiler is very choosy. It may report warning about comparison
492 // between UINTN and 0 . So we add 1 in each size of the
494 ASSERT (TokenNumber
+ 1 < mPcdTotalTokenCount
+ 1);
496 // EBC compiler is very choosy. It may report warning about comparison
497 // between UINTN and 0 . So we add 1 in each size of the
499 IsPeiDb
= (BOOLEAN
)(TokenNumber
+ 1 < mPeiLocalTokenCount
+ 1);
501 TokenNumber
= IsPeiDb
? TokenNumber
:
502 (TokenNumber
- mPeiLocalTokenCount
);
504 LocalTokenNumberTable
= IsPeiDb
? (UINT32
*)((UINT8
*)mPcdDatabase
.PeiDb
+ mPcdDatabase
.PeiDb
->LocalTokenNumberTableOffset
)
505 : (UINT32
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->LocalTokenNumberTableOffset
);
507 Size
= (LocalTokenNumberTable
[TokenNumber
] & PCD_DATUM_TYPE_ALL_SET
) >> PCD_DATUM_TYPE_SHIFT
;
511 // For pointer type, we need to scan the SIZE_TABLE to get the current size.
513 return GetPtrTypeSize (TmpTokenNumber
, &MaxSize
);
520 Retrieves an 8-bit value for a given PCD token.
522 Retrieves the 8-bit value of a particular PCD token.
523 If the TokenNumber is invalid or the token space
524 specified by Guid does not exist, the results are
527 @param[in] Guid The token space for the token number.
528 @param[in] ExTokenNumber The PCD token number.
530 @return The size 8-bit value for the PCD token.
536 IN CONST EFI_GUID
*Guid
,
537 IN UINTN ExTokenNumber
540 return *((UINT8
*)ExGetWorker (Guid
, ExTokenNumber
, sizeof (UINT8
)));
544 Retrieves an 16-bit value for a given PCD token.
546 Retrieves the 16-bit value of a particular PCD token.
547 If the TokenNumber is invalid or the token space
548 specified by Guid does not exist, the results are
551 @param[in] Guid The token space for the token number.
552 @param[in] ExTokenNumber The PCD token number.
554 @return The size 16-bit value for the PCD token.
560 IN CONST EFI_GUID
*Guid
,
561 IN UINTN ExTokenNumber
564 return ReadUnaligned16 (ExGetWorker (Guid
, ExTokenNumber
, sizeof (UINT16
)));
568 Retrieves an 32-bit value for a given PCD token.
570 Retrieves the 32-bit value of a particular PCD token.
571 If the TokenNumber is invalid or the token space
572 specified by Guid does not exist, the results are
575 @param[in] Guid The token space for the token number.
576 @param[in] ExTokenNumber The PCD token number.
578 @return The size 32-bit value for the PCD token.
584 IN CONST EFI_GUID
*Guid
,
585 IN UINTN ExTokenNumber
588 return ReadUnaligned32 (ExGetWorker (Guid
, ExTokenNumber
, sizeof (UINT32
)));
592 Retrieves an 64-bit value for a given PCD token.
594 Retrieves the 64-bit value of a particular PCD token.
595 If the TokenNumber is invalid or the token space
596 specified by Guid does not exist, the results are
599 @param[in] Guid The token space for the token number.
600 @param[in] ExTokenNumber The PCD token number.
602 @return The size 64-bit value for the PCD token.
608 IN CONST EFI_GUID
*Guid
,
609 IN UINTN ExTokenNumber
612 return ReadUnaligned64 (ExGetWorker (Guid
, ExTokenNumber
, sizeof (UINT64
)));
616 Retrieves a pointer to a value for a given PCD token.
618 Retrieves the current pointer to the buffer for a PCD token number.
619 Do not make any assumptions about the alignment of the pointer that
620 is returned by this function call. If the TokenNumber is invalid,
621 the results are unpredictable.
623 @param[in] Guid The token space for the token number.
624 @param[in] ExTokenNumber The PCD token number.
626 @return The pointer to the buffer to be retrived.
632 IN CONST EFI_GUID
*Guid
,
633 IN UINTN ExTokenNumber
636 return ExGetWorker (Guid
, ExTokenNumber
, 0);
640 Retrieves an Boolean value for a given PCD token.
642 Retrieves the Boolean value of a particular PCD token.
643 If the TokenNumber is invalid or the token space
644 specified by Guid does not exist, the results are
647 @param[in] Guid The token space for the token number.
648 @param[in] ExTokenNumber The PCD token number.
650 @return The size Boolean value for the PCD token.
656 IN CONST EFI_GUID
*Guid
,
657 IN UINTN ExTokenNumber
660 return *((BOOLEAN
*)ExGetWorker (Guid
, ExTokenNumber
, sizeof (BOOLEAN
)));
664 Retrieves the size of the value for a given PCD token.
666 Retrieves the current size of a particular PCD token.
667 If the TokenNumber is invalid, the results are unpredictable.
669 @param[in] Guid The token space for the token number.
670 @param[in] ExTokenNumber The PCD token number.
672 @return The size of the value for the PCD token.
678 IN CONST EFI_GUID
*Guid
,
679 IN UINTN ExTokenNumber
682 return DxePcdGetSize (GetExPcdTokenNumber (Guid
, (UINT32
)ExTokenNumber
));
686 Sets an 8-bit value for a given PCD token.
688 When the PCD service sets a value, it will check to ensure that the
689 size of the value being set is compatible with the Token's existing definition.
690 If it is not, an error will be returned.
692 @param[in] TokenNumber The PCD token number.
693 @param[in] Value The value to set for the PCD token.
695 @retval EFI_SUCCESS Procedure returned successfully.
696 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
697 being set was incompatible with a call to this function.
698 Use GetSize() to retrieve the size of the target data.
699 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
705 IN UINTN TokenNumber
,
709 return SetValueWorker (TokenNumber
, &Value
, sizeof (Value
));
713 Sets an 16-bit value for a given PCD token.
715 When the PCD service sets a value, it will check to ensure that the
716 size of the value being set is compatible with the Token's existing definition.
717 If it is not, an error will be returned.
719 @param[in] TokenNumber The PCD token number.
720 @param[in] Value The value to set for the PCD token.
722 @retval EFI_SUCCESS Procedure returned successfully.
723 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
724 being set was incompatible with a call to this function.
725 Use GetSize() to retrieve the size of the target data.
726 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
732 IN UINTN TokenNumber
,
736 return SetValueWorker (TokenNumber
, &Value
, sizeof (Value
));
740 Sets an 32-bit value for a given PCD token.
742 When the PCD service sets a value, it will check to ensure that the
743 size of the value being set is compatible with the Token's existing definition.
744 If it is not, an error will be returned.
746 @param[in] TokenNumber The PCD token number.
747 @param[in] Value The value to set for the PCD token.
749 @retval EFI_SUCCESS Procedure returned successfully.
750 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
751 being set was incompatible with a call to this function.
752 Use GetSize() to retrieve the size of the target data.
753 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
759 IN UINTN TokenNumber
,
763 return SetValueWorker (TokenNumber
, &Value
, sizeof (Value
));
767 Sets an 64-bit value for a given PCD token.
769 When the PCD service sets a value, it will check to ensure that the
770 size of the value being set is compatible with the Token's existing definition.
771 If it is not, an error will be returned.
773 @param[in] TokenNumber The PCD token number.
774 @param[in] Value The value to set for the PCD token.
776 @retval EFI_SUCCESS Procedure returned successfully.
777 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
778 being set was incompatible with a call to this function.
779 Use GetSize() to retrieve the size of the target data.
780 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
786 IN UINTN TokenNumber
,
790 return SetValueWorker (TokenNumber
, &Value
, sizeof (Value
));
794 Sets a value of a specified size for a given PCD token.
796 When the PCD service sets a value, it will check to ensure that the
797 size of the value being set is compatible with the Token's existing definition.
798 If it is not, an error will be returned.
800 @param[in] TokenNumber The PCD token number.
801 @param[in, out] SizeOfBuffer A pointer to the length of the value being set for the PCD token.
802 On input, if the SizeOfValue is greater than the maximum size supported
803 for this TokenNumber then the output value of SizeOfValue will reflect
804 the maximum size supported for this TokenNumber.
805 @param[in] Buffer The buffer to set for the PCD token.
807 @retval EFI_SUCCESS Procedure returned successfully.
808 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
809 being set was incompatible with a call to this function.
810 Use GetSize() to retrieve the size of the target data.
811 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
817 IN UINTN TokenNumber
,
818 IN OUT UINTN
*SizeOfBuffer
,
822 return SetWorker (TokenNumber
, Buffer
, SizeOfBuffer
, TRUE
);
826 Sets an Boolean value for a given PCD token.
828 When the PCD service sets a value, it will check to ensure that the
829 size of the value being set is compatible with the Token's existing definition.
830 If it is not, an error will be returned.
832 @param[in] TokenNumber The PCD token number.
833 @param[in] Value The value to set for the PCD token.
835 @retval EFI_SUCCESS Procedure returned successfully.
836 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
837 being set was incompatible with a call to this function.
838 Use GetSize() to retrieve the size of the target data.
839 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
845 IN UINTN TokenNumber
,
849 return SetValueWorker (TokenNumber
, &Value
, sizeof (Value
));
853 Sets an 8-bit value for a given PCD token.
855 When the PCD service sets a value, it will check to ensure that the
856 size of the value being set is compatible with the Token's existing definition.
857 If it is not, an error will be returned.
859 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
860 @param[in] ExTokenNumber The PCD token number.
861 @param[in] Value The value to set for the PCD token.
863 @retval EFI_SUCCESS Procedure returned successfully.
864 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
865 being set was incompatible with a call to this function.
866 Use GetSize() to retrieve the size of the target data.
867 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
873 IN CONST EFI_GUID
*Guid
,
874 IN UINTN ExTokenNumber
,
878 return ExSetValueWorker (ExTokenNumber
, Guid
, &Value
, sizeof (Value
));
882 Sets an 16-bit value for a given PCD token.
884 When the PCD service sets a value, it will check to ensure that the
885 size of the value being set is compatible with the Token's existing definition.
886 If it is not, an error will be returned.
888 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
889 @param[in] ExTokenNumber The PCD token number.
890 @param[in] Value The value to set for the PCD token.
892 @retval EFI_SUCCESS Procedure returned successfully.
893 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
894 being set was incompatible with a call to this function.
895 Use GetSize() to retrieve the size of the target data.
896 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
902 IN CONST EFI_GUID
*Guid
,
903 IN UINTN ExTokenNumber
,
908 // PcdSetNvStoreDefaultId should be set in PEI phase to take effect.
911 !(CompareGuid (Guid
, &gEfiMdeModulePkgTokenSpaceGuid
) &&
912 (ExTokenNumber
== PcdToken (PcdSetNvStoreDefaultId
)))
914 return ExSetValueWorker (ExTokenNumber
, Guid
, &Value
, sizeof (Value
));
918 Sets an 32-bit value for a given PCD token.
920 When the PCD service sets a value, it will check to ensure that the
921 size of the value being set is compatible with the Token's existing definition.
922 If it is not, an error will be returned.
924 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
925 @param[in] ExTokenNumber The PCD token number.
926 @param[in] Value The value to set for the PCD token.
928 @retval EFI_SUCCESS Procedure returned successfully.
929 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
930 being set was incompatible with a call to this function.
931 Use GetSize() to retrieve the size of the target data.
932 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
938 IN CONST EFI_GUID
*Guid
,
939 IN UINTN ExTokenNumber
,
943 return ExSetValueWorker (ExTokenNumber
, Guid
, &Value
, sizeof (Value
));
947 Sets an 64-bit value for a given PCD token.
949 When the PCD service sets a value, it will check to ensure that the
950 size of the value being set is compatible with the Token's existing definition.
951 If it is not, an error will be returned.
953 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
954 @param[in] ExTokenNumber The PCD token number.
955 @param[in] Value The value to set for the PCD token.
957 @retval EFI_SUCCESS Procedure returned successfully.
958 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
959 being set was incompatible with a call to this function.
960 Use GetSize() to retrieve the size of the target data.
961 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
967 IN CONST EFI_GUID
*Guid
,
968 IN UINTN ExTokenNumber
,
972 return ExSetValueWorker (ExTokenNumber
, Guid
, &Value
, sizeof (Value
));
976 Sets a value of a specified size for a given PCD token.
978 When the PCD service sets a value, it will check to ensure that the
979 size of the value being set is compatible with the Token's existing definition.
980 If it is not, an error will be returned.
982 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
983 @param[in] ExTokenNumber The PCD token number.
984 @param[in, out] SizeOfBuffer A pointer to the length of the value being set for the PCD token.
985 On input, if the SizeOfValue is greater than the maximum size supported
986 for this TokenNumber then the output value of SizeOfValue will reflect
987 the maximum size supported for this TokenNumber.
988 @param[in] Buffer The buffer to set for the PCD token.
990 @retval EFI_SUCCESS Procedure returned successfully.
991 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
992 being set was incompatible with a call to this function.
993 Use GetSize() to retrieve the size of the target data.
994 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
1000 IN CONST EFI_GUID
*Guid
,
1001 IN UINTN ExTokenNumber
,
1002 IN OUT UINTN
*SizeOfBuffer
,
1006 return ExSetWorker (ExTokenNumber
, Guid
, Buffer
, SizeOfBuffer
, TRUE
);
1010 Sets an Boolean value for a given PCD token.
1012 When the PCD service sets a value, it will check to ensure that the
1013 size of the value being set is compatible with the Token's existing definition.
1014 If it is not, an error will be returned.
1016 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
1017 @param[in] ExTokenNumber The PCD token number.
1018 @param[in] Value The value to set for the PCD token.
1020 @retval EFI_SUCCESS Procedure returned successfully.
1021 @retval EFI_INVALID_PARAMETER The PCD service determined that the size of the data
1022 being set was incompatible with a call to this function.
1023 Use GetSize() to retrieve the size of the target data.
1024 @retval EFI_NOT_FOUND The PCD service could not find the requested token number.
1030 IN CONST EFI_GUID
*Guid
,
1031 IN UINTN ExTokenNumber
,
1035 return ExSetValueWorker (ExTokenNumber
, Guid
, &Value
, sizeof (Value
));
1039 Specifies a function to be called anytime the value of a designated token is changed.
1041 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
1042 @param[in] TokenNumber The PCD token number.
1043 @param[in] CallBackFunction The function prototype called when the value associated with the CallBackToken is set.
1045 @retval EFI_SUCCESS The PCD service has successfully established a call event
1046 for the CallBackToken requested.
1047 @retval EFI_NOT_FOUND The PCD service could not find the referenced token number.
1052 DxeRegisterCallBackOnSet (
1053 IN CONST EFI_GUID
*Guid OPTIONAL
,
1054 IN UINTN TokenNumber
,
1055 IN PCD_PROTOCOL_CALLBACK CallBackFunction
1060 if (CallBackFunction
== NULL
) {
1061 return EFI_INVALID_PARAMETER
;
1065 // Aquire lock to prevent reentrance from TPL_CALLBACK level
1067 EfiAcquireLock (&mPcdDatabaseLock
);
1069 Status
= DxeRegisterCallBackWorker (TokenNumber
, Guid
, CallBackFunction
);
1071 EfiReleaseLock (&mPcdDatabaseLock
);
1077 Cancels a previously set callback function for a particular PCD token number.
1079 @param[in] Guid The 128-bit unique value that designates the namespace from which to extract the value.
1080 @param[in] TokenNumber The PCD token number.
1081 @param[in] CallBackFunction The function prototype called when the value associated with the CallBackToken is set.
1083 @retval EFI_SUCCESS The PCD service has successfully established a call event
1084 for the CallBackToken requested.
1085 @retval EFI_NOT_FOUND The PCD service could not find the referenced token number.
1090 DxeUnRegisterCallBackOnSet (
1091 IN CONST EFI_GUID
*Guid OPTIONAL
,
1092 IN UINTN TokenNumber
,
1093 IN PCD_PROTOCOL_CALLBACK CallBackFunction
1098 if (CallBackFunction
== NULL
) {
1099 return EFI_INVALID_PARAMETER
;
1103 // Aquire lock to prevent reentrance from TPL_CALLBACK level
1105 EfiAcquireLock (&mPcdDatabaseLock
);
1107 Status
= DxeUnRegisterCallBackWorker (TokenNumber
, Guid
, CallBackFunction
);
1109 EfiReleaseLock (&mPcdDatabaseLock
);
1115 Retrieves the next valid token number in a given namespace.
1117 This is useful since the PCD infrastructure contains a sparse list of token numbers,
1118 and one cannot a priori know what token numbers are valid in the database.
1120 If TokenNumber is 0 and Guid is not NULL, then the first token from the token space specified by Guid is returned.
1121 If TokenNumber is not 0 and Guid is not NULL, then the next token in the token space specified by Guid is returned.
1122 If TokenNumber is 0 and Guid is NULL, then the first token in the default token space is returned.
1123 If TokenNumber is not 0 and Guid is NULL, then the next token in the default token space is returned.
1124 The token numbers in the default token space may not be related to token numbers in token spaces that are named by Guid.
1125 If the next token number can be retrieved, then it is returned in TokenNumber, and EFI_SUCCESS is returned.
1126 If TokenNumber represents the last token number in the token space specified by Guid, then EFI_NOT_FOUND is returned.
1127 If TokenNumber is not present in the token space specified by Guid, then EFI_NOT_FOUND is returned.
1130 @param[in] Guid The 128-bit unique value that designates the namespace from which to retrieve the next token.
1131 This is an optional parameter that may be NULL. If this parameter is NULL, then a request is
1132 being made to retrieve tokens from the default token space.
1133 @param[in, out] TokenNumber
1134 A pointer to the PCD token number to use to find the subsequent token number.
1136 @retval EFI_SUCCESS The PCD service has retrieved the next valid token number.
1137 @retval EFI_NOT_FOUND The PCD service could not find data from the requested token number.
1142 DxePcdGetNextToken (
1143 IN CONST EFI_GUID
*Guid OPTIONAL
,
1144 IN OUT UINTN
*TokenNumber
1148 BOOLEAN PeiExMapTableEmpty
;
1149 BOOLEAN DxeExMapTableEmpty
;
1151 Status
= EFI_NOT_FOUND
;
1152 PeiExMapTableEmpty
= mPeiExMapTableEmpty
;
1153 DxeExMapTableEmpty
= mDxeExMapTableEmpty
;
1156 // Scan the local token space
1159 // EBC compiler is very choosy. It may report warning about comparison
1160 // between UINTN and 0 . So we add 1 in each size of the
1162 if (((*TokenNumber
+ 1 > mPeiNexTokenCount
+ 1) && (*TokenNumber
+ 1 <= mPeiLocalTokenCount
+ 1)) ||
1163 ((*TokenNumber
+ 1 > (mPeiLocalTokenCount
+ mDxeNexTokenCount
+ 1))))
1165 return EFI_NOT_FOUND
;
1169 if ((*TokenNumber
+ 1 > mPeiNexTokenCount
+ 1) &&
1170 (*TokenNumber
+ 1 <= mPeiLocalTokenCount
+ 1))
1173 // The first Non-Ex type Token Number for DXE PCD
1174 // database is mPeiLocalTokenCount + 1
1176 if (mDxeNexTokenCount
> 0) {
1177 *TokenNumber
= mPeiLocalTokenCount
+ 1;
1179 *TokenNumber
= PCD_INVALID_TOKEN_NUMBER
;
1180 return EFI_NOT_FOUND
;
1182 } else if (*TokenNumber
+ 1 > mDxeNexTokenCount
+ mPeiLocalTokenCount
+ 1) {
1183 *TokenNumber
= PCD_INVALID_TOKEN_NUMBER
;
1184 return EFI_NOT_FOUND
;
1190 if (PeiExMapTableEmpty
&& DxeExMapTableEmpty
) {
1191 return EFI_NOT_FOUND
;
1194 if (!PeiExMapTableEmpty
) {
1195 Status
= ExGetNextTokeNumber (
1198 (EFI_GUID
*)((UINT8
*)mPcdDatabase
.PeiDb
+ mPcdDatabase
.PeiDb
->GuidTableOffset
),
1200 (DYNAMICEX_MAPPING
*)((UINT8
*)mPcdDatabase
.PeiDb
+ mPcdDatabase
.PeiDb
->ExMapTableOffset
),
1201 mPeiExMapppingTableSize
1205 if (Status
== EFI_SUCCESS
) {
1209 if (!DxeExMapTableEmpty
) {
1210 Status
= ExGetNextTokeNumber (
1213 (EFI_GUID
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->GuidTableOffset
),
1215 (DYNAMICEX_MAPPING
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->ExMapTableOffset
),
1216 mDxeExMapppingTableSize
1224 Get all token space guid table which is different with given token space guid.
1226 @param ExMapTableSize The size of ExMapTable in item
1227 @param ExMapTable Token space guid table that want to be scaned.
1228 @param GuidTable Guid table
1230 @return all token space guid table which is different with given token space guid.
1234 GetDistinctTokenSpace (
1235 IN OUT UINTN
*ExMapTableSize
,
1236 IN DYNAMICEX_MAPPING
*ExMapTable
,
1237 IN EFI_GUID
*GuidTable
1240 EFI_GUID
**DistinctTokenSpace
;
1247 DistinctTokenSpace
= AllocateZeroPool (*ExMapTableSize
* sizeof (EFI_GUID
*));
1248 ASSERT (DistinctTokenSpace
!= NULL
);
1251 OldGuidIndex
= ExMapTable
[0].ExGuidIndex
;
1252 DistinctTokenSpace
[TsIdx
] = &GuidTable
[OldGuidIndex
];
1253 for (Idx
= 1; Idx
< *ExMapTableSize
; Idx
++) {
1255 OldGuidIndex
= ExMapTable
[Idx
].ExGuidIndex
;
1256 for (TempTsIdx
= 0; TempTsIdx
<= TsIdx
; TempTsIdx
++) {
1257 if (&GuidTable
[OldGuidIndex
] == DistinctTokenSpace
[TempTsIdx
]) {
1259 // Have recorded this GUID.
1267 DistinctTokenSpace
[++TsIdx
] = &GuidTable
[OldGuidIndex
];
1272 // The total number of Distinct Token Space
1273 // is TsIdx + 1 because we use TsIdx as a index
1274 // to the DistinctTokenSpace[]
1276 *ExMapTableSize
= TsIdx
+ 1;
1277 return DistinctTokenSpace
;
1281 Retrieves the next valid PCD token namespace for a given namespace.
1283 Gets the next valid token namespace for a given namespace. This is useful to traverse the valid
1284 token namespaces on a platform.
1286 @param[in, out] Guid An indirect pointer to EFI_GUID. On input it designates a known token
1287 namespace from which the search will start. On output, it designates the next valid
1288 token namespace on the platform. If *Guid is NULL, then the GUID of the first token
1289 space of the current platform is returned. If the search cannot locate the next valid
1290 token namespace, an error is returned and the value of *Guid is undefined.
1292 @retval EFI_SUCCESS The PCD service retrieved the value requested.
1293 @retval EFI_NOT_FOUND The PCD service could not find the next valid token namespace.
1298 DxePcdGetNextTokenSpace (
1299 IN OUT CONST EFI_GUID
**Guid
1305 UINTN PeiTokenSpaceTableSize
;
1306 UINTN DxeTokenSpaceTableSize
;
1307 EFI_GUID
**PeiTokenSpaceTable
;
1308 EFI_GUID
**DxeTokenSpaceTable
;
1310 BOOLEAN PeiExMapTableEmpty
;
1311 BOOLEAN DxeExMapTableEmpty
;
1313 ASSERT (Guid
!= NULL
);
1315 PeiExMapTableEmpty
= mPeiExMapTableEmpty
;
1316 DxeExMapTableEmpty
= mDxeExMapTableEmpty
;
1318 if (PeiExMapTableEmpty
&& DxeExMapTableEmpty
) {
1319 return EFI_NOT_FOUND
;
1322 if (TmpTokenSpaceBuffer
[0] == NULL
) {
1323 PeiTokenSpaceTableSize
= 0;
1325 if (!PeiExMapTableEmpty
) {
1326 PeiTokenSpaceTableSize
= mPeiExMapppingTableSize
/ sizeof (DYNAMICEX_MAPPING
);
1327 PeiTokenSpaceTable
= GetDistinctTokenSpace (
1328 &PeiTokenSpaceTableSize
,
1329 (DYNAMICEX_MAPPING
*)((UINT8
*)mPcdDatabase
.PeiDb
+ mPcdDatabase
.PeiDb
->ExMapTableOffset
),
1330 (EFI_GUID
*)((UINT8
*)mPcdDatabase
.PeiDb
+ mPcdDatabase
.PeiDb
->GuidTableOffset
)
1332 CopyMem (TmpTokenSpaceBuffer
, PeiTokenSpaceTable
, sizeof (EFI_GUID
*) * PeiTokenSpaceTableSize
);
1333 TmpTokenSpaceBufferCount
= PeiTokenSpaceTableSize
;
1334 FreePool (PeiTokenSpaceTable
);
1337 if (!DxeExMapTableEmpty
) {
1338 DxeTokenSpaceTableSize
= mDxeExMapppingTableSize
/ sizeof (DYNAMICEX_MAPPING
);
1339 DxeTokenSpaceTable
= GetDistinctTokenSpace (
1340 &DxeTokenSpaceTableSize
,
1341 (DYNAMICEX_MAPPING
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->ExMapTableOffset
),
1342 (EFI_GUID
*)((UINT8
*)mPcdDatabase
.DxeDb
+ mPcdDatabase
.DxeDb
->GuidTableOffset
)
1346 // Make sure EFI_GUID in DxeTokenSpaceTable does not exist in PeiTokenSpaceTable
1348 for (Idx2
= 0, Idx3
= PeiTokenSpaceTableSize
; Idx2
< DxeTokenSpaceTableSize
; Idx2
++) {
1350 for (Idx
= 0; Idx
< PeiTokenSpaceTableSize
; Idx
++) {
1351 if (CompareGuid (TmpTokenSpaceBuffer
[Idx
], DxeTokenSpaceTable
[Idx2
])) {
1358 TmpTokenSpaceBuffer
[Idx3
++] = DxeTokenSpaceTable
[Idx2
];
1362 TmpTokenSpaceBufferCount
= Idx3
;
1363 FreePool (DxeTokenSpaceTable
);
1367 if (*Guid
== NULL
) {
1368 *Guid
= TmpTokenSpaceBuffer
[0];
1372 for (Idx
= 0; Idx
< TmpTokenSpaceBufferCount
; Idx
++) {
1373 if (CompareGuid (*Guid
, TmpTokenSpaceBuffer
[Idx
])) {
1374 if (Idx
== TmpTokenSpaceBufferCount
- 1) {
1376 // It has been the last token namespace.
1379 return EFI_NOT_FOUND
;
1382 *Guid
= TmpTokenSpaceBuffer
[Idx
];
1388 return EFI_NOT_FOUND
;