3 Vfr common library functions.
5 Copyright (c) 2004 - 2017, 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.
18 #include "CommonLib.h"
19 #include "VfrUtilityLib.h"
20 #include "VfrFormPkg.h"
23 CVfrBinaryOutput::WriteLine (
26 IN CONST CHAR8
*LineHeader
,
33 if ((pFile
== NULL
) || (LineHeader
== NULL
) || (BlkBuf
== NULL
)) {
37 for (Index
= 0; Index
< BlkSize
; Index
++) {
38 if ((Index
% LineBytes
) == 0) {
39 fprintf (pFile
, "\n%s", LineHeader
);
41 fprintf (pFile
, "0x%02X, ", (UINT8
)BlkBuf
[Index
]);
46 CVfrBinaryOutput::WriteEnd (
49 IN CONST CHAR8
*LineHeader
,
56 if ((BlkSize
== 0) || (pFile
== NULL
) || (LineHeader
== NULL
) || (BlkBuf
== NULL
)) {
60 for (Index
= 0; Index
< BlkSize
- 1; Index
++) {
61 if ((Index
% LineBytes
) == 0) {
62 fprintf (pFile
, "\n%s", LineHeader
);
64 fprintf (pFile
, "0x%02X, ", (UINT8
)BlkBuf
[Index
]);
67 if ((Index
% LineBytes
) == 0) {
68 fprintf (pFile
, "\n%s", LineHeader
);
70 fprintf (pFile
, "0x%02X\n", (UINT8
)BlkBuf
[Index
]);
73 SConfigInfo::SConfigInfo (
77 IN EFI_IFR_TYPE_VALUE Value
82 mWidth
= (UINT16
)Width
;
83 mValue
= new UINT8
[mWidth
];
89 case EFI_IFR_TYPE_NUM_SIZE_8
:
90 memcpy (mValue
, &Value
.u8
, mWidth
);
92 case EFI_IFR_TYPE_NUM_SIZE_16
:
93 memcpy (mValue
, &Value
.u16
, mWidth
);
95 case EFI_IFR_TYPE_NUM_SIZE_32
:
96 memcpy (mValue
, &Value
.u32
, mWidth
);
98 case EFI_IFR_TYPE_NUM_SIZE_64
:
99 memcpy (mValue
, &Value
.u64
, mWidth
);
101 case EFI_IFR_TYPE_BOOLEAN
:
102 memcpy (mValue
, &Value
.b
, mWidth
);
104 case EFI_IFR_TYPE_TIME
:
105 memcpy (mValue
, &Value
.time
, mWidth
);
107 case EFI_IFR_TYPE_DATE
:
108 memcpy (mValue
, &Value
.date
, mWidth
);
110 case EFI_IFR_TYPE_STRING
:
111 memcpy (mValue
, &Value
.string
, mWidth
);
113 case EFI_IFR_TYPE_BUFFER
:
114 memcpy (mValue
, &Value
.u8
, mWidth
);
117 case EFI_IFR_TYPE_OTHER
:
122 SConfigInfo::~SConfigInfo (
126 ARRAY_SAFE_FREE (mValue
);
129 SConfigItem::SConfigItem (
142 if ((mName
= new CHAR8
[strlen (Name
) + 1]) != NULL
) {
143 strcpy (mName
, Name
);
148 if ((mGuid
= (EFI_GUID
*) new CHAR8
[sizeof (EFI_GUID
)]) != NULL
) {
149 memcpy (mGuid
, Guid
, sizeof (EFI_GUID
));
154 if ((mId
= new CHAR8
[strlen (Id
) + 1]) != NULL
) {
160 SConfigItem::SConfigItem (
167 IN EFI_IFR_TYPE_VALUE Value
177 if ((mName
= new CHAR8
[strlen (Name
) + 1]) != NULL
) {
178 strcpy (mName
, Name
);
183 if ((mGuid
= (EFI_GUID
*) new CHAR8
[sizeof (EFI_GUID
)]) != NULL
) {
184 memcpy (mGuid
, Guid
, sizeof (EFI_GUID
));
189 if ((mId
= new CHAR8
[strlen (Id
) + 1]) != NULL
) {
194 mInfoStrList
= new SConfigInfo(Type
, Offset
, Width
, Value
);
197 SConfigItem::~SConfigItem (
203 ARRAY_SAFE_FREE (mName
);
204 ARRAY_SAFE_FREE (mGuid
);
205 ARRAY_SAFE_FREE (mId
);
206 while (mInfoStrList
!= NULL
) {
208 mInfoStrList
= mInfoStrList
->mNext
;
210 BUFFER_SAFE_FREE (Info
);
215 CVfrBufferConfig::Register (
223 if (Select (Name
, Guid
) == 0) {
227 if ((pNew
= new SConfigItem (Name
, Guid
, Id
)) == NULL
) {
231 if (mItemListHead
== NULL
) {
232 mItemListHead
= pNew
;
233 mItemListTail
= pNew
;
235 mItemListTail
->mNext
= pNew
;
236 mItemListTail
= pNew
;
244 CVfrBufferConfig::Open (
248 mItemListPos
= mItemListHead
;
252 CVfrBufferConfig::Eof(
256 return (mItemListPos
== NULL
) ? TRUE
: FALSE
;
260 CVfrBufferConfig::Select (
268 if (Name
== NULL
|| Guid
== NULL
) {
269 mItemListPos
= mItemListHead
;
272 for (p
= mItemListHead
; p
!= NULL
; p
= p
->mNext
) {
273 if ((strcmp (p
->mName
, Name
) != 0) || (memcmp (p
->mGuid
, Guid
, sizeof (EFI_GUID
)) != 0)) {
278 if (p
->mId
== NULL
|| strcmp (p
->mId
, Id
) != 0) {
281 } else if (p
->mId
!= NULL
) {
294 CVfrBufferConfig::Write (
302 IN EFI_IFR_TYPE_VALUE Value
309 if ((Ret
= Select (Name
, Guid
)) != 0) {
315 if (Select (Name
, Guid
, Id
) != 0) {
316 if ((pItem
= new SConfigItem (Name
, Guid
, Id
, Type
, Offset
, (UINT16
) Width
, Value
)) == NULL
) {
319 if (mItemListHead
== NULL
) {
320 mItemListHead
= pItem
;
321 mItemListTail
= pItem
;
323 mItemListTail
->mNext
= pItem
;
324 mItemListTail
= pItem
;
326 mItemListPos
= pItem
;
328 // tranverse the list to find out if there's already the value for the same offset
329 for (pInfo
= mItemListPos
->mInfoStrList
; pInfo
!= NULL
; pInfo
= pInfo
->mNext
) {
330 if (pInfo
->mOffset
== Offset
) {
334 if((pInfo
= new SConfigInfo (Type
, Offset
, Width
, Value
)) == NULL
) {
337 pInfo
->mNext
= mItemListPos
->mInfoStrList
;
338 mItemListPos
->mInfoStrList
= pInfo
;
343 if (mItemListHead
== mItemListPos
) {
344 mItemListHead
= mItemListPos
->mNext
;
349 for (pItem
= mItemListHead
; pItem
->mNext
!= mItemListPos
; pItem
= pItem
->mNext
)
352 pItem
->mNext
= mItemListPos
->mNext
;
353 if (mItemListTail
== mItemListPos
) {
354 mItemListTail
= pItem
;
357 mItemListPos
= pItem
->mNext
;
360 case 'i' : // set info
361 if (mItemListPos
->mId
!= NULL
) {
362 delete mItemListPos
->mId
;
364 mItemListPos
->mId
= NULL
;
366 if ((mItemListPos
->mId
= new CHAR8
[strlen (Id
) + 1]) == NULL
) {
369 strcpy (mItemListPos
->mId
, Id
);
382 CVfrBufferConfig::Close (
389 #define BYTES_PRE_LINE 0x10
392 CVfrBufferConfig::OutputCFile (
397 CVfrBinaryOutput Output
;
406 for (Item
= mItemListHead
; Item
!= NULL
; Item
= Item
->mNext
) {
407 if (Item
->mId
!= NULL
|| Item
->mInfoStrList
== NULL
) {
410 fprintf (pFile
, "\nunsigned char %s%sBlockName[] = {", BaseName
, Item
->mName
);
412 TotalLen
= sizeof (UINT32
);
413 for (Info
= Item
->mInfoStrList
; Info
!= NULL
; Info
= Info
->mNext
) {
414 TotalLen
+= sizeof (UINT16
) * 2;
416 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&TotalLen
, sizeof (UINT32
));
418 for (Info
= Item
->mInfoStrList
; Info
!= NULL
; Info
= Info
->mNext
) {
419 fprintf (pFile
, "\n");
420 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&Info
->mOffset
, sizeof (UINT16
));
421 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&Info
->mWidth
, sizeof (UINT16
));
423 fprintf (pFile
, "\n};\n");
426 for (Item
= mItemListHead
; Item
!= NULL
; Item
= Item
->mNext
) {
427 if (Item
->mId
!= NULL
&& Item
->mInfoStrList
!= NULL
) {
428 fprintf (pFile
, "\nunsigned char %s%sDefault%s[] = {", BaseName
, Item
->mName
, Item
->mId
);
430 TotalLen
= sizeof (UINT32
);
431 for (Info
= Item
->mInfoStrList
; Info
!= NULL
; Info
= Info
->mNext
) {
432 TotalLen
+= Info
->mWidth
+ sizeof (UINT16
) * 2;
434 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&TotalLen
, sizeof (UINT32
));
436 for (Info
= Item
->mInfoStrList
; Info
!= NULL
; Info
= Info
->mNext
) {
437 fprintf (pFile
, "\n");
438 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&Info
->mOffset
, sizeof (UINT16
));
439 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)&Info
->mWidth
, sizeof (UINT16
));
440 if (Info
->mNext
== NULL
) {
441 Output
.WriteEnd (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)Info
->mValue
, Info
->mWidth
);
443 Output
.WriteLine (pFile
, BYTES_PRE_LINE
, " ", (CHAR8
*)Info
->mValue
, Info
->mWidth
);
446 fprintf (pFile
, "\n};\n");
451 CVfrBufferConfig::CVfrBufferConfig (
455 mItemListHead
= NULL
;
456 mItemListTail
= NULL
;
460 CVfrBufferConfig::~CVfrBufferConfig (
466 while (mItemListHead
!= NULL
) {
468 mItemListHead
= mItemListHead
->mNext
;
472 mItemListHead
= NULL
;
473 mItemListTail
= NULL
;
477 CVfrBufferConfig gCVfrBufferConfig
;
480 CONST CHAR8
*mTypeName
;
484 } gInternalTypesTable
[] = {
485 {"UINT64", EFI_IFR_TYPE_NUM_SIZE_64
, sizeof (UINT64
), sizeof (UINT64
)},
486 {"UINT32", EFI_IFR_TYPE_NUM_SIZE_32
, sizeof (UINT32
), sizeof (UINT32
)},
487 {"UINT16", EFI_IFR_TYPE_NUM_SIZE_16
, sizeof (UINT16
), sizeof (UINT16
)},
488 {"UINT8", EFI_IFR_TYPE_NUM_SIZE_8
, sizeof (UINT8
), sizeof (UINT8
)},
489 {"BOOLEAN", EFI_IFR_TYPE_BOOLEAN
, sizeof (BOOLEAN
), sizeof (BOOLEAN
)},
490 {"EFI_HII_DATE", EFI_IFR_TYPE_DATE
, sizeof (EFI_HII_DATE
), sizeof (UINT16
)},
491 {"EFI_STRING_ID", EFI_IFR_TYPE_STRING
, sizeof (EFI_STRING_ID
),sizeof (EFI_STRING_ID
)},
492 {"EFI_HII_TIME", EFI_IFR_TYPE_TIME
, sizeof (EFI_HII_TIME
), sizeof (UINT8
)},
493 {"EFI_HII_REF", EFI_IFR_TYPE_REF
, sizeof (EFI_HII_REF
), sizeof (EFI_GUID
)},
494 {NULL
, EFI_IFR_TYPE_OTHER
, 0, 0}
505 if (TypeName
== NULL
) {
509 for (Index
= 0; gInternalTypesTable
[Index
].mTypeName
!= NULL
; Index
++) {
510 if (strcmp (TypeName
, gInternalTypesTable
[Index
].mTypeName
) == 0) {
527 while (*Str
&& *Str
== ' ') {
530 while (*Str
&& *Str
== '0') {
533 if (*Str
&& (*Str
== 'x' || *Str
== 'X')) {
550 Str
= TrimHex (Str
, &IsHex
);
551 for (Value
= 0; (c
= *Str
) != '\0'; Str
++) {
553 // BUG: does not handle overflow here
555 (IsHex
== TRUE
) ? (Value
<<= 4) : (Value
*= 10);
557 if ((IsHex
== TRUE
) && (c
>= 'a') && (c
<= 'f')) {
558 Value
+= (c
- 'a' + 10);
560 if ((IsHex
== TRUE
) && (c
>= 'A') && (c
<= 'F')) {
561 Value
+= (c
- 'A' + 10);
563 if (c
>= '0' && c
<= '9') {
572 CVfrVarDataTypeDB::RegisterNewType (
576 New
->mNext
= mDataTypeList
;
581 CVfrVarDataTypeDB::ExtractStructTypeName (
587 return VFR_RETURN_FATAL_ERROR
;
590 while((*VarStr
!= '\0') && (*VarStr
!= '.')) {
596 if (*VarStr
== '.') {
600 return VFR_RETURN_SUCCESS
;
604 Check whether the DataType contain bit field.
606 @param TypeName The name of the type.
610 CVfrVarDataTypeDB::DataTypeHasBitField (
614 SVfrDataType
*pType
= NULL
;
617 GetDataType (TypeName
, &pType
);
622 for (pTmp
= pType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
623 if (pTmp
->mIsBitField
) {
631 Check whether the field is bit field or not.
633 @param VarStr Point to the field name which may contain the structure name.
637 CVfrVarDataTypeDB::IsThisBitField (
641 CHAR8 FName
[MAX_NAME_LEN
];
642 CHAR8 TName
[MAX_NAME_LEN
];
644 SVfrDataType
*pType
= NULL
;
645 SVfrDataField
*pField
= NULL
;
647 CHECK_ERROR_RETURN (ExtractStructTypeName (VarStr
, TName
), VFR_RETURN_SUCCESS
);
648 CHECK_ERROR_RETURN (GetDataType (TName
, &pType
), VFR_RETURN_SUCCESS
);
650 while (*VarStr
!= '\0') {
651 CHECK_ERROR_RETURN(ExtractFieldNameAndArrary(VarStr
, FName
, ArrayIdx
), VFR_RETURN_SUCCESS
);
652 CHECK_ERROR_RETURN(GetTypeField (FName
, pType
, pField
), VFR_RETURN_SUCCESS
);
653 pType
= pField
->mFieldType
;
655 if (pField
!= NULL
&& pField
->mIsBitField
) {
663 CVfrVarDataTypeDB::ExtractFieldNameAndArrary (
670 CHAR8 ArrayStr
[MAX_NAME_LEN
+ 1];
672 ArrayIdx
= INVALID_ARRAY_INDEX
;
675 return VFR_RETURN_FATAL_ERROR
;
678 while((*VarStr
!= '\0') &&
692 return VFR_RETURN_SUCCESS
;
695 for (Idx
= 0; (Idx
< MAX_NAME_LEN
) && (*VarStr
!= '\0') && (*VarStr
!= ']'); VarStr
++, Idx
++) {
696 ArrayStr
[Idx
] = *VarStr
;
698 ArrayStr
[Idx
] = '\0';
700 if ((*VarStr
!= ']') && (ArrayStr
[0] == '\0')) {
701 return VFR_RETURN_DATA_STRING_ERROR
;
703 ArrayIdx
= _STR2U32 (ArrayStr
);
704 if (*VarStr
== ']') {
707 if (*VarStr
== '.') {
710 return VFR_RETURN_SUCCESS
;
712 return VFR_RETURN_DATA_STRING_ERROR
;
715 return VFR_RETURN_SUCCESS
;
719 CVfrVarDataTypeDB::GetTypeField (
720 IN CONST CHAR8
*FName
,
721 IN SVfrDataType
*Type
,
722 OUT SVfrDataField
*&Field
725 SVfrDataField
*pField
= NULL
;
727 if ((FName
== NULL
) || (Type
== NULL
)) {
728 return VFR_RETURN_FATAL_ERROR
;
731 for (pField
= Type
->mMembers
; pField
!= NULL
; pField
= pField
->mNext
) {
733 // For type EFI_IFR_TYPE_TIME, because field name is not correctly wrote,
734 // add code to adjust it.
736 if (Type
->mType
== EFI_IFR_TYPE_TIME
) {
737 if (strcmp (FName
, "Hour") == 0) {
739 } else if (strcmp (FName
, "Minute") == 0) {
741 } else if (strcmp (FName
, "Second") == 0) {
746 if (strcmp (pField
->mFieldName
, FName
) == 0) {
748 return VFR_RETURN_SUCCESS
;
752 return VFR_RETURN_UNDEFINED
;
756 CVfrVarDataTypeDB::GetFieldOffset (
757 IN SVfrDataField
*Field
,
760 IN BOOLEAN IsBitField
764 return VFR_RETURN_FATAL_ERROR
;
768 // Framework Vfr file Array Index is from 1.
769 // But Uefi Vfr file Array Index is from 0.
771 if (VfrCompatibleMode
&& ArrayIdx
!= INVALID_ARRAY_INDEX
) {
773 return VFR_RETURN_ERROR_ARRARY_NUM
;
775 ArrayIdx
= ArrayIdx
- 1;
778 if ((ArrayIdx
!= INVALID_ARRAY_INDEX
) && ((Field
->mArrayNum
== 0) || (Field
->mArrayNum
<= ArrayIdx
))) {
779 return VFR_RETURN_ERROR_ARRARY_NUM
;
783 // Be compatible with the current usage
784 // If ArraryIdx is not specified, the first one is used.
786 // if ArrayNum is larger than zero, ArraryIdx must be specified.
788 // if ((ArrayIdx == INVALID_ARRAY_INDEX) && (Field->mArrayNum > 0)) {
789 // return VFR_RETURN_ERROR_ARRARY_NUM;
793 Offset
= Field
->mBitOffset
+ Field
->mFieldType
->mTotalSize
* ((ArrayIdx
== INVALID_ARRAY_INDEX
) ? 0 : ArrayIdx
) * 8;
795 Offset
= Field
->mOffset
+ Field
->mFieldType
->mTotalSize
* ((ArrayIdx
== INVALID_ARRAY_INDEX
) ? 0 : ArrayIdx
);
797 return VFR_RETURN_SUCCESS
;
801 CVfrVarDataTypeDB::GetFieldWidth (
802 IN SVfrDataField
*Field
809 return Field
->mFieldType
->mType
;
813 CVfrVarDataTypeDB::GetFieldSize (
814 IN SVfrDataField
*Field
,
820 return VFR_RETURN_FATAL_ERROR
;
823 if ((ArrayIdx
== INVALID_ARRAY_INDEX
) && (Field
->mArrayNum
!= 0)) {
824 return Field
->mFieldType
->mTotalSize
* Field
->mArrayNum
;
827 return Field
->mBitWidth
;
829 return Field
->mFieldType
->mTotalSize
;
835 CVfrVarDataTypeDB::InternalTypesListInit (
839 SVfrDataType
*New
= NULL
;
842 for (Index
= 0; gInternalTypesTable
[Index
].mTypeName
!= NULL
; Index
++) {
843 New
= new SVfrDataType
;
845 strcpy (New
->mTypeName
, gInternalTypesTable
[Index
].mTypeName
);
846 New
->mType
= gInternalTypesTable
[Index
].mType
;
847 New
->mAlign
= gInternalTypesTable
[Index
].mAlign
;
848 New
->mTotalSize
= gInternalTypesTable
[Index
].mSize
;
849 if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_DATE") == 0) {
850 SVfrDataField
*pYearField
= new SVfrDataField
;
851 SVfrDataField
*pMonthField
= new SVfrDataField
;
852 SVfrDataField
*pDayField
= new SVfrDataField
;
854 strcpy (pYearField
->mFieldName
, "Year");
855 GetDataType ((CHAR8
*)"UINT16", &pYearField
->mFieldType
);
856 pYearField
->mOffset
= 0;
857 pYearField
->mNext
= pMonthField
;
858 pYearField
->mArrayNum
= 0;
859 pYearField
->mIsBitField
= FALSE
;
861 strcpy (pMonthField
->mFieldName
, "Month");
862 GetDataType ((CHAR8
*)"UINT8", &pMonthField
->mFieldType
);
863 pMonthField
->mOffset
= 2;
864 pMonthField
->mNext
= pDayField
;
865 pMonthField
->mArrayNum
= 0;
866 pMonthField
->mIsBitField
= FALSE
;
868 strcpy (pDayField
->mFieldName
, "Day");
869 GetDataType ((CHAR8
*)"UINT8", &pDayField
->mFieldType
);
870 pDayField
->mOffset
= 3;
871 pDayField
->mNext
= NULL
;
872 pDayField
->mArrayNum
= 0;
873 pDayField
->mIsBitField
= FALSE
;
875 New
->mMembers
= pYearField
;
876 } else if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_TIME") == 0) {
877 SVfrDataField
*pHoursField
= new SVfrDataField
;
878 SVfrDataField
*pMinutesField
= new SVfrDataField
;
879 SVfrDataField
*pSecondsField
= new SVfrDataField
;
881 strcpy (pHoursField
->mFieldName
, "Hours");
882 GetDataType ((CHAR8
*)"UINT8", &pHoursField
->mFieldType
);
883 pHoursField
->mOffset
= 0;
884 pHoursField
->mNext
= pMinutesField
;
885 pHoursField
->mArrayNum
= 0;
886 pHoursField
->mIsBitField
= FALSE
;
888 strcpy (pMinutesField
->mFieldName
, "Minutes");
889 GetDataType ((CHAR8
*)"UINT8", &pMinutesField
->mFieldType
);
890 pMinutesField
->mOffset
= 1;
891 pMinutesField
->mNext
= pSecondsField
;
892 pMinutesField
->mArrayNum
= 0;
893 pMinutesField
->mIsBitField
= FALSE
;
895 strcpy (pSecondsField
->mFieldName
, "Seconds");
896 GetDataType ((CHAR8
*)"UINT8", &pSecondsField
->mFieldType
);
897 pSecondsField
->mOffset
= 2;
898 pSecondsField
->mNext
= NULL
;
899 pSecondsField
->mArrayNum
= 0;
900 pSecondsField
->mIsBitField
= FALSE
;
902 New
->mMembers
= pHoursField
;
903 } else if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_REF") == 0) {
904 SVfrDataField
*pQuestionIdField
= new SVfrDataField
;
905 SVfrDataField
*pFormIdField
= new SVfrDataField
;
906 SVfrDataField
*pFormSetGuidField
= new SVfrDataField
;
907 SVfrDataField
*pDevicePathField
= new SVfrDataField
;
909 strcpy (pQuestionIdField
->mFieldName
, "QuestionId");
910 GetDataType ((CHAR8
*)"UINT16", &pQuestionIdField
->mFieldType
);
911 pQuestionIdField
->mOffset
= 0;
912 pQuestionIdField
->mNext
= pFormIdField
;
913 pQuestionIdField
->mArrayNum
= 0;
914 pQuestionIdField
->mIsBitField
= FALSE
;
916 strcpy (pFormIdField
->mFieldName
, "FormId");
917 GetDataType ((CHAR8
*)"UINT16", &pFormIdField
->mFieldType
);
918 pFormIdField
->mOffset
= 2;
919 pFormIdField
->mNext
= pFormSetGuidField
;
920 pFormIdField
->mArrayNum
= 0;
921 pFormIdField
->mIsBitField
= FALSE
;
923 strcpy (pFormSetGuidField
->mFieldName
, "FormSetGuid");
924 GetDataType ((CHAR8
*)"EFI_GUID", &pFormSetGuidField
->mFieldType
);
925 pFormSetGuidField
->mOffset
= 4;
926 pFormSetGuidField
->mNext
= pDevicePathField
;
927 pFormSetGuidField
->mArrayNum
= 0;
928 pFormSetGuidField
->mIsBitField
= FALSE
;
930 strcpy (pDevicePathField
->mFieldName
, "DevicePath");
931 GetDataType ((CHAR8
*)"EFI_STRING_ID", &pDevicePathField
->mFieldType
);
932 pDevicePathField
->mOffset
= 20;
933 pDevicePathField
->mNext
= NULL
;
934 pDevicePathField
->mArrayNum
= 0;
935 pDevicePathField
->mIsBitField
= FALSE
;
937 New
->mMembers
= pQuestionIdField
;
939 New
->mMembers
= NULL
;
942 RegisterNewType (New
);
948 CVfrVarDataTypeDB::CVfrVarDataTypeDB (
952 mDataTypeList
= NULL
;
954 mCurrDataField
= NULL
;
955 mPackAlign
= DEFAULT_PACK_ALIGN
;
957 mFirstNewDataTypeName
= NULL
;
959 InternalTypesListInit ();
962 CVfrVarDataTypeDB::~CVfrVarDataTypeDB (
967 SVfrDataField
*pField
;
968 SVfrPackStackNode
*pPack
;
970 if (mNewDataType
!= NULL
) {
974 while (mDataTypeList
!= NULL
) {
975 pType
= mDataTypeList
;
976 mDataTypeList
= mDataTypeList
->mNext
;
977 while(pType
->mMembers
!= NULL
) {
978 pField
= pType
->mMembers
;
979 pType
->mMembers
= pType
->mMembers
->mNext
;
985 while (mPackStack
!= NULL
) {
987 mPackStack
= mPackStack
->mNext
;
993 CVfrVarDataTypeDB::Pack (
996 IN CHAR8
*Identifier
,
1001 CHAR8 Msg
[MAX_STRING_LEN
] = {0, };
1003 if (Action
& VFR_PACK_SHOW
) {
1004 sprintf (Msg
, "value of pragma pack(show) == %d", mPackAlign
);
1005 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Warning", Msg
);
1008 if (Action
& VFR_PACK_PUSH
) {
1009 SVfrPackStackNode
*pNew
= NULL
;
1011 if ((pNew
= new SVfrPackStackNode (Identifier
, mPackAlign
)) == NULL
) {
1012 return VFR_RETURN_FATAL_ERROR
;
1014 pNew
->mNext
= mPackStack
;
1018 if (Action
& VFR_PACK_POP
) {
1019 SVfrPackStackNode
*pNode
= NULL
;
1021 if (mPackStack
== NULL
) {
1022 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Error", "#pragma pack(pop...) : more pops than pushes");
1025 for (pNode
= mPackStack
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
1026 if (pNode
->Match (Identifier
) == TRUE
) {
1027 mPackAlign
= pNode
->mNumber
;
1028 mPackStack
= pNode
->mNext
;
1033 if (Action
& VFR_PACK_ASSIGN
) {
1034 PackAlign
= (Number
> 1) ? Number
+ Number
% 2 : Number
;
1035 if ((PackAlign
== 0) || (PackAlign
> 16)) {
1036 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Error", "expected pragma parameter to be '1', '2', '4', '8', or '16'");
1038 mPackAlign
= PackAlign
;
1042 return VFR_RETURN_SUCCESS
;
1046 CVfrVarDataTypeDB::DeclareDataTypeBegin (
1050 SVfrDataType
*pNewType
= NULL
;
1052 pNewType
= new SVfrDataType
;
1053 pNewType
->mTypeName
[0] = '\0';
1054 pNewType
->mType
= EFI_IFR_TYPE_OTHER
;
1055 pNewType
->mAlign
= DEFAULT_ALIGN
;
1056 pNewType
->mTotalSize
= 0;
1057 pNewType
->mMembers
= NULL
;
1058 pNewType
->mNext
= NULL
;
1059 pNewType
->mHasBitField
= FALSE
;
1061 mNewDataType
= pNewType
;
1065 CVfrVarDataTypeDB::SetNewTypeName (
1069 SVfrDataType
*pType
;
1071 if (mNewDataType
== NULL
) {
1072 return VFR_RETURN_ERROR_SKIPED
;
1074 if (TypeName
== NULL
) {
1075 return VFR_RETURN_FATAL_ERROR
;
1077 if (strlen(TypeName
) >= MAX_NAME_LEN
) {
1078 return VFR_RETURN_INVALID_PARAMETER
;
1081 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1082 if (strcmp(pType
->mTypeName
, TypeName
) == 0) {
1083 return VFR_RETURN_REDEFINED
;
1087 strcpy(mNewDataType
->mTypeName
, TypeName
);
1088 return VFR_RETURN_SUCCESS
;
1092 Record the bit field info in the data type.
1094 @param FieldName Point to the field name.
1095 @param TypeName Point to the type name.
1096 @param Width The bit width.
1097 @param FieldInUnion The filed is in Union type or Structure type.
1101 CVfrVarDataTypeDB::DataTypeAddBitField (
1102 IN CHAR8
*FieldName
,
1105 IN BOOLEAN FieldInUnion
1108 SVfrDataField
*pNewField
= NULL
;
1109 SVfrDataType
*pFieldType
= NULL
;
1110 SVfrDataField
*pTmp
;
1112 UINT32 MaxDataTypeSize
;
1113 BOOLEAN UpdateTotalSize
;
1115 CHECK_ERROR_RETURN (GetDataType (TypeName
, &pFieldType
), VFR_RETURN_SUCCESS
);
1117 if (Width
> MAX_BIT_WIDTH
) {
1118 return VFR_RETURN_BIT_WIDTH_ERROR
;
1121 if (Width
> pFieldType
->mTotalSize
* 8) {
1122 return VFR_RETURN_BIT_WIDTH_ERROR
;
1125 if (FieldName
!= NULL
&& strlen (FieldName
) >= MAX_NAME_LEN
) {
1126 return VFR_RETURN_INVALID_PARAMETER
;
1129 if (Width
== 0 && FieldName
!= NULL
) {
1130 return VFR_RETURN_INVALID_PARAMETER
;
1133 for (pTmp
= mNewDataType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
1134 if (FieldName
!= NULL
&& strcmp (pTmp
->mFieldName
, FieldName
) == 0) {
1135 return VFR_RETURN_REDEFINED
;
1139 Align
= MIN (mPackAlign
, pFieldType
->mAlign
);
1140 UpdateTotalSize
= FALSE
;
1142 if ((pNewField
= new SVfrDataField
) == NULL
) {
1143 return VFR_RETURN_OUT_FOR_RESOURCES
;
1146 MaxDataTypeSize
= mNewDataType
->mTotalSize
;
1147 if (FieldName
!= NULL
) {
1148 strcpy (pNewField
->mFieldName
, FieldName
);
1150 pNewField
->mFieldType
= pFieldType
;
1151 pNewField
->mIsBitField
= TRUE
;
1152 pNewField
->mBitWidth
= Width
;
1153 pNewField
->mArrayNum
= 0;
1154 pNewField
->mBitOffset
= 0;
1155 pNewField
->mOffset
= 0;
1157 if (mNewDataType
->mMembers
== NULL
) {
1158 mNewDataType
->mMembers
= pNewField
;
1159 pNewField
->mNext
= NULL
;
1161 for (pTmp
= mNewDataType
->mMembers
; pTmp
->mNext
!= NULL
; pTmp
= pTmp
->mNext
)
1163 pTmp
->mNext
= pNewField
;
1164 pNewField
->mNext
= NULL
;
1168 pNewField
->mOffset
= 0;
1169 if (MaxDataTypeSize
< pNewField
->mFieldType
->mTotalSize
) {
1170 mNewDataType
->mTotalSize
= pNewField
->mFieldType
->mTotalSize
;
1174 // Check whether the bit fileds can be contained within one FieldType.
1176 if (pTmp
!= NULL
&& pTmp
->mIsBitField
&& strcmp (pTmp
->mFieldType
->mTypeName
, pNewField
->mFieldType
->mTypeName
) == 0 &&
1177 (pTmp
->mBitOffset
- pTmp
->mOffset
* 8) + pTmp
->mBitWidth
+ pNewField
->mBitWidth
<= pNewField
->mFieldType
->mTotalSize
* 8) {
1178 pNewField
->mBitOffset
= pTmp
->mBitOffset
+ pTmp
->mBitWidth
;
1179 pNewField
->mOffset
= pTmp
->mOffset
;
1181 // If BitWidth=0,used to force alignment at the next word boundary.
1182 // So make this bit field occupy the remaing bit width of current field type.
1184 if (pNewField
->mBitWidth
== 0) {
1185 pNewField
->mBitWidth
= pNewField
->mFieldType
->mTotalSize
* 8 - (pNewField
->mBitOffset
- pTmp
->mOffset
* 8);
1189 // The bit filed start a new memory
1191 pNewField
->mBitOffset
= mNewDataType
->mTotalSize
* 8;
1192 UpdateTotalSize
= TRUE
;
1196 if (UpdateTotalSize
){
1197 if ((mNewDataType
->mTotalSize
% Align
) == 0) {
1198 pNewField
->mOffset
= mNewDataType
->mTotalSize
;
1200 pNewField
->mOffset
= mNewDataType
->mTotalSize
+ ALIGN_STUFF(mNewDataType
->mTotalSize
, Align
);
1202 mNewDataType
->mTotalSize
= pNewField
->mOffset
+ (pNewField
->mFieldType
->mTotalSize
);
1205 mNewDataType
->mAlign
= MIN (mPackAlign
, MAX (pFieldType
->mAlign
, mNewDataType
->mAlign
));
1206 mNewDataType
->mHasBitField
= TRUE
;
1207 return VFR_RETURN_SUCCESS
;
1211 CVfrVarDataTypeDB::DataTypeAddField (
1212 IN CHAR8
*FieldName
,
1215 IN BOOLEAN FieldInUnion
1218 SVfrDataField
*pNewField
= NULL
;
1219 SVfrDataType
*pFieldType
= NULL
;
1220 SVfrDataField
*pTmp
;
1222 UINT32 MaxDataTypeSize
;
1224 CHECK_ERROR_RETURN (GetDataType (TypeName
, &pFieldType
), VFR_RETURN_SUCCESS
);
1225 MaxDataTypeSize
= mNewDataType
->mTotalSize
;
1227 if (strlen (FieldName
) >= MAX_NAME_LEN
) {
1228 return VFR_RETURN_INVALID_PARAMETER
;
1231 for (pTmp
= mNewDataType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
1232 if (strcmp (pTmp
->mFieldName
, FieldName
) == 0) {
1233 return VFR_RETURN_REDEFINED
;
1237 Align
= MIN (mPackAlign
, pFieldType
->mAlign
);
1239 if ((pNewField
= new SVfrDataField
) == NULL
) {
1240 return VFR_RETURN_OUT_FOR_RESOURCES
;
1242 strcpy (pNewField
->mFieldName
, FieldName
);
1243 pNewField
->mFieldType
= pFieldType
;
1244 pNewField
->mArrayNum
= ArrayNum
;
1245 pNewField
->mIsBitField
= FALSE
;
1246 if ((mNewDataType
->mTotalSize
% Align
) == 0) {
1247 pNewField
->mOffset
= mNewDataType
->mTotalSize
;
1249 pNewField
->mOffset
= mNewDataType
->mTotalSize
+ ALIGN_STUFF(mNewDataType
->mTotalSize
, Align
);
1251 if (mNewDataType
->mMembers
== NULL
) {
1252 mNewDataType
->mMembers
= pNewField
;
1253 pNewField
->mNext
= NULL
;
1255 for (pTmp
= mNewDataType
->mMembers
; pTmp
->mNext
!= NULL
; pTmp
= pTmp
->mNext
)
1257 pTmp
->mNext
= pNewField
;
1258 pNewField
->mNext
= NULL
;
1261 mNewDataType
->mAlign
= MIN (mPackAlign
, MAX (pFieldType
->mAlign
, mNewDataType
->mAlign
));
1264 if (MaxDataTypeSize
< pNewField
->mFieldType
->mTotalSize
) {
1265 mNewDataType
->mTotalSize
= pNewField
->mFieldType
->mTotalSize
;
1267 pNewField
->mOffset
= 0;
1269 mNewDataType
->mTotalSize
= pNewField
->mOffset
+ (pNewField
->mFieldType
->mTotalSize
) * ((ArrayNum
== 0) ? 1 : ArrayNum
);
1272 return VFR_RETURN_SUCCESS
;
1276 CVfrVarDataTypeDB::DeclareDataTypeEnd (
1280 if (mNewDataType
->mTypeName
[0] == '\0') {
1284 if ((mNewDataType
->mTotalSize
% mNewDataType
->mAlign
) !=0) {
1285 mNewDataType
->mTotalSize
+= ALIGN_STUFF (mNewDataType
->mTotalSize
, mNewDataType
->mAlign
);
1288 RegisterNewType (mNewDataType
);
1289 if (mFirstNewDataTypeName
== NULL
) {
1290 mFirstNewDataTypeName
= mNewDataType
->mTypeName
;
1293 mNewDataType
= NULL
;
1297 CVfrVarDataTypeDB::GetDataType (
1299 OUT SVfrDataType
**DataType
1302 SVfrDataType
*pDataType
= NULL
;
1304 if (TypeName
== NULL
) {
1305 return VFR_RETURN_ERROR_SKIPED
;
1308 if (DataType
== NULL
) {
1309 return VFR_RETURN_FATAL_ERROR
;
1314 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1315 if (strcmp (TypeName
, pDataType
->mTypeName
) == 0) {
1316 *DataType
= pDataType
;
1317 return VFR_RETURN_SUCCESS
;
1321 return VFR_RETURN_UNDEFINED
;
1325 CVfrVarDataTypeDB::GetDataTypeSize (
1330 SVfrDataType
*pDataType
= NULL
;
1333 return VFR_RETURN_FATAL_ERROR
;
1337 DataType
= DataType
& 0x0F;
1340 // For user defined data type, the size can't be got by this function.
1342 if (DataType
== EFI_IFR_TYPE_OTHER
) {
1343 return VFR_RETURN_SUCCESS
;
1346 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1347 if (DataType
== pDataType
->mType
) {
1348 *Size
= pDataType
->mTotalSize
;
1349 return VFR_RETURN_SUCCESS
;
1353 return VFR_RETURN_UNDEFINED
;
1357 CVfrVarDataTypeDB::GetDataTypeSize (
1362 SVfrDataType
*pDataType
= NULL
;
1365 return VFR_RETURN_FATAL_ERROR
;
1370 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1371 if (strcmp (TypeName
, pDataType
->mTypeName
) == 0) {
1372 *Size
= pDataType
->mTotalSize
;
1373 return VFR_RETURN_SUCCESS
;
1377 return VFR_RETURN_UNDEFINED
;
1381 CVfrVarDataTypeDB::GetDataFieldInfo (
1386 OUT BOOLEAN
&BitField
1389 CHAR8 TName
[MAX_NAME_LEN
], FName
[MAX_NAME_LEN
];
1390 UINT32 ArrayIdx
, Tmp
;
1391 SVfrDataType
*pType
= NULL
;
1392 SVfrDataField
*pField
= NULL
;
1396 Type
= EFI_IFR_TYPE_OTHER
;
1398 VarStrName
= VarStr
;
1400 CHECK_ERROR_RETURN (ExtractStructTypeName (VarStr
, TName
), VFR_RETURN_SUCCESS
);
1401 CHECK_ERROR_RETURN (GetDataType (TName
, &pType
), VFR_RETURN_SUCCESS
);
1403 BitField
= IsThisBitField (VarStrName
);
1406 // if it is not struct data type
1408 Type
= pType
->mType
;
1409 Size
= pType
->mTotalSize
;
1411 while (*VarStr
!= '\0') {
1412 CHECK_ERROR_RETURN(ExtractFieldNameAndArrary(VarStr
, FName
, ArrayIdx
), VFR_RETURN_SUCCESS
);
1413 CHECK_ERROR_RETURN(GetTypeField (FName
, pType
, pField
), VFR_RETURN_SUCCESS
);
1414 pType
= pField
->mFieldType
;
1415 CHECK_ERROR_RETURN(GetFieldOffset (pField
, ArrayIdx
, Tmp
, pField
->mIsBitField
), VFR_RETURN_SUCCESS
);
1416 if (BitField
&& !pField
->mIsBitField
) {
1417 Offset
= (UINT16
) (Offset
+ Tmp
* 8);
1419 Offset
= (UINT16
) (Offset
+ Tmp
);
1421 Type
= GetFieldWidth (pField
);
1422 Size
= GetFieldSize (pField
, ArrayIdx
, BitField
);
1424 return VFR_RETURN_SUCCESS
;
1428 CVfrVarDataTypeDB::GetUserDefinedTypeNameList (
1429 OUT CHAR8
***NameList
,
1430 OUT UINT32
*ListSize
1434 SVfrDataType
*pType
;
1436 if ((NameList
== NULL
) || (ListSize
== NULL
)) {
1437 return VFR_RETURN_FATAL_ERROR
;
1443 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1444 if (_IS_INTERNAL_TYPE(pType
->mTypeName
) == FALSE
) {
1449 if (*ListSize
== 0) {
1450 return VFR_RETURN_SUCCESS
;
1453 if ((*NameList
= new CHAR8
*[*ListSize
]) == NULL
) {
1455 return VFR_RETURN_OUT_FOR_RESOURCES
;
1458 for (Index
= 0, pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
, Index
++) {
1459 if (_IS_INTERNAL_TYPE(pType
->mTypeName
) == FALSE
) {
1460 (*NameList
)[Index
] = pType
->mTypeName
;
1463 return VFR_RETURN_SUCCESS
;
1467 CVfrVarDataTypeDB::IsTypeNameDefined (
1471 SVfrDataType
*pType
;
1473 if (TypeName
== NULL
) {
1477 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1478 if (strcmp (pType
->mTypeName
, TypeName
) == 0) {
1487 CVfrVarDataTypeDB::Dump (
1491 SVfrDataType
*pTNode
;
1492 SVfrDataField
*pFNode
;
1494 fprintf (File
, "\n\n***************************************************************\n");
1495 fprintf (File
, "\t\tmPackAlign = %x\n", mPackAlign
);
1496 for (pTNode
= mDataTypeList
; pTNode
!= NULL
; pTNode
= pTNode
->mNext
) {
1497 fprintf (File
, "\t\tstruct %s : mAlign [%d] mTotalSize [0x%x]\n\n", pTNode
->mTypeName
, pTNode
->mAlign
, pTNode
->mTotalSize
);
1498 fprintf (File
, "\t\tstruct %s {\n", pTNode
->mTypeName
);
1499 for (pFNode
= pTNode
->mMembers
; pFNode
!= NULL
; pFNode
= pFNode
->mNext
) {
1500 if (pFNode
->mArrayNum
> 0) {
1501 fprintf (File
, "\t\t\t+%08d[%08x] %s[%d] <%s>\n", pFNode
->mOffset
, pFNode
->mOffset
,
1502 pFNode
->mFieldName
, pFNode
->mArrayNum
, pFNode
->mFieldType
->mTypeName
);
1504 fprintf (File
, "\t\t\t+%08d[%08x] %s <%s>\n", pFNode
->mOffset
, pFNode
->mOffset
,
1505 pFNode
->mFieldName
, pFNode
->mFieldType
->mTypeName
);
1508 fprintf (File
, "\t\t};\n");
1509 fprintf (File
, "---------------------------------------------------------------\n");
1511 fprintf (File
, "***************************************************************\n");
1514 #ifdef CVFR_VARDATATYPEDB_DEBUG
1516 CVfrVarDataTypeDB::ParserDB (
1520 SVfrDataType
*pTNode
;
1521 SVfrDataField
*pFNode
;
1523 printf ("***************************************************************\n");
1524 printf ("\t\tmPackAlign = %x\n", mPackAlign
);
1525 for (pTNode
= mDataTypeList
; pTNode
!= NULL
; pTNode
= pTNode
->mNext
) {
1526 printf ("\t\tstruct %s : mAlign [%x] mTotalSize [%x]\n\n", pTNode
->mTypeName
, pTNode
->mAlign
, pTNode
->mTotalSize
);
1527 printf ("\t\tstruct %s {\n", pTNode
->mTypeName
);
1528 for (pFNode
= pTNode
->mMembers
; pFNode
!= NULL
; pFNode
= pFNode
->mNext
) {
1529 printf ("\t\t\t%s\t%s\n", pFNode
->mFieldType
->mTypeName
, pFNode
->mFieldName
);
1531 printf ("\t\t};\n");
1532 printf ("---------------------------------------------------------------\n");
1534 printf ("***************************************************************\n");
1538 SVfrVarStorageNode::SVfrVarStorageNode (
1540 IN CHAR8
*StoreName
,
1541 IN EFI_VARSTORE_ID VarStoreId
,
1542 IN EFI_STRING_ID VarName
,
1550 memset (&mGuid
, 0, sizeof (EFI_GUID
));
1552 if (StoreName
!= NULL
) {
1553 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1554 strcpy (mVarStoreName
, StoreName
);
1556 mVarStoreName
= NULL
;
1559 mVarStoreId
= VarStoreId
;
1560 mVarStoreType
= EFI_VFR_VARSTORE_EFI
;
1561 mStorageInfo
.mEfiVar
.mEfiVarName
= VarName
;
1562 mStorageInfo
.mEfiVar
.mEfiVarSize
= VarSize
;
1563 mAssignedFlag
= Flag
;
1566 SVfrVarStorageNode::SVfrVarStorageNode (
1568 IN CHAR8
*StoreName
,
1569 IN EFI_VARSTORE_ID VarStoreId
,
1570 IN SVfrDataType
*DataType
,
1571 IN BOOLEAN BitsVarstore
,
1578 memset (&mGuid
, 0, sizeof (EFI_GUID
));
1580 if (StoreName
!= NULL
) {
1581 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1582 strcpy (mVarStoreName
, StoreName
);
1584 mVarStoreName
= NULL
;
1587 mVarStoreId
= VarStoreId
;
1589 mVarStoreType
= EFI_VFR_VARSTORE_BUFFER_BITS
;
1591 mVarStoreType
= EFI_VFR_VARSTORE_BUFFER
;
1593 mStorageInfo
.mDataType
= DataType
;
1594 mAssignedFlag
= Flag
;
1597 SVfrVarStorageNode::SVfrVarStorageNode (
1598 IN CHAR8
*StoreName
,
1599 IN EFI_VARSTORE_ID VarStoreId
1602 if (StoreName
!= NULL
) {
1603 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1604 strcpy (mVarStoreName
, StoreName
);
1606 mVarStoreName
= NULL
;
1609 mVarStoreId
= VarStoreId
;
1610 mVarStoreType
= EFI_VFR_VARSTORE_NAME
;
1611 mStorageInfo
.mNameSpace
.mNameTable
= new EFI_VARSTORE_ID
[DEFAULT_NAME_TABLE_ITEMS
];
1612 mStorageInfo
.mNameSpace
.mTableSize
= 0;
1615 SVfrVarStorageNode::~SVfrVarStorageNode (
1619 if (mVarStoreName
!= NULL
) {
1620 delete[] mVarStoreName
;
1623 if (mVarStoreType
== EFI_VFR_VARSTORE_NAME
) {
1624 delete mStorageInfo
.mNameSpace
.mNameTable
;
1628 CVfrDataStorage::CVfrDataStorage (
1634 for (Index
= 0; Index
< EFI_FREE_VARSTORE_ID_BITMAP_SIZE
; Index
++) {
1635 mFreeVarStoreIdBitMap
[Index
] = 0;
1638 // Question ID 0 is reserved.
1639 mFreeVarStoreIdBitMap
[0] = 0x80000000;
1641 mBufferVarStoreList
= NULL
;
1642 mEfiVarStoreList
= NULL
;
1643 mNameVarStoreList
= NULL
;
1644 mCurrVarStorageNode
= NULL
;
1645 mNewVarStorageNode
= NULL
;
1646 mBufferFieldInfoListHead
= NULL
;
1647 mBufferFieldInfoListTail
= NULL
;
1650 CVfrDataStorage::~CVfrDataStorage (
1654 SVfrVarStorageNode
*pNode
;
1656 while (mBufferVarStoreList
!= NULL
) {
1657 pNode
= mBufferVarStoreList
;
1658 mBufferVarStoreList
= mBufferVarStoreList
->mNext
;
1661 while (mEfiVarStoreList
!= NULL
) {
1662 pNode
= mEfiVarStoreList
;
1663 mEfiVarStoreList
= mEfiVarStoreList
->mNext
;
1666 while (mNameVarStoreList
!= NULL
) {
1667 pNode
= mNameVarStoreList
;
1668 mNameVarStoreList
= mNameVarStoreList
->mNext
;
1671 if (mNewVarStorageNode
!= NULL
) {
1672 delete mNewVarStorageNode
;
1677 CVfrDataStorage::GetFreeVarStoreId (
1678 EFI_VFR_VARSTORE_TYPE VarType
1681 UINT32 Index
, Mask
, Offset
;
1684 // Assign the different ID range for the different type VarStore to support Framework Vfr
1687 if ((!VfrCompatibleMode
) || (VarType
== EFI_VFR_VARSTORE_BUFFER
)) {
1689 } else if (VarType
== EFI_VFR_VARSTORE_EFI
) {
1691 } else if (VarType
== EFI_VFR_VARSTORE_NAME
) {
1695 for (; Index
< EFI_FREE_VARSTORE_ID_BITMAP_SIZE
; Index
++) {
1696 if (mFreeVarStoreIdBitMap
[Index
] != 0xFFFFFFFF) {
1701 if (Index
== EFI_FREE_VARSTORE_ID_BITMAP_SIZE
) {
1702 return EFI_VARSTORE_ID_INVALID
;
1705 for (Offset
= 0, Mask
= 0x80000000; Mask
!= 0; Mask
>>= 1, Offset
++) {
1706 if ((mFreeVarStoreIdBitMap
[Index
] & Mask
) == 0) {
1707 mFreeVarStoreIdBitMap
[Index
] |= Mask
;
1708 return (EFI_VARSTORE_ID
)((Index
<< EFI_BITS_SHIFT_PER_UINT32
) + Offset
);
1712 return EFI_VARSTORE_ID_INVALID
;
1716 CVfrDataStorage::ChekVarStoreIdFree (
1717 IN EFI_VARSTORE_ID VarStoreId
1720 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1721 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1723 return (mFreeVarStoreIdBitMap
[Index
] & (0x80000000 >> Offset
)) == 0;
1727 CVfrDataStorage::MarkVarStoreIdUsed (
1728 IN EFI_VARSTORE_ID VarStoreId
1731 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1732 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1734 mFreeVarStoreIdBitMap
[Index
] |= (0x80000000 >> Offset
);
1738 CVfrDataStorage::MarkVarStoreIdUnused (
1739 IN EFI_VARSTORE_ID VarStoreId
1742 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1743 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1745 mFreeVarStoreIdBitMap
[Index
] &= ~(0x80000000 >> Offset
);
1749 CVfrDataStorage::DeclareNameVarStoreBegin (
1750 IN CHAR8
*StoreName
,
1751 IN EFI_VARSTORE_ID VarStoreId
1754 SVfrVarStorageNode
*pNode
= NULL
;
1755 EFI_VARSTORE_ID TmpVarStoreId
;
1757 if (StoreName
== NULL
) {
1758 return VFR_RETURN_FATAL_ERROR
;
1761 if (GetVarStoreId (StoreName
, &TmpVarStoreId
) == VFR_RETURN_SUCCESS
) {
1762 return VFR_RETURN_REDEFINED
;
1765 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
1766 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_NAME
);
1768 if (ChekVarStoreIdFree (VarStoreId
) == FALSE
) {
1769 return VFR_RETURN_VARSTOREID_REDEFINED
;
1771 MarkVarStoreIdUsed (VarStoreId
);
1774 if ((pNode
= new SVfrVarStorageNode (StoreName
, VarStoreId
)) == NULL
) {
1775 return VFR_RETURN_UNDEFINED
;
1778 mNewVarStorageNode
= pNode
;
1780 return VFR_RETURN_SUCCESS
;
1784 CVfrDataStorage::NameTableAddItem (
1785 IN EFI_STRING_ID Item
1788 EFI_VARSTORE_ID
*NewTable
, *OldTable
;
1791 OldTable
= mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
;
1792 TableSize
= mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mTableSize
;
1794 if ((TableSize
!= 0) && ((TableSize
% DEFAULT_NAME_TABLE_ITEMS
) == 0)) {
1795 if ((NewTable
= new EFI_VARSTORE_ID
[TableSize
+ DEFAULT_NAME_TABLE_ITEMS
]) == NULL
) {
1796 return VFR_RETURN_OUT_FOR_RESOURCES
;
1798 memcpy (NewTable
, OldTable
, TableSize
);
1799 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
= NewTable
;
1802 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
[TableSize
++] = Item
;
1803 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mTableSize
= TableSize
;
1805 return VFR_RETURN_SUCCESS
;
1809 CVfrDataStorage::DeclareNameVarStoreEnd (
1813 mNewVarStorageNode
->mGuid
= *Guid
;
1814 mNewVarStorageNode
->mNext
= mNameVarStoreList
;
1815 mNameVarStoreList
= mNewVarStorageNode
;
1817 mNewVarStorageNode
= NULL
;
1819 return VFR_RETURN_SUCCESS
;
1823 CVfrDataStorage::DeclareEfiVarStore (
1824 IN CHAR8
*StoreName
,
1826 IN EFI_STRING_ID NameStrId
,
1831 SVfrVarStorageNode
*pNode
;
1832 EFI_VARSTORE_ID VarStoreId
;
1834 if ((StoreName
== NULL
) || (Guid
== NULL
)) {
1835 return VFR_RETURN_FATAL_ERROR
;
1838 if (VarSize
> sizeof (UINT64
)) {
1839 return VFR_RETURN_EFIVARSTORE_SIZE_ERROR
;
1842 if (GetVarStoreId (StoreName
, &VarStoreId
, Guid
) == VFR_RETURN_SUCCESS
) {
1843 return VFR_RETURN_REDEFINED
;
1846 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_EFI
);
1847 if ((pNode
= new SVfrVarStorageNode (Guid
, StoreName
, VarStoreId
, NameStrId
, VarSize
, Flag
)) == NULL
) {
1848 return VFR_RETURN_OUT_FOR_RESOURCES
;
1851 pNode
->mNext
= mEfiVarStoreList
;
1852 mEfiVarStoreList
= pNode
;
1854 return VFR_RETURN_SUCCESS
;
1858 CVfrDataStorage::DeclareBufferVarStore (
1859 IN CHAR8
*StoreName
,
1861 IN CVfrVarDataTypeDB
*DataTypeDB
,
1863 IN EFI_VARSTORE_ID VarStoreId
,
1864 IN BOOLEAN IsBitVarStore
,
1868 SVfrVarStorageNode
*pNew
= NULL
;
1869 SVfrDataType
*pDataType
= NULL
;
1870 EFI_VARSTORE_ID TempVarStoreId
;
1872 if ((StoreName
== NULL
) || (Guid
== NULL
) || (DataTypeDB
== NULL
)) {
1873 return VFR_RETURN_FATAL_ERROR
;
1876 if (GetVarStoreId (StoreName
, &TempVarStoreId
, Guid
) == VFR_RETURN_SUCCESS
) {
1877 return VFR_RETURN_REDEFINED
;
1880 CHECK_ERROR_RETURN(DataTypeDB
->GetDataType (TypeName
, &pDataType
), VFR_RETURN_SUCCESS
);
1882 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
1883 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_BUFFER
);
1885 if (ChekVarStoreIdFree (VarStoreId
) == FALSE
) {
1886 return VFR_RETURN_VARSTOREID_REDEFINED
;
1888 MarkVarStoreIdUsed (VarStoreId
);
1891 if ((pNew
= new SVfrVarStorageNode (Guid
, StoreName
, VarStoreId
, pDataType
, IsBitVarStore
, Flag
)) == NULL
) {
1892 return VFR_RETURN_OUT_FOR_RESOURCES
;
1895 pNew
->mNext
= mBufferVarStoreList
;
1896 mBufferVarStoreList
= pNew
;
1898 if (gCVfrBufferConfig
.Register(StoreName
, Guid
) != 0) {
1899 return VFR_RETURN_FATAL_ERROR
;
1902 return VFR_RETURN_SUCCESS
;
1906 CVfrDataStorage::GetVarStoreByDataType (
1907 IN CHAR8
*DataTypeName
,
1908 OUT SVfrVarStorageNode
**VarNode
,
1909 IN EFI_GUID
*VarGuid
1912 SVfrVarStorageNode
*pNode
;
1913 SVfrVarStorageNode
*MatchNode
;
1916 // Framework VFR uses Data type name as varstore name, so don't need check again.
1918 if (VfrCompatibleMode
) {
1919 return VFR_RETURN_UNDEFINED
;
1923 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
1924 if (strcmp (pNode
->mStorageInfo
.mDataType
->mTypeName
, DataTypeName
) != 0) {
1928 if ((VarGuid
!= NULL
)) {
1929 if (memcmp (VarGuid
, &pNode
->mGuid
, sizeof (EFI_GUID
)) == 0) {
1931 return VFR_RETURN_SUCCESS
;
1934 if (MatchNode
== NULL
) {
1938 // More than one varstores referred the same data structures.
1940 return VFR_RETURN_VARSTORE_DATATYPE_REDEFINED_ERROR
;
1945 if (MatchNode
== NULL
) {
1946 return VFR_RETURN_UNDEFINED
;
1949 *VarNode
= MatchNode
;
1950 return VFR_RETURN_SUCCESS
;
1954 CVfrDataStorage::CheckGuidField (
1955 IN SVfrVarStorageNode
*pNode
,
1956 IN EFI_GUID
*StoreGuid
,
1957 IN BOOLEAN
*HasFoundOne
,
1958 OUT EFI_VFR_RETURN_CODE
*ReturnCode
1961 if (StoreGuid
!= NULL
) {
1963 // If has guid info, compare the guid filed.
1965 if (memcmp (StoreGuid
, &pNode
->mGuid
, sizeof (EFI_GUID
)) == 0) {
1967 // Both name and guid are same, this this varstore.
1969 mCurrVarStorageNode
= pNode
;
1970 *ReturnCode
= VFR_RETURN_SUCCESS
;
1975 // Not has Guid field, check whether this name is the only one.
1979 // The name has conflict, return name redefined.
1981 *ReturnCode
= VFR_RETURN_VARSTORE_NAME_REDEFINED_ERROR
;
1985 *HasFoundOne
= TRUE
;
1986 mCurrVarStorageNode
= pNode
;
1993 Base on the input store name and guid to find the varstore id.
1995 If both name and guid are inputed, base on the name and guid to
1996 found the varstore. If only name inputed, base on the name to
1997 found the varstore and go on to check whether more than one varstore
1998 has the same name. If only has found one varstore, return this
1999 varstore; if more than one varstore has same name, return varstore
2000 name redefined error. If no varstore found by varstore name, call
2001 function GetVarStoreByDataType and use inputed varstore name as
2002 data type name to search.
2005 CVfrDataStorage::GetVarStoreId (
2006 IN CHAR8
*StoreName
,
2007 OUT EFI_VARSTORE_ID
*VarStoreId
,
2008 IN EFI_GUID
*StoreGuid
2011 EFI_VFR_RETURN_CODE ReturnCode
;
2012 SVfrVarStorageNode
*pNode
;
2013 BOOLEAN HasFoundOne
= FALSE
;
2015 mCurrVarStorageNode
= NULL
;
2017 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2018 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2019 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2020 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2026 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2027 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2028 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2029 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2035 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2036 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2037 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2038 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2045 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2046 return VFR_RETURN_SUCCESS
;
2049 *VarStoreId
= EFI_VARSTORE_ID_INVALID
;
2052 // Assume that Data strucutre name is used as StoreName, and check again.
2054 ReturnCode
= GetVarStoreByDataType (StoreName
, &pNode
, StoreGuid
);
2055 if (pNode
!= NULL
) {
2056 mCurrVarStorageNode
= pNode
;
2057 *VarStoreId
= pNode
->mVarStoreId
;
2064 CVfrDataStorage::GetBufferVarStoreDataTypeName (
2065 IN EFI_VARSTORE_ID VarStoreId
,
2066 OUT CHAR8
**DataTypeName
2069 SVfrVarStorageNode
*pNode
;
2071 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2072 return VFR_RETURN_FATAL_ERROR
;
2075 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2076 if (pNode
->mVarStoreId
== VarStoreId
) {
2077 *DataTypeName
= pNode
->mStorageInfo
.mDataType
->mTypeName
;
2078 return VFR_RETURN_SUCCESS
;
2082 return VFR_RETURN_UNDEFINED
;
2085 EFI_VFR_VARSTORE_TYPE
2086 CVfrDataStorage::GetVarStoreType (
2087 IN EFI_VARSTORE_ID VarStoreId
2090 SVfrVarStorageNode
*pNode
;
2091 EFI_VFR_VARSTORE_TYPE VarStoreType
;
2093 VarStoreType
= EFI_VFR_VARSTORE_INVALID
;
2095 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2096 return VarStoreType
;
2099 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2100 if (pNode
->mVarStoreId
== VarStoreId
) {
2101 VarStoreType
= pNode
->mVarStoreType
;
2102 return VarStoreType
;
2106 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2107 if (pNode
->mVarStoreId
== VarStoreId
) {
2108 VarStoreType
= pNode
->mVarStoreType
;
2109 return VarStoreType
;
2113 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2114 if (pNode
->mVarStoreId
== VarStoreId
) {
2115 VarStoreType
= pNode
->mVarStoreType
;
2116 return VarStoreType
;
2120 return VarStoreType
;
2124 CVfrDataStorage::GetVarStoreGuid (
2125 IN EFI_VARSTORE_ID VarStoreId
2128 SVfrVarStorageNode
*pNode
;
2133 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2137 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2138 if (pNode
->mVarStoreId
== VarStoreId
) {
2139 VarGuid
= &pNode
->mGuid
;
2144 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2145 if (pNode
->mVarStoreId
== VarStoreId
) {
2146 VarGuid
= &pNode
->mGuid
;
2151 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2152 if (pNode
->mVarStoreId
== VarStoreId
) {
2153 VarGuid
= &pNode
->mGuid
;
2162 CVfrDataStorage::GetVarStoreName (
2163 IN EFI_VARSTORE_ID VarStoreId
,
2164 OUT CHAR8
**VarStoreName
2167 SVfrVarStorageNode
*pNode
;
2169 if (VarStoreName
== NULL
) {
2170 return VFR_RETURN_FATAL_ERROR
;
2173 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2174 if (pNode
->mVarStoreId
== VarStoreId
) {
2175 *VarStoreName
= pNode
->mVarStoreName
;
2176 return VFR_RETURN_SUCCESS
;
2180 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2181 if (pNode
->mVarStoreId
== VarStoreId
) {
2182 *VarStoreName
= pNode
->mVarStoreName
;
2183 return VFR_RETURN_SUCCESS
;
2187 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2188 if (pNode
->mVarStoreId
== VarStoreId
) {
2189 *VarStoreName
= pNode
->mVarStoreName
;
2190 return VFR_RETURN_SUCCESS
;
2194 *VarStoreName
= NULL
;
2195 return VFR_RETURN_UNDEFINED
;
2199 CVfrDataStorage::GetEfiVarStoreInfo (
2200 IN OUT EFI_VARSTORE_INFO
*Info
2204 return VFR_RETURN_FATAL_ERROR
;
2207 if (mCurrVarStorageNode
== NULL
) {
2208 return VFR_RETURN_GET_EFIVARSTORE_ERROR
;
2211 Info
->mInfo
.mVarName
= mCurrVarStorageNode
->mStorageInfo
.mEfiVar
.mEfiVarName
;
2212 Info
->mVarTotalSize
= mCurrVarStorageNode
->mStorageInfo
.mEfiVar
.mEfiVarSize
;
2213 switch (Info
->mVarTotalSize
) {
2215 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_8
;
2218 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_16
;
2221 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_32
;
2224 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_64
;
2227 return VFR_RETURN_FATAL_ERROR
;
2230 return VFR_RETURN_SUCCESS
;
2234 CVfrDataStorage::AddBufferVarStoreFieldInfo (
2235 IN EFI_VARSTORE_INFO
*Info
2238 BufferVarStoreFieldInfoNode
*pNew
;
2240 if ((pNew
= new BufferVarStoreFieldInfoNode(Info
)) == NULL
) {
2241 return VFR_RETURN_FATAL_ERROR
;
2244 if (mBufferFieldInfoListHead
== NULL
) {
2245 mBufferFieldInfoListHead
= pNew
;
2246 mBufferFieldInfoListTail
= pNew
;
2248 mBufferFieldInfoListTail
->mNext
= pNew
;
2249 mBufferFieldInfoListTail
= pNew
;
2252 return VFR_RETURN_SUCCESS
;
2256 CVfrDataStorage::GetBufferVarStoreFieldInfo (
2257 IN OUT EFI_VARSTORE_INFO
*Info
2260 BufferVarStoreFieldInfoNode
*pNode
;
2262 pNode
= mBufferFieldInfoListHead
;
2263 while (pNode
!= NULL
) {
2264 if (Info
->mVarStoreId
== pNode
->mVarStoreInfo
.mVarStoreId
&&
2265 Info
->mInfo
.mVarOffset
== pNode
->mVarStoreInfo
.mInfo
.mVarOffset
) {
2266 Info
->mVarTotalSize
= pNode
->mVarStoreInfo
.mVarTotalSize
;
2267 Info
->mVarType
= pNode
->mVarStoreInfo
.mVarType
;
2268 return VFR_RETURN_SUCCESS
;
2270 pNode
= pNode
->mNext
;
2272 return VFR_RETURN_FATAL_ERROR
;
2276 CVfrDataStorage::GetNameVarStoreInfo (
2277 OUT EFI_VARSTORE_INFO
*Info
,
2282 return VFR_RETURN_FATAL_ERROR
;
2285 if (mCurrVarStorageNode
== NULL
) {
2286 return VFR_RETURN_GET_NVVARSTORE_ERROR
;
2290 // Framework Vfr file Index is from 1, but Uefi Vfr file Index is from 0.
2292 if (VfrCompatibleMode
) {
2294 return VFR_RETURN_ERROR_ARRARY_NUM
;
2299 Info
->mInfo
.mVarName
= mCurrVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
[Index
];
2301 return VFR_RETURN_SUCCESS
;
2304 SVfrDefaultStoreNode::SVfrDefaultStoreNode (
2305 IN EFI_IFR_DEFAULTSTORE
*ObjBinAddr
,
2307 IN EFI_STRING_ID DefaultStoreNameId
,
2311 mObjBinAddr
= ObjBinAddr
;
2313 if (RefName
!= NULL
) {
2314 mRefName
= new CHAR8
[strlen (RefName
) + 1];
2315 strcpy (mRefName
, RefName
);
2321 mDefaultId
= DefaultId
;
2322 mDefaultStoreNameId
= DefaultStoreNameId
;
2325 SVfrDefaultStoreNode::~SVfrDefaultStoreNode (
2329 if (mRefName
!= NULL
) {
2334 CVfrDefaultStore::CVfrDefaultStore (
2338 mDefaultStoreList
= NULL
;
2341 CVfrDefaultStore::~CVfrDefaultStore (
2345 SVfrDefaultStoreNode
*pTmp
= NULL
;
2347 while (mDefaultStoreList
!= NULL
) {
2348 pTmp
= mDefaultStoreList
;
2349 mDefaultStoreList
= mDefaultStoreList
->mNext
;
2355 CVfrDefaultStore::RegisterDefaultStore (
2356 IN CHAR8
*ObjBinAddr
,
2358 IN EFI_STRING_ID DefaultStoreNameId
,
2362 SVfrDefaultStoreNode
*pNode
= NULL
;
2364 if (RefName
== NULL
) {
2365 return VFR_RETURN_FATAL_ERROR
;
2368 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2369 if (strcmp (pNode
->mRefName
, RefName
) == 0) {
2370 return VFR_RETURN_REDEFINED
;
2374 if ((pNode
= new SVfrDefaultStoreNode ((EFI_IFR_DEFAULTSTORE
*)ObjBinAddr
, RefName
, DefaultStoreNameId
, DefaultId
)) == NULL
) {
2375 return VFR_RETURN_OUT_FOR_RESOURCES
;
2378 pNode
->mNext
= mDefaultStoreList
;
2379 mDefaultStoreList
= pNode
;
2381 return VFR_RETURN_SUCCESS
;
2385 * assign new reference name or new default store name id only if
2386 * the original is invalid
2389 CVfrDefaultStore::ReRegisterDefaultStoreById (
2390 IN UINT16 DefaultId
,
2392 IN EFI_STRING_ID DefaultStoreNameId
2395 SVfrDefaultStoreNode
*pNode
= NULL
;
2397 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2398 if (pNode
->mDefaultId
== DefaultId
) {
2403 if (pNode
== NULL
) {
2404 return VFR_RETURN_UNDEFINED
;
2406 if (pNode
->mDefaultStoreNameId
== EFI_STRING_ID_INVALID
) {
2407 pNode
->mDefaultStoreNameId
= DefaultStoreNameId
;
2408 if (pNode
->mObjBinAddr
!= NULL
) {
2409 pNode
->mObjBinAddr
->DefaultName
= DefaultStoreNameId
;
2412 return VFR_RETURN_REDEFINED
;
2415 if (RefName
!= NULL
) {
2416 delete pNode
->mRefName
;
2417 pNode
->mRefName
= new CHAR8
[strlen (RefName
) + 1];
2418 if (pNode
->mRefName
!= NULL
) {
2419 strcpy (pNode
->mRefName
, RefName
);
2424 return VFR_RETURN_SUCCESS
;
2428 CVfrDefaultStore::DefaultIdRegistered (
2432 SVfrDefaultStoreNode
*pNode
= NULL
;
2434 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2435 if (pNode
->mDefaultId
== DefaultId
) {
2444 CVfrDefaultStore::GetDefaultId (
2446 OUT UINT16
*DefaultId
2449 SVfrDefaultStoreNode
*pTmp
= NULL
;
2451 if (DefaultId
== NULL
) {
2452 return VFR_RETURN_FATAL_ERROR
;
2455 for (pTmp
= mDefaultStoreList
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
2456 if (strcmp (pTmp
->mRefName
, RefName
) == 0) {
2457 *DefaultId
= pTmp
->mDefaultId
;
2458 return VFR_RETURN_SUCCESS
;
2462 return VFR_RETURN_UNDEFINED
;
2466 CVfrDefaultStore::BufferVarStoreAltConfigAdd (
2467 IN EFI_VARSTORE_ID DefaultId
,
2468 IN EFI_VARSTORE_INFO
&Info
,
2469 IN CHAR8
*VarStoreName
,
2470 IN EFI_GUID
*VarStoreGuid
,
2472 IN EFI_IFR_TYPE_VALUE Value
2475 SVfrDefaultStoreNode
*pNode
= NULL
;
2476 CHAR8 NewAltCfg
[2 * 2 * sizeof (UINT16
) + 1] = {0,};
2477 INTN Returnvalue
= 0;
2479 if (VarStoreName
== NULL
) {
2480 return VFR_RETURN_FATAL_ERROR
;
2483 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2484 if (pNode
->mDefaultId
== DefaultId
) {
2489 if (pNode
== NULL
) {
2490 return VFR_RETURN_UNDEFINED
;
2493 gCVfrBufferConfig
.Open ();
2495 sprintf (NewAltCfg
, "%04x", pNode
->mDefaultId
);
2496 if ((Returnvalue
= gCVfrBufferConfig
.Select(VarStoreName
, VarStoreGuid
)) == 0) {
2497 if ((Returnvalue
= gCVfrBufferConfig
.Write ('a', VarStoreName
, VarStoreGuid
, NewAltCfg
, Type
, Info
.mInfo
.mVarOffset
, Info
.mVarTotalSize
, Value
)) != 0) {
2502 gCVfrBufferConfig
.Close ();
2504 return VFR_RETURN_SUCCESS
;
2507 gCVfrBufferConfig
.Close ();
2508 return (EFI_VFR_RETURN_CODE
)Returnvalue
;
2511 SVfrRuleNode::SVfrRuleNode (
2516 if (RuleName
!= NULL
) {
2517 mRuleName
= new CHAR8
[strlen (RuleName
) + 1];
2518 strcpy (mRuleName
, RuleName
);
2527 SVfrRuleNode::~SVfrRuleNode (
2531 if (mRuleName
!= NULL
) {
2536 CVfrRulesDB::CVfrRulesDB ()
2539 mFreeRuleId
= EFI_VARSTORE_ID_START
;
2542 CVfrRulesDB::~CVfrRulesDB ()
2544 SVfrRuleNode
*pNode
;
2546 while(mRuleList
!= NULL
) {
2548 mRuleList
= mRuleList
->mNext
;
2554 CVfrRulesDB::RegisterRule (
2560 if (RuleName
== NULL
) {
2564 if ((pNew
= new SVfrRuleNode (RuleName
, mFreeRuleId
)) == NULL
) {
2570 pNew
->mNext
= mRuleList
;
2575 CVfrRulesDB::GetRuleId (
2579 SVfrRuleNode
*pNode
;
2581 if (RuleName
== NULL
) {
2582 return EFI_RULE_ID_INVALID
;
2585 for (pNode
= mRuleList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2586 if (strcmp (pNode
->mRuleName
, RuleName
) == 0) {
2587 return pNode
->mRuleId
;
2591 return EFI_RULE_ID_INVALID
;
2594 CVfrRulesDB gCVfrRulesDB
;
2596 EFI_VARSTORE_INFO::EFI_VARSTORE_INFO (
2600 mVarStoreId
= EFI_VARSTORE_ID_INVALID
;
2601 mInfo
.mVarName
= EFI_STRING_ID_INVALID
;
2602 mInfo
.mVarOffset
= EFI_VAROFFSET_INVALID
;
2603 mVarType
= EFI_IFR_TYPE_OTHER
;
2608 EFI_VARSTORE_INFO::EFI_VARSTORE_INFO (
2609 IN EFI_VARSTORE_INFO
&Info
2612 mVarStoreId
= Info
.mVarStoreId
;
2613 mInfo
.mVarName
= Info
.mInfo
.mVarName
;
2614 mInfo
.mVarOffset
= Info
.mInfo
.mVarOffset
;
2615 mVarType
= Info
.mVarType
;
2616 mVarTotalSize
= Info
.mVarTotalSize
;
2617 mIsBitVar
= Info
.mIsBitVar
;
2621 EFI_VARSTORE_INFO::operator= (
2622 IN CONST EFI_VARSTORE_INFO
&Info
2625 if (this != &Info
) {
2626 mVarStoreId
= Info
.mVarStoreId
;
2627 mInfo
.mVarName
= Info
.mInfo
.mVarName
;
2628 mInfo
.mVarOffset
= Info
.mInfo
.mVarOffset
;
2629 mVarType
= Info
.mVarType
;
2630 mVarTotalSize
= Info
.mVarTotalSize
;
2631 mIsBitVar
= Info
.mIsBitVar
;
2638 EFI_VARSTORE_INFO::operator == (
2639 IN EFI_VARSTORE_INFO
*Info
2642 if ((mVarStoreId
== Info
->mVarStoreId
) &&
2643 (mInfo
.mVarName
== Info
->mInfo
.mVarName
) &&
2644 (mInfo
.mVarOffset
== Info
->mInfo
.mVarOffset
) &&
2645 (mVarType
== Info
->mVarType
) &&
2646 (mVarTotalSize
== Info
->mVarTotalSize
) &&
2647 (mIsBitVar
== Info
->mIsBitVar
)) {
2654 BufferVarStoreFieldInfoNode::BufferVarStoreFieldInfoNode(
2655 IN EFI_VARSTORE_INFO
*Info
2658 mVarStoreInfo
.mVarType
= Info
->mVarType
;
2659 mVarStoreInfo
.mVarTotalSize
= Info
->mVarTotalSize
;
2660 mVarStoreInfo
.mInfo
.mVarOffset
= Info
->mInfo
.mVarOffset
;
2661 mVarStoreInfo
.mVarStoreId
= Info
->mVarStoreId
;
2665 BufferVarStoreFieldInfoNode::~BufferVarStoreFieldInfoNode ()
2667 mVarStoreInfo
.mVarType
= EFI_IFR_TYPE_OTHER
;
2668 mVarStoreInfo
.mVarTotalSize
= 0;
2669 mVarStoreInfo
.mInfo
.mVarOffset
= EFI_VAROFFSET_INVALID
;
2670 mVarStoreInfo
.mVarStoreId
= EFI_VARSTORE_ID_INVALID
;
2674 static EFI_VARSTORE_INFO gEfiInvalidVarStoreInfo
;
2677 CVfrQuestionDB::GetFreeQuestionId (
2681 UINT32 Index
, Mask
, Offset
;
2683 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2684 if (mFreeQIdBitMap
[Index
] != 0xFFFFFFFF) {
2689 if (Index
== EFI_FREE_QUESTION_ID_BITMAP_SIZE
) {
2690 return EFI_QUESTION_ID_INVALID
;
2693 for (Offset
= 0, Mask
= 0x80000000; Mask
!= 0; Mask
>>= 1, Offset
++) {
2694 if ((mFreeQIdBitMap
[Index
] & Mask
) == 0) {
2695 mFreeQIdBitMap
[Index
] |= Mask
;
2696 return (EFI_QUESTION_ID
)((Index
<< EFI_BITS_SHIFT_PER_UINT32
) + Offset
);
2700 return EFI_QUESTION_ID_INVALID
;
2704 CVfrQuestionDB::ChekQuestionIdFree (
2705 IN EFI_QUESTION_ID QId
2708 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2709 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2711 return (mFreeQIdBitMap
[Index
] & (0x80000000 >> Offset
)) == 0;
2715 CVfrQuestionDB::MarkQuestionIdUsed (
2716 IN EFI_QUESTION_ID QId
2719 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2720 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2722 mFreeQIdBitMap
[Index
] |= (0x80000000 >> Offset
);
2726 CVfrQuestionDB::MarkQuestionIdUnused (
2727 IN EFI_QUESTION_ID QId
2730 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2731 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2733 mFreeQIdBitMap
[Index
] &= ~(0x80000000 >> Offset
);
2736 SVfrQuestionNode::SVfrQuestionNode (
2744 mQuestionId
= EFI_QUESTION_ID_INVALID
;
2747 mQtype
= QUESTION_NORMAL
;
2750 mName
= new CHAR8
[strlen ("$DEFAULT") + 1];
2751 strcpy (mName
, "$DEFAULT");
2753 mName
= new CHAR8
[strlen (Name
) + 1];
2754 strcpy (mName
, Name
);
2757 if (VarIdStr
!= NULL
) {
2758 mVarIdStr
= new CHAR8
[strlen (VarIdStr
) + 1];
2759 strcpy (mVarIdStr
, VarIdStr
);
2761 mVarIdStr
= new CHAR8
[strlen ("$") + 1];
2762 strcpy (mVarIdStr
, "$");
2766 SVfrQuestionNode::~SVfrQuestionNode (
2770 if (mName
!= NULL
) {
2774 if (mVarIdStr
!= NULL
) {
2779 CVfrQuestionDB::CVfrQuestionDB ()
2783 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2784 mFreeQIdBitMap
[Index
] = 0;
2787 // Question ID 0 is reserved.
2788 mFreeQIdBitMap
[0] = 0x80000000;
2789 mQuestionList
= NULL
;
2792 CVfrQuestionDB::~CVfrQuestionDB ()
2794 SVfrQuestionNode
*pNode
;
2796 while (mQuestionList
!= NULL
) {
2797 pNode
= mQuestionList
;
2798 mQuestionList
= mQuestionList
->mNext
;
2804 // Reset to init state
2807 CVfrQuestionDB::ResetInit(
2812 SVfrQuestionNode
*pNode
;
2814 while (mQuestionList
!= NULL
) {
2815 pNode
= mQuestionList
;
2816 mQuestionList
= mQuestionList
->mNext
;
2820 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2821 mFreeQIdBitMap
[Index
] = 0;
2824 // Question ID 0 is reserved.
2825 mFreeQIdBitMap
[0] = 0x80000000;
2826 mQuestionList
= NULL
;
2830 CVfrQuestionDB::PrintAllQuestion (
2834 SVfrQuestionNode
*pNode
= NULL
;
2836 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2837 printf ("Question VarId is %s and QuesitonId is 0x%x\n", pNode
->mVarIdStr
, pNode
->mQuestionId
);
2842 CVfrQuestionDB::RegisterQuestion (
2845 IN OUT EFI_QUESTION_ID
&QuestionId
2848 SVfrQuestionNode
*pNode
= NULL
;
2850 if ((Name
!= NULL
) && (FindQuestion(Name
) == VFR_RETURN_SUCCESS
)) {
2851 return VFR_RETURN_REDEFINED
;
2854 if ((pNode
= new SVfrQuestionNode (Name
, VarIdStr
)) == NULL
) {
2855 return VFR_RETURN_OUT_FOR_RESOURCES
;
2858 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2859 QuestionId
= GetFreeQuestionId ();
2862 // For Framework Vfr, don't check question ID conflict.
2864 if (!VfrCompatibleMode
&& ChekQuestionIdFree (QuestionId
) == FALSE
) {
2866 return VFR_RETURN_QUESTIONID_REDEFINED
;
2868 MarkQuestionIdUsed (QuestionId
);
2870 pNode
->mQuestionId
= QuestionId
;
2872 pNode
->mNext
= mQuestionList
;
2873 mQuestionList
= pNode
;
2875 gCFormPkg
.DoPendingAssign (VarIdStr
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2877 return VFR_RETURN_SUCCESS
;
2881 CVfrQuestionDB::RegisterOldDateQuestion (
2882 IN CHAR8
*YearVarId
,
2883 IN CHAR8
*MonthVarId
,
2885 IN OUT EFI_QUESTION_ID
&QuestionId
2888 SVfrQuestionNode
*pNode
[3] = {NULL
, };
2891 if ((YearVarId
== NULL
) || (MonthVarId
== NULL
) || (DayVarId
== NULL
)) {
2895 if ((pNode
[0] = new SVfrQuestionNode (NULL
, YearVarId
, DATE_YEAR_BITMASK
)) == NULL
) {
2898 if ((pNode
[1] = new SVfrQuestionNode (NULL
, MonthVarId
, DATE_MONTH_BITMASK
)) == NULL
) {
2901 if ((pNode
[2] = new SVfrQuestionNode (NULL
, DayVarId
, DATE_DAY_BITMASK
)) == NULL
) {
2905 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2906 QuestionId
= GetFreeQuestionId ();
2908 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
2911 MarkQuestionIdUsed (QuestionId
);
2914 pNode
[0]->mQuestionId
= QuestionId
;
2915 pNode
[1]->mQuestionId
= QuestionId
;
2916 pNode
[2]->mQuestionId
= QuestionId
;
2917 pNode
[0]->mQtype
= QUESTION_DATE
;
2918 pNode
[1]->mQtype
= QUESTION_DATE
;
2919 pNode
[2]->mQtype
= QUESTION_DATE
;
2920 pNode
[0]->mNext
= pNode
[1];
2921 pNode
[1]->mNext
= pNode
[2];
2922 pNode
[2]->mNext
= mQuestionList
;
2923 mQuestionList
= pNode
[0];
2925 gCFormPkg
.DoPendingAssign (YearVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2926 gCFormPkg
.DoPendingAssign (MonthVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2927 gCFormPkg
.DoPendingAssign (DayVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2932 for (Index
= 0; Index
< 3; Index
++) {
2933 if (pNode
[Index
] != NULL
) {
2934 delete pNode
[Index
];
2937 QuestionId
= EFI_QUESTION_ID_INVALID
;
2941 CVfrQuestionDB::RegisterNewDateQuestion (
2943 IN CHAR8
*BaseVarId
,
2944 IN OUT EFI_QUESTION_ID
&QuestionId
2947 SVfrQuestionNode
*pNode
[3] = {NULL
, };
2949 CHAR8
*VarIdStr
[3] = {NULL
, };
2952 if (BaseVarId
== NULL
&& Name
== NULL
) {
2953 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2954 QuestionId
= GetFreeQuestionId ();
2956 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
2959 MarkQuestionIdUsed (QuestionId
);
2964 if (BaseVarId
!= NULL
) {
2965 Len
= strlen (BaseVarId
);
2967 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Year") + 1];
2968 if (VarIdStr
[0] != NULL
) {
2969 strcpy (VarIdStr
[0], BaseVarId
);
2970 strcat (VarIdStr
[0], ".Year");
2972 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Month") + 1];
2973 if (VarIdStr
[1] != NULL
) {
2974 strcpy (VarIdStr
[1], BaseVarId
);
2975 strcat (VarIdStr
[1], ".Month");
2977 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Day") + 1];
2978 if (VarIdStr
[2] != NULL
) {
2979 strcpy (VarIdStr
[2], BaseVarId
);
2980 strcat (VarIdStr
[2], ".Day");
2983 Len
= strlen (Name
);
2985 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Year") + 1];
2986 if (VarIdStr
[0] != NULL
) {
2987 strcpy (VarIdStr
[0], Name
);
2988 strcat (VarIdStr
[0], ".Year");
2990 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Month") + 1];
2991 if (VarIdStr
[1] != NULL
) {
2992 strcpy (VarIdStr
[1], Name
);
2993 strcat (VarIdStr
[1], ".Month");
2995 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Day") + 1];
2996 if (VarIdStr
[2] != NULL
) {
2997 strcpy (VarIdStr
[2], Name
);
2998 strcat (VarIdStr
[2], ".Day");
3002 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0], DATE_YEAR_BITMASK
)) == NULL
) {
3005 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1], DATE_MONTH_BITMASK
)) == NULL
) {
3008 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2], DATE_DAY_BITMASK
)) == NULL
) {
3012 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3013 QuestionId
= GetFreeQuestionId ();
3015 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3018 MarkQuestionIdUsed (QuestionId
);
3021 pNode
[0]->mQuestionId
= QuestionId
;
3022 pNode
[1]->mQuestionId
= QuestionId
;
3023 pNode
[2]->mQuestionId
= QuestionId
;
3024 pNode
[0]->mQtype
= QUESTION_DATE
;
3025 pNode
[1]->mQtype
= QUESTION_DATE
;
3026 pNode
[2]->mQtype
= QUESTION_DATE
;
3027 pNode
[0]->mNext
= pNode
[1];
3028 pNode
[1]->mNext
= pNode
[2];
3029 pNode
[2]->mNext
= mQuestionList
;
3030 mQuestionList
= pNode
[0];
3032 for (Index
= 0; Index
< 3; Index
++) {
3033 if (VarIdStr
[Index
] != NULL
) {
3034 delete VarIdStr
[Index
];
3038 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3039 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3040 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3045 for (Index
= 0; Index
< 3; Index
++) {
3046 if (pNode
[Index
] != NULL
) {
3047 delete pNode
[Index
];
3050 if (VarIdStr
[Index
] != NULL
) {
3051 delete VarIdStr
[Index
];
3057 CVfrQuestionDB::RegisterOldTimeQuestion (
3058 IN CHAR8
*HourVarId
,
3059 IN CHAR8
*MinuteVarId
,
3060 IN CHAR8
*SecondVarId
,
3061 IN OUT EFI_QUESTION_ID
&QuestionId
3064 SVfrQuestionNode
*pNode
[3] = {NULL
, };
3067 if ((HourVarId
== NULL
) || (MinuteVarId
== NULL
) || (SecondVarId
== NULL
)) {
3071 if ((pNode
[0] = new SVfrQuestionNode (NULL
, HourVarId
, TIME_HOUR_BITMASK
)) == NULL
) {
3074 if ((pNode
[1] = new SVfrQuestionNode (NULL
, MinuteVarId
, TIME_MINUTE_BITMASK
)) == NULL
) {
3077 if ((pNode
[2] = new SVfrQuestionNode (NULL
, SecondVarId
, TIME_SECOND_BITMASK
)) == NULL
) {
3081 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3082 QuestionId
= GetFreeQuestionId ();
3084 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3087 MarkQuestionIdUsed (QuestionId
);
3090 pNode
[0]->mQuestionId
= QuestionId
;
3091 pNode
[1]->mQuestionId
= QuestionId
;
3092 pNode
[2]->mQuestionId
= QuestionId
;
3093 pNode
[0]->mQtype
= QUESTION_TIME
;
3094 pNode
[1]->mQtype
= QUESTION_TIME
;
3095 pNode
[2]->mQtype
= QUESTION_TIME
;
3096 pNode
[0]->mNext
= pNode
[1];
3097 pNode
[1]->mNext
= pNode
[2];
3098 pNode
[2]->mNext
= mQuestionList
;
3099 mQuestionList
= pNode
[0];
3101 gCFormPkg
.DoPendingAssign (HourVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3102 gCFormPkg
.DoPendingAssign (MinuteVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3103 gCFormPkg
.DoPendingAssign (SecondVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3108 for (Index
= 0; Index
< 3; Index
++) {
3109 if (pNode
[Index
] != NULL
) {
3110 delete pNode
[Index
];
3113 QuestionId
= EFI_QUESTION_ID_INVALID
;
3117 CVfrQuestionDB::RegisterNewTimeQuestion (
3119 IN CHAR8
*BaseVarId
,
3120 IN OUT EFI_QUESTION_ID
&QuestionId
3123 SVfrQuestionNode
*pNode
[3] = {NULL
, };
3125 CHAR8
*VarIdStr
[3] = {NULL
, };
3128 if (BaseVarId
== NULL
&& Name
== NULL
) {
3129 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3130 QuestionId
= GetFreeQuestionId ();
3132 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3135 MarkQuestionIdUsed (QuestionId
);
3140 if (BaseVarId
!= NULL
) {
3141 Len
= strlen (BaseVarId
);
3143 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Hour") + 1];
3144 if (VarIdStr
[0] != NULL
) {
3145 strcpy (VarIdStr
[0], BaseVarId
);
3146 strcat (VarIdStr
[0], ".Hour");
3148 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Minute") + 1];
3149 if (VarIdStr
[1] != NULL
) {
3150 strcpy (VarIdStr
[1], BaseVarId
);
3151 strcat (VarIdStr
[1], ".Minute");
3153 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Second") + 1];
3154 if (VarIdStr
[2] != NULL
) {
3155 strcpy (VarIdStr
[2], BaseVarId
);
3156 strcat (VarIdStr
[2], ".Second");
3159 Len
= strlen (Name
);
3161 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Hour") + 1];
3162 if (VarIdStr
[0] != NULL
) {
3163 strcpy (VarIdStr
[0], Name
);
3164 strcat (VarIdStr
[0], ".Hour");
3166 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Minute") + 1];
3167 if (VarIdStr
[1] != NULL
) {
3168 strcpy (VarIdStr
[1], Name
);
3169 strcat (VarIdStr
[1], ".Minute");
3171 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Second") + 1];
3172 if (VarIdStr
[2] != NULL
) {
3173 strcpy (VarIdStr
[2], Name
);
3174 strcat (VarIdStr
[2], ".Second");
3178 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0], TIME_HOUR_BITMASK
)) == NULL
) {
3181 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1], TIME_MINUTE_BITMASK
)) == NULL
) {
3184 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2], TIME_SECOND_BITMASK
)) == NULL
) {
3188 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3189 QuestionId
= GetFreeQuestionId ();
3191 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3194 MarkQuestionIdUsed (QuestionId
);
3197 pNode
[0]->mQuestionId
= QuestionId
;
3198 pNode
[1]->mQuestionId
= QuestionId
;
3199 pNode
[2]->mQuestionId
= QuestionId
;
3200 pNode
[0]->mQtype
= QUESTION_TIME
;
3201 pNode
[1]->mQtype
= QUESTION_TIME
;
3202 pNode
[2]->mQtype
= QUESTION_TIME
;
3203 pNode
[0]->mNext
= pNode
[1];
3204 pNode
[1]->mNext
= pNode
[2];
3205 pNode
[2]->mNext
= mQuestionList
;
3206 mQuestionList
= pNode
[0];
3208 for (Index
= 0; Index
< 3; Index
++) {
3209 if (VarIdStr
[Index
] != NULL
) {
3210 delete VarIdStr
[Index
];
3214 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3215 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3216 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3221 for (Index
= 0; Index
< 3; Index
++) {
3222 if (pNode
[Index
] != NULL
) {
3223 delete pNode
[Index
];
3226 if (VarIdStr
[Index
] != NULL
) {
3227 delete VarIdStr
[Index
];
3233 CVfrQuestionDB::RegisterRefQuestion (
3235 IN CHAR8
*BaseVarId
,
3236 IN OUT EFI_QUESTION_ID
&QuestionId
3239 SVfrQuestionNode
*pNode
[4] = {NULL
, };
3241 CHAR8
*VarIdStr
[4] = {NULL
, };
3244 if (BaseVarId
== NULL
&& Name
== NULL
) {
3248 if (BaseVarId
!= NULL
) {
3249 Len
= strlen (BaseVarId
);
3251 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".QuestionId") + 1];
3252 if (VarIdStr
[0] != NULL
) {
3253 strcpy (VarIdStr
[0], BaseVarId
);
3254 strcat (VarIdStr
[0], ".QuestionId");
3256 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".FormId") + 1];
3257 if (VarIdStr
[1] != NULL
) {
3258 strcpy (VarIdStr
[1], BaseVarId
);
3259 strcat (VarIdStr
[1], ".FormId");
3261 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".FormSetGuid") + 1];
3262 if (VarIdStr
[2] != NULL
) {
3263 strcpy (VarIdStr
[2], BaseVarId
);
3264 strcat (VarIdStr
[2], ".FormSetGuid");
3266 VarIdStr
[3] = new CHAR8
[Len
+ strlen (".DevicePath") + 1];
3267 if (VarIdStr
[3] != NULL
) {
3268 strcpy (VarIdStr
[3], BaseVarId
);
3269 strcat (VarIdStr
[3], ".DevicePath");
3272 Len
= strlen (Name
);
3274 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".QuestionId") + 1];
3275 if (VarIdStr
[0] != NULL
) {
3276 strcpy (VarIdStr
[0], Name
);
3277 strcat (VarIdStr
[0], ".QuestionId");
3279 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".FormId") + 1];
3280 if (VarIdStr
[1] != NULL
) {
3281 strcpy (VarIdStr
[1], Name
);
3282 strcat (VarIdStr
[1], ".FormId");
3284 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".FormSetGuid") + 1];
3285 if (VarIdStr
[2] != NULL
) {
3286 strcpy (VarIdStr
[2], Name
);
3287 strcat (VarIdStr
[2], ".FormSetGuid");
3289 VarIdStr
[3] = new CHAR8
[Len
+ strlen (".DevicePath") + 1];
3290 if (VarIdStr
[3] != NULL
) {
3291 strcpy (VarIdStr
[3], Name
);
3292 strcat (VarIdStr
[3], ".DevicePath");
3296 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0])) == NULL
) {
3299 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1])) == NULL
) {
3302 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2])) == NULL
) {
3305 if ((pNode
[3] = new SVfrQuestionNode (Name
, VarIdStr
[3])) == NULL
) {
3309 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3310 QuestionId
= GetFreeQuestionId ();
3312 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3315 MarkQuestionIdUsed (QuestionId
);
3318 pNode
[0]->mQuestionId
= QuestionId
;
3319 pNode
[1]->mQuestionId
= QuestionId
;
3320 pNode
[2]->mQuestionId
= QuestionId
;
3321 pNode
[3]->mQuestionId
= QuestionId
;
3322 pNode
[0]->mQtype
= QUESTION_REF
;
3323 pNode
[1]->mQtype
= QUESTION_REF
;
3324 pNode
[2]->mQtype
= QUESTION_REF
;
3325 pNode
[3]->mQtype
= QUESTION_REF
;
3326 pNode
[0]->mNext
= pNode
[1];
3327 pNode
[1]->mNext
= pNode
[2];
3328 pNode
[2]->mNext
= pNode
[3];
3329 pNode
[3]->mNext
= mQuestionList
;
3330 mQuestionList
= pNode
[0];
3332 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3333 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3334 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3335 gCFormPkg
.DoPendingAssign (VarIdStr
[3], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3340 for (Index
= 0; Index
< 4; Index
++) {
3341 if (pNode
[Index
] != NULL
) {
3342 delete pNode
[Index
];
3345 if (VarIdStr
[Index
] != NULL
) {
3346 delete VarIdStr
[Index
];
3352 CVfrQuestionDB::UpdateQuestionId (
3353 IN EFI_QUESTION_ID QId
,
3354 IN EFI_QUESTION_ID NewQId
3357 SVfrQuestionNode
*pNode
= NULL
;
3359 if (QId
== NewQId
) {
3361 return VFR_RETURN_SUCCESS
;
3365 // For Framework Vfr, don't check question ID conflict.
3367 if (!VfrCompatibleMode
&& ChekQuestionIdFree (NewQId
) == FALSE
) {
3368 return VFR_RETURN_REDEFINED
;
3371 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3372 if (pNode
->mQuestionId
== QId
) {
3377 if (pNode
== NULL
) {
3378 return VFR_RETURN_UNDEFINED
;
3381 MarkQuestionIdUnused (QId
);
3382 pNode
->mQuestionId
= NewQId
;
3383 MarkQuestionIdUsed (NewQId
);
3385 gCFormPkg
.DoPendingAssign (pNode
->mVarIdStr
, (VOID
*)&NewQId
, sizeof(EFI_QUESTION_ID
));
3387 return VFR_RETURN_SUCCESS
;
3391 CVfrQuestionDB::GetQuestionId (
3394 OUT EFI_QUESTION_ID
&QuestionId
,
3395 OUT UINT32
&BitMask
,
3396 OUT EFI_QUESION_TYPE
*QType
3399 SVfrQuestionNode
*pNode
;
3401 QuestionId
= EFI_QUESTION_ID_INVALID
;
3402 BitMask
= 0x00000000;
3403 if (QType
!= NULL
) {
3404 *QType
= QUESTION_NORMAL
;
3407 if ((Name
== NULL
) && (VarIdStr
== NULL
)) {
3411 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3413 if (strcmp (pNode
->mName
, Name
) != 0) {
3418 if (VarIdStr
!= NULL
) {
3419 if (strcmp (pNode
->mVarIdStr
, VarIdStr
) != 0) {
3424 QuestionId
= pNode
->mQuestionId
;
3425 BitMask
= pNode
->mBitMask
;
3426 if (QType
!= NULL
) {
3427 *QType
= pNode
->mQtype
;
3436 CVfrQuestionDB::FindQuestion (
3437 IN EFI_QUESTION_ID QuestionId
3440 SVfrQuestionNode
*pNode
;
3442 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3443 return VFR_RETURN_INVALID_PARAMETER
;
3446 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3447 if (pNode
->mQuestionId
== QuestionId
) {
3448 return VFR_RETURN_SUCCESS
;
3452 return VFR_RETURN_UNDEFINED
;
3456 CVfrQuestionDB::FindQuestion (
3460 SVfrQuestionNode
*pNode
;
3463 return VFR_RETURN_FATAL_ERROR
;
3466 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3467 if (strcmp (pNode
->mName
, Name
) == 0) {
3468 return VFR_RETURN_SUCCESS
;
3472 return VFR_RETURN_UNDEFINED
;
3475 CVfrStringDB::CVfrStringDB ()
3477 mStringFileName
= NULL
;
3480 CVfrStringDB::~CVfrStringDB ()
3482 if (mStringFileName
!= NULL
) {
3483 delete mStringFileName
;
3485 mStringFileName
= NULL
;
3490 CVfrStringDB::SetStringFileName(IN CHAR8
*StringFileName
)
3494 if (StringFileName
== NULL
) {
3498 FileLen
= strlen (StringFileName
) + 1;
3499 mStringFileName
= new CHAR8
[FileLen
];
3500 if (mStringFileName
== NULL
) {
3504 strcpy (mStringFileName
, StringFileName
);
3505 mStringFileName
[FileLen
- 1] = '\0';
3510 Returns TRUE or FALSE whether SupportedLanguages contains the best matching language
3511 from a set of supported languages.
3513 @param[in] SupportedLanguages A pointer to a Null-terminated ASCII string that
3514 contains a set of language codes.
3515 @param[in] Language A variable that contains pointers to Null-terminated
3516 ASCII strings that contain one language codes.
3518 @retval FALSE The best matching language could not be found in SupportedLanguages.
3519 @retval TRUE The best matching language could be found in SupportedLanguages.
3523 CVfrStringDB::GetBestLanguage (
3524 IN CONST CHAR8
*SupportedLanguages
,
3528 UINTN CompareLength
;
3529 UINTN LanguageLength
;
3530 CONST CHAR8
*Supported
;
3532 if (SupportedLanguages
== NULL
|| Language
== NULL
){
3537 // Determine the length of the first RFC 4646 language code in Language
3539 for (LanguageLength
= 0; Language
[LanguageLength
] != 0 && Language
[LanguageLength
] != ';'; LanguageLength
++);
3542 // Trim back the length of Language used until it is empty
3544 while (LanguageLength
> 0) {
3546 // Loop through all language codes in SupportedLanguages
3548 for (Supported
= SupportedLanguages
; *Supported
!= '\0'; Supported
+= CompareLength
) {
3550 // Skip ';' characters in Supported
3552 for (; *Supported
!= '\0' && *Supported
== ';'; Supported
++);
3554 // Determine the length of the next language code in Supported
3556 for (CompareLength
= 0; Supported
[CompareLength
] != 0 && Supported
[CompareLength
] != ';'; CompareLength
++);
3558 // If Language is longer than the Supported, then skip to the next language
3560 if (LanguageLength
> CompareLength
) {
3565 // See if the first LanguageLength characters in Supported match Language
3567 if (strncmp (Supported
, Language
, LanguageLength
) == 0) {
3573 // Trim Language from the right to the next '-' character
3575 for (LanguageLength
--; LanguageLength
> 0 && Language
[LanguageLength
] != '-'; LanguageLength
--);
3579 // No matches were found
3586 CVfrStringDB::GetVarStoreNameFormStringId (
3587 IN EFI_STRING_ID StringId
3590 FILE *pInFile
= NULL
;
3595 CHAR16
*UnicodeString
;
3596 CHAR8
*VarStoreName
= NULL
;
3600 CHAR8 LineBuf
[EFI_IFR_MAX_LENGTH
];
3602 EFI_HII_STRING_PACKAGE_HDR
*PkgHeader
;
3604 if (mStringFileName
== NULL
) {
3608 if ((pInFile
= fopen (LongFilePath (mStringFileName
), "rb")) == NULL
) {
3615 fseek (pInFile
, 0, SEEK_END
);
3616 Length
= ftell (pInFile
);
3617 fseek (pInFile
, 0, SEEK_SET
);
3622 StringPtr
= new UINT8
[Length
];
3623 if (StringPtr
== NULL
) {
3627 fread ((char *)StringPtr
, sizeof (UINT8
), Length
, pInFile
);
3630 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) StringPtr
;
3632 // Check the String package.
3634 if (PkgHeader
->Header
.Type
!= EFI_HII_PACKAGE_STRINGS
) {
3640 // Search the language, get best language base on RFC 4647 matching algorithm.
3642 Current
= StringPtr
;
3643 while (!GetBestLanguage ("en", PkgHeader
->Language
)) {
3644 Current
+= PkgHeader
->Header
.Length
;
3645 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) Current
;
3647 // If can't find string package base on language, just return the first string package.
3649 if (Current
- StringPtr
>= Length
) {
3650 Current
= StringPtr
;
3651 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) StringPtr
;
3656 Current
+= PkgHeader
->HdrSize
;
3658 // Find the string block according the stringId.
3660 Status
= FindStringBlock(Current
, StringId
, &NameOffset
, &BlockType
);
3661 if (Status
!= EFI_SUCCESS
) {
3667 // Get varstore name according the string type.
3669 switch (BlockType
) {
3670 case EFI_HII_SIBT_STRING_SCSU
:
3671 case EFI_HII_SIBT_STRING_SCSU_FONT
:
3672 case EFI_HII_SIBT_STRINGS_SCSU
:
3673 case EFI_HII_SIBT_STRINGS_SCSU_FONT
:
3674 StringName
= (CHAR8
*)(Current
+ NameOffset
);
3675 VarStoreName
= new CHAR8
[strlen(StringName
) + 1];
3676 strcpy (VarStoreName
, StringName
);
3678 case EFI_HII_SIBT_STRING_UCS2
:
3679 case EFI_HII_SIBT_STRING_UCS2_FONT
:
3680 case EFI_HII_SIBT_STRINGS_UCS2
:
3681 case EFI_HII_SIBT_STRINGS_UCS2_FONT
:
3682 UnicodeString
= (CHAR16
*)(Current
+ NameOffset
);
3683 Length
= GetUnicodeStringTextSize ((UINT8
*)UnicodeString
) ;
3684 DestTmp
= new CHAR8
[Length
/ 2 + 1];
3685 VarStoreName
= DestTmp
;
3686 while (*UnicodeString
!= '\0') {
3687 *(DestTmp
++) = (CHAR8
) *(UnicodeString
++);
3697 return VarStoreName
;
3701 CVfrStringDB::FindStringBlock (
3702 IN UINT8
*StringData
,
3703 IN EFI_STRING_ID StringId
,
3704 OUT UINT32
*StringTextOffset
,
3705 OUT UINT8
*BlockType
3709 EFI_STRING_ID CurrentStringId
;
3712 UINT8
*StringTextPtr
;
3717 EFI_HII_SIBT_EXT2_BLOCK Ext2
;
3721 CurrentStringId
= 1;
3724 // Parse the string blocks to get the string text and font.
3726 BlockHdr
= StringData
;
3729 while (*BlockHdr
!= EFI_HII_SIBT_END
) {
3730 switch (*BlockHdr
) {
3731 case EFI_HII_SIBT_STRING_SCSU
:
3732 Offset
= sizeof (EFI_HII_STRING_BLOCK
);
3733 StringTextPtr
= BlockHdr
+ Offset
;
3734 BlockSize
+= Offset
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3738 case EFI_HII_SIBT_STRING_SCSU_FONT
:
3739 Offset
= sizeof (EFI_HII_SIBT_STRING_SCSU_FONT_BLOCK
) - sizeof (UINT8
);
3740 StringTextPtr
= BlockHdr
+ Offset
;
3741 BlockSize
+= Offset
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3745 case EFI_HII_SIBT_STRINGS_SCSU
:
3746 memcpy (&StringCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3747 StringTextPtr
= BlockHdr
+ sizeof (EFI_HII_SIBT_STRINGS_SCSU_BLOCK
) - sizeof (UINT8
);
3748 BlockSize
+= StringTextPtr
- BlockHdr
;
3750 for (Index
= 0; Index
< StringCount
; Index
++) {
3751 BlockSize
+= strlen ((CHAR8
*) StringTextPtr
) + 1;
3752 if (CurrentStringId
== StringId
) {
3753 *BlockType
= *BlockHdr
;
3754 *StringTextOffset
= StringTextPtr
- StringData
;
3757 StringTextPtr
= StringTextPtr
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3762 case EFI_HII_SIBT_STRINGS_SCSU_FONT
:
3765 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3768 StringTextPtr
= BlockHdr
+ sizeof (EFI_HII_SIBT_STRINGS_SCSU_FONT_BLOCK
) - sizeof (UINT8
);
3769 BlockSize
+= StringTextPtr
- BlockHdr
;
3771 for (Index
= 0; Index
< StringCount
; Index
++) {
3772 BlockSize
+= strlen ((CHAR8
*) StringTextPtr
) + 1;
3773 if (CurrentStringId
== StringId
) {
3774 *BlockType
= *BlockHdr
;
3775 *StringTextOffset
= StringTextPtr
- StringData
;
3778 StringTextPtr
= StringTextPtr
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3783 case EFI_HII_SIBT_STRING_UCS2
:
3784 Offset
= sizeof (EFI_HII_STRING_BLOCK
);
3785 StringTextPtr
= BlockHdr
+ Offset
;
3787 // Use StringSize to store the size of the specified string, including the NULL
3790 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3791 BlockSize
+= Offset
+ StringSize
;
3795 case EFI_HII_SIBT_STRING_UCS2_FONT
:
3796 Offset
= sizeof (EFI_HII_SIBT_STRING_UCS2_FONT_BLOCK
) - sizeof (CHAR16
);
3797 StringTextPtr
= BlockHdr
+ Offset
;
3799 // Use StrSize to store the size of the specified string, including the NULL
3802 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3803 BlockSize
+= Offset
+ StringSize
;
3807 case EFI_HII_SIBT_STRINGS_UCS2
:
3808 Offset
= sizeof (EFI_HII_SIBT_STRINGS_UCS2_BLOCK
) - sizeof (CHAR16
);
3809 StringTextPtr
= BlockHdr
+ Offset
;
3810 BlockSize
+= Offset
;
3811 memcpy (&StringCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3812 for (Index
= 0; Index
< StringCount
; Index
++) {
3813 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3814 BlockSize
+= StringSize
;
3815 if (CurrentStringId
== StringId
) {
3816 *BlockType
= *BlockHdr
;
3817 *StringTextOffset
= StringTextPtr
- StringData
;
3820 StringTextPtr
= StringTextPtr
+ StringSize
;
3825 case EFI_HII_SIBT_STRINGS_UCS2_FONT
:
3826 Offset
= sizeof (EFI_HII_SIBT_STRINGS_UCS2_FONT_BLOCK
) - sizeof (CHAR16
);
3827 StringTextPtr
= BlockHdr
+ Offset
;
3828 BlockSize
+= Offset
;
3831 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3834 for (Index
= 0; Index
< StringCount
; Index
++) {
3835 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3836 BlockSize
+= StringSize
;
3837 if (CurrentStringId
== StringId
) {
3838 *BlockType
= *BlockHdr
;
3839 *StringTextOffset
= StringTextPtr
- StringData
;
3842 StringTextPtr
= StringTextPtr
+ StringSize
;
3847 case EFI_HII_SIBT_DUPLICATE
:
3848 if (CurrentStringId
== StringId
) {
3850 // Incoming StringId is an id of a duplicate string block.
3851 // Update the StringId to be the previous string block.
3852 // Go back to the header of string block to search.
3856 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
),
3857 sizeof (EFI_STRING_ID
)
3859 CurrentStringId
= 1;
3862 BlockSize
+= sizeof (EFI_HII_SIBT_DUPLICATE_BLOCK
);
3867 case EFI_HII_SIBT_SKIP1
:
3868 SkipCount
= (UINT16
) (*(BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
)));
3869 CurrentStringId
= (UINT16
) (CurrentStringId
+ SkipCount
);
3870 BlockSize
+= sizeof (EFI_HII_SIBT_SKIP1_BLOCK
);
3873 case EFI_HII_SIBT_SKIP2
:
3874 memcpy (&SkipCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3875 CurrentStringId
= (UINT16
) (CurrentStringId
+ SkipCount
);
3876 BlockSize
+= sizeof (EFI_HII_SIBT_SKIP2_BLOCK
);
3879 case EFI_HII_SIBT_EXT1
:
3882 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3885 BlockSize
+= Length8
;
3888 case EFI_HII_SIBT_EXT2
:
3889 memcpy (&Ext2
, BlockHdr
, sizeof (EFI_HII_SIBT_EXT2_BLOCK
));
3890 BlockSize
+= Ext2
.Length
;
3893 case EFI_HII_SIBT_EXT4
:
3896 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3900 BlockSize
+= Length32
;
3907 if (StringId
> 0 && StringId
!= (EFI_STRING_ID
)(-1)) {
3908 *StringTextOffset
= BlockHdr
- StringData
+ Offset
;
3909 *BlockType
= *BlockHdr
;
3911 if (StringId
== CurrentStringId
- 1) {
3913 // if only one skip item, return EFI_NOT_FOUND.
3915 if(*BlockType
== EFI_HII_SIBT_SKIP2
|| *BlockType
== EFI_HII_SIBT_SKIP1
) {
3916 return EFI_NOT_FOUND
;
3922 if (StringId
< CurrentStringId
- 1) {
3923 return EFI_NOT_FOUND
;
3926 BlockHdr
= StringData
+ BlockSize
;
3929 return EFI_NOT_FOUND
;
3933 CVfrStringDB::GetUnicodeStringTextSize (
3940 StringSize
= sizeof (CHAR16
);
3941 StringPtr
= (UINT16
*)StringSrc
;
3942 while (*StringPtr
++ != L
'\0') {
3943 StringSize
+= sizeof (CHAR16
);
3949 BOOLEAN VfrCompatibleMode
= FALSE
;
3951 CVfrVarDataTypeDB gCVfrVarDataTypeDB
;
3952 CVfrDefaultStore gCVfrDefaultStore
;
3953 CVfrDataStorage gCVfrDataStorage
;