2 Var Check Hii bin generation.
4 Copyright (c) 2015, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include "VarCheckHiiGen.h"
17 LIST_ENTRY mVarCheckHiiList
= INITIALIZE_LIST_HEAD_VARIABLE (mVarCheckHiiList
);
19 #define VAR_CHECK_HII_VARIABLE_NODE_SIGNATURE SIGNATURE_32 ('V', 'C', 'H', 'V')
24 VAR_CHECK_HII_VARIABLE_HEADER
*HiiVariable
;
25 EFI_VARSTORE_ID VarStoreId
;
27 VAR_CHECK_HII_QUESTION_HEADER
**HiiQuestionArray
;
28 } VAR_CHECK_HII_VARIABLE_NODE
;
30 #define VAR_CHECK_HII_VARIABLE_FROM_LINK(a) CR (a, VAR_CHECK_HII_VARIABLE_NODE, Link, VAR_CHECK_HII_VARIABLE_NODE_SIGNATURE)
32 CHAR16
*mVarName
= NULL
;
33 UINTN mMaxVarNameSize
= 0;
36 GLOBAL_REMOVE_IF_UNREFERENCED VAR_CHECK_HII_OPCODE_STRING mIfrOpCodeStringTable
[] = {
37 {EFI_IFR_VARSTORE_OP
, "EFI_IFR_VARSTORE_OP"},
38 {EFI_IFR_VARSTORE_EFI_OP
, "EFI_IFR_VARSTORE_EFI_OP"},
39 {EFI_IFR_ONE_OF_OP
, "EFI_IFR_ONE_OF_OP"},
40 {EFI_IFR_CHECKBOX_OP
, "EFI_IFR_CHECKBOX_OP"},
41 {EFI_IFR_NUMERIC_OP
, "EFI_IFR_NUMERIC_OP"},
42 {EFI_IFR_ORDERED_LIST_OP
, "EFI_IFR_ORDERED_LIST_OP"},
43 {EFI_IFR_ONE_OF_OPTION_OP
, "EFI_IFR_ONE_OF_OPTION_OP"},
49 @param[in] IfrOpCode Ifr OpCode.
51 @return Pointer to string.
60 for (Index
= 0; Index
< sizeof (mIfrOpCodeStringTable
) / sizeof (mIfrOpCodeStringTable
[0]); Index
++) {
61 if (mIfrOpCodeStringTable
[Index
].HiiOpCode
== IfrOpCode
) {
62 return mIfrOpCodeStringTable
[Index
].HiiOpCodeStr
;
66 return "<UnknownIfrOpCode>";
69 GLOBAL_REMOVE_IF_UNREFERENCED VAR_CHECK_HII_PACKAGE_TYPE_STRING mPackageTypeStringTable
[] = {
70 {EFI_HII_PACKAGE_TYPE_ALL
, "EFI_HII_PACKAGE_TYPE_ALL"},
71 {EFI_HII_PACKAGE_TYPE_GUID
, "EFI_HII_PACKAGE_TYPE_GUID"},
72 {EFI_HII_PACKAGE_FORMS
, "EFI_HII_PACKAGE_FORMS"},
73 {EFI_HII_PACKAGE_STRINGS
, "EFI_HII_PACKAGE_STRINGS"},
74 {EFI_HII_PACKAGE_FONTS
, "EFI_HII_PACKAGE_FONTS"},
75 {EFI_HII_PACKAGE_IMAGES
, "EFI_HII_PACKAGE_IMAGES"},
76 {EFI_HII_PACKAGE_SIMPLE_FONTS
, "EFI_HII_PACKAGE_SIMPLE_FONTS"},
77 {EFI_HII_PACKAGE_DEVICE_PATH
, "EFI_HII_PACKAGE_DEVICE_PATH"},
78 {EFI_HII_PACKAGE_KEYBOARD_LAYOUT
, "EFI_HII_PACKAGE_KEYBOARD_LAYOUT"},
79 {EFI_HII_PACKAGE_ANIMATIONS
, "EFI_HII_PACKAGE_ANIMATIONS"},
80 {EFI_HII_PACKAGE_END
, "EFI_HII_PACKAGE_END"},
81 {EFI_HII_PACKAGE_TYPE_SYSTEM_BEGIN
, "EFI_HII_PACKAGE_TYPE_SYSTEM_BEGIN"},
82 {EFI_HII_PACKAGE_TYPE_SYSTEM_END
, "EFI_HII_PACKAGE_TYPE_SYSTEM_END"},
86 Hii Package type to string.
88 @param[in] PackageType Package Type
90 @return Pointer to string.
99 for (Index
= 0; Index
< sizeof (mPackageTypeStringTable
) / sizeof (mPackageTypeStringTable
[0]); Index
++) {
100 if (mPackageTypeStringTable
[Index
].PackageType
== PackageType
) {
101 return mPackageTypeStringTable
[Index
].PackageTypeStr
;
105 return "<UnknownPackageType>";
111 @param[in] HiiPackage Pointer to Hii Package.
119 EFI_HII_PACKAGE_HEADER
*HiiPackageHeader
;
120 EFI_IFR_OP_HEADER
*IfrOpCodeHeader
;
121 EFI_IFR_VARSTORE
*IfrVarStore
;
122 EFI_IFR_VARSTORE_EFI
*IfrEfiVarStore
;
124 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) HiiPackage
;
126 DEBUG ((EFI_D_INFO
, " HiiPackageHeader->Type - 0x%02x (%a)\n", HiiPackageHeader
->Type
, HiiPackageTypeToStr ((UINT8
) HiiPackageHeader
->Type
)));
127 DEBUG ((EFI_D_INFO
, " HiiPackageHeader->Length - 0x%06x\n", HiiPackageHeader
->Length
));
129 switch (HiiPackageHeader
->Type
) {
130 case EFI_HII_PACKAGE_FORMS
:
131 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) (HiiPackageHeader
+ 1);
133 while ((UINTN
) IfrOpCodeHeader
< ((UINTN
) HiiPackageHeader
+ HiiPackageHeader
->Length
)) {
134 switch (IfrOpCodeHeader
->OpCode
) {
135 case EFI_IFR_VARSTORE_OP
:
136 IfrVarStore
= (EFI_IFR_VARSTORE
*) IfrOpCodeHeader
;
137 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->OpCode - 0x%02x (%a)\n", IfrOpCodeHeader
->OpCode
, IfrOpCodeToStr (IfrOpCodeHeader
->OpCode
)));
138 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Length - 0x%02x\n", IfrOpCodeHeader
->Length
));
139 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Scope - 0x%02x\n", IfrOpCodeHeader
->Scope
));
140 DEBUG ((EFI_D_INFO
, " Guid - %g\n", &IfrVarStore
->Guid
));
141 DEBUG ((EFI_D_INFO
, " VarStoreId - 0x%04x\n", IfrVarStore
->VarStoreId
));
142 DEBUG ((EFI_D_INFO
, " Size - 0x%04x\n", IfrVarStore
->Size
));
143 DEBUG ((EFI_D_INFO
, " Name - %a\n", IfrVarStore
->Name
));
146 case EFI_IFR_VARSTORE_EFI_OP
:
147 IfrEfiVarStore
= (EFI_IFR_VARSTORE_EFI
*) IfrOpCodeHeader
;
148 if (IfrEfiVarStore
->Header
.Length
>= sizeof (EFI_IFR_VARSTORE_EFI
)) {
149 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->OpCode - 0x%02x (%a)\n", IfrOpCodeHeader
->OpCode
, IfrOpCodeToStr (IfrOpCodeHeader
->OpCode
)));
150 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Length - 0x02%x\n", IfrOpCodeHeader
->Length
));
151 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Scope - 0x02%x\n", IfrOpCodeHeader
->Scope
));
152 DEBUG ((EFI_D_INFO
, " Guid - %g\n", &IfrEfiVarStore
->Guid
));
153 DEBUG ((EFI_D_INFO
, " VarStoreId - 0x%04x\n", IfrEfiVarStore
->VarStoreId
));
154 DEBUG ((EFI_D_INFO
, " Size - 0x%04x\n", IfrEfiVarStore
->Size
));
155 DEBUG ((EFI_D_INFO
, " Attributes - 0x%08x\n", IfrEfiVarStore
->Attributes
));
156 DEBUG ((EFI_D_INFO
, " Name - %a\n", IfrEfiVarStore
->Name
));
160 case EFI_IFR_ONE_OF_OP
:
161 case EFI_IFR_CHECKBOX_OP
:
162 case EFI_IFR_NUMERIC_OP
:
163 case EFI_IFR_ORDERED_LIST_OP
:
164 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->OpCode - 0x%02x (%a)\n", IfrOpCodeHeader
->OpCode
, IfrOpCodeToStr (IfrOpCodeHeader
->OpCode
)));
165 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Length - 0x02%x\n", IfrOpCodeHeader
->Length
));
166 DEBUG ((EFI_D_INFO
, " IfrOpCodeHeader->Scope - 0x02%x\n", IfrOpCodeHeader
->Scope
));
167 DEBUG ((EFI_D_INFO
, " Prompt - 0x%04x\n", ((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.Header
.Prompt
));
168 DEBUG ((EFI_D_INFO
, " Help - 0x%04x\n", ((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.Header
.Help
));
169 DEBUG ((EFI_D_INFO
, " QuestionId - 0x%04x\n", ((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.QuestionId
));
170 DEBUG ((EFI_D_INFO
, " VarStoreId - 0x%04x\n", ((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.VarStoreId
));
171 DEBUG ((EFI_D_INFO
, " VarStoreInfo - 0x%04x\n", ((EFI_IFR_ONE_OF
* )IfrOpCodeHeader
)->Question
.VarStoreInfo
.VarOffset
));
173 EFI_IFR_ONE_OF
*IfrOneOf
;
174 EFI_IFR_CHECKBOX
*IfrCheckBox
;
175 EFI_IFR_NUMERIC
*IfrNumeric
;
176 EFI_IFR_ORDERED_LIST
*IfrOrderedList
;
178 switch (IfrOpCodeHeader
->OpCode
) {
179 case EFI_IFR_ONE_OF_OP
:
180 IfrOneOf
= (EFI_IFR_ONE_OF
*) IfrOpCodeHeader
;
181 DEBUG ((EFI_D_INFO
, " Flags - 0x%02x\n", IfrOneOf
->Flags
));
182 switch (IfrOneOf
->Flags
& EFI_IFR_NUMERIC_SIZE
) {
183 case EFI_IFR_NUMERIC_SIZE_1
:
184 DEBUG ((EFI_D_INFO
, " MinValue - 0x%02x\n", IfrOneOf
->data
.u8
.MinValue
));
185 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%02x\n", IfrOneOf
->data
.u8
.MaxValue
));
186 DEBUG ((EFI_D_INFO
, " Step - 0x%02x\n", IfrOneOf
->data
.u8
.Step
));
188 case EFI_IFR_NUMERIC_SIZE_2
:
189 DEBUG ((EFI_D_INFO
, " MinValue - 0x%04x\n", IfrOneOf
->data
.u16
.MinValue
));
190 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%04x\n", IfrOneOf
->data
.u16
.MaxValue
));
191 DEBUG ((EFI_D_INFO
, " Step - 0x%04x\n", IfrOneOf
->data
.u16
.Step
));
193 case EFI_IFR_NUMERIC_SIZE_4
:
194 DEBUG ((EFI_D_INFO
, " MinValue - 0x%08x\n", IfrOneOf
->data
.u32
.MinValue
));
195 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%08x\n", IfrOneOf
->data
.u32
.MaxValue
));
196 DEBUG ((EFI_D_INFO
, " Step - 0x%08x\n", IfrOneOf
->data
.u32
.Step
));
198 case EFI_IFR_NUMERIC_SIZE_8
:
199 DEBUG ((EFI_D_INFO
, " MinValue - 0x%016lx\n", IfrOneOf
->data
.u64
.MinValue
));
200 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%016lx\n", IfrOneOf
->data
.u64
.MaxValue
));
201 DEBUG ((EFI_D_INFO
, " Step - 0x%016lx\n", IfrOneOf
->data
.u64
.Step
));
205 case EFI_IFR_CHECKBOX_OP
:
206 IfrCheckBox
= (EFI_IFR_CHECKBOX
*) IfrOpCodeHeader
;
207 DEBUG ((EFI_D_INFO
, " Flags - 0x%02x\n", IfrCheckBox
->Flags
));
209 case EFI_IFR_NUMERIC_OP
:
210 IfrNumeric
= (EFI_IFR_NUMERIC
*) IfrOpCodeHeader
;
211 DEBUG ((EFI_D_INFO
, " Flags - 0x%02x\n", IfrNumeric
->Flags
));
212 switch (IfrNumeric
->Flags
& EFI_IFR_NUMERIC_SIZE
) {
213 case EFI_IFR_NUMERIC_SIZE_1
:
214 DEBUG ((EFI_D_INFO
, " MinValue - 0x%02x\n", IfrNumeric
->data
.u8
.MinValue
));
215 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%02x\n", IfrNumeric
->data
.u8
.MaxValue
));
216 DEBUG ((EFI_D_INFO
, " Step - 0x%02x\n", IfrNumeric
->data
.u8
.Step
));
218 case EFI_IFR_NUMERIC_SIZE_2
:
219 DEBUG ((EFI_D_INFO
, " MinValue - 0x%04x\n", IfrNumeric
->data
.u16
.MinValue
));
220 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%04x\n", IfrNumeric
->data
.u16
.MaxValue
));
221 DEBUG ((EFI_D_INFO
, " Step - 0x%04x\n", IfrNumeric
->data
.u16
.Step
));
223 case EFI_IFR_NUMERIC_SIZE_4
:
224 DEBUG ((EFI_D_INFO
, " MinValue - 0x%08x\n", IfrNumeric
->data
.u32
.MinValue
));
225 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%08x\n", IfrNumeric
->data
.u32
.MaxValue
));
226 DEBUG ((EFI_D_INFO
, " Step - 0x%08x\n", IfrNumeric
->data
.u32
.Step
));
228 case EFI_IFR_NUMERIC_SIZE_8
:
229 DEBUG ((EFI_D_INFO
, " MinValue - 0x%016lx\n", IfrNumeric
->data
.u64
.MinValue
));
230 DEBUG ((EFI_D_INFO
, " MaxValue - 0x%016lx\n", IfrNumeric
->data
.u64
.MaxValue
));
231 DEBUG ((EFI_D_INFO
, " Step - 0x%016lx\n", IfrNumeric
->data
.u64
.Step
));
235 case EFI_IFR_ORDERED_LIST_OP
:
236 IfrOrderedList
= (EFI_IFR_ORDERED_LIST
*) IfrOpCodeHeader
;
237 DEBUG ((EFI_D_INFO
, " MaxContainers - 0x%02x\n", IfrOrderedList
->MaxContainers
));
238 DEBUG ((EFI_D_INFO
, " Flags - 0x%02x\n", IfrOrderedList
->Flags
));
244 if (IfrOpCodeHeader
->Scope
!= 0) {
246 EFI_IFR_ONE_OF_OPTION
*IfrOneOfOption
;
248 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
251 switch (IfrOpCodeHeader
->OpCode
) {
252 case EFI_IFR_ONE_OF_OPTION_OP
:
253 IfrOneOfOption
= (EFI_IFR_ONE_OF_OPTION
*)IfrOpCodeHeader
;
254 DEBUG ((EFI_D_INFO
, "!!!! IfrOpCodeHeader->OpCode - 0x%02x (%a)\n", (UINTN
)IfrOpCodeHeader
->OpCode
, IfrOpCodeToStr (IfrOpCodeHeader
->OpCode
)));
255 DEBUG ((EFI_D_INFO
, "!!!! IfrOpCodeHeader->Scope - 0x%02x\n", IfrOpCodeHeader
->Scope
));
256 DEBUG ((EFI_D_INFO
, "!!!! Option - 0x%04x\n", IfrOneOfOption
->Option
));
257 DEBUG ((EFI_D_INFO
, "!!!! Flags - 0x%02x\n", IfrOneOfOption
->Flags
));
258 DEBUG ((EFI_D_INFO
, "!!!! Type - 0x%02x\n", IfrOneOfOption
->Type
));
259 switch (IfrOneOfOption
->Type
) {
260 case EFI_IFR_TYPE_NUM_SIZE_8
:
261 DEBUG ((EFI_D_INFO
, "!!!! Value - 0x%02x\n", IfrOneOfOption
->Value
.u8
));
263 case EFI_IFR_TYPE_NUM_SIZE_16
:
264 DEBUG ((EFI_D_INFO
, "!!!! Value - 0x%04x\n", IfrOneOfOption
->Value
.u16
));
266 case EFI_IFR_TYPE_NUM_SIZE_32
:
267 DEBUG ((EFI_D_INFO
, "!!!! Value - 0x%08x\n", IfrOneOfOption
->Value
.u32
));
269 case EFI_IFR_TYPE_NUM_SIZE_64
:
270 DEBUG ((EFI_D_INFO
, "!!!! Value - 0x%016lx\n", IfrOneOfOption
->Value
.u64
));
272 case EFI_IFR_TYPE_BOOLEAN
:
273 DEBUG ((EFI_D_INFO
, "!!!! Value - 0x%02x\n", IfrOneOfOption
->Value
.b
));
281 if (IfrOpCodeHeader
->OpCode
== EFI_IFR_END_OP
) {
287 } else if (IfrOpCodeHeader
->Scope
!= 0) {
290 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
297 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
308 @param[in] HiiDatabase Pointer to Hii Database.
309 @param[in] HiiDatabaseSize Hii Database size.
314 IN VOID
*HiiDatabase
,
315 IN UINTN HiiDatabaseSize
318 EFI_HII_PACKAGE_LIST_HEADER
*HiiPackageListHeader
;
319 EFI_HII_PACKAGE_HEADER
*HiiPackageHeader
;
321 DEBUG ((EFI_D_INFO
, "HiiDatabaseSize - 0x%x\n", HiiDatabaseSize
));
322 HiiPackageListHeader
= (EFI_HII_PACKAGE_LIST_HEADER
*) HiiDatabase
;
324 while ((UINTN
) HiiPackageListHeader
< ((UINTN
) HiiDatabase
+ HiiDatabaseSize
)) {
325 DEBUG ((EFI_D_INFO
, "HiiPackageListHeader->PackageListGuid - %g\n", &HiiPackageListHeader
->PackageListGuid
));
326 DEBUG ((EFI_D_INFO
, "HiiPackageListHeader->PackageLength - 0x%x\n", (UINTN
)HiiPackageListHeader
->PackageLength
));
327 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*)(HiiPackageListHeader
+ 1);
329 while ((UINTN
) HiiPackageHeader
< (UINTN
) HiiPackageListHeader
+ HiiPackageListHeader
->PackageLength
) {
331 DumpHiiPackage (HiiPackageHeader
);
333 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) ((UINTN
) HiiPackageHeader
+ HiiPackageHeader
->Length
);
336 HiiPackageListHeader
= (EFI_HII_PACKAGE_LIST_HEADER
*) ((UINTN
) HiiPackageListHeader
+ HiiPackageListHeader
->PackageLength
);
344 Allocates a buffer of a certain pool type.
346 Allocates the number bytes specified by AllocationSize of a certain pool type and returns a
347 pointer to the allocated buffer. If AllocationSize is 0, then a valid buffer of 0 size is
348 returned. If there is not enough memory remaining to satisfy the request, then NULL is returned.
350 @param MemoryType The type of memory to allocate.
351 @param AllocationSize The number of bytes to allocate.
353 @return A pointer to the allocated buffer or NULL if allocation fails.
357 InternalVarCheckAllocatePool (
358 IN EFI_MEMORY_TYPE MemoryType
,
359 IN UINTN AllocationSize
365 Status
= gBS
->AllocatePool (MemoryType
, AllocationSize
, &Memory
);
366 if (EFI_ERROR (Status
)) {
373 Allocates and zeros a buffer of type EfiBootServicesData.
375 Allocates the number bytes specified by AllocationSize of type EfiBootServicesData, clears the
376 buffer with zeros, and returns a pointer to the allocated buffer. If AllocationSize is 0, then a
377 valid buffer of 0 size is returned. If there is not enough memory remaining to satisfy the
378 request, then NULL is returned.
380 @param AllocationSize The number of bytes to allocate and zero.
382 @return A pointer to the allocated buffer or NULL if allocation fails.
386 InternalVarCheckAllocateZeroPool (
387 IN UINTN AllocationSize
392 Memory
= InternalVarCheckAllocatePool (EfiBootServicesData
, AllocationSize
);
393 if (Memory
!= NULL
) {
394 Memory
= ZeroMem (Memory
, AllocationSize
);
400 Frees a buffer that was previously allocated with one of the pool allocation functions in the
401 Memory Allocation Library.
403 Frees the buffer specified by Buffer. Buffer must have been allocated on a previous call to the
404 pool allocation services of the Memory Allocation Library. If it is not possible to free pool
405 resources, then this function will perform no actions.
407 If Buffer was not allocated with a pool allocation function in the Memory Allocation Library,
410 @param Buffer The pointer to the buffer to free.
415 InternalVarCheckFreePool (
421 Status
= gBS
->FreePool (Buffer
);
422 ASSERT_EFI_ERROR (Status
);
426 Reallocates a buffer of type EfiBootServicesData.
428 Allocates and zeros the number bytes specified by NewSize from memory of type
429 EfiBootServicesData. If OldBuffer is not NULL, then the smaller of OldSize and
430 NewSize bytes are copied from OldBuffer to the newly allocated buffer, and
431 OldBuffer is freed. A pointer to the newly allocated buffer is returned.
432 If NewSize is 0, then a valid buffer of 0 size is returned. If there is not
433 enough memory remaining to satisfy the request, then NULL is returned.
435 If the allocation of the new buffer is successful and the smaller of NewSize and OldSize
436 is greater than (MAX_ADDRESS - OldBuffer + 1), then ASSERT().
438 @param OldSize The size, in bytes, of OldBuffer.
439 @param NewSize The size, in bytes, of the buffer to reallocate.
440 @param OldBuffer The buffer to copy to the allocated buffer. This is an optional
441 parameter that may be NULL.
443 @return A pointer to the allocated buffer or NULL if allocation fails.
447 InternalVarCheckReallocatePool (
450 IN VOID
*OldBuffer OPTIONAL
455 NewBuffer
= InternalVarCheckAllocateZeroPool (NewSize
);
456 if (NewBuffer
!= NULL
&& OldBuffer
!= NULL
) {
457 CopyMem (NewBuffer
, OldBuffer
, MIN (OldSize
, NewSize
));
458 InternalVarCheckFreePool (OldBuffer
);
466 @param[in, out] HiiVariableNode Pointer to Hii Variable node.
467 @param[in] HiiQuestion Pointer to Hii Question.
468 @param[in] FromFv Hii Question from FV.
473 IN OUT VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
,
474 IN VAR_CHECK_HII_QUESTION_HEADER
*HiiQuestion
,
478 VAR_CHECK_HII_QUESTION_HEADER
*HiiQuestion1
;
479 VAR_CHECK_HII_QUESTION_HEADER
*HiiQuestion2
;
480 VAR_CHECK_HII_QUESTION_HEADER
*NewHiiQuestion
;
493 // Hii Question from Hii Database has high priority.
494 // Do not to merge Hii Question from Fv to Hii Question from Hii Database.
497 InternalVarCheckFreePool (HiiQuestion
);
501 HiiQuestion1
= HiiVariableNode
->HiiQuestionArray
[HiiQuestion
->VarOffset
];
502 HiiQuestion2
= HiiQuestion
;
504 ASSERT ((HiiQuestion1
->OpCode
== HiiQuestion2
->OpCode
) && (HiiQuestion1
->StorageWidth
== HiiQuestion2
->StorageWidth
));
506 switch (HiiQuestion1
->OpCode
) {
507 case EFI_IFR_ONE_OF_OP
:
508 DEBUG ((EFI_D_INFO
, "MergeHiiQuestion - EFI_IFR_ONE_OF_OP VarOffset = 0x%04x\n", HiiQuestion1
->VarOffset
));
510 // Get the length of Hii Question 1.
512 NewLength
= HiiQuestion1
->Length
;
515 // Check if the one of options in Hii Question 2 have been in Hii Question 1.
517 Ptr2
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ONEOF
*) HiiQuestion2
+ 1);
518 while ((UINTN
) Ptr2
< (UINTN
) HiiQuestion2
+ HiiQuestion2
->Length
) {
520 CopyMem (&OneValue2
, Ptr2
, HiiQuestion2
->StorageWidth
);
522 Ptr1
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ONEOF
*) HiiQuestion1
+ 1);
523 while ((UINTN
) Ptr1
< (UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
) {
525 CopyMem (&OneValue1
, Ptr1
, HiiQuestion1
->StorageWidth
);
526 if (OneValue2
== OneValue1
) {
532 Ptr1
+= HiiQuestion1
->StorageWidth
;
534 if ((UINTN
) Ptr1
>= ((UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
)) {
538 NewLength
= (UINT8
) (NewLength
+ HiiQuestion1
->StorageWidth
);
540 Ptr2
+= HiiQuestion2
->StorageWidth
;
543 if (NewLength
> HiiQuestion1
->Length
) {
545 // Merge the one of options of Hii Question 2 and Hii Question 1.
547 NewHiiQuestion
= InternalVarCheckAllocateZeroPool (NewLength
);
548 ASSERT (NewHiiQuestion
!= NULL
);
549 CopyMem (NewHiiQuestion
, HiiQuestion1
, HiiQuestion1
->Length
);
551 // Use the new length.
553 NewHiiQuestion
->Length
= NewLength
;
554 Ptr
= (UINT8
*) NewHiiQuestion
+ HiiQuestion1
->Length
;
556 Ptr2
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ONEOF
*) HiiQuestion2
+ 1);
557 while ((UINTN
) Ptr2
< (UINTN
) HiiQuestion2
+ HiiQuestion2
->Length
) {
559 CopyMem (&OneValue2
, Ptr2
, HiiQuestion2
->StorageWidth
);
561 Ptr1
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ONEOF
*) HiiQuestion1
+ 1);
562 while ((UINTN
) Ptr1
< (UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
) {
564 CopyMem (&OneValue1
, Ptr1
, HiiQuestion1
->StorageWidth
);
565 if (OneValue2
== OneValue1
) {
571 Ptr1
+= HiiQuestion1
->StorageWidth
;
573 if ((UINTN
) Ptr1
>= ((UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
)) {
577 CopyMem (Ptr
, &OneValue2
, HiiQuestion1
->StorageWidth
);
578 Ptr
+= HiiQuestion1
->StorageWidth
;
580 Ptr2
+= HiiQuestion2
->StorageWidth
;
583 HiiVariableNode
->HiiQuestionArray
[HiiQuestion1
->VarOffset
] = NewHiiQuestion
;
584 InternalVarCheckFreePool (HiiQuestion1
);
588 case EFI_IFR_CHECKBOX_OP
:
589 DEBUG ((EFI_D_INFO
, "MergeHiiQuestion - EFI_IFR_CHECKBOX_OP VarOffset = 0x%04x\n", HiiQuestion1
->VarOffset
));
592 case EFI_IFR_NUMERIC_OP
:
593 DEBUG ((EFI_D_INFO
, "MergeHiiQuestion - EFI_IFR_NUMERIC_OP VarOffset = 0x%04x\n", HiiQuestion1
->VarOffset
));
595 // Get minimum and maximum of Hii Question 1.
599 Ptr
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_NUMERIC
*) HiiQuestion1
+ 1);
600 CopyMem (&Minimum1
, Ptr
, HiiQuestion1
->StorageWidth
);
601 Ptr
+= HiiQuestion1
->StorageWidth
;
602 CopyMem (&Maximum1
, Ptr
, HiiQuestion1
->StorageWidth
);
605 // Get minimum and maximum of Hii Question 2.
609 Ptr
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_NUMERIC
*) HiiQuestion2
+ 1);
610 CopyMem (&Minimum2
, Ptr
, HiiQuestion2
->StorageWidth
);
611 Ptr
+= HiiQuestion2
->StorageWidth
;
612 CopyMem (&Maximum2
, Ptr
, HiiQuestion2
->StorageWidth
);
617 Ptr
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_NUMERIC
*) HiiQuestion1
+ 1);
618 if (Minimum2
< Minimum1
) {
620 CopyMem (Ptr
, &Minimum1
, HiiQuestion1
->StorageWidth
);
625 Ptr
+= HiiQuestion1
->StorageWidth
;
626 if (Maximum2
> Maximum1
) {
628 CopyMem (Ptr
, &Maximum1
, HiiQuestion1
->StorageWidth
);
632 case EFI_IFR_ORDERED_LIST_OP
:
633 DEBUG ((EFI_D_INFO
, "MergeHiiQuestion - EFI_IFR_ORDERED_LIST_OP VarOffset = 0x%04x\n", HiiQuestion1
->VarOffset
));
635 // Get the length of Hii Question 1.
637 NewLength
= HiiQuestion1
->Length
;
640 // Check if the one of options in Hii Question 2 have been in Hii Question 1.
642 Ptr2
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ORDEREDLIST
*) HiiQuestion2
+ 1);
643 while ((UINTN
) Ptr2
< (UINTN
) HiiQuestion2
+ HiiQuestion2
->Length
) {
645 CopyMem (&OneValue2
, Ptr2
, HiiQuestion2
->StorageWidth
);
647 Ptr1
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ORDEREDLIST
*) HiiQuestion1
+ 1);
648 while ((UINTN
) Ptr1
< (UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
) {
650 CopyMem (&OneValue1
, Ptr1
, HiiQuestion1
->StorageWidth
);
651 if (OneValue2
== OneValue1
) {
657 Ptr1
+= HiiQuestion1
->StorageWidth
;
659 if ((UINTN
) Ptr1
>= ((UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
)) {
663 NewLength
= (UINT8
) (NewLength
+ HiiQuestion1
->StorageWidth
);
665 Ptr2
+= HiiQuestion2
->StorageWidth
;
668 if (NewLength
> HiiQuestion1
->Length
) {
670 // Merge the one of options of Hii Question 2 and Hii Question 1.
672 NewHiiQuestion
= InternalVarCheckAllocateZeroPool (NewLength
);
673 ASSERT (NewHiiQuestion
!= NULL
);
674 CopyMem (NewHiiQuestion
, HiiQuestion1
, HiiQuestion1
->Length
);
676 // Use the new length.
678 NewHiiQuestion
->Length
= NewLength
;
679 Ptr
= (UINT8
*) NewHiiQuestion
+ HiiQuestion1
->Length
;
681 Ptr2
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ORDEREDLIST
*) HiiQuestion2
+ 1);
682 while ((UINTN
) Ptr2
< (UINTN
) HiiQuestion2
+ HiiQuestion2
->Length
) {
684 CopyMem (&OneValue2
, Ptr2
, HiiQuestion2
->StorageWidth
);
686 Ptr1
= (UINT8
*) ((VAR_CHECK_HII_QUESTION_ORDEREDLIST
*) HiiQuestion1
+ 1);
687 while ((UINTN
) Ptr1
< (UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
) {
689 CopyMem (&OneValue1
, Ptr1
, HiiQuestion1
->StorageWidth
);
690 if (OneValue2
== OneValue1
) {
696 Ptr1
+= HiiQuestion1
->StorageWidth
;
698 if ((UINTN
) Ptr1
>= ((UINTN
) HiiQuestion1
+ HiiQuestion1
->Length
)) {
702 CopyMem (Ptr
, &OneValue2
, HiiQuestion1
->StorageWidth
);
703 Ptr
+= HiiQuestion1
->StorageWidth
;
705 Ptr2
+= HiiQuestion2
->StorageWidth
;
708 HiiVariableNode
->HiiQuestionArray
[HiiQuestion1
->VarOffset
] = NewHiiQuestion
;
709 InternalVarCheckFreePool (HiiQuestion1
);
721 // Hii Question 2 has been merged with Hii Question 1.
723 InternalVarCheckFreePool (HiiQuestion2
);
727 Get OneOf option data.
729 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
730 @param[out] Count Pointer to option count.
731 @param[out] Width Pointer to option width.
732 @param[out] OptionBuffer Pointer to option buffer.
737 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
,
740 OUT VOID
*OptionBuffer OPTIONAL
744 EFI_IFR_ONE_OF_OPTION
*IfrOneOfOption
;
747 // Assume all OPTION has same Width.
751 if (IfrOpCodeHeader
->Scope
!= 0) {
756 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
758 switch (IfrOpCodeHeader
->OpCode
) {
759 case EFI_IFR_ONE_OF_OPTION_OP
:
760 IfrOneOfOption
= (EFI_IFR_ONE_OF_OPTION
*) IfrOpCodeHeader
;
761 switch (IfrOneOfOption
->Type
) {
762 case EFI_IFR_TYPE_NUM_SIZE_8
:
764 *Width
= sizeof (UINT8
);
765 if (OptionBuffer
!= NULL
) {
766 CopyMem (OptionBuffer
, &IfrOneOfOption
->Value
.u8
, sizeof (UINT8
));
767 OptionBuffer
= (UINT8
*) OptionBuffer
+ 1;
770 case EFI_IFR_TYPE_NUM_SIZE_16
:
772 *Width
= sizeof (UINT16
);
773 if (OptionBuffer
!= NULL
) {
774 CopyMem (OptionBuffer
, &IfrOneOfOption
->Value
.u16
, sizeof (UINT16
));
775 OptionBuffer
= (UINT16
*) OptionBuffer
+ 1;
778 case EFI_IFR_TYPE_NUM_SIZE_32
:
780 *Width
= sizeof (UINT32
);
781 if (OptionBuffer
!= NULL
) {
782 CopyMem (OptionBuffer
, &IfrOneOfOption
->Value
.u32
, sizeof (UINT32
));
783 OptionBuffer
= (UINT32
*) OptionBuffer
+ 1;
786 case EFI_IFR_TYPE_NUM_SIZE_64
:
788 *Width
= sizeof (UINT64
);
789 if (OptionBuffer
!= NULL
) {
790 CopyMem (OptionBuffer
, &IfrOneOfOption
->Value
.u64
, sizeof (UINT64
));
791 OptionBuffer
= (UINT64
*) OptionBuffer
+ 1;
794 case EFI_IFR_TYPE_BOOLEAN
:
796 *Width
= sizeof (BOOLEAN
);
797 if (OptionBuffer
!= NULL
) {
798 CopyMem (OptionBuffer
, &IfrOneOfOption
->Value
.b
, sizeof (BOOLEAN
));
799 OptionBuffer
= (BOOLEAN
*) OptionBuffer
+ 1;
811 if (IfrOpCodeHeader
->OpCode
== EFI_IFR_END_OP
) {
817 } else if (IfrOpCodeHeader
->Scope
!= 0) {
823 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
831 Parse Hii Question Oneof.
833 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
835 return Pointer to Hii Question.
838 VAR_CHECK_HII_QUESTION_HEADER
*
839 ParseHiiQuestionOneOf (
840 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
843 EFI_IFR_ONE_OF
*IfrOneOf
;
844 VAR_CHECK_HII_QUESTION_ONEOF
*OneOf
;
850 IfrOneOf
= (EFI_IFR_ONE_OF
*) IfrOpCodeHeader
;
852 Width
= (UINT8
) (1 << (IfrOneOf
->Flags
& EFI_IFR_NUMERIC_SIZE
));
854 GetOneOfOption (IfrOpCodeHeader
, &OptionCount
, &OptionWidth
, NULL
);
855 ASSERT (Width
== OptionWidth
);
857 Length
= sizeof (*OneOf
) + OptionCount
* Width
;
859 OneOf
= InternalVarCheckAllocateZeroPool (Length
);
860 ASSERT (OneOf
!= NULL
);
861 OneOf
->OpCode
= EFI_IFR_ONE_OF_OP
;
862 OneOf
->Length
= (UINT8
) Length
;
863 OneOf
->VarOffset
= IfrOneOf
->Question
.VarStoreInfo
.VarOffset
;
864 OneOf
->StorageWidth
= Width
;
866 GetOneOfOption (IfrOpCodeHeader
, &OptionCount
, &OptionWidth
, OneOf
+ 1);
868 return (VAR_CHECK_HII_QUESTION_HEADER
*) OneOf
;
872 Parse Hii Question CheckBox.
874 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
876 return Pointer to Hii Question.
879 VAR_CHECK_HII_QUESTION_HEADER
*
880 ParseHiiQuestionCheckBox (
881 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
884 EFI_IFR_CHECKBOX
*IfrCheckBox
;
885 VAR_CHECK_HII_QUESTION_CHECKBOX
*CheckBox
;
887 IfrCheckBox
= (EFI_IFR_CHECKBOX
*) IfrOpCodeHeader
;
889 CheckBox
= InternalVarCheckAllocateZeroPool (sizeof (*CheckBox
));
890 ASSERT (CheckBox
!= NULL
);
891 CheckBox
->OpCode
= EFI_IFR_CHECKBOX_OP
;
892 CheckBox
->Length
= (UINT8
) sizeof (*CheckBox
);;
893 CheckBox
->VarOffset
= IfrCheckBox
->Question
.VarStoreInfo
.VarOffset
;
894 CheckBox
->StorageWidth
= (UINT8
) sizeof (BOOLEAN
);
896 return (VAR_CHECK_HII_QUESTION_HEADER
*) CheckBox
;
900 Parse Hii Question Numeric.
902 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
904 return Pointer to Hii Question.
907 VAR_CHECK_HII_QUESTION_HEADER
*
908 ParseHiiQuestionNumeric (
909 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
912 EFI_IFR_NUMERIC
*IfrNumeric
;
913 VAR_CHECK_HII_QUESTION_NUMERIC
*Numeric
;
916 IfrNumeric
= (EFI_IFR_NUMERIC
*) IfrOpCodeHeader
;
918 Numeric
= InternalVarCheckAllocateZeroPool (sizeof (VAR_CHECK_HII_QUESTION_NUMERIC
) + 2 * sizeof (UINT64
));
919 ASSERT (Numeric
!= NULL
);
921 Width
= (UINT8
) (1 << (IfrNumeric
->Flags
& EFI_IFR_NUMERIC_SIZE
));
923 Numeric
->OpCode
= EFI_IFR_NUMERIC_OP
;
924 Numeric
->Length
= (UINT8
) (sizeof (VAR_CHECK_HII_QUESTION_NUMERIC
) + 2 * Width
);
925 Numeric
->VarOffset
= IfrNumeric
->Question
.VarStoreInfo
.VarOffset
;
926 Numeric
->StorageWidth
= Width
;
928 CopyMem (Numeric
+ 1, &IfrNumeric
->data
, Width
* 2);
930 return (VAR_CHECK_HII_QUESTION_HEADER
*) Numeric
;
934 Parse Hii Question OrderedList.
936 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
938 return Pointer to Hii Question.
941 VAR_CHECK_HII_QUESTION_HEADER
*
942 ParseHiiQuestionOrderedList (
943 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
946 EFI_IFR_ORDERED_LIST
*IfrOrderedList
;
947 VAR_CHECK_HII_QUESTION_ORDEREDLIST
*OrderedList
;
952 IfrOrderedList
= (EFI_IFR_ORDERED_LIST
*) IfrOpCodeHeader
;
954 GetOneOfOption (IfrOpCodeHeader
, &OptionCount
, &OptionWidth
, NULL
);
956 Length
= sizeof (*OrderedList
) + OptionCount
* OptionWidth
;
958 OrderedList
= InternalVarCheckAllocateZeroPool (Length
);
959 ASSERT (OrderedList
!= NULL
);
960 OrderedList
->OpCode
= EFI_IFR_ORDERED_LIST_OP
;
961 OrderedList
->Length
= (UINT8
) Length
;
962 OrderedList
->VarOffset
= IfrOrderedList
->Question
.VarStoreInfo
.VarOffset
;
963 OrderedList
->StorageWidth
= OptionWidth
;
964 OrderedList
->MaxContainers
= IfrOrderedList
->MaxContainers
;
966 GetOneOfOption (IfrOpCodeHeader
, &OptionCount
, &OptionWidth
, OrderedList
+ 1);
968 return (VAR_CHECK_HII_QUESTION_HEADER
*) OrderedList
;
972 Parse and create Hii Question node.
974 @param[in] HiiVariableNode Pointer to Hii Variable node.
975 @param[in] IfrOpCodeHeader Pointer to Ifr OpCode header.
976 @param[in] FromFv Hii Question from FV.
981 IN VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
,
982 IN EFI_IFR_OP_HEADER
*IfrOpCodeHeader
,
986 VAR_CHECK_HII_QUESTION_HEADER
*HiiQuestion
;
988 switch (IfrOpCodeHeader
->OpCode
) {
989 case EFI_IFR_ONE_OF_OP
:
990 HiiQuestion
= ParseHiiQuestionOneOf (IfrOpCodeHeader
);
993 case EFI_IFR_CHECKBOX_OP
:
994 HiiQuestion
= ParseHiiQuestionCheckBox (IfrOpCodeHeader
);
997 case EFI_IFR_NUMERIC_OP
:
998 HiiQuestion
= ParseHiiQuestionNumeric (IfrOpCodeHeader
);
1001 case EFI_IFR_ORDERED_LIST_OP
:
1002 HiiQuestion
= ParseHiiQuestionOrderedList (IfrOpCodeHeader
);
1011 if (HiiVariableNode
->HiiQuestionArray
[HiiQuestion
->VarOffset
] != NULL
) {
1012 MergeHiiQuestion (HiiVariableNode
, HiiQuestion
, FromFv
);
1014 HiiVariableNode
->HiiQuestionArray
[HiiQuestion
->VarOffset
] = HiiQuestion
;
1019 Find Hii variable node by name and GUID.
1021 @param[in] Name Pointer to variable name.
1022 @param[in] Guid Pointer to vendor GUID.
1024 @return Pointer to Hii Variable node.
1027 VAR_CHECK_HII_VARIABLE_NODE
*
1028 FindHiiVariableNode (
1033 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1036 for (Link
= mVarCheckHiiList
.ForwardLink
1037 ;Link
!= &mVarCheckHiiList
1038 ;Link
= Link
->ForwardLink
) {
1039 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (Link
);
1041 if ((StrCmp (Name
, (CHAR16
*) (HiiVariableNode
->HiiVariable
+ 1)) == 0) &&
1042 CompareGuid (Guid
, &HiiVariableNode
->HiiVariable
->Guid
)) {
1043 return HiiVariableNode
;
1051 Find Hii variable node by var store id.
1053 @param[in] VarStoreId Var store id.
1055 @return Pointer to Hii Variable node.
1058 VAR_CHECK_HII_VARIABLE_NODE
*
1059 FindHiiVariableNodeByVarStoreId (
1060 IN EFI_VARSTORE_ID VarStoreId
1063 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1066 if (VarStoreId
== 0) {
1068 // The variable store identifier, which is unique within the current form set.
1069 // A value of zero is invalid.
1074 for (Link
= mVarCheckHiiList
.ForwardLink
1075 ;Link
!= &mVarCheckHiiList
1076 ;Link
= Link
->ForwardLink
) {
1077 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (Link
);
1079 // The variable store identifier, which is unique within the current form set.
1081 if (VarStoreId
== HiiVariableNode
->VarStoreId
) {
1082 return HiiVariableNode
;
1090 Destroy var store id in the Hii Variable node after parsing one Hii Package.
1098 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1101 for (Link
= mVarCheckHiiList
.ForwardLink
1102 ;Link
!= &mVarCheckHiiList
1103 ;Link
= Link
->ForwardLink
) {
1104 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (Link
);
1106 // The variable store identifier, which is unique within the current form set.
1107 // A value of zero is invalid.
1109 HiiVariableNode
->VarStoreId
= 0;
1114 Create Hii Variable node.
1116 @param[in] IfrEfiVarStore Pointer to EFI VARSTORE.
1120 CreateHiiVariableNode (
1121 IN EFI_IFR_VARSTORE_EFI
*IfrEfiVarStore
1124 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1125 VAR_CHECK_HII_VARIABLE_HEADER
*HiiVariable
;
1131 // Get variable name.
1133 VarNameSize
= AsciiStrSize ((CHAR8
*) IfrEfiVarStore
->Name
) * 2;
1134 if (VarNameSize
> mMaxVarNameSize
) {
1135 mVarName
= InternalVarCheckReallocatePool (mMaxVarNameSize
, VarNameSize
, mVarName
);
1136 ASSERT (mVarName
!= NULL
);
1137 mMaxVarNameSize
= VarNameSize
;
1139 AsciiStrToUnicodeStr ((CHAR8
*) IfrEfiVarStore
->Name
, mVarName
);
1142 HiiVariableNode
= FindHiiVariableNode (
1144 &IfrEfiVarStore
->Guid
1146 if (HiiVariableNode
== NULL
) {
1148 // Not found, then create new.
1150 HeaderLength
= sizeof (*HiiVariable
) + VarNameSize
;
1151 HiiVariable
= InternalVarCheckAllocateZeroPool (HeaderLength
);
1152 ASSERT (HiiVariable
!= NULL
);
1153 HiiVariable
->Revision
= VAR_CHECK_HII_REVISION
;
1154 HiiVariable
->OpCode
= EFI_IFR_VARSTORE_EFI_OP
;
1155 HiiVariable
->HeaderLength
= (UINT16
) HeaderLength
;
1156 HiiVariable
->Size
= IfrEfiVarStore
->Size
;
1157 HiiVariable
->Attributes
= IfrEfiVarStore
->Attributes
;
1158 CopyGuid (&HiiVariable
->Guid
, &IfrEfiVarStore
->Guid
);
1159 StrCpyS ((CHAR16
*) (HiiVariable
+ 1), VarNameSize
/ sizeof (CHAR16
), VarName
);
1161 HiiVariableNode
= InternalVarCheckAllocateZeroPool (sizeof (*HiiVariableNode
));
1162 ASSERT (HiiVariableNode
!= NULL
);
1163 HiiVariableNode
->Signature
= VAR_CHECK_HII_VARIABLE_NODE_SIGNATURE
;
1164 HiiVariableNode
->HiiVariable
= HiiVariable
;
1166 // The variable store identifier, which is unique within the current form set.
1168 HiiVariableNode
->VarStoreId
= IfrEfiVarStore
->VarStoreId
;
1169 HiiVariableNode
->HiiQuestionArray
= InternalVarCheckAllocateZeroPool (IfrEfiVarStore
->Size
* sizeof (VAR_CHECK_HII_QUESTION_HEADER
*));
1171 InsertTailList (&mVarCheckHiiList
, &HiiVariableNode
->Link
);
1173 HiiVariableNode
->VarStoreId
= IfrEfiVarStore
->VarStoreId
;
1178 Parse and create Hii Variable node list.
1180 @param[in] HiiPackage Pointer to Hii Package.
1188 EFI_HII_PACKAGE_HEADER
*HiiPackageHeader
;
1189 EFI_IFR_OP_HEADER
*IfrOpCodeHeader
;
1190 EFI_IFR_VARSTORE_EFI
*IfrEfiVarStore
;
1192 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) HiiPackage
;
1194 switch (HiiPackageHeader
->Type
) {
1195 case EFI_HII_PACKAGE_FORMS
:
1196 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) (HiiPackageHeader
+ 1);
1198 while ((UINTN
) IfrOpCodeHeader
< (UINTN
) HiiPackageHeader
+ HiiPackageHeader
->Length
) {
1199 switch (IfrOpCodeHeader
->OpCode
) {
1200 case EFI_IFR_VARSTORE_EFI_OP
:
1202 // Come to EFI VARSTORE in Form Package.
1204 IfrEfiVarStore
= (EFI_IFR_VARSTORE_EFI
*) IfrOpCodeHeader
;
1205 if ((IfrEfiVarStore
->Header
.Length
>= sizeof (EFI_IFR_VARSTORE_EFI
)) &&
1206 ((IfrEfiVarStore
->Attributes
& EFI_VARIABLE_NON_VOLATILE
) != 0)) {
1208 // Only create node list for Hii Variable with NV attribute.
1210 CreateHiiVariableNode (IfrEfiVarStore
);
1217 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
1227 Var Check Parse Hii Package.
1229 @param[in] HiiPackage Pointer to Hii Package.
1230 @param[in] FromFv Hii Package from FV.
1234 VarCheckParseHiiPackage (
1235 IN VOID
*HiiPackage
,
1239 EFI_HII_PACKAGE_HEADER
*HiiPackageHeader
;
1240 EFI_IFR_OP_HEADER
*IfrOpCodeHeader
;
1241 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1244 // Parse and create Hii Variable node list for this Hii Package.
1246 ParseHiiVariable (HiiPackage
);
1248 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) HiiPackage
;
1250 switch (HiiPackageHeader
->Type
) {
1251 case EFI_HII_PACKAGE_FORMS
:
1252 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) (HiiPackageHeader
+ 1);
1254 while ((UINTN
) IfrOpCodeHeader
< (UINTN
) HiiPackageHeader
+ HiiPackageHeader
->Length
) {
1255 switch (IfrOpCodeHeader
->OpCode
) {
1256 case EFI_IFR_ONE_OF_OP
:
1257 case EFI_IFR_CHECKBOX_OP
:
1258 case EFI_IFR_NUMERIC_OP
:
1259 case EFI_IFR_ORDERED_LIST_OP
:
1260 HiiVariableNode
= FindHiiVariableNodeByVarStoreId (((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.VarStoreId
);
1261 if ((HiiVariableNode
== NULL
) ||
1263 // No related Hii Variable node found.
1265 ((((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.Header
.Prompt
== 0) && (((EFI_IFR_ONE_OF
*) IfrOpCodeHeader
)->Question
.Header
.Help
== 0))) {
1267 // meanless IFR item introduced by ECP.
1273 ParseHiiQuestion (HiiVariableNode
, IfrOpCodeHeader
, FromFv
);
1278 IfrOpCodeHeader
= (EFI_IFR_OP_HEADER
*) ((UINTN
) IfrOpCodeHeader
+ IfrOpCodeHeader
->Length
);
1285 DestroyVarStoreId ();
1289 Var Check Parse Hii Database.
1291 @param[in] HiiDatabase Pointer to Hii Database.
1292 @param[in] HiiDatabaseSize Hii Database size.
1296 VarCheckParseHiiDatabase (
1297 IN VOID
*HiiDatabase
,
1298 IN UINTN HiiDatabaseSize
1301 EFI_HII_PACKAGE_LIST_HEADER
*HiiPackageListHeader
;
1302 EFI_HII_PACKAGE_HEADER
*HiiPackageHeader
;
1304 HiiPackageListHeader
= (EFI_HII_PACKAGE_LIST_HEADER
*) HiiDatabase
;
1306 while ((UINTN
) HiiPackageListHeader
< ((UINTN
) HiiDatabase
+ HiiDatabaseSize
)) {
1307 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) (HiiPackageListHeader
+ 1);
1309 while ((UINTN
) HiiPackageHeader
< ((UINTN
) HiiPackageListHeader
+ HiiPackageListHeader
->PackageLength
)) {
1311 // Parse Hii Pacakge.
1313 VarCheckParseHiiPackage (HiiPackageHeader
, FALSE
);
1315 HiiPackageHeader
= (EFI_HII_PACKAGE_HEADER
*) ((UINTN
) HiiPackageHeader
+ HiiPackageHeader
->Length
);
1318 HiiPackageListHeader
= (EFI_HII_PACKAGE_LIST_HEADER
*) ((UINTN
) HiiPackageListHeader
+ HiiPackageListHeader
->PackageLength
);
1323 Destroy Hii Variable node.
1327 DestroyHiiVariableNode (
1331 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1332 LIST_ENTRY
*HiiVariableLink
;
1335 while (mVarCheckHiiList
.ForwardLink
!= &mVarCheckHiiList
) {
1336 HiiVariableLink
= mVarCheckHiiList
.ForwardLink
;
1337 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (HiiVariableLink
);
1339 RemoveEntryList (&HiiVariableNode
->Link
);
1342 // Free the allocated buffer.
1344 for (Index
= 0; Index
< HiiVariableNode
->HiiVariable
->Size
; Index
++) {
1345 if (HiiVariableNode
->HiiQuestionArray
[Index
] != NULL
) {
1346 InternalVarCheckFreePool (HiiVariableNode
->HiiQuestionArray
[Index
]);
1349 InternalVarCheckFreePool (HiiVariableNode
->HiiQuestionArray
);
1350 InternalVarCheckFreePool (HiiVariableNode
->HiiVariable
);
1351 InternalVarCheckFreePool (HiiVariableNode
);
1356 Build VarCheckHiiBin.
1358 @param[out] Size Pointer to VarCheckHii size.
1360 @return Pointer to VarCheckHiiBin.
1364 BuildVarCheckHiiBin (
1368 VAR_CHECK_HII_VARIABLE_NODE
*HiiVariableNode
;
1369 LIST_ENTRY
*HiiVariableLink
;
1374 UINT32 HiiVariableLength
;
1381 for (HiiVariableLink
= mVarCheckHiiList
.ForwardLink
1382 ;HiiVariableLink
!= &mVarCheckHiiList
1383 ;HiiVariableLink
= HiiVariableLink
->ForwardLink
) {
1385 // For Hii Variable header align.
1387 BinSize
= (UINT32
) HEADER_ALIGN (BinSize
);
1389 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (HiiVariableLink
);
1390 HiiVariableLength
= HiiVariableNode
->HiiVariable
->HeaderLength
;
1392 for (Index
= 0; Index
< HiiVariableNode
->HiiVariable
->Size
; Index
++) {
1393 if (HiiVariableNode
->HiiQuestionArray
[Index
] != NULL
) {
1395 // For Hii Question header align.
1397 HiiVariableLength
= (UINT32
) HEADER_ALIGN (HiiVariableLength
);
1398 HiiVariableLength
+= HiiVariableNode
->HiiQuestionArray
[Index
]->Length
;
1402 HiiVariableNode
->HiiVariable
->Length
= HiiVariableLength
;
1403 BinSize
+= HiiVariableLength
;
1406 DEBUG ((EFI_D_INFO
, "VarCheckHiiBin - size = 0x%x\n", BinSize
));
1413 // AllocatePages () and AllocatePool () from gBS are used for the process of VarCheckHiiBin generation.
1414 // Only here AllocateRuntimeZeroPool () from MemoryAllocateLib is used for runtime access
1415 // in SetVariable check handler.
1417 Data
= AllocateRuntimeZeroPool (BinSize
);
1418 ASSERT (Data
!= NULL
);
1419 DEBUG ((EFI_D_INFO
, "VarCheckHiiBin - built at 0x%x\n", Data
));
1425 for (HiiVariableLink
= mVarCheckHiiList
.ForwardLink
1426 ;HiiVariableLink
!= &mVarCheckHiiList
1427 ;HiiVariableLink
= HiiVariableLink
->ForwardLink
) {
1429 // For Hii Variable header align.
1431 Ptr
= (UINT8
*) HEADER_ALIGN (Ptr
);
1433 HiiVariableNode
= VAR_CHECK_HII_VARIABLE_FROM_LINK (HiiVariableLink
);
1434 CopyMem (Ptr
, HiiVariableNode
->HiiVariable
, HiiVariableNode
->HiiVariable
->HeaderLength
);
1435 Ptr
+= HiiVariableNode
->HiiVariable
->HeaderLength
;
1437 for (Index
= 0; Index
< HiiVariableNode
->HiiVariable
->Size
; Index
++) {
1438 if (HiiVariableNode
->HiiQuestionArray
[Index
] != NULL
) {
1440 // For Hii Question header align.
1442 Ptr
= (UINT8
*) HEADER_ALIGN (Ptr
);
1443 CopyMem (Ptr
, HiiVariableNode
->HiiQuestionArray
[Index
], HiiVariableNode
->HiiQuestionArray
[Index
]->Length
);
1444 Ptr
+= HiiVariableNode
->HiiQuestionArray
[Index
]->Length
;
1454 Generate VarCheckHiiBin from Hii Database and FV.
1463 VarCheckHiiGenFromHiiDatabase ();
1464 VarCheckHiiGenFromFv ();
1466 mVarCheckHiiBin
= BuildVarCheckHiiBin (&mVarCheckHiiBinSize
);
1467 if (mVarCheckHiiBin
== NULL
) {
1468 DEBUG ((EFI_D_INFO
, "[VarCheckHii] This driver could be removed from *.dsc and *.fdf\n"));
1472 DestroyHiiVariableNode ();
1473 if (mVarName
!= NULL
) {
1474 InternalVarCheckFreePool (mVarName
);
1477 #ifdef DUMP_VAR_CHECK_HII
1479 DumpVarCheckHii (mVarCheckHiiBin
, mVarCheckHiiBinSize
);