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
);
618 for (pTmp
= pType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
619 if (pTmp
->mIsBitField
) {
627 Check whether the field is bit field or not.
629 @param VarStr Point to the field name which may contain the structure name.
633 CVfrVarDataTypeDB::IsThisBitField (
637 CHAR8 FName
[MAX_NAME_LEN
];
638 CHAR8 TName
[MAX_NAME_LEN
];
640 SVfrDataType
*pType
= NULL
;
641 SVfrDataField
*pField
= NULL
;
643 CHECK_ERROR_RETURN (ExtractStructTypeName (VarStr
, TName
), VFR_RETURN_SUCCESS
);
644 CHECK_ERROR_RETURN (GetDataType (TName
, &pType
), VFR_RETURN_SUCCESS
);
646 while (*VarStr
!= '\0') {
647 CHECK_ERROR_RETURN(ExtractFieldNameAndArrary(VarStr
, FName
, ArrayIdx
), VFR_RETURN_SUCCESS
);
648 CHECK_ERROR_RETURN(GetTypeField (FName
, pType
, pField
), VFR_RETURN_SUCCESS
);
649 pType
= pField
->mFieldType
;
651 if (pField
->mIsBitField
) {
659 CVfrVarDataTypeDB::ExtractFieldNameAndArrary (
666 CHAR8 ArrayStr
[MAX_NAME_LEN
+ 1];
668 ArrayIdx
= INVALID_ARRAY_INDEX
;
671 return VFR_RETURN_FATAL_ERROR
;
674 while((*VarStr
!= '\0') &&
688 return VFR_RETURN_SUCCESS
;
691 for (Idx
= 0; (Idx
< MAX_NAME_LEN
) && (*VarStr
!= '\0') && (*VarStr
!= ']'); VarStr
++, Idx
++) {
692 ArrayStr
[Idx
] = *VarStr
;
694 ArrayStr
[Idx
] = '\0';
696 if ((*VarStr
!= ']') && (ArrayStr
[0] == '\0')) {
697 return VFR_RETURN_DATA_STRING_ERROR
;
699 ArrayIdx
= _STR2U32 (ArrayStr
);
700 if (*VarStr
== ']') {
703 if (*VarStr
== '.') {
706 return VFR_RETURN_SUCCESS
;
708 return VFR_RETURN_DATA_STRING_ERROR
;
711 return VFR_RETURN_SUCCESS
;
715 CVfrVarDataTypeDB::GetTypeField (
716 IN CONST CHAR8
*FName
,
717 IN SVfrDataType
*Type
,
718 OUT SVfrDataField
*&Field
721 SVfrDataField
*pField
= NULL
;
723 if ((FName
== NULL
) || (Type
== NULL
)) {
724 return VFR_RETURN_FATAL_ERROR
;
727 for (pField
= Type
->mMembers
; pField
!= NULL
; pField
= pField
->mNext
) {
729 // For type EFI_IFR_TYPE_TIME, because field name is not correctly wrote,
730 // add code to adjust it.
732 if (Type
->mType
== EFI_IFR_TYPE_TIME
) {
733 if (strcmp (FName
, "Hour") == 0) {
735 } else if (strcmp (FName
, "Minute") == 0) {
737 } else if (strcmp (FName
, "Second") == 0) {
742 if (strcmp (pField
->mFieldName
, FName
) == 0) {
744 return VFR_RETURN_SUCCESS
;
748 return VFR_RETURN_UNDEFINED
;
752 CVfrVarDataTypeDB::GetFieldOffset (
753 IN SVfrDataField
*Field
,
756 IN BOOLEAN IsBitField
760 return VFR_RETURN_FATAL_ERROR
;
764 // Framework Vfr file Array Index is from 1.
765 // But Uefi Vfr file Array Index is from 0.
767 if (VfrCompatibleMode
&& ArrayIdx
!= INVALID_ARRAY_INDEX
) {
769 return VFR_RETURN_ERROR_ARRARY_NUM
;
771 ArrayIdx
= ArrayIdx
- 1;
774 if ((ArrayIdx
!= INVALID_ARRAY_INDEX
) && ((Field
->mArrayNum
== 0) || (Field
->mArrayNum
<= ArrayIdx
))) {
775 return VFR_RETURN_ERROR_ARRARY_NUM
;
779 // Be compatible with the current usage
780 // If ArraryIdx is not specified, the first one is used.
782 // if ArrayNum is larger than zero, ArraryIdx must be specified.
784 // if ((ArrayIdx == INVALID_ARRAY_INDEX) && (Field->mArrayNum > 0)) {
785 // return VFR_RETURN_ERROR_ARRARY_NUM;
789 Offset
= Field
->mBitOffset
+ Field
->mFieldType
->mTotalSize
* ((ArrayIdx
== INVALID_ARRAY_INDEX
) ? 0 : ArrayIdx
) * 8;
791 Offset
= Field
->mOffset
+ Field
->mFieldType
->mTotalSize
* ((ArrayIdx
== INVALID_ARRAY_INDEX
) ? 0 : ArrayIdx
);
793 return VFR_RETURN_SUCCESS
;
797 CVfrVarDataTypeDB::GetFieldWidth (
798 IN SVfrDataField
*Field
805 return Field
->mFieldType
->mType
;
809 CVfrVarDataTypeDB::GetFieldSize (
810 IN SVfrDataField
*Field
,
816 return VFR_RETURN_FATAL_ERROR
;
819 if ((ArrayIdx
== INVALID_ARRAY_INDEX
) && (Field
->mArrayNum
!= 0)) {
820 return Field
->mFieldType
->mTotalSize
* Field
->mArrayNum
;
823 return Field
->mBitWidth
;
825 return Field
->mFieldType
->mTotalSize
;
831 CVfrVarDataTypeDB::InternalTypesListInit (
835 SVfrDataType
*New
= NULL
;
838 for (Index
= 0; gInternalTypesTable
[Index
].mTypeName
!= NULL
; Index
++) {
839 New
= new SVfrDataType
;
841 strcpy (New
->mTypeName
, gInternalTypesTable
[Index
].mTypeName
);
842 New
->mType
= gInternalTypesTable
[Index
].mType
;
843 New
->mAlign
= gInternalTypesTable
[Index
].mAlign
;
844 New
->mTotalSize
= gInternalTypesTable
[Index
].mSize
;
845 if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_DATE") == 0) {
846 SVfrDataField
*pYearField
= new SVfrDataField
;
847 SVfrDataField
*pMonthField
= new SVfrDataField
;
848 SVfrDataField
*pDayField
= new SVfrDataField
;
850 strcpy (pYearField
->mFieldName
, "Year");
851 GetDataType ((CHAR8
*)"UINT16", &pYearField
->mFieldType
);
852 pYearField
->mOffset
= 0;
853 pYearField
->mNext
= pMonthField
;
854 pYearField
->mArrayNum
= 0;
855 pYearField
->mIsBitField
= FALSE
;
857 strcpy (pMonthField
->mFieldName
, "Month");
858 GetDataType ((CHAR8
*)"UINT8", &pMonthField
->mFieldType
);
859 pMonthField
->mOffset
= 2;
860 pMonthField
->mNext
= pDayField
;
861 pMonthField
->mArrayNum
= 0;
862 pMonthField
->mIsBitField
= FALSE
;
864 strcpy (pDayField
->mFieldName
, "Day");
865 GetDataType ((CHAR8
*)"UINT8", &pDayField
->mFieldType
);
866 pDayField
->mOffset
= 3;
867 pDayField
->mNext
= NULL
;
868 pDayField
->mArrayNum
= 0;
869 pDayField
->mIsBitField
= FALSE
;
871 New
->mMembers
= pYearField
;
872 } else if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_TIME") == 0) {
873 SVfrDataField
*pHoursField
= new SVfrDataField
;
874 SVfrDataField
*pMinutesField
= new SVfrDataField
;
875 SVfrDataField
*pSecondsField
= new SVfrDataField
;
877 strcpy (pHoursField
->mFieldName
, "Hours");
878 GetDataType ((CHAR8
*)"UINT8", &pHoursField
->mFieldType
);
879 pHoursField
->mOffset
= 0;
880 pHoursField
->mNext
= pMinutesField
;
881 pHoursField
->mArrayNum
= 0;
882 pHoursField
->mIsBitField
= FALSE
;
884 strcpy (pMinutesField
->mFieldName
, "Minutes");
885 GetDataType ((CHAR8
*)"UINT8", &pMinutesField
->mFieldType
);
886 pMinutesField
->mOffset
= 1;
887 pMinutesField
->mNext
= pSecondsField
;
888 pMinutesField
->mArrayNum
= 0;
889 pMinutesField
->mIsBitField
= FALSE
;
891 strcpy (pSecondsField
->mFieldName
, "Seconds");
892 GetDataType ((CHAR8
*)"UINT8", &pSecondsField
->mFieldType
);
893 pSecondsField
->mOffset
= 2;
894 pSecondsField
->mNext
= NULL
;
895 pSecondsField
->mArrayNum
= 0;
896 pSecondsField
->mIsBitField
= FALSE
;
898 New
->mMembers
= pHoursField
;
899 } else if (strcmp (gInternalTypesTable
[Index
].mTypeName
, "EFI_HII_REF") == 0) {
900 SVfrDataField
*pQuestionIdField
= new SVfrDataField
;
901 SVfrDataField
*pFormIdField
= new SVfrDataField
;
902 SVfrDataField
*pFormSetGuidField
= new SVfrDataField
;
903 SVfrDataField
*pDevicePathField
= new SVfrDataField
;
905 strcpy (pQuestionIdField
->mFieldName
, "QuestionId");
906 GetDataType ((CHAR8
*)"UINT16", &pQuestionIdField
->mFieldType
);
907 pQuestionIdField
->mOffset
= 0;
908 pQuestionIdField
->mNext
= pFormIdField
;
909 pQuestionIdField
->mArrayNum
= 0;
910 pQuestionIdField
->mIsBitField
= FALSE
;
912 strcpy (pFormIdField
->mFieldName
, "FormId");
913 GetDataType ((CHAR8
*)"UINT16", &pFormIdField
->mFieldType
);
914 pFormIdField
->mOffset
= 2;
915 pFormIdField
->mNext
= pFormSetGuidField
;
916 pFormIdField
->mArrayNum
= 0;
917 pFormIdField
->mIsBitField
= FALSE
;
919 strcpy (pFormSetGuidField
->mFieldName
, "FormSetGuid");
920 GetDataType ((CHAR8
*)"EFI_GUID", &pFormSetGuidField
->mFieldType
);
921 pFormSetGuidField
->mOffset
= 4;
922 pFormSetGuidField
->mNext
= pDevicePathField
;
923 pFormSetGuidField
->mArrayNum
= 0;
924 pFormSetGuidField
->mIsBitField
= FALSE
;
926 strcpy (pDevicePathField
->mFieldName
, "DevicePath");
927 GetDataType ((CHAR8
*)"EFI_STRING_ID", &pDevicePathField
->mFieldType
);
928 pDevicePathField
->mOffset
= 20;
929 pDevicePathField
->mNext
= NULL
;
930 pDevicePathField
->mArrayNum
= 0;
931 pDevicePathField
->mIsBitField
= FALSE
;
933 New
->mMembers
= pQuestionIdField
;
935 New
->mMembers
= NULL
;
938 RegisterNewType (New
);
944 CVfrVarDataTypeDB::CVfrVarDataTypeDB (
948 mDataTypeList
= NULL
;
950 mCurrDataField
= NULL
;
951 mPackAlign
= DEFAULT_PACK_ALIGN
;
953 mFirstNewDataTypeName
= NULL
;
955 InternalTypesListInit ();
958 CVfrVarDataTypeDB::~CVfrVarDataTypeDB (
963 SVfrDataField
*pField
;
964 SVfrPackStackNode
*pPack
;
966 if (mNewDataType
!= NULL
) {
970 while (mDataTypeList
!= NULL
) {
971 pType
= mDataTypeList
;
972 mDataTypeList
= mDataTypeList
->mNext
;
973 while(pType
->mMembers
!= NULL
) {
974 pField
= pType
->mMembers
;
975 pType
->mMembers
= pType
->mMembers
->mNext
;
981 while (mPackStack
!= NULL
) {
983 mPackStack
= mPackStack
->mNext
;
989 CVfrVarDataTypeDB::Pack (
992 IN CHAR8
*Identifier
,
997 CHAR8 Msg
[MAX_STRING_LEN
] = {0, };
999 if (Action
& VFR_PACK_SHOW
) {
1000 sprintf (Msg
, "value of pragma pack(show) == %d", mPackAlign
);
1001 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Warning", Msg
);
1004 if (Action
& VFR_PACK_PUSH
) {
1005 SVfrPackStackNode
*pNew
= NULL
;
1007 if ((pNew
= new SVfrPackStackNode (Identifier
, mPackAlign
)) == NULL
) {
1008 return VFR_RETURN_FATAL_ERROR
;
1010 pNew
->mNext
= mPackStack
;
1014 if (Action
& VFR_PACK_POP
) {
1015 SVfrPackStackNode
*pNode
= NULL
;
1017 if (mPackStack
== NULL
) {
1018 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Error", "#pragma pack(pop...) : more pops than pushes");
1021 for (pNode
= mPackStack
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
1022 if (pNode
->Match (Identifier
) == TRUE
) {
1023 mPackAlign
= pNode
->mNumber
;
1024 mPackStack
= pNode
->mNext
;
1029 if (Action
& VFR_PACK_ASSIGN
) {
1030 PackAlign
= (Number
> 1) ? Number
+ Number
% 2 : Number
;
1031 if ((PackAlign
== 0) || (PackAlign
> 16)) {
1032 gCVfrErrorHandle
.PrintMsg (LineNum
, NULL
, "Error", "expected pragma parameter to be '1', '2', '4', '8', or '16'");
1034 mPackAlign
= PackAlign
;
1038 return VFR_RETURN_SUCCESS
;
1042 CVfrVarDataTypeDB::DeclareDataTypeBegin (
1046 SVfrDataType
*pNewType
= NULL
;
1048 pNewType
= new SVfrDataType
;
1049 pNewType
->mTypeName
[0] = '\0';
1050 pNewType
->mType
= EFI_IFR_TYPE_OTHER
;
1051 pNewType
->mAlign
= DEFAULT_ALIGN
;
1052 pNewType
->mTotalSize
= 0;
1053 pNewType
->mMembers
= NULL
;
1054 pNewType
->mNext
= NULL
;
1055 pNewType
->mHasBitField
= FALSE
;
1057 mNewDataType
= pNewType
;
1061 CVfrVarDataTypeDB::SetNewTypeName (
1065 SVfrDataType
*pType
;
1067 if (mNewDataType
== NULL
) {
1068 return VFR_RETURN_ERROR_SKIPED
;
1070 if (TypeName
== NULL
) {
1071 return VFR_RETURN_FATAL_ERROR
;
1073 if (strlen(TypeName
) >= MAX_NAME_LEN
) {
1074 return VFR_RETURN_INVALID_PARAMETER
;
1077 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1078 if (strcmp(pType
->mTypeName
, TypeName
) == 0) {
1079 return VFR_RETURN_REDEFINED
;
1083 strcpy(mNewDataType
->mTypeName
, TypeName
);
1084 return VFR_RETURN_SUCCESS
;
1088 Record the bit field info in the data type.
1090 @param FieldName Point to the field name.
1091 @param TypeName Point to the type name.
1092 @param Width The bit width.
1093 @param FieldInUnion The filed is in Union type or Structure type.
1097 CVfrVarDataTypeDB::DataTypeAddBitField (
1098 IN CHAR8
*FieldName
,
1101 IN BOOLEAN FieldInUnion
1104 SVfrDataField
*pNewField
= NULL
;
1105 SVfrDataType
*pFieldType
= NULL
;
1106 SVfrDataField
*pTmp
;
1108 UINT32 MaxDataTypeSize
;
1109 BOOLEAN UpdateTotalSize
;
1111 CHECK_ERROR_RETURN (GetDataType (TypeName
, &pFieldType
), VFR_RETURN_SUCCESS
);
1113 if (Width
> MAX_BIT_WIDTH
) {
1114 return VFR_RETURN_BIT_WIDTH_ERROR
;
1117 if (Width
> pFieldType
->mTotalSize
* 8) {
1118 return VFR_RETURN_BIT_WIDTH_ERROR
;
1121 if (FieldName
!= NULL
&& strlen (FieldName
) >= MAX_NAME_LEN
) {
1122 return VFR_RETURN_INVALID_PARAMETER
;
1125 if (Width
== 0 && FieldName
!= NULL
) {
1126 return VFR_RETURN_INVALID_PARAMETER
;
1129 for (pTmp
= mNewDataType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
1130 if (FieldName
!= NULL
&& strcmp (pTmp
->mFieldName
, FieldName
) == 0) {
1131 return VFR_RETURN_REDEFINED
;
1135 Align
= MIN (mPackAlign
, pFieldType
->mAlign
);
1136 UpdateTotalSize
= FALSE
;
1138 if ((pNewField
= new SVfrDataField
) == NULL
) {
1139 return VFR_RETURN_OUT_FOR_RESOURCES
;
1142 MaxDataTypeSize
= mNewDataType
->mTotalSize
;
1143 if (FieldName
!= NULL
) {
1144 strcpy (pNewField
->mFieldName
, FieldName
);
1146 pNewField
->mFieldType
= pFieldType
;
1147 pNewField
->mIsBitField
= TRUE
;
1148 pNewField
->mBitWidth
= Width
;
1149 pNewField
->mArrayNum
= 0;
1150 pNewField
->mBitOffset
= 0;
1151 pNewField
->mOffset
= 0;
1153 if (mNewDataType
->mMembers
== NULL
) {
1154 mNewDataType
->mMembers
= pNewField
;
1155 pNewField
->mNext
= NULL
;
1157 for (pTmp
= mNewDataType
->mMembers
; pTmp
->mNext
!= NULL
; pTmp
= pTmp
->mNext
)
1159 pTmp
->mNext
= pNewField
;
1160 pNewField
->mNext
= NULL
;
1164 pNewField
->mOffset
= 0;
1165 if (MaxDataTypeSize
< pNewField
->mFieldType
->mTotalSize
) {
1166 mNewDataType
->mTotalSize
= pNewField
->mFieldType
->mTotalSize
;
1170 // Check whether the bit fileds can be contained within one FieldType.
1172 if (pTmp
!= NULL
&& pTmp
->mIsBitField
&& strcmp (pTmp
->mFieldType
->mTypeName
, pNewField
->mFieldType
->mTypeName
) == 0 &&
1173 (pTmp
->mBitOffset
- pTmp
->mOffset
* 8) + pTmp
->mBitWidth
+ pNewField
->mBitWidth
<= pNewField
->mFieldType
->mTotalSize
* 8) {
1174 pNewField
->mBitOffset
= pTmp
->mBitOffset
+ pTmp
->mBitWidth
;
1175 pNewField
->mOffset
= pTmp
->mOffset
;
1177 // If BitWidth=0,used to force alignment at the next word boundary.
1178 // So make this bit field occupy the remaing bit width of current field type.
1180 if (pNewField
->mBitWidth
== 0) {
1181 pNewField
->mBitWidth
= pNewField
->mFieldType
->mTotalSize
* 8 - (pNewField
->mBitOffset
- pTmp
->mOffset
* 8);
1185 // The bit filed start a new memory
1187 pNewField
->mBitOffset
= mNewDataType
->mTotalSize
* 8;
1188 UpdateTotalSize
= TRUE
;
1192 if (UpdateTotalSize
){
1193 if ((mNewDataType
->mTotalSize
% Align
) == 0) {
1194 pNewField
->mOffset
= mNewDataType
->mTotalSize
;
1196 pNewField
->mOffset
= mNewDataType
->mTotalSize
+ ALIGN_STUFF(mNewDataType
->mTotalSize
, Align
);
1198 mNewDataType
->mTotalSize
= pNewField
->mOffset
+ (pNewField
->mFieldType
->mTotalSize
);
1201 mNewDataType
->mAlign
= MIN (mPackAlign
, MAX (pFieldType
->mAlign
, mNewDataType
->mAlign
));
1202 mNewDataType
->mHasBitField
= TRUE
;
1203 return VFR_RETURN_SUCCESS
;
1207 CVfrVarDataTypeDB::DataTypeAddField (
1208 IN CHAR8
*FieldName
,
1211 IN BOOLEAN FieldInUnion
1214 SVfrDataField
*pNewField
= NULL
;
1215 SVfrDataType
*pFieldType
= NULL
;
1216 SVfrDataField
*pTmp
;
1218 UINT32 MaxDataTypeSize
;
1220 CHECK_ERROR_RETURN (GetDataType (TypeName
, &pFieldType
), VFR_RETURN_SUCCESS
);
1221 MaxDataTypeSize
= mNewDataType
->mTotalSize
;
1223 if (strlen (FieldName
) >= MAX_NAME_LEN
) {
1224 return VFR_RETURN_INVALID_PARAMETER
;
1227 for (pTmp
= mNewDataType
->mMembers
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
1228 if (strcmp (pTmp
->mFieldName
, FieldName
) == 0) {
1229 return VFR_RETURN_REDEFINED
;
1233 Align
= MIN (mPackAlign
, pFieldType
->mAlign
);
1235 if ((pNewField
= new SVfrDataField
) == NULL
) {
1236 return VFR_RETURN_OUT_FOR_RESOURCES
;
1238 strcpy (pNewField
->mFieldName
, FieldName
);
1239 pNewField
->mFieldType
= pFieldType
;
1240 pNewField
->mArrayNum
= ArrayNum
;
1241 pNewField
->mIsBitField
= FALSE
;
1242 if ((mNewDataType
->mTotalSize
% Align
) == 0) {
1243 pNewField
->mOffset
= mNewDataType
->mTotalSize
;
1245 pNewField
->mOffset
= mNewDataType
->mTotalSize
+ ALIGN_STUFF(mNewDataType
->mTotalSize
, Align
);
1247 if (mNewDataType
->mMembers
== NULL
) {
1248 mNewDataType
->mMembers
= pNewField
;
1249 pNewField
->mNext
= NULL
;
1251 for (pTmp
= mNewDataType
->mMembers
; pTmp
->mNext
!= NULL
; pTmp
= pTmp
->mNext
)
1253 pTmp
->mNext
= pNewField
;
1254 pNewField
->mNext
= NULL
;
1257 mNewDataType
->mAlign
= MIN (mPackAlign
, MAX (pFieldType
->mAlign
, mNewDataType
->mAlign
));
1260 if (MaxDataTypeSize
< pNewField
->mFieldType
->mTotalSize
) {
1261 mNewDataType
->mTotalSize
= pNewField
->mFieldType
->mTotalSize
;
1263 pNewField
->mOffset
= 0;
1265 mNewDataType
->mTotalSize
= pNewField
->mOffset
+ (pNewField
->mFieldType
->mTotalSize
) * ((ArrayNum
== 0) ? 1 : ArrayNum
);
1268 return VFR_RETURN_SUCCESS
;
1272 CVfrVarDataTypeDB::DeclareDataTypeEnd (
1276 if (mNewDataType
->mTypeName
[0] == '\0') {
1280 if ((mNewDataType
->mTotalSize
% mNewDataType
->mAlign
) !=0) {
1281 mNewDataType
->mTotalSize
+= ALIGN_STUFF (mNewDataType
->mTotalSize
, mNewDataType
->mAlign
);
1284 RegisterNewType (mNewDataType
);
1285 if (mFirstNewDataTypeName
== NULL
) {
1286 mFirstNewDataTypeName
= mNewDataType
->mTypeName
;
1289 mNewDataType
= NULL
;
1293 CVfrVarDataTypeDB::GetDataType (
1295 OUT SVfrDataType
**DataType
1298 SVfrDataType
*pDataType
= NULL
;
1300 if (TypeName
== NULL
) {
1301 return VFR_RETURN_ERROR_SKIPED
;
1304 if (DataType
== NULL
) {
1305 return VFR_RETURN_FATAL_ERROR
;
1310 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1311 if (strcmp (TypeName
, pDataType
->mTypeName
) == 0) {
1312 *DataType
= pDataType
;
1313 return VFR_RETURN_SUCCESS
;
1317 return VFR_RETURN_UNDEFINED
;
1321 CVfrVarDataTypeDB::GetDataTypeSize (
1326 SVfrDataType
*pDataType
= NULL
;
1329 return VFR_RETURN_FATAL_ERROR
;
1333 DataType
= DataType
& 0x0F;
1336 // For user defined data type, the size can't be got by this function.
1338 if (DataType
== EFI_IFR_TYPE_OTHER
) {
1339 return VFR_RETURN_SUCCESS
;
1342 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1343 if (DataType
== pDataType
->mType
) {
1344 *Size
= pDataType
->mTotalSize
;
1345 return VFR_RETURN_SUCCESS
;
1349 return VFR_RETURN_UNDEFINED
;
1353 CVfrVarDataTypeDB::GetDataTypeSize (
1358 SVfrDataType
*pDataType
= NULL
;
1361 return VFR_RETURN_FATAL_ERROR
;
1366 for (pDataType
= mDataTypeList
; pDataType
!= NULL
; pDataType
= pDataType
->mNext
) {
1367 if (strcmp (TypeName
, pDataType
->mTypeName
) == 0) {
1368 *Size
= pDataType
->mTotalSize
;
1369 return VFR_RETURN_SUCCESS
;
1373 return VFR_RETURN_UNDEFINED
;
1377 CVfrVarDataTypeDB::GetDataFieldInfo (
1382 OUT BOOLEAN
&BitField
1385 CHAR8 TName
[MAX_NAME_LEN
], FName
[MAX_NAME_LEN
];
1386 UINT32 ArrayIdx
, Tmp
;
1387 SVfrDataType
*pType
= NULL
;
1388 SVfrDataField
*pField
= NULL
;
1392 Type
= EFI_IFR_TYPE_OTHER
;
1394 VarStrName
= VarStr
;
1396 CHECK_ERROR_RETURN (ExtractStructTypeName (VarStr
, TName
), VFR_RETURN_SUCCESS
);
1397 CHECK_ERROR_RETURN (GetDataType (TName
, &pType
), VFR_RETURN_SUCCESS
);
1399 BitField
= IsThisBitField (VarStrName
);
1402 // if it is not struct data type
1404 Type
= pType
->mType
;
1405 Size
= pType
->mTotalSize
;
1407 while (*VarStr
!= '\0') {
1408 CHECK_ERROR_RETURN(ExtractFieldNameAndArrary(VarStr
, FName
, ArrayIdx
), VFR_RETURN_SUCCESS
);
1409 CHECK_ERROR_RETURN(GetTypeField (FName
, pType
, pField
), VFR_RETURN_SUCCESS
);
1410 pType
= pField
->mFieldType
;
1411 CHECK_ERROR_RETURN(GetFieldOffset (pField
, ArrayIdx
, Tmp
, pField
->mIsBitField
), VFR_RETURN_SUCCESS
);
1412 if (BitField
&& !pField
->mIsBitField
) {
1413 Offset
= (UINT16
) (Offset
+ Tmp
* 8);
1415 Offset
= (UINT16
) (Offset
+ Tmp
);
1417 Type
= GetFieldWidth (pField
);
1418 Size
= GetFieldSize (pField
, ArrayIdx
, BitField
);
1420 return VFR_RETURN_SUCCESS
;
1424 CVfrVarDataTypeDB::GetUserDefinedTypeNameList (
1425 OUT CHAR8
***NameList
,
1426 OUT UINT32
*ListSize
1430 SVfrDataType
*pType
;
1432 if ((NameList
== NULL
) || (ListSize
== NULL
)) {
1433 return VFR_RETURN_FATAL_ERROR
;
1439 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1440 if (_IS_INTERNAL_TYPE(pType
->mTypeName
) == FALSE
) {
1445 if (*ListSize
== 0) {
1446 return VFR_RETURN_SUCCESS
;
1449 if ((*NameList
= new CHAR8
*[*ListSize
]) == NULL
) {
1451 return VFR_RETURN_OUT_FOR_RESOURCES
;
1454 for (Index
= 0, pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
, Index
++) {
1455 if (_IS_INTERNAL_TYPE(pType
->mTypeName
) == FALSE
) {
1456 (*NameList
)[Index
] = pType
->mTypeName
;
1459 return VFR_RETURN_SUCCESS
;
1463 CVfrVarDataTypeDB::IsTypeNameDefined (
1467 SVfrDataType
*pType
;
1469 if (TypeName
== NULL
) {
1473 for (pType
= mDataTypeList
; pType
!= NULL
; pType
= pType
->mNext
) {
1474 if (strcmp (pType
->mTypeName
, TypeName
) == 0) {
1483 CVfrVarDataTypeDB::Dump (
1487 SVfrDataType
*pTNode
;
1488 SVfrDataField
*pFNode
;
1490 fprintf (File
, "\n\n***************************************************************\n");
1491 fprintf (File
, "\t\tmPackAlign = %x\n", mPackAlign
);
1492 for (pTNode
= mDataTypeList
; pTNode
!= NULL
; pTNode
= pTNode
->mNext
) {
1493 fprintf (File
, "\t\tstruct %s : mAlign [%d] mTotalSize [0x%x]\n\n", pTNode
->mTypeName
, pTNode
->mAlign
, pTNode
->mTotalSize
);
1494 fprintf (File
, "\t\tstruct %s {\n", pTNode
->mTypeName
);
1495 for (pFNode
= pTNode
->mMembers
; pFNode
!= NULL
; pFNode
= pFNode
->mNext
) {
1496 if (pFNode
->mArrayNum
> 0) {
1497 fprintf (File
, "\t\t\t+%08d[%08x] %s[%d] <%s>\n", pFNode
->mOffset
, pFNode
->mOffset
,
1498 pFNode
->mFieldName
, pFNode
->mArrayNum
, pFNode
->mFieldType
->mTypeName
);
1500 fprintf (File
, "\t\t\t+%08d[%08x] %s <%s>\n", pFNode
->mOffset
, pFNode
->mOffset
,
1501 pFNode
->mFieldName
, pFNode
->mFieldType
->mTypeName
);
1504 fprintf (File
, "\t\t};\n");
1505 fprintf (File
, "---------------------------------------------------------------\n");
1507 fprintf (File
, "***************************************************************\n");
1510 #ifdef CVFR_VARDATATYPEDB_DEBUG
1512 CVfrVarDataTypeDB::ParserDB (
1516 SVfrDataType
*pTNode
;
1517 SVfrDataField
*pFNode
;
1519 printf ("***************************************************************\n");
1520 printf ("\t\tmPackAlign = %x\n", mPackAlign
);
1521 for (pTNode
= mDataTypeList
; pTNode
!= NULL
; pTNode
= pTNode
->mNext
) {
1522 printf ("\t\tstruct %s : mAlign [%x] mTotalSize [%x]\n\n", pTNode
->mTypeName
, pTNode
->mAlign
, pTNode
->mTotalSize
);
1523 printf ("\t\tstruct %s {\n", pTNode
->mTypeName
);
1524 for (pFNode
= pTNode
->mMembers
; pFNode
!= NULL
; pFNode
= pFNode
->mNext
) {
1525 printf ("\t\t\t%s\t%s\n", pFNode
->mFieldType
->mTypeName
, pFNode
->mFieldName
);
1527 printf ("\t\t};\n");
1528 printf ("---------------------------------------------------------------\n");
1530 printf ("***************************************************************\n");
1534 SVfrVarStorageNode::SVfrVarStorageNode (
1536 IN CHAR8
*StoreName
,
1537 IN EFI_VARSTORE_ID VarStoreId
,
1538 IN EFI_STRING_ID VarName
,
1546 memset (&mGuid
, 0, sizeof (EFI_GUID
));
1548 if (StoreName
!= NULL
) {
1549 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1550 strcpy (mVarStoreName
, StoreName
);
1552 mVarStoreName
= NULL
;
1555 mVarStoreId
= VarStoreId
;
1556 mVarStoreType
= EFI_VFR_VARSTORE_EFI
;
1557 mStorageInfo
.mEfiVar
.mEfiVarName
= VarName
;
1558 mStorageInfo
.mEfiVar
.mEfiVarSize
= VarSize
;
1559 mAssignedFlag
= Flag
;
1562 SVfrVarStorageNode::SVfrVarStorageNode (
1564 IN CHAR8
*StoreName
,
1565 IN EFI_VARSTORE_ID VarStoreId
,
1566 IN SVfrDataType
*DataType
,
1567 IN BOOLEAN BitsVarstore
,
1574 memset (&mGuid
, 0, sizeof (EFI_GUID
));
1576 if (StoreName
!= NULL
) {
1577 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1578 strcpy (mVarStoreName
, StoreName
);
1580 mVarStoreName
= NULL
;
1583 mVarStoreId
= VarStoreId
;
1585 mVarStoreType
= EFI_VFR_VARSTORE_BUFFER_BITS
;
1587 mVarStoreType
= EFI_VFR_VARSTORE_BUFFER
;
1589 mStorageInfo
.mDataType
= DataType
;
1590 mAssignedFlag
= Flag
;
1593 SVfrVarStorageNode::SVfrVarStorageNode (
1594 IN CHAR8
*StoreName
,
1595 IN EFI_VARSTORE_ID VarStoreId
1598 if (StoreName
!= NULL
) {
1599 mVarStoreName
= new CHAR8
[strlen(StoreName
) + 1];
1600 strcpy (mVarStoreName
, StoreName
);
1602 mVarStoreName
= NULL
;
1605 mVarStoreId
= VarStoreId
;
1606 mVarStoreType
= EFI_VFR_VARSTORE_NAME
;
1607 mStorageInfo
.mNameSpace
.mNameTable
= new EFI_VARSTORE_ID
[DEFAULT_NAME_TABLE_ITEMS
];
1608 mStorageInfo
.mNameSpace
.mTableSize
= 0;
1611 SVfrVarStorageNode::~SVfrVarStorageNode (
1615 if (mVarStoreName
!= NULL
) {
1616 delete[] mVarStoreName
;
1619 if (mVarStoreType
== EFI_VFR_VARSTORE_NAME
) {
1620 delete mStorageInfo
.mNameSpace
.mNameTable
;
1624 CVfrDataStorage::CVfrDataStorage (
1630 for (Index
= 0; Index
< EFI_FREE_VARSTORE_ID_BITMAP_SIZE
; Index
++) {
1631 mFreeVarStoreIdBitMap
[Index
] = 0;
1634 // Question ID 0 is reserved.
1635 mFreeVarStoreIdBitMap
[0] = 0x80000000;
1637 mBufferVarStoreList
= NULL
;
1638 mEfiVarStoreList
= NULL
;
1639 mNameVarStoreList
= NULL
;
1640 mCurrVarStorageNode
= NULL
;
1641 mNewVarStorageNode
= NULL
;
1642 mBufferFieldInfoListHead
= NULL
;
1643 mBufferFieldInfoListTail
= NULL
;
1646 CVfrDataStorage::~CVfrDataStorage (
1650 SVfrVarStorageNode
*pNode
;
1652 while (mBufferVarStoreList
!= NULL
) {
1653 pNode
= mBufferVarStoreList
;
1654 mBufferVarStoreList
= mBufferVarStoreList
->mNext
;
1657 while (mEfiVarStoreList
!= NULL
) {
1658 pNode
= mEfiVarStoreList
;
1659 mEfiVarStoreList
= mEfiVarStoreList
->mNext
;
1662 while (mNameVarStoreList
!= NULL
) {
1663 pNode
= mNameVarStoreList
;
1664 mNameVarStoreList
= mNameVarStoreList
->mNext
;
1667 if (mNewVarStorageNode
!= NULL
) {
1668 delete mNewVarStorageNode
;
1673 CVfrDataStorage::GetFreeVarStoreId (
1674 EFI_VFR_VARSTORE_TYPE VarType
1677 UINT32 Index
, Mask
, Offset
;
1680 // Assign the different ID range for the different type VarStore to support Framework Vfr
1683 if ((!VfrCompatibleMode
) || (VarType
== EFI_VFR_VARSTORE_BUFFER
)) {
1685 } else if (VarType
== EFI_VFR_VARSTORE_EFI
) {
1687 } else if (VarType
== EFI_VFR_VARSTORE_NAME
) {
1691 for (; Index
< EFI_FREE_VARSTORE_ID_BITMAP_SIZE
; Index
++) {
1692 if (mFreeVarStoreIdBitMap
[Index
] != 0xFFFFFFFF) {
1697 if (Index
== EFI_FREE_VARSTORE_ID_BITMAP_SIZE
) {
1698 return EFI_VARSTORE_ID_INVALID
;
1701 for (Offset
= 0, Mask
= 0x80000000; Mask
!= 0; Mask
>>= 1, Offset
++) {
1702 if ((mFreeVarStoreIdBitMap
[Index
] & Mask
) == 0) {
1703 mFreeVarStoreIdBitMap
[Index
] |= Mask
;
1704 return (EFI_VARSTORE_ID
)((Index
<< EFI_BITS_SHIFT_PER_UINT32
) + Offset
);
1708 return EFI_VARSTORE_ID_INVALID
;
1712 CVfrDataStorage::ChekVarStoreIdFree (
1713 IN EFI_VARSTORE_ID VarStoreId
1716 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1717 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1719 return (mFreeVarStoreIdBitMap
[Index
] & (0x80000000 >> Offset
)) == 0;
1723 CVfrDataStorage::MarkVarStoreIdUsed (
1724 IN EFI_VARSTORE_ID VarStoreId
1727 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1728 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1730 mFreeVarStoreIdBitMap
[Index
] |= (0x80000000 >> Offset
);
1734 CVfrDataStorage::MarkVarStoreIdUnused (
1735 IN EFI_VARSTORE_ID VarStoreId
1738 UINT32 Index
= (VarStoreId
/ EFI_BITS_PER_UINT32
);
1739 UINT32 Offset
= (VarStoreId
% EFI_BITS_PER_UINT32
);
1741 mFreeVarStoreIdBitMap
[Index
] &= ~(0x80000000 >> Offset
);
1745 CVfrDataStorage::DeclareNameVarStoreBegin (
1746 IN CHAR8
*StoreName
,
1747 IN EFI_VARSTORE_ID VarStoreId
1750 SVfrVarStorageNode
*pNode
= NULL
;
1751 EFI_VARSTORE_ID TmpVarStoreId
;
1753 if (StoreName
== NULL
) {
1754 return VFR_RETURN_FATAL_ERROR
;
1757 if (GetVarStoreId (StoreName
, &TmpVarStoreId
) == VFR_RETURN_SUCCESS
) {
1758 return VFR_RETURN_REDEFINED
;
1761 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
1762 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_NAME
);
1764 if (ChekVarStoreIdFree (VarStoreId
) == FALSE
) {
1765 return VFR_RETURN_VARSTOREID_REDEFINED
;
1767 MarkVarStoreIdUsed (VarStoreId
);
1770 if ((pNode
= new SVfrVarStorageNode (StoreName
, VarStoreId
)) == NULL
) {
1771 return VFR_RETURN_UNDEFINED
;
1774 mNewVarStorageNode
= pNode
;
1776 return VFR_RETURN_SUCCESS
;
1780 CVfrDataStorage::NameTableAddItem (
1781 IN EFI_STRING_ID Item
1784 EFI_VARSTORE_ID
*NewTable
, *OldTable
;
1787 OldTable
= mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
;
1788 TableSize
= mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mTableSize
;
1790 if ((TableSize
!= 0) && ((TableSize
% DEFAULT_NAME_TABLE_ITEMS
) == 0)) {
1791 if ((NewTable
= new EFI_VARSTORE_ID
[TableSize
+ DEFAULT_NAME_TABLE_ITEMS
]) == NULL
) {
1792 return VFR_RETURN_OUT_FOR_RESOURCES
;
1794 memcpy (NewTable
, OldTable
, TableSize
);
1795 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
= NewTable
;
1798 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
[TableSize
++] = Item
;
1799 mNewVarStorageNode
->mStorageInfo
.mNameSpace
.mTableSize
= TableSize
;
1801 return VFR_RETURN_SUCCESS
;
1805 CVfrDataStorage::DeclareNameVarStoreEnd (
1809 mNewVarStorageNode
->mGuid
= *Guid
;
1810 mNewVarStorageNode
->mNext
= mNameVarStoreList
;
1811 mNameVarStoreList
= mNewVarStorageNode
;
1813 mNewVarStorageNode
= NULL
;
1815 return VFR_RETURN_SUCCESS
;
1819 CVfrDataStorage::DeclareEfiVarStore (
1820 IN CHAR8
*StoreName
,
1822 IN EFI_STRING_ID NameStrId
,
1827 SVfrVarStorageNode
*pNode
;
1828 EFI_VARSTORE_ID VarStoreId
;
1830 if ((StoreName
== NULL
) || (Guid
== NULL
)) {
1831 return VFR_RETURN_FATAL_ERROR
;
1834 if (VarSize
> sizeof (UINT64
)) {
1835 return VFR_RETURN_EFIVARSTORE_SIZE_ERROR
;
1838 if (GetVarStoreId (StoreName
, &VarStoreId
, Guid
) == VFR_RETURN_SUCCESS
) {
1839 return VFR_RETURN_REDEFINED
;
1842 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_EFI
);
1843 if ((pNode
= new SVfrVarStorageNode (Guid
, StoreName
, VarStoreId
, NameStrId
, VarSize
, Flag
)) == NULL
) {
1844 return VFR_RETURN_OUT_FOR_RESOURCES
;
1847 pNode
->mNext
= mEfiVarStoreList
;
1848 mEfiVarStoreList
= pNode
;
1850 return VFR_RETURN_SUCCESS
;
1854 CVfrDataStorage::DeclareBufferVarStore (
1855 IN CHAR8
*StoreName
,
1857 IN CVfrVarDataTypeDB
*DataTypeDB
,
1859 IN EFI_VARSTORE_ID VarStoreId
,
1860 IN BOOLEAN IsBitVarStore
,
1864 SVfrVarStorageNode
*pNew
= NULL
;
1865 SVfrDataType
*pDataType
= NULL
;
1866 EFI_VARSTORE_ID TempVarStoreId
;
1868 if ((StoreName
== NULL
) || (Guid
== NULL
) || (DataTypeDB
== NULL
)) {
1869 return VFR_RETURN_FATAL_ERROR
;
1872 if (GetVarStoreId (StoreName
, &TempVarStoreId
, Guid
) == VFR_RETURN_SUCCESS
) {
1873 return VFR_RETURN_REDEFINED
;
1876 CHECK_ERROR_RETURN(DataTypeDB
->GetDataType (TypeName
, &pDataType
), VFR_RETURN_SUCCESS
);
1878 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
1879 VarStoreId
= GetFreeVarStoreId (EFI_VFR_VARSTORE_BUFFER
);
1881 if (ChekVarStoreIdFree (VarStoreId
) == FALSE
) {
1882 return VFR_RETURN_VARSTOREID_REDEFINED
;
1884 MarkVarStoreIdUsed (VarStoreId
);
1887 if ((pNew
= new SVfrVarStorageNode (Guid
, StoreName
, VarStoreId
, pDataType
, IsBitVarStore
, Flag
)) == NULL
) {
1888 return VFR_RETURN_OUT_FOR_RESOURCES
;
1891 pNew
->mNext
= mBufferVarStoreList
;
1892 mBufferVarStoreList
= pNew
;
1894 if (gCVfrBufferConfig
.Register(StoreName
, Guid
) != 0) {
1895 return VFR_RETURN_FATAL_ERROR
;
1898 return VFR_RETURN_SUCCESS
;
1902 CVfrDataStorage::GetVarStoreByDataType (
1903 IN CHAR8
*DataTypeName
,
1904 OUT SVfrVarStorageNode
**VarNode
,
1905 IN EFI_GUID
*VarGuid
1908 SVfrVarStorageNode
*pNode
;
1909 SVfrVarStorageNode
*MatchNode
;
1912 // Framework VFR uses Data type name as varstore name, so don't need check again.
1914 if (VfrCompatibleMode
) {
1915 return VFR_RETURN_UNDEFINED
;
1919 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
1920 if (strcmp (pNode
->mStorageInfo
.mDataType
->mTypeName
, DataTypeName
) != 0) {
1924 if ((VarGuid
!= NULL
)) {
1925 if (memcmp (VarGuid
, &pNode
->mGuid
, sizeof (EFI_GUID
)) == 0) {
1927 return VFR_RETURN_SUCCESS
;
1930 if (MatchNode
== NULL
) {
1934 // More than one varstores referred the same data structures.
1936 return VFR_RETURN_VARSTORE_DATATYPE_REDEFINED_ERROR
;
1941 if (MatchNode
== NULL
) {
1942 return VFR_RETURN_UNDEFINED
;
1945 *VarNode
= MatchNode
;
1946 return VFR_RETURN_SUCCESS
;
1950 CVfrDataStorage::CheckGuidField (
1951 IN SVfrVarStorageNode
*pNode
,
1952 IN EFI_GUID
*StoreGuid
,
1953 IN BOOLEAN
*HasFoundOne
,
1954 OUT EFI_VFR_RETURN_CODE
*ReturnCode
1957 if (StoreGuid
!= NULL
) {
1959 // If has guid info, compare the guid filed.
1961 if (memcmp (StoreGuid
, &pNode
->mGuid
, sizeof (EFI_GUID
)) == 0) {
1963 // Both name and guid are same, this this varstore.
1965 mCurrVarStorageNode
= pNode
;
1966 *ReturnCode
= VFR_RETURN_SUCCESS
;
1971 // Not has Guid field, check whether this name is the only one.
1975 // The name has conflict, return name redefined.
1977 *ReturnCode
= VFR_RETURN_VARSTORE_NAME_REDEFINED_ERROR
;
1981 *HasFoundOne
= TRUE
;
1982 mCurrVarStorageNode
= pNode
;
1989 Base on the input store name and guid to find the varstore id.
1991 If both name and guid are inputed, base on the name and guid to
1992 found the varstore. If only name inputed, base on the name to
1993 found the varstore and go on to check whether more than one varstore
1994 has the same name. If only has found one varstore, return this
1995 varstore; if more than one varstore has same name, return varstore
1996 name redefined error. If no varstore found by varstore name, call
1997 function GetVarStoreByDataType and use inputed varstore name as
1998 data type name to search.
2001 CVfrDataStorage::GetVarStoreId (
2002 IN CHAR8
*StoreName
,
2003 OUT EFI_VARSTORE_ID
*VarStoreId
,
2004 IN EFI_GUID
*StoreGuid
2007 EFI_VFR_RETURN_CODE ReturnCode
;
2008 SVfrVarStorageNode
*pNode
;
2009 BOOLEAN HasFoundOne
= FALSE
;
2011 mCurrVarStorageNode
= NULL
;
2013 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2014 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2015 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2016 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2022 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2023 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2024 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2025 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2031 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2032 if (strcmp (pNode
->mVarStoreName
, StoreName
) == 0) {
2033 if (CheckGuidField(pNode
, StoreGuid
, &HasFoundOne
, &ReturnCode
)) {
2034 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2041 *VarStoreId
= mCurrVarStorageNode
->mVarStoreId
;
2042 return VFR_RETURN_SUCCESS
;
2045 *VarStoreId
= EFI_VARSTORE_ID_INVALID
;
2048 // Assume that Data strucutre name is used as StoreName, and check again.
2050 ReturnCode
= GetVarStoreByDataType (StoreName
, &pNode
, StoreGuid
);
2051 if (pNode
!= NULL
) {
2052 mCurrVarStorageNode
= pNode
;
2053 *VarStoreId
= pNode
->mVarStoreId
;
2060 CVfrDataStorage::GetBufferVarStoreDataTypeName (
2061 IN EFI_VARSTORE_ID VarStoreId
,
2062 OUT CHAR8
**DataTypeName
2065 SVfrVarStorageNode
*pNode
;
2067 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2068 return VFR_RETURN_FATAL_ERROR
;
2071 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2072 if (pNode
->mVarStoreId
== VarStoreId
) {
2073 *DataTypeName
= pNode
->mStorageInfo
.mDataType
->mTypeName
;
2074 return VFR_RETURN_SUCCESS
;
2078 return VFR_RETURN_UNDEFINED
;
2081 EFI_VFR_VARSTORE_TYPE
2082 CVfrDataStorage::GetVarStoreType (
2083 IN EFI_VARSTORE_ID VarStoreId
2086 SVfrVarStorageNode
*pNode
;
2087 EFI_VFR_VARSTORE_TYPE VarStoreType
;
2089 VarStoreType
= EFI_VFR_VARSTORE_INVALID
;
2091 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2092 return VarStoreType
;
2095 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2096 if (pNode
->mVarStoreId
== VarStoreId
) {
2097 VarStoreType
= pNode
->mVarStoreType
;
2098 return VarStoreType
;
2102 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2103 if (pNode
->mVarStoreId
== VarStoreId
) {
2104 VarStoreType
= pNode
->mVarStoreType
;
2105 return VarStoreType
;
2109 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2110 if (pNode
->mVarStoreId
== VarStoreId
) {
2111 VarStoreType
= pNode
->mVarStoreType
;
2112 return VarStoreType
;
2116 return VarStoreType
;
2120 CVfrDataStorage::GetVarStoreGuid (
2121 IN EFI_VARSTORE_ID VarStoreId
2124 SVfrVarStorageNode
*pNode
;
2129 if (VarStoreId
== EFI_VARSTORE_ID_INVALID
) {
2133 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2134 if (pNode
->mVarStoreId
== VarStoreId
) {
2135 VarGuid
= &pNode
->mGuid
;
2140 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2141 if (pNode
->mVarStoreId
== VarStoreId
) {
2142 VarGuid
= &pNode
->mGuid
;
2147 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2148 if (pNode
->mVarStoreId
== VarStoreId
) {
2149 VarGuid
= &pNode
->mGuid
;
2158 CVfrDataStorage::GetVarStoreName (
2159 IN EFI_VARSTORE_ID VarStoreId
,
2160 OUT CHAR8
**VarStoreName
2163 SVfrVarStorageNode
*pNode
;
2165 if (VarStoreName
== NULL
) {
2166 return VFR_RETURN_FATAL_ERROR
;
2169 for (pNode
= mBufferVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2170 if (pNode
->mVarStoreId
== VarStoreId
) {
2171 *VarStoreName
= pNode
->mVarStoreName
;
2172 return VFR_RETURN_SUCCESS
;
2176 for (pNode
= mEfiVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2177 if (pNode
->mVarStoreId
== VarStoreId
) {
2178 *VarStoreName
= pNode
->mVarStoreName
;
2179 return VFR_RETURN_SUCCESS
;
2183 for (pNode
= mNameVarStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2184 if (pNode
->mVarStoreId
== VarStoreId
) {
2185 *VarStoreName
= pNode
->mVarStoreName
;
2186 return VFR_RETURN_SUCCESS
;
2190 *VarStoreName
= NULL
;
2191 return VFR_RETURN_UNDEFINED
;
2195 CVfrDataStorage::GetEfiVarStoreInfo (
2196 IN OUT EFI_VARSTORE_INFO
*Info
2200 return VFR_RETURN_FATAL_ERROR
;
2203 if (mCurrVarStorageNode
== NULL
) {
2204 return VFR_RETURN_GET_EFIVARSTORE_ERROR
;
2207 Info
->mInfo
.mVarName
= mCurrVarStorageNode
->mStorageInfo
.mEfiVar
.mEfiVarName
;
2208 Info
->mVarTotalSize
= mCurrVarStorageNode
->mStorageInfo
.mEfiVar
.mEfiVarSize
;
2209 switch (Info
->mVarTotalSize
) {
2211 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_8
;
2214 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_16
;
2217 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_32
;
2220 Info
->mVarType
= EFI_IFR_TYPE_NUM_SIZE_64
;
2223 return VFR_RETURN_FATAL_ERROR
;
2226 return VFR_RETURN_SUCCESS
;
2230 CVfrDataStorage::AddBufferVarStoreFieldInfo (
2231 IN EFI_VARSTORE_INFO
*Info
2234 BufferVarStoreFieldInfoNode
*pNew
;
2236 if ((pNew
= new BufferVarStoreFieldInfoNode(Info
)) == NULL
) {
2237 return VFR_RETURN_FATAL_ERROR
;
2240 if (mBufferFieldInfoListHead
== NULL
) {
2241 mBufferFieldInfoListHead
= pNew
;
2242 mBufferFieldInfoListTail
= pNew
;
2244 mBufferFieldInfoListTail
->mNext
= pNew
;
2245 mBufferFieldInfoListTail
= pNew
;
2248 return VFR_RETURN_SUCCESS
;
2252 CVfrDataStorage::GetBufferVarStoreFieldInfo (
2253 IN OUT EFI_VARSTORE_INFO
*Info
2256 BufferVarStoreFieldInfoNode
*pNode
;
2258 pNode
= mBufferFieldInfoListHead
;
2259 while (pNode
!= NULL
) {
2260 if (Info
->mVarStoreId
== pNode
->mVarStoreInfo
.mVarStoreId
&&
2261 Info
->mInfo
.mVarOffset
== pNode
->mVarStoreInfo
.mInfo
.mVarOffset
) {
2262 Info
->mVarTotalSize
= pNode
->mVarStoreInfo
.mVarTotalSize
;
2263 Info
->mVarType
= pNode
->mVarStoreInfo
.mVarType
;
2264 return VFR_RETURN_SUCCESS
;
2266 pNode
= pNode
->mNext
;
2268 return VFR_RETURN_FATAL_ERROR
;
2272 CVfrDataStorage::GetNameVarStoreInfo (
2273 OUT EFI_VARSTORE_INFO
*Info
,
2278 return VFR_RETURN_FATAL_ERROR
;
2281 if (mCurrVarStorageNode
== NULL
) {
2282 return VFR_RETURN_GET_NVVARSTORE_ERROR
;
2286 // Framework Vfr file Index is from 1, but Uefi Vfr file Index is from 0.
2288 if (VfrCompatibleMode
) {
2290 return VFR_RETURN_ERROR_ARRARY_NUM
;
2295 Info
->mInfo
.mVarName
= mCurrVarStorageNode
->mStorageInfo
.mNameSpace
.mNameTable
[Index
];
2297 return VFR_RETURN_SUCCESS
;
2300 SVfrDefaultStoreNode::SVfrDefaultStoreNode (
2301 IN EFI_IFR_DEFAULTSTORE
*ObjBinAddr
,
2303 IN EFI_STRING_ID DefaultStoreNameId
,
2307 mObjBinAddr
= ObjBinAddr
;
2309 if (RefName
!= NULL
) {
2310 mRefName
= new CHAR8
[strlen (RefName
) + 1];
2311 strcpy (mRefName
, RefName
);
2317 mDefaultId
= DefaultId
;
2318 mDefaultStoreNameId
= DefaultStoreNameId
;
2321 SVfrDefaultStoreNode::~SVfrDefaultStoreNode (
2325 if (mRefName
!= NULL
) {
2330 CVfrDefaultStore::CVfrDefaultStore (
2334 mDefaultStoreList
= NULL
;
2337 CVfrDefaultStore::~CVfrDefaultStore (
2341 SVfrDefaultStoreNode
*pTmp
= NULL
;
2343 while (mDefaultStoreList
!= NULL
) {
2344 pTmp
= mDefaultStoreList
;
2345 mDefaultStoreList
= mDefaultStoreList
->mNext
;
2351 CVfrDefaultStore::RegisterDefaultStore (
2352 IN CHAR8
*ObjBinAddr
,
2354 IN EFI_STRING_ID DefaultStoreNameId
,
2358 SVfrDefaultStoreNode
*pNode
= NULL
;
2360 if (RefName
== NULL
) {
2361 return VFR_RETURN_FATAL_ERROR
;
2364 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2365 if (strcmp (pNode
->mRefName
, RefName
) == 0) {
2366 return VFR_RETURN_REDEFINED
;
2370 if ((pNode
= new SVfrDefaultStoreNode ((EFI_IFR_DEFAULTSTORE
*)ObjBinAddr
, RefName
, DefaultStoreNameId
, DefaultId
)) == NULL
) {
2371 return VFR_RETURN_OUT_FOR_RESOURCES
;
2374 pNode
->mNext
= mDefaultStoreList
;
2375 mDefaultStoreList
= pNode
;
2377 return VFR_RETURN_SUCCESS
;
2381 * assign new reference name or new default store name id only if
2382 * the original is invalid
2385 CVfrDefaultStore::ReRegisterDefaultStoreById (
2386 IN UINT16 DefaultId
,
2388 IN EFI_STRING_ID DefaultStoreNameId
2391 SVfrDefaultStoreNode
*pNode
= NULL
;
2393 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2394 if (pNode
->mDefaultId
== DefaultId
) {
2399 if (pNode
== NULL
) {
2400 return VFR_RETURN_UNDEFINED
;
2402 if (pNode
->mDefaultStoreNameId
== EFI_STRING_ID_INVALID
) {
2403 pNode
->mDefaultStoreNameId
= DefaultStoreNameId
;
2404 if (pNode
->mObjBinAddr
!= NULL
) {
2405 pNode
->mObjBinAddr
->DefaultName
= DefaultStoreNameId
;
2408 return VFR_RETURN_REDEFINED
;
2411 if (RefName
!= NULL
) {
2412 delete pNode
->mRefName
;
2413 pNode
->mRefName
= new CHAR8
[strlen (RefName
) + 1];
2414 if (pNode
->mRefName
!= NULL
) {
2415 strcpy (pNode
->mRefName
, RefName
);
2420 return VFR_RETURN_SUCCESS
;
2424 CVfrDefaultStore::DefaultIdRegistered (
2428 SVfrDefaultStoreNode
*pNode
= NULL
;
2430 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2431 if (pNode
->mDefaultId
== DefaultId
) {
2440 CVfrDefaultStore::GetDefaultId (
2442 OUT UINT16
*DefaultId
2445 SVfrDefaultStoreNode
*pTmp
= NULL
;
2447 if (DefaultId
== NULL
) {
2448 return VFR_RETURN_FATAL_ERROR
;
2451 for (pTmp
= mDefaultStoreList
; pTmp
!= NULL
; pTmp
= pTmp
->mNext
) {
2452 if (strcmp (pTmp
->mRefName
, RefName
) == 0) {
2453 *DefaultId
= pTmp
->mDefaultId
;
2454 return VFR_RETURN_SUCCESS
;
2458 return VFR_RETURN_UNDEFINED
;
2462 CVfrDefaultStore::BufferVarStoreAltConfigAdd (
2463 IN EFI_VARSTORE_ID DefaultId
,
2464 IN EFI_VARSTORE_INFO
&Info
,
2465 IN CHAR8
*VarStoreName
,
2466 IN EFI_GUID
*VarStoreGuid
,
2468 IN EFI_IFR_TYPE_VALUE Value
2471 SVfrDefaultStoreNode
*pNode
= NULL
;
2472 CHAR8 NewAltCfg
[2 * 2 * sizeof (UINT16
) + 1] = {0,};
2473 INTN Returnvalue
= 0;
2475 if (VarStoreName
== NULL
) {
2476 return VFR_RETURN_FATAL_ERROR
;
2479 for (pNode
= mDefaultStoreList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2480 if (pNode
->mDefaultId
== DefaultId
) {
2485 if (pNode
== NULL
) {
2486 return VFR_RETURN_UNDEFINED
;
2489 gCVfrBufferConfig
.Open ();
2491 sprintf (NewAltCfg
, "%04x", pNode
->mDefaultId
);
2492 if ((Returnvalue
= gCVfrBufferConfig
.Select(VarStoreName
, VarStoreGuid
)) == 0) {
2493 if ((Returnvalue
= gCVfrBufferConfig
.Write ('a', VarStoreName
, VarStoreGuid
, NewAltCfg
, Type
, Info
.mInfo
.mVarOffset
, Info
.mVarTotalSize
, Value
)) != 0) {
2498 gCVfrBufferConfig
.Close ();
2500 return VFR_RETURN_SUCCESS
;
2503 gCVfrBufferConfig
.Close ();
2504 return (EFI_VFR_RETURN_CODE
)Returnvalue
;
2507 SVfrRuleNode::SVfrRuleNode (
2512 if (RuleName
!= NULL
) {
2513 mRuleName
= new CHAR8
[strlen (RuleName
) + 1];
2514 strcpy (mRuleName
, RuleName
);
2523 SVfrRuleNode::~SVfrRuleNode (
2527 if (mRuleName
!= NULL
) {
2532 CVfrRulesDB::CVfrRulesDB ()
2535 mFreeRuleId
= EFI_VARSTORE_ID_START
;
2538 CVfrRulesDB::~CVfrRulesDB ()
2540 SVfrRuleNode
*pNode
;
2542 while(mRuleList
!= NULL
) {
2544 mRuleList
= mRuleList
->mNext
;
2550 CVfrRulesDB::RegisterRule (
2556 if (RuleName
== NULL
) {
2560 if ((pNew
= new SVfrRuleNode (RuleName
, mFreeRuleId
)) == NULL
) {
2566 pNew
->mNext
= mRuleList
;
2571 CVfrRulesDB::GetRuleId (
2575 SVfrRuleNode
*pNode
;
2577 if (RuleName
== NULL
) {
2578 return EFI_RULE_ID_INVALID
;
2581 for (pNode
= mRuleList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2582 if (strcmp (pNode
->mRuleName
, RuleName
) == 0) {
2583 return pNode
->mRuleId
;
2587 return EFI_RULE_ID_INVALID
;
2590 CVfrRulesDB gCVfrRulesDB
;
2592 EFI_VARSTORE_INFO::EFI_VARSTORE_INFO (
2596 mVarStoreId
= EFI_VARSTORE_ID_INVALID
;
2597 mInfo
.mVarName
= EFI_STRING_ID_INVALID
;
2598 mInfo
.mVarOffset
= EFI_VAROFFSET_INVALID
;
2599 mVarType
= EFI_IFR_TYPE_OTHER
;
2604 EFI_VARSTORE_INFO::EFI_VARSTORE_INFO (
2605 IN EFI_VARSTORE_INFO
&Info
2608 mVarStoreId
= Info
.mVarStoreId
;
2609 mInfo
.mVarName
= Info
.mInfo
.mVarName
;
2610 mInfo
.mVarOffset
= Info
.mInfo
.mVarOffset
;
2611 mVarType
= Info
.mVarType
;
2612 mVarTotalSize
= Info
.mVarTotalSize
;
2613 mIsBitVar
= Info
.mIsBitVar
;
2617 EFI_VARSTORE_INFO::operator= (
2618 IN CONST EFI_VARSTORE_INFO
&Info
2621 if (this != &Info
) {
2622 mVarStoreId
= Info
.mVarStoreId
;
2623 mInfo
.mVarName
= Info
.mInfo
.mVarName
;
2624 mInfo
.mVarOffset
= Info
.mInfo
.mVarOffset
;
2625 mVarType
= Info
.mVarType
;
2626 mVarTotalSize
= Info
.mVarTotalSize
;
2627 mIsBitVar
= Info
.mIsBitVar
;
2634 EFI_VARSTORE_INFO::operator == (
2635 IN EFI_VARSTORE_INFO
*Info
2638 if ((mVarStoreId
== Info
->mVarStoreId
) &&
2639 (mInfo
.mVarName
== Info
->mInfo
.mVarName
) &&
2640 (mInfo
.mVarOffset
== Info
->mInfo
.mVarOffset
) &&
2641 (mVarType
== Info
->mVarType
) &&
2642 (mVarTotalSize
== Info
->mVarTotalSize
) &&
2643 (mIsBitVar
== Info
->mIsBitVar
)) {
2650 BufferVarStoreFieldInfoNode::BufferVarStoreFieldInfoNode(
2651 IN EFI_VARSTORE_INFO
*Info
2654 mVarStoreInfo
.mVarType
= Info
->mVarType
;
2655 mVarStoreInfo
.mVarTotalSize
= Info
->mVarTotalSize
;
2656 mVarStoreInfo
.mInfo
.mVarOffset
= Info
->mInfo
.mVarOffset
;
2657 mVarStoreInfo
.mVarStoreId
= Info
->mVarStoreId
;
2661 BufferVarStoreFieldInfoNode::~BufferVarStoreFieldInfoNode ()
2663 mVarStoreInfo
.mVarType
= EFI_IFR_TYPE_OTHER
;
2664 mVarStoreInfo
.mVarTotalSize
= 0;
2665 mVarStoreInfo
.mInfo
.mVarOffset
= EFI_VAROFFSET_INVALID
;
2666 mVarStoreInfo
.mVarStoreId
= EFI_VARSTORE_ID_INVALID
;
2670 static EFI_VARSTORE_INFO gEfiInvalidVarStoreInfo
;
2673 CVfrQuestionDB::GetFreeQuestionId (
2677 UINT32 Index
, Mask
, Offset
;
2679 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2680 if (mFreeQIdBitMap
[Index
] != 0xFFFFFFFF) {
2685 if (Index
== EFI_FREE_QUESTION_ID_BITMAP_SIZE
) {
2686 return EFI_QUESTION_ID_INVALID
;
2689 for (Offset
= 0, Mask
= 0x80000000; Mask
!= 0; Mask
>>= 1, Offset
++) {
2690 if ((mFreeQIdBitMap
[Index
] & Mask
) == 0) {
2691 mFreeQIdBitMap
[Index
] |= Mask
;
2692 return (EFI_QUESTION_ID
)((Index
<< EFI_BITS_SHIFT_PER_UINT32
) + Offset
);
2696 return EFI_QUESTION_ID_INVALID
;
2700 CVfrQuestionDB::ChekQuestionIdFree (
2701 IN EFI_QUESTION_ID QId
2704 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2705 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2707 return (mFreeQIdBitMap
[Index
] & (0x80000000 >> Offset
)) == 0;
2711 CVfrQuestionDB::MarkQuestionIdUsed (
2712 IN EFI_QUESTION_ID QId
2715 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2716 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2718 mFreeQIdBitMap
[Index
] |= (0x80000000 >> Offset
);
2722 CVfrQuestionDB::MarkQuestionIdUnused (
2723 IN EFI_QUESTION_ID QId
2726 UINT32 Index
= (QId
/ EFI_BITS_PER_UINT32
);
2727 UINT32 Offset
= (QId
% EFI_BITS_PER_UINT32
);
2729 mFreeQIdBitMap
[Index
] &= ~(0x80000000 >> Offset
);
2732 SVfrQuestionNode::SVfrQuestionNode (
2740 mQuestionId
= EFI_QUESTION_ID_INVALID
;
2743 mQtype
= QUESTION_NORMAL
;
2746 mName
= new CHAR8
[strlen ("$DEFAULT") + 1];
2747 strcpy (mName
, "$DEFAULT");
2749 mName
= new CHAR8
[strlen (Name
) + 1];
2750 strcpy (mName
, Name
);
2753 if (VarIdStr
!= NULL
) {
2754 mVarIdStr
= new CHAR8
[strlen (VarIdStr
) + 1];
2755 strcpy (mVarIdStr
, VarIdStr
);
2757 mVarIdStr
= new CHAR8
[strlen ("$") + 1];
2758 strcpy (mVarIdStr
, "$");
2762 SVfrQuestionNode::~SVfrQuestionNode (
2766 if (mName
!= NULL
) {
2770 if (mVarIdStr
!= NULL
) {
2775 CVfrQuestionDB::CVfrQuestionDB ()
2779 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2780 mFreeQIdBitMap
[Index
] = 0;
2783 // Question ID 0 is reserved.
2784 mFreeQIdBitMap
[0] = 0x80000000;
2785 mQuestionList
= NULL
;
2788 CVfrQuestionDB::~CVfrQuestionDB ()
2790 SVfrQuestionNode
*pNode
;
2792 while (mQuestionList
!= NULL
) {
2793 pNode
= mQuestionList
;
2794 mQuestionList
= mQuestionList
->mNext
;
2800 // Reset to init state
2803 CVfrQuestionDB::ResetInit(
2808 SVfrQuestionNode
*pNode
;
2810 while (mQuestionList
!= NULL
) {
2811 pNode
= mQuestionList
;
2812 mQuestionList
= mQuestionList
->mNext
;
2816 for (Index
= 0; Index
< EFI_FREE_QUESTION_ID_BITMAP_SIZE
; Index
++) {
2817 mFreeQIdBitMap
[Index
] = 0;
2820 // Question ID 0 is reserved.
2821 mFreeQIdBitMap
[0] = 0x80000000;
2822 mQuestionList
= NULL
;
2826 CVfrQuestionDB::PrintAllQuestion (
2830 SVfrQuestionNode
*pNode
= NULL
;
2832 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
2833 printf ("Question VarId is %s and QuesitonId is 0x%x\n", pNode
->mVarIdStr
, pNode
->mQuestionId
);
2838 CVfrQuestionDB::RegisterQuestion (
2841 IN OUT EFI_QUESTION_ID
&QuestionId
2844 SVfrQuestionNode
*pNode
= NULL
;
2846 if ((Name
!= NULL
) && (FindQuestion(Name
) == VFR_RETURN_SUCCESS
)) {
2847 return VFR_RETURN_REDEFINED
;
2850 if ((pNode
= new SVfrQuestionNode (Name
, VarIdStr
)) == NULL
) {
2851 return VFR_RETURN_OUT_FOR_RESOURCES
;
2854 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2855 QuestionId
= GetFreeQuestionId ();
2858 // For Framework Vfr, don't check question ID conflict.
2860 if (!VfrCompatibleMode
&& ChekQuestionIdFree (QuestionId
) == FALSE
) {
2862 return VFR_RETURN_QUESTIONID_REDEFINED
;
2864 MarkQuestionIdUsed (QuestionId
);
2866 pNode
->mQuestionId
= QuestionId
;
2868 pNode
->mNext
= mQuestionList
;
2869 mQuestionList
= pNode
;
2871 gCFormPkg
.DoPendingAssign (VarIdStr
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2873 return VFR_RETURN_SUCCESS
;
2877 CVfrQuestionDB::RegisterOldDateQuestion (
2878 IN CHAR8
*YearVarId
,
2879 IN CHAR8
*MonthVarId
,
2881 IN OUT EFI_QUESTION_ID
&QuestionId
2884 SVfrQuestionNode
*pNode
[3] = {NULL
, };
2887 if ((YearVarId
== NULL
) || (MonthVarId
== NULL
) || (DayVarId
== NULL
)) {
2891 if ((pNode
[0] = new SVfrQuestionNode (NULL
, YearVarId
, DATE_YEAR_BITMASK
)) == NULL
) {
2894 if ((pNode
[1] = new SVfrQuestionNode (NULL
, MonthVarId
, DATE_MONTH_BITMASK
)) == NULL
) {
2897 if ((pNode
[2] = new SVfrQuestionNode (NULL
, DayVarId
, DATE_DAY_BITMASK
)) == NULL
) {
2901 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2902 QuestionId
= GetFreeQuestionId ();
2904 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
2907 MarkQuestionIdUsed (QuestionId
);
2910 pNode
[0]->mQuestionId
= QuestionId
;
2911 pNode
[1]->mQuestionId
= QuestionId
;
2912 pNode
[2]->mQuestionId
= QuestionId
;
2913 pNode
[0]->mQtype
= QUESTION_DATE
;
2914 pNode
[1]->mQtype
= QUESTION_DATE
;
2915 pNode
[2]->mQtype
= QUESTION_DATE
;
2916 pNode
[0]->mNext
= pNode
[1];
2917 pNode
[1]->mNext
= pNode
[2];
2918 pNode
[2]->mNext
= mQuestionList
;
2919 mQuestionList
= pNode
[0];
2921 gCFormPkg
.DoPendingAssign (YearVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2922 gCFormPkg
.DoPendingAssign (MonthVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2923 gCFormPkg
.DoPendingAssign (DayVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
2928 for (Index
= 0; Index
< 3; Index
++) {
2929 if (pNode
[Index
] != NULL
) {
2930 delete pNode
[Index
];
2933 QuestionId
= EFI_QUESTION_ID_INVALID
;
2937 CVfrQuestionDB::RegisterNewDateQuestion (
2939 IN CHAR8
*BaseVarId
,
2940 IN OUT EFI_QUESTION_ID
&QuestionId
2943 SVfrQuestionNode
*pNode
[3] = {NULL
, };
2945 CHAR8
*VarIdStr
[3] = {NULL
, };
2948 if (BaseVarId
== NULL
&& Name
== NULL
) {
2949 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
2950 QuestionId
= GetFreeQuestionId ();
2952 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
2955 MarkQuestionIdUsed (QuestionId
);
2960 if (BaseVarId
!= NULL
) {
2961 Len
= strlen (BaseVarId
);
2963 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Year") + 1];
2964 if (VarIdStr
[0] != NULL
) {
2965 strcpy (VarIdStr
[0], BaseVarId
);
2966 strcat (VarIdStr
[0], ".Year");
2968 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Month") + 1];
2969 if (VarIdStr
[1] != NULL
) {
2970 strcpy (VarIdStr
[1], BaseVarId
);
2971 strcat (VarIdStr
[1], ".Month");
2973 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Day") + 1];
2974 if (VarIdStr
[2] != NULL
) {
2975 strcpy (VarIdStr
[2], BaseVarId
);
2976 strcat (VarIdStr
[2], ".Day");
2979 Len
= strlen (Name
);
2981 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Year") + 1];
2982 if (VarIdStr
[0] != NULL
) {
2983 strcpy (VarIdStr
[0], Name
);
2984 strcat (VarIdStr
[0], ".Year");
2986 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Month") + 1];
2987 if (VarIdStr
[1] != NULL
) {
2988 strcpy (VarIdStr
[1], Name
);
2989 strcat (VarIdStr
[1], ".Month");
2991 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Day") + 1];
2992 if (VarIdStr
[2] != NULL
) {
2993 strcpy (VarIdStr
[2], Name
);
2994 strcat (VarIdStr
[2], ".Day");
2998 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0], DATE_YEAR_BITMASK
)) == NULL
) {
3001 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1], DATE_MONTH_BITMASK
)) == NULL
) {
3004 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2], DATE_DAY_BITMASK
)) == NULL
) {
3008 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3009 QuestionId
= GetFreeQuestionId ();
3011 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3014 MarkQuestionIdUsed (QuestionId
);
3017 pNode
[0]->mQuestionId
= QuestionId
;
3018 pNode
[1]->mQuestionId
= QuestionId
;
3019 pNode
[2]->mQuestionId
= QuestionId
;
3020 pNode
[0]->mQtype
= QUESTION_DATE
;
3021 pNode
[1]->mQtype
= QUESTION_DATE
;
3022 pNode
[2]->mQtype
= QUESTION_DATE
;
3023 pNode
[0]->mNext
= pNode
[1];
3024 pNode
[1]->mNext
= pNode
[2];
3025 pNode
[2]->mNext
= mQuestionList
;
3026 mQuestionList
= pNode
[0];
3028 for (Index
= 0; Index
< 3; Index
++) {
3029 if (VarIdStr
[Index
] != NULL
) {
3030 delete VarIdStr
[Index
];
3034 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3035 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3036 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3041 for (Index
= 0; Index
< 3; Index
++) {
3042 if (pNode
[Index
] != NULL
) {
3043 delete pNode
[Index
];
3046 if (VarIdStr
[Index
] != NULL
) {
3047 delete VarIdStr
[Index
];
3053 CVfrQuestionDB::RegisterOldTimeQuestion (
3054 IN CHAR8
*HourVarId
,
3055 IN CHAR8
*MinuteVarId
,
3056 IN CHAR8
*SecondVarId
,
3057 IN OUT EFI_QUESTION_ID
&QuestionId
3060 SVfrQuestionNode
*pNode
[3] = {NULL
, };
3063 if ((HourVarId
== NULL
) || (MinuteVarId
== NULL
) || (SecondVarId
== NULL
)) {
3067 if ((pNode
[0] = new SVfrQuestionNode (NULL
, HourVarId
, TIME_HOUR_BITMASK
)) == NULL
) {
3070 if ((pNode
[1] = new SVfrQuestionNode (NULL
, MinuteVarId
, TIME_MINUTE_BITMASK
)) == NULL
) {
3073 if ((pNode
[2] = new SVfrQuestionNode (NULL
, SecondVarId
, TIME_SECOND_BITMASK
)) == NULL
) {
3077 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3078 QuestionId
= GetFreeQuestionId ();
3080 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3083 MarkQuestionIdUsed (QuestionId
);
3086 pNode
[0]->mQuestionId
= QuestionId
;
3087 pNode
[1]->mQuestionId
= QuestionId
;
3088 pNode
[2]->mQuestionId
= QuestionId
;
3089 pNode
[0]->mQtype
= QUESTION_TIME
;
3090 pNode
[1]->mQtype
= QUESTION_TIME
;
3091 pNode
[2]->mQtype
= QUESTION_TIME
;
3092 pNode
[0]->mNext
= pNode
[1];
3093 pNode
[1]->mNext
= pNode
[2];
3094 pNode
[2]->mNext
= mQuestionList
;
3095 mQuestionList
= pNode
[0];
3097 gCFormPkg
.DoPendingAssign (HourVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3098 gCFormPkg
.DoPendingAssign (MinuteVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3099 gCFormPkg
.DoPendingAssign (SecondVarId
, (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3104 for (Index
= 0; Index
< 3; Index
++) {
3105 if (pNode
[Index
] != NULL
) {
3106 delete pNode
[Index
];
3109 QuestionId
= EFI_QUESTION_ID_INVALID
;
3113 CVfrQuestionDB::RegisterNewTimeQuestion (
3115 IN CHAR8
*BaseVarId
,
3116 IN OUT EFI_QUESTION_ID
&QuestionId
3119 SVfrQuestionNode
*pNode
[3] = {NULL
, };
3121 CHAR8
*VarIdStr
[3] = {NULL
, };
3124 if (BaseVarId
== NULL
&& Name
== NULL
) {
3125 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3126 QuestionId
= GetFreeQuestionId ();
3128 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3131 MarkQuestionIdUsed (QuestionId
);
3136 if (BaseVarId
!= NULL
) {
3137 Len
= strlen (BaseVarId
);
3139 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Hour") + 1];
3140 if (VarIdStr
[0] != NULL
) {
3141 strcpy (VarIdStr
[0], BaseVarId
);
3142 strcat (VarIdStr
[0], ".Hour");
3144 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Minute") + 1];
3145 if (VarIdStr
[1] != NULL
) {
3146 strcpy (VarIdStr
[1], BaseVarId
);
3147 strcat (VarIdStr
[1], ".Minute");
3149 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Second") + 1];
3150 if (VarIdStr
[2] != NULL
) {
3151 strcpy (VarIdStr
[2], BaseVarId
);
3152 strcat (VarIdStr
[2], ".Second");
3155 Len
= strlen (Name
);
3157 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".Hour") + 1];
3158 if (VarIdStr
[0] != NULL
) {
3159 strcpy (VarIdStr
[0], Name
);
3160 strcat (VarIdStr
[0], ".Hour");
3162 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".Minute") + 1];
3163 if (VarIdStr
[1] != NULL
) {
3164 strcpy (VarIdStr
[1], Name
);
3165 strcat (VarIdStr
[1], ".Minute");
3167 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".Second") + 1];
3168 if (VarIdStr
[2] != NULL
) {
3169 strcpy (VarIdStr
[2], Name
);
3170 strcat (VarIdStr
[2], ".Second");
3174 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0], TIME_HOUR_BITMASK
)) == NULL
) {
3177 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1], TIME_MINUTE_BITMASK
)) == NULL
) {
3180 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2], TIME_SECOND_BITMASK
)) == NULL
) {
3184 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3185 QuestionId
= GetFreeQuestionId ();
3187 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3190 MarkQuestionIdUsed (QuestionId
);
3193 pNode
[0]->mQuestionId
= QuestionId
;
3194 pNode
[1]->mQuestionId
= QuestionId
;
3195 pNode
[2]->mQuestionId
= QuestionId
;
3196 pNode
[0]->mQtype
= QUESTION_TIME
;
3197 pNode
[1]->mQtype
= QUESTION_TIME
;
3198 pNode
[2]->mQtype
= QUESTION_TIME
;
3199 pNode
[0]->mNext
= pNode
[1];
3200 pNode
[1]->mNext
= pNode
[2];
3201 pNode
[2]->mNext
= mQuestionList
;
3202 mQuestionList
= pNode
[0];
3204 for (Index
= 0; Index
< 3; Index
++) {
3205 if (VarIdStr
[Index
] != NULL
) {
3206 delete VarIdStr
[Index
];
3210 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3211 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3212 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3217 for (Index
= 0; Index
< 3; Index
++) {
3218 if (pNode
[Index
] != NULL
) {
3219 delete pNode
[Index
];
3222 if (VarIdStr
[Index
] != NULL
) {
3223 delete VarIdStr
[Index
];
3229 CVfrQuestionDB::RegisterRefQuestion (
3231 IN CHAR8
*BaseVarId
,
3232 IN OUT EFI_QUESTION_ID
&QuestionId
3235 SVfrQuestionNode
*pNode
[4] = {NULL
, };
3237 CHAR8
*VarIdStr
[4] = {NULL
, };
3240 if (BaseVarId
== NULL
&& Name
== NULL
) {
3244 if (BaseVarId
!= NULL
) {
3245 Len
= strlen (BaseVarId
);
3247 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".QuestionId") + 1];
3248 if (VarIdStr
[0] != NULL
) {
3249 strcpy (VarIdStr
[0], BaseVarId
);
3250 strcat (VarIdStr
[0], ".QuestionId");
3252 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".FormId") + 1];
3253 if (VarIdStr
[1] != NULL
) {
3254 strcpy (VarIdStr
[1], BaseVarId
);
3255 strcat (VarIdStr
[1], ".FormId");
3257 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".FormSetGuid") + 1];
3258 if (VarIdStr
[2] != NULL
) {
3259 strcpy (VarIdStr
[2], BaseVarId
);
3260 strcat (VarIdStr
[2], ".FormSetGuid");
3262 VarIdStr
[3] = new CHAR8
[Len
+ strlen (".DevicePath") + 1];
3263 if (VarIdStr
[3] != NULL
) {
3264 strcpy (VarIdStr
[3], BaseVarId
);
3265 strcat (VarIdStr
[3], ".DevicePath");
3268 Len
= strlen (Name
);
3270 VarIdStr
[0] = new CHAR8
[Len
+ strlen (".QuestionId") + 1];
3271 if (VarIdStr
[0] != NULL
) {
3272 strcpy (VarIdStr
[0], Name
);
3273 strcat (VarIdStr
[0], ".QuestionId");
3275 VarIdStr
[1] = new CHAR8
[Len
+ strlen (".FormId") + 1];
3276 if (VarIdStr
[1] != NULL
) {
3277 strcpy (VarIdStr
[1], Name
);
3278 strcat (VarIdStr
[1], ".FormId");
3280 VarIdStr
[2] = new CHAR8
[Len
+ strlen (".FormSetGuid") + 1];
3281 if (VarIdStr
[2] != NULL
) {
3282 strcpy (VarIdStr
[2], Name
);
3283 strcat (VarIdStr
[2], ".FormSetGuid");
3285 VarIdStr
[3] = new CHAR8
[Len
+ strlen (".DevicePath") + 1];
3286 if (VarIdStr
[3] != NULL
) {
3287 strcpy (VarIdStr
[3], Name
);
3288 strcat (VarIdStr
[3], ".DevicePath");
3292 if ((pNode
[0] = new SVfrQuestionNode (Name
, VarIdStr
[0])) == NULL
) {
3295 if ((pNode
[1] = new SVfrQuestionNode (Name
, VarIdStr
[1])) == NULL
) {
3298 if ((pNode
[2] = new SVfrQuestionNode (Name
, VarIdStr
[2])) == NULL
) {
3301 if ((pNode
[3] = new SVfrQuestionNode (Name
, VarIdStr
[3])) == NULL
) {
3305 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3306 QuestionId
= GetFreeQuestionId ();
3308 if (ChekQuestionIdFree (QuestionId
) == FALSE
) {
3311 MarkQuestionIdUsed (QuestionId
);
3314 pNode
[0]->mQuestionId
= QuestionId
;
3315 pNode
[1]->mQuestionId
= QuestionId
;
3316 pNode
[2]->mQuestionId
= QuestionId
;
3317 pNode
[3]->mQuestionId
= QuestionId
;
3318 pNode
[0]->mQtype
= QUESTION_REF
;
3319 pNode
[1]->mQtype
= QUESTION_REF
;
3320 pNode
[2]->mQtype
= QUESTION_REF
;
3321 pNode
[3]->mQtype
= QUESTION_REF
;
3322 pNode
[0]->mNext
= pNode
[1];
3323 pNode
[1]->mNext
= pNode
[2];
3324 pNode
[2]->mNext
= pNode
[3];
3325 pNode
[3]->mNext
= mQuestionList
;
3326 mQuestionList
= pNode
[0];
3328 gCFormPkg
.DoPendingAssign (VarIdStr
[0], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3329 gCFormPkg
.DoPendingAssign (VarIdStr
[1], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3330 gCFormPkg
.DoPendingAssign (VarIdStr
[2], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3331 gCFormPkg
.DoPendingAssign (VarIdStr
[3], (VOID
*)&QuestionId
, sizeof(EFI_QUESTION_ID
));
3336 for (Index
= 0; Index
< 4; Index
++) {
3337 if (pNode
[Index
] != NULL
) {
3338 delete pNode
[Index
];
3341 if (VarIdStr
[Index
] != NULL
) {
3342 delete VarIdStr
[Index
];
3348 CVfrQuestionDB::UpdateQuestionId (
3349 IN EFI_QUESTION_ID QId
,
3350 IN EFI_QUESTION_ID NewQId
3353 SVfrQuestionNode
*pNode
= NULL
;
3355 if (QId
== NewQId
) {
3357 return VFR_RETURN_SUCCESS
;
3361 // For Framework Vfr, don't check question ID conflict.
3363 if (!VfrCompatibleMode
&& ChekQuestionIdFree (NewQId
) == FALSE
) {
3364 return VFR_RETURN_REDEFINED
;
3367 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3368 if (pNode
->mQuestionId
== QId
) {
3373 if (pNode
== NULL
) {
3374 return VFR_RETURN_UNDEFINED
;
3377 MarkQuestionIdUnused (QId
);
3378 pNode
->mQuestionId
= NewQId
;
3379 MarkQuestionIdUsed (NewQId
);
3381 gCFormPkg
.DoPendingAssign (pNode
->mVarIdStr
, (VOID
*)&NewQId
, sizeof(EFI_QUESTION_ID
));
3383 return VFR_RETURN_SUCCESS
;
3387 CVfrQuestionDB::GetQuestionId (
3390 OUT EFI_QUESTION_ID
&QuestionId
,
3391 OUT UINT32
&BitMask
,
3392 OUT EFI_QUESION_TYPE
*QType
3395 SVfrQuestionNode
*pNode
;
3397 QuestionId
= EFI_QUESTION_ID_INVALID
;
3398 BitMask
= 0x00000000;
3399 if (QType
!= NULL
) {
3400 *QType
= QUESTION_NORMAL
;
3403 if ((Name
== NULL
) && (VarIdStr
== NULL
)) {
3407 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3409 if (strcmp (pNode
->mName
, Name
) != 0) {
3414 if (VarIdStr
!= NULL
) {
3415 if (strcmp (pNode
->mVarIdStr
, VarIdStr
) != 0) {
3420 QuestionId
= pNode
->mQuestionId
;
3421 BitMask
= pNode
->mBitMask
;
3422 if (QType
!= NULL
) {
3423 *QType
= pNode
->mQtype
;
3432 CVfrQuestionDB::FindQuestion (
3433 IN EFI_QUESTION_ID QuestionId
3436 SVfrQuestionNode
*pNode
;
3438 if (QuestionId
== EFI_QUESTION_ID_INVALID
) {
3439 return VFR_RETURN_INVALID_PARAMETER
;
3442 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3443 if (pNode
->mQuestionId
== QuestionId
) {
3444 return VFR_RETURN_SUCCESS
;
3448 return VFR_RETURN_UNDEFINED
;
3452 CVfrQuestionDB::FindQuestion (
3456 SVfrQuestionNode
*pNode
;
3459 return VFR_RETURN_FATAL_ERROR
;
3462 for (pNode
= mQuestionList
; pNode
!= NULL
; pNode
= pNode
->mNext
) {
3463 if (strcmp (pNode
->mName
, Name
) == 0) {
3464 return VFR_RETURN_SUCCESS
;
3468 return VFR_RETURN_UNDEFINED
;
3471 CVfrStringDB::CVfrStringDB ()
3473 mStringFileName
= NULL
;
3476 CVfrStringDB::~CVfrStringDB ()
3478 if (mStringFileName
!= NULL
) {
3479 delete mStringFileName
;
3481 mStringFileName
= NULL
;
3486 CVfrStringDB::SetStringFileName(IN CHAR8
*StringFileName
)
3490 if (StringFileName
== NULL
) {
3494 FileLen
= strlen (StringFileName
) + 1;
3495 mStringFileName
= new CHAR8
[FileLen
];
3496 if (mStringFileName
== NULL
) {
3500 strcpy (mStringFileName
, StringFileName
);
3501 mStringFileName
[FileLen
- 1] = '\0';
3506 Returns TRUE or FALSE whether SupportedLanguages contains the best matching language
3507 from a set of supported languages.
3509 @param[in] SupportedLanguages A pointer to a Null-terminated ASCII string that
3510 contains a set of language codes.
3511 @param[in] Language A variable that contains pointers to Null-terminated
3512 ASCII strings that contain one language codes.
3514 @retval FALSE The best matching language could not be found in SupportedLanguages.
3515 @retval TRUE The best matching language could be found in SupportedLanguages.
3519 CVfrStringDB::GetBestLanguage (
3520 IN CONST CHAR8
*SupportedLanguages
,
3524 UINTN CompareLength
;
3525 UINTN LanguageLength
;
3526 CONST CHAR8
*Supported
;
3528 if (SupportedLanguages
== NULL
|| Language
== NULL
){
3533 // Determine the length of the first RFC 4646 language code in Language
3535 for (LanguageLength
= 0; Language
[LanguageLength
] != 0 && Language
[LanguageLength
] != ';'; LanguageLength
++);
3538 // Trim back the length of Language used until it is empty
3540 while (LanguageLength
> 0) {
3542 // Loop through all language codes in SupportedLanguages
3544 for (Supported
= SupportedLanguages
; *Supported
!= '\0'; Supported
+= CompareLength
) {
3546 // Skip ';' characters in Supported
3548 for (; *Supported
!= '\0' && *Supported
== ';'; Supported
++);
3550 // Determine the length of the next language code in Supported
3552 for (CompareLength
= 0; Supported
[CompareLength
] != 0 && Supported
[CompareLength
] != ';'; CompareLength
++);
3554 // If Language is longer than the Supported, then skip to the next language
3556 if (LanguageLength
> CompareLength
) {
3561 // See if the first LanguageLength characters in Supported match Language
3563 if (strncmp (Supported
, Language
, LanguageLength
) == 0) {
3569 // Trim Language from the right to the next '-' character
3571 for (LanguageLength
--; LanguageLength
> 0 && Language
[LanguageLength
] != '-'; LanguageLength
--);
3575 // No matches were found
3582 CVfrStringDB::GetVarStoreNameFormStringId (
3583 IN EFI_STRING_ID StringId
3586 FILE *pInFile
= NULL
;
3591 CHAR16
*UnicodeString
;
3592 CHAR8
*VarStoreName
= NULL
;
3596 CHAR8 LineBuf
[EFI_IFR_MAX_LENGTH
];
3598 EFI_HII_STRING_PACKAGE_HDR
*PkgHeader
;
3600 if (mStringFileName
== NULL
) {
3604 if ((pInFile
= fopen (LongFilePath (mStringFileName
), "rb")) == NULL
) {
3611 fseek (pInFile
, 0, SEEK_END
);
3612 Length
= ftell (pInFile
);
3613 fseek (pInFile
, 0, SEEK_SET
);
3618 StringPtr
= new UINT8
[Length
];
3619 if (StringPtr
== NULL
) {
3623 fread ((char *)StringPtr
, sizeof (UINT8
), Length
, pInFile
);
3626 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) StringPtr
;
3628 // Check the String package.
3630 if (PkgHeader
->Header
.Type
!= EFI_HII_PACKAGE_STRINGS
) {
3636 // Search the language, get best language base on RFC 4647 matching algorithm.
3638 Current
= StringPtr
;
3639 while (!GetBestLanguage ("en", PkgHeader
->Language
)) {
3640 Current
+= PkgHeader
->Header
.Length
;
3641 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) Current
;
3643 // If can't find string package base on language, just return the first string package.
3645 if (Current
- StringPtr
>= Length
) {
3646 Current
= StringPtr
;
3647 PkgHeader
= (EFI_HII_STRING_PACKAGE_HDR
*) StringPtr
;
3652 Current
+= PkgHeader
->HdrSize
;
3654 // Find the string block according the stringId.
3656 Status
= FindStringBlock(Current
, StringId
, &NameOffset
, &BlockType
);
3657 if (Status
!= EFI_SUCCESS
) {
3663 // Get varstore name according the string type.
3665 switch (BlockType
) {
3666 case EFI_HII_SIBT_STRING_SCSU
:
3667 case EFI_HII_SIBT_STRING_SCSU_FONT
:
3668 case EFI_HII_SIBT_STRINGS_SCSU
:
3669 case EFI_HII_SIBT_STRINGS_SCSU_FONT
:
3670 StringName
= (CHAR8
*)(Current
+ NameOffset
);
3671 VarStoreName
= new CHAR8
[strlen(StringName
) + 1];
3672 strcpy (VarStoreName
, StringName
);
3674 case EFI_HII_SIBT_STRING_UCS2
:
3675 case EFI_HII_SIBT_STRING_UCS2_FONT
:
3676 case EFI_HII_SIBT_STRINGS_UCS2
:
3677 case EFI_HII_SIBT_STRINGS_UCS2_FONT
:
3678 UnicodeString
= (CHAR16
*)(Current
+ NameOffset
);
3679 Length
= GetUnicodeStringTextSize ((UINT8
*)UnicodeString
) ;
3680 DestTmp
= new CHAR8
[Length
/ 2 + 1];
3681 VarStoreName
= DestTmp
;
3682 while (*UnicodeString
!= '\0') {
3683 *(DestTmp
++) = (CHAR8
) *(UnicodeString
++);
3693 return VarStoreName
;
3697 CVfrStringDB::FindStringBlock (
3698 IN UINT8
*StringData
,
3699 IN EFI_STRING_ID StringId
,
3700 OUT UINT32
*StringTextOffset
,
3701 OUT UINT8
*BlockType
3705 EFI_STRING_ID CurrentStringId
;
3708 UINT8
*StringTextPtr
;
3713 EFI_HII_SIBT_EXT2_BLOCK Ext2
;
3717 CurrentStringId
= 1;
3720 // Parse the string blocks to get the string text and font.
3722 BlockHdr
= StringData
;
3725 while (*BlockHdr
!= EFI_HII_SIBT_END
) {
3726 switch (*BlockHdr
) {
3727 case EFI_HII_SIBT_STRING_SCSU
:
3728 Offset
= sizeof (EFI_HII_STRING_BLOCK
);
3729 StringTextPtr
= BlockHdr
+ Offset
;
3730 BlockSize
+= Offset
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3734 case EFI_HII_SIBT_STRING_SCSU_FONT
:
3735 Offset
= sizeof (EFI_HII_SIBT_STRING_SCSU_FONT_BLOCK
) - sizeof (UINT8
);
3736 StringTextPtr
= BlockHdr
+ Offset
;
3737 BlockSize
+= Offset
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3741 case EFI_HII_SIBT_STRINGS_SCSU
:
3742 memcpy (&StringCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3743 StringTextPtr
= BlockHdr
+ sizeof (EFI_HII_SIBT_STRINGS_SCSU_BLOCK
) - sizeof (UINT8
);
3744 BlockSize
+= StringTextPtr
- BlockHdr
;
3746 for (Index
= 0; Index
< StringCount
; Index
++) {
3747 BlockSize
+= strlen ((CHAR8
*) StringTextPtr
) + 1;
3748 if (CurrentStringId
== StringId
) {
3749 *BlockType
= *BlockHdr
;
3750 *StringTextOffset
= StringTextPtr
- StringData
;
3753 StringTextPtr
= StringTextPtr
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3758 case EFI_HII_SIBT_STRINGS_SCSU_FONT
:
3761 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3764 StringTextPtr
= BlockHdr
+ sizeof (EFI_HII_SIBT_STRINGS_SCSU_FONT_BLOCK
) - sizeof (UINT8
);
3765 BlockSize
+= StringTextPtr
- BlockHdr
;
3767 for (Index
= 0; Index
< StringCount
; Index
++) {
3768 BlockSize
+= strlen ((CHAR8
*) StringTextPtr
) + 1;
3769 if (CurrentStringId
== StringId
) {
3770 *BlockType
= *BlockHdr
;
3771 *StringTextOffset
= StringTextPtr
- StringData
;
3774 StringTextPtr
= StringTextPtr
+ strlen ((CHAR8
*) StringTextPtr
) + 1;
3779 case EFI_HII_SIBT_STRING_UCS2
:
3780 Offset
= sizeof (EFI_HII_STRING_BLOCK
);
3781 StringTextPtr
= BlockHdr
+ Offset
;
3783 // Use StringSize to store the size of the specified string, including the NULL
3786 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3787 BlockSize
+= Offset
+ StringSize
;
3791 case EFI_HII_SIBT_STRING_UCS2_FONT
:
3792 Offset
= sizeof (EFI_HII_SIBT_STRING_UCS2_FONT_BLOCK
) - sizeof (CHAR16
);
3793 StringTextPtr
= BlockHdr
+ Offset
;
3795 // Use StrSize to store the size of the specified string, including the NULL
3798 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3799 BlockSize
+= Offset
+ StringSize
;
3803 case EFI_HII_SIBT_STRINGS_UCS2
:
3804 Offset
= sizeof (EFI_HII_SIBT_STRINGS_UCS2_BLOCK
) - sizeof (CHAR16
);
3805 StringTextPtr
= BlockHdr
+ Offset
;
3806 BlockSize
+= Offset
;
3807 memcpy (&StringCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3808 for (Index
= 0; Index
< StringCount
; Index
++) {
3809 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3810 BlockSize
+= StringSize
;
3811 if (CurrentStringId
== StringId
) {
3812 *BlockType
= *BlockHdr
;
3813 *StringTextOffset
= StringTextPtr
- StringData
;
3816 StringTextPtr
= StringTextPtr
+ StringSize
;
3821 case EFI_HII_SIBT_STRINGS_UCS2_FONT
:
3822 Offset
= sizeof (EFI_HII_SIBT_STRINGS_UCS2_FONT_BLOCK
) - sizeof (CHAR16
);
3823 StringTextPtr
= BlockHdr
+ Offset
;
3824 BlockSize
+= Offset
;
3827 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3830 for (Index
= 0; Index
< StringCount
; Index
++) {
3831 StringSize
= GetUnicodeStringTextSize (StringTextPtr
);
3832 BlockSize
+= StringSize
;
3833 if (CurrentStringId
== StringId
) {
3834 *BlockType
= *BlockHdr
;
3835 *StringTextOffset
= StringTextPtr
- StringData
;
3838 StringTextPtr
= StringTextPtr
+ StringSize
;
3843 case EFI_HII_SIBT_DUPLICATE
:
3844 if (CurrentStringId
== StringId
) {
3846 // Incoming StringId is an id of a duplicate string block.
3847 // Update the StringId to be the previous string block.
3848 // Go back to the header of string block to search.
3852 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
),
3853 sizeof (EFI_STRING_ID
)
3855 CurrentStringId
= 1;
3858 BlockSize
+= sizeof (EFI_HII_SIBT_DUPLICATE_BLOCK
);
3863 case EFI_HII_SIBT_SKIP1
:
3864 SkipCount
= (UINT16
) (*(BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
)));
3865 CurrentStringId
= (UINT16
) (CurrentStringId
+ SkipCount
);
3866 BlockSize
+= sizeof (EFI_HII_SIBT_SKIP1_BLOCK
);
3869 case EFI_HII_SIBT_SKIP2
:
3870 memcpy (&SkipCount
, BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
), sizeof (UINT16
));
3871 CurrentStringId
= (UINT16
) (CurrentStringId
+ SkipCount
);
3872 BlockSize
+= sizeof (EFI_HII_SIBT_SKIP2_BLOCK
);
3875 case EFI_HII_SIBT_EXT1
:
3878 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3881 BlockSize
+= Length8
;
3884 case EFI_HII_SIBT_EXT2
:
3885 memcpy (&Ext2
, BlockHdr
, sizeof (EFI_HII_SIBT_EXT2_BLOCK
));
3886 BlockSize
+= Ext2
.Length
;
3889 case EFI_HII_SIBT_EXT4
:
3892 BlockHdr
+ sizeof (EFI_HII_STRING_BLOCK
) + sizeof (UINT8
),
3896 BlockSize
+= Length32
;
3903 if (StringId
> 0 && StringId
!= (EFI_STRING_ID
)(-1)) {
3904 *StringTextOffset
= BlockHdr
- StringData
+ Offset
;
3905 *BlockType
= *BlockHdr
;
3907 if (StringId
== CurrentStringId
- 1) {
3909 // if only one skip item, return EFI_NOT_FOUND.
3911 if(*BlockType
== EFI_HII_SIBT_SKIP2
|| *BlockType
== EFI_HII_SIBT_SKIP1
) {
3912 return EFI_NOT_FOUND
;
3918 if (StringId
< CurrentStringId
- 1) {
3919 return EFI_NOT_FOUND
;
3922 BlockHdr
= StringData
+ BlockSize
;
3925 return EFI_NOT_FOUND
;
3929 CVfrStringDB::GetUnicodeStringTextSize (
3936 StringSize
= sizeof (CHAR16
);
3937 StringPtr
= (UINT16
*)StringSrc
;
3938 while (*StringPtr
++ != L
'\0') {
3939 StringSize
+= sizeof (CHAR16
);
3945 BOOLEAN VfrCompatibleMode
= FALSE
;
3947 CVfrVarDataTypeDB gCVfrVarDataTypeDB
;
3948 CVfrDefaultStore gCVfrDefaultStore
;
3949 CVfrDataStorage gCVfrDataStorage
;