]> git.proxmox.com Git - mirror_edk2.git/blame_incremental - MdeModulePkg/Universal/SetupBrowserDxe/IfrParse.c
Print Arrow for Goto button.
[mirror_edk2.git] / MdeModulePkg / Universal / SetupBrowserDxe / IfrParse.c
... / ...
CommitLineData
1/** @file\r
2Parser for IFR binary encoding.\r
3\r
4Copyright (c) 2007 - 2010, Intel Corporation. All rights reserved.<BR>\r
5This program and the accompanying materials\r
6are licensed and made available under the terms and conditions of the BSD License\r
7which accompanies this distribution. The full text of the license may be found at\r
8http://opensource.org/licenses/bsd-license.php\r
9\r
10THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
11WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
12\r
13**/\r
14\r
15#include "Setup.h"\r
16\r
17UINT16 mStatementIndex;\r
18UINT16 mExpressionOpCodeIndex;\r
19\r
20BOOLEAN mInScopeSubtitle;\r
21BOOLEAN mInScopeSuppress;\r
22BOOLEAN mInScopeGrayOut;\r
23BOOLEAN mInScopeDisable;\r
24FORM_EXPRESSION *mSuppressExpression;\r
25FORM_EXPRESSION *mGrayOutExpression;\r
26FORM_EXPRESSION *mDisableExpression;\r
27\r
28/**\r
29 Initialize Statement header members.\r
30\r
31 @param OpCodeData Pointer of the raw OpCode data.\r
32 @param FormSet Pointer of the current FormSe.\r
33 @param Form Pointer of the current Form.\r
34\r
35 @return The Statement.\r
36\r
37**/\r
38FORM_BROWSER_STATEMENT *\r
39CreateStatement (\r
40 IN UINT8 *OpCodeData,\r
41 IN OUT FORM_BROWSER_FORMSET *FormSet,\r
42 IN OUT FORM_BROWSER_FORM *Form\r
43 )\r
44{\r
45 FORM_BROWSER_STATEMENT *Statement;\r
46 EFI_IFR_STATEMENT_HEADER *StatementHdr;\r
47\r
48 if (Form == NULL) {\r
49 //\r
50 // We are currently not in a Form Scope, so just skip this Statement\r
51 //\r
52 return NULL;\r
53 }\r
54\r
55 Statement = &FormSet->StatementBuffer[mStatementIndex];\r
56 mStatementIndex++;\r
57\r
58 InitializeListHead (&Statement->DefaultListHead);\r
59 InitializeListHead (&Statement->OptionListHead);\r
60 InitializeListHead (&Statement->InconsistentListHead);\r
61 InitializeListHead (&Statement->NoSubmitListHead);\r
62\r
63 Statement->Signature = FORM_BROWSER_STATEMENT_SIGNATURE;\r
64\r
65 Statement->Operand = ((EFI_IFR_OP_HEADER *) OpCodeData)->OpCode;\r
66\r
67 StatementHdr = (EFI_IFR_STATEMENT_HEADER *) (OpCodeData + sizeof (EFI_IFR_OP_HEADER));\r
68 CopyMem (&Statement->Prompt, &StatementHdr->Prompt, sizeof (EFI_STRING_ID));\r
69 CopyMem (&Statement->Help, &StatementHdr->Help, sizeof (EFI_STRING_ID));\r
70\r
71 if (mInScopeSuppress) {\r
72 Statement->SuppressExpression = mSuppressExpression;\r
73 }\r
74\r
75 if (mInScopeGrayOut) {\r
76 Statement->GrayOutExpression = mGrayOutExpression;\r
77 }\r
78\r
79\r
80 if (mInScopeDisable) {\r
81 Statement->DisableExpression = mDisableExpression;\r
82 }\r
83\r
84 Statement->InSubtitle = mInScopeSubtitle;\r
85\r
86 //\r
87 // Insert this Statement into current Form\r
88 //\r
89 InsertTailList (&Form->StatementListHead, &Statement->Link);\r
90\r
91 return Statement;\r
92}\r
93\r
94/**\r
95 Convert a numeric value to a Unicode String and insert it to String Package.\r
96 This string is used as the Unicode Name for the EFI Variable. This is to support\r
97 the deprecated vareqval opcode.\r
98\r
99 @param FormSet The FormSet.\r
100 @param Statement The numeric question whose VarStoreInfo.VarName is the\r
101 numeric value which is used to produce the Unicode Name\r
102 for the EFI Variable.\r
103\r
104 If the Statement is NULL, the ASSERT.\r
105 If the opcode is not Numeric, then ASSERT.\r
106\r
107 @retval EFI_SUCCESS The funtion always succeeds.\r
108**/\r
109EFI_STATUS\r
110UpdateCheckBoxStringToken (\r
111 IN CONST FORM_BROWSER_FORMSET *FormSet,\r
112 IN FORM_BROWSER_STATEMENT *Statement\r
113 )\r
114{\r
115 CHAR16 Str[MAXIMUM_VALUE_CHARACTERS];\r
116 EFI_STRING_ID Id;\r
117\r
118 ASSERT (Statement != NULL);\r
119 ASSERT (Statement->Operand == EFI_IFR_NUMERIC_OP);\r
120\r
121 UnicodeValueToString (Str, 0, Statement->VarStoreInfo.VarName, MAXIMUM_VALUE_CHARACTERS - 1);\r
122\r
123 Id = HiiSetString (FormSet->HiiHandle, 0, Str, NULL);\r
124 if (Id == 0) {\r
125 return EFI_OUT_OF_RESOURCES;\r
126 }\r
127\r
128 Statement->VarStoreInfo.VarName = Id;\r
129\r
130 return EFI_SUCCESS;\r
131}\r
132\r
133/**\r
134 Check if the next opcode is the EFI_IFR_EXTEND_OP_VAREQNAME.\r
135\r
136 @param OpCodeData The current opcode.\r
137\r
138 @retval TRUE Yes.\r
139 @retval FALSE No.\r
140**/\r
141BOOLEAN\r
142IsNextOpCodeGuidedVarEqName (\r
143 IN UINT8 *OpCodeData\r
144 )\r
145{\r
146 //\r
147 // Get next opcode\r
148 //\r
149 OpCodeData += ((EFI_IFR_OP_HEADER *) OpCodeData)->Length;\r
150 if (*OpCodeData == EFI_IFR_GUID_OP) {\r
151 if (CompareGuid (&gEfiIfrFrameworkGuid, (EFI_GUID *)(OpCodeData + sizeof (EFI_IFR_OP_HEADER)))) {\r
152 //\r
153 // Specific GUIDed opcodes to support IFR generated from Framework HII VFR\r
154 //\r
155 if ((((EFI_IFR_GUID_VAREQNAME *) OpCodeData)->ExtendOpCode) == EFI_IFR_EXTEND_OP_VAREQNAME) {\r
156 return TRUE;\r
157 }\r
158 }\r
159 }\r
160\r
161 return FALSE;\r
162}\r
163\r
164/**\r
165 Initialize Question's members.\r
166\r
167 @param OpCodeData Pointer of the raw OpCode data.\r
168 @param FormSet Pointer of the current FormSet.\r
169 @param Form Pointer of the current Form.\r
170\r
171 @return The Question.\r
172\r
173**/\r
174FORM_BROWSER_STATEMENT *\r
175CreateQuestion (\r
176 IN UINT8 *OpCodeData,\r
177 IN OUT FORM_BROWSER_FORMSET *FormSet,\r
178 IN OUT FORM_BROWSER_FORM *Form\r
179 )\r
180{\r
181 FORM_BROWSER_STATEMENT *Statement;\r
182 EFI_IFR_QUESTION_HEADER *QuestionHdr;\r
183 LIST_ENTRY *Link;\r
184 FORMSET_STORAGE *Storage;\r
185 NAME_VALUE_NODE *NameValueNode;\r
186 EFI_STATUS Status;\r
187\r
188 Statement = CreateStatement (OpCodeData, FormSet, Form);\r
189 if (Statement == NULL) {\r
190 return NULL;\r
191 }\r
192\r
193 QuestionHdr = (EFI_IFR_QUESTION_HEADER *) (OpCodeData + sizeof (EFI_IFR_OP_HEADER));\r
194 CopyMem (&Statement->QuestionId, &QuestionHdr->QuestionId, sizeof (EFI_QUESTION_ID));\r
195 CopyMem (&Statement->VarStoreId, &QuestionHdr->VarStoreId, sizeof (EFI_VARSTORE_ID));\r
196 CopyMem (&Statement->VarStoreInfo.VarOffset, &QuestionHdr->VarStoreInfo.VarOffset, sizeof (UINT16));\r
197\r
198 Statement->QuestionFlags = QuestionHdr->Flags;\r
199\r
200 if (Statement->VarStoreId == 0) {\r
201 //\r
202 // VarStoreId of zero indicates no variable storage\r
203 //\r
204 return Statement;\r
205 }\r
206\r
207 //\r
208 // Take a look at next OpCode to see whether it is a GUIDed opcode to support\r
209 // Framework Compatibility\r
210 //\r
211 if (FeaturePcdGet (PcdFrameworkCompatibilitySupport)) {\r
212 if ((*OpCodeData == EFI_IFR_NUMERIC_OP) && IsNextOpCodeGuidedVarEqName (OpCodeData)) {\r
213 Status = UpdateCheckBoxStringToken (FormSet, Statement);\r
214 if (EFI_ERROR (Status)) {\r
215 return NULL;\r
216 }\r
217 }\r
218 }\r
219\r
220 //\r
221 // Find Storage for this Question\r
222 //\r
223 Link = GetFirstNode (&FormSet->StorageListHead);\r
224 while (!IsNull (&FormSet->StorageListHead, Link)) {\r
225 Storage = FORMSET_STORAGE_FROM_LINK (Link);\r
226\r
227 if (Storage->VarStoreId == Statement->VarStoreId) {\r
228 Statement->Storage = Storage;\r
229 break;\r
230 }\r
231\r
232 Link = GetNextNode (&FormSet->StorageListHead, Link);\r
233 }\r
234 ASSERT (Statement->Storage != NULL);\r
235\r
236 //\r
237 // Initialilze varname for Name/Value or EFI Variable\r
238 //\r
239 if ((Statement->Storage->Type == EFI_HII_VARSTORE_NAME_VALUE) ||\r
240 (Statement->Storage->Type == EFI_HII_VARSTORE_EFI_VARIABLE)) {\r
241 Statement->VariableName = GetToken (Statement->VarStoreInfo.VarName, FormSet->HiiHandle);\r
242 ASSERT (Statement->VariableName != NULL);\r
243\r
244 if (Statement->Storage->Type == EFI_HII_VARSTORE_NAME_VALUE) {\r
245 //\r
246 // Insert to Name/Value varstore list\r
247 //\r
248 NameValueNode = AllocateZeroPool (sizeof (NAME_VALUE_NODE));\r
249 ASSERT (NameValueNode != NULL);\r
250 NameValueNode->Signature = NAME_VALUE_NODE_SIGNATURE;\r
251 NameValueNode->Name = AllocateCopyPool (StrSize (Statement->VariableName), Statement->VariableName);\r
252 ASSERT (NameValueNode->Name != NULL);\r
253 NameValueNode->Value = AllocateZeroPool (0x10);\r
254 ASSERT (NameValueNode->Value != NULL);\r
255 NameValueNode->EditValue = AllocateZeroPool (0x10);\r
256 ASSERT (NameValueNode->EditValue != NULL);\r
257\r
258 InsertTailList (&Statement->Storage->NameValueListHead, &NameValueNode->Link);\r
259 }\r
260 }\r
261\r
262 return Statement;\r
263}\r
264\r
265\r
266/**\r
267 Allocate a FORM_EXPRESSION node.\r
268\r
269 @param Form The Form associated with this Expression\r
270\r
271 @return Pointer to a FORM_EXPRESSION data structure.\r
272\r
273**/\r
274FORM_EXPRESSION *\r
275CreateExpression (\r
276 IN OUT FORM_BROWSER_FORM *Form\r
277 )\r
278{\r
279 FORM_EXPRESSION *Expression;\r
280\r
281 Expression = AllocateZeroPool (sizeof (FORM_EXPRESSION));\r
282 ASSERT (Expression != NULL);\r
283 Expression->Signature = FORM_EXPRESSION_SIGNATURE;\r
284 InitializeListHead (&Expression->OpCodeListHead);\r
285\r
286 return Expression;\r
287}\r
288\r
289\r
290/**\r
291 Allocate a FORMSET_STORAGE data structure and insert to FormSet Storage List.\r
292\r
293 @param FormSet Pointer of the current FormSet\r
294\r
295 @return Pointer to a FORMSET_STORAGE data structure.\r
296\r
297**/\r
298FORMSET_STORAGE *\r
299CreateStorage (\r
300 IN FORM_BROWSER_FORMSET *FormSet\r
301 )\r
302{\r
303 FORMSET_STORAGE *Storage;\r
304\r
305 Storage = AllocateZeroPool (sizeof (FORMSET_STORAGE));\r
306 ASSERT (Storage != NULL);\r
307 Storage->Signature = FORMSET_STORAGE_SIGNATURE;\r
308 InitializeListHead (&Storage->NameValueListHead);\r
309 InsertTailList (&FormSet->StorageListHead, &Storage->Link);\r
310\r
311 return Storage;\r
312}\r
313\r
314\r
315/**\r
316 Create ConfigHdr string for a storage.\r
317\r
318 @param FormSet Pointer of the current FormSet\r
319 @param Storage Pointer of the storage\r
320\r
321 @retval EFI_SUCCESS Initialize ConfigHdr success\r
322\r
323**/\r
324EFI_STATUS\r
325InitializeConfigHdr (\r
326 IN FORM_BROWSER_FORMSET *FormSet,\r
327 IN OUT FORMSET_STORAGE *Storage\r
328 )\r
329{\r
330 CHAR16 *Name;\r
331\r
332 if (Storage->Type == EFI_HII_VARSTORE_BUFFER) {\r
333 Name = Storage->Name;\r
334 } else {\r
335 Name = NULL;\r
336 }\r
337\r
338 Storage->ConfigHdr = HiiConstructConfigHdr (\r
339 &Storage->Guid,\r
340 Name,\r
341 FormSet->DriverHandle\r
342 );\r
343\r
344 if (Storage->ConfigHdr == NULL) {\r
345 return EFI_NOT_FOUND;\r
346 }\r
347\r
348 Storage->ConfigRequest = AllocateCopyPool (StrSize (Storage->ConfigHdr), Storage->ConfigHdr);\r
349 Storage->SpareStrLen = 0;\r
350\r
351 return EFI_SUCCESS;\r
352}\r
353\r
354\r
355/**\r
356 Initialize Request Element of a Question. <RequestElement> ::= '&'<BlockName> | '&'<Label>\r
357\r
358 @param FormSet Pointer of the current FormSet.\r
359 @param Question The Question to be initialized.\r
360\r
361 @retval EFI_SUCCESS Function success.\r
362 @retval EFI_INVALID_PARAMETER No storage associated with the Question.\r
363\r
364**/\r
365EFI_STATUS\r
366InitializeRequestElement (\r
367 IN OUT FORM_BROWSER_FORMSET *FormSet,\r
368 IN OUT FORM_BROWSER_STATEMENT *Question\r
369 )\r
370{\r
371 FORMSET_STORAGE *Storage;\r
372 UINTN StrLen;\r
373 UINTN StringSize;\r
374 CHAR16 *NewStr;\r
375 CHAR16 RequestElement[30];\r
376\r
377 Storage = Question->Storage;\r
378 if (Storage == NULL) {\r
379 return EFI_INVALID_PARAMETER;\r
380 }\r
381\r
382 if (Storage->Type == EFI_HII_VARSTORE_EFI_VARIABLE) {\r
383 //\r
384 // <ConfigRequest> is unnecessary for EFI variable storage,\r
385 // GetVariable()/SetVariable() will be used to retrieve/save values\r
386 //\r
387 return EFI_SUCCESS;\r
388 }\r
389\r
390 //\r
391 // Prepare <RequestElement>\r
392 //\r
393 if (Storage->Type == EFI_HII_VARSTORE_BUFFER) {\r
394 StrLen = UnicodeSPrint (\r
395 RequestElement,\r
396 30 * sizeof (CHAR16),\r
397 L"&OFFSET=%x&WIDTH=%x",\r
398 Question->VarStoreInfo.VarOffset,\r
399 Question->StorageWidth\r
400 );\r
401 Question->BlockName = AllocateCopyPool ((StrLen + 1) * sizeof (CHAR16), RequestElement);\r
402 } else {\r
403 StrLen = UnicodeSPrint (RequestElement, 30 * sizeof (CHAR16), L"&%s", Question->VariableName);\r
404 }\r
405\r
406 if ((Question->Operand == EFI_IFR_PASSWORD_OP) && ((Question->QuestionFlags & EFI_IFR_FLAG_CALLBACK) == EFI_IFR_FLAG_CALLBACK)) {\r
407 //\r
408 // Password with CALLBACK flag is stored in encoded format,\r
409 // so don't need to append it to <ConfigRequest>\r
410 //\r
411 return EFI_SUCCESS;\r
412 }\r
413\r
414 //\r
415 // Append <RequestElement> to <ConfigRequest>\r
416 //\r
417 if (StrLen > Storage->SpareStrLen) {\r
418 //\r
419 // Old String buffer is not sufficient for RequestElement, allocate a new one\r
420 //\r
421 StringSize = (Storage->ConfigRequest != NULL) ? StrSize (Storage->ConfigRequest) : sizeof (CHAR16);\r
422 NewStr = AllocateZeroPool (StringSize + CONFIG_REQUEST_STRING_INCREMENTAL * sizeof (CHAR16));\r
423 ASSERT (NewStr != NULL);\r
424 if (Storage->ConfigRequest != NULL) {\r
425 CopyMem (NewStr, Storage->ConfigRequest, StringSize);\r
426 FreePool (Storage->ConfigRequest);\r
427 }\r
428 Storage->ConfigRequest = NewStr;\r
429 Storage->SpareStrLen = CONFIG_REQUEST_STRING_INCREMENTAL;\r
430 }\r
431\r
432 StrCat (Storage->ConfigRequest, RequestElement);\r
433 Storage->ElementCount++;\r
434 Storage->SpareStrLen -= StrLen;\r
435\r
436 return EFI_SUCCESS;\r
437}\r
438\r
439\r
440/**\r
441 Free resources of a Expression.\r
442\r
443 @param FormSet Pointer of the Expression\r
444\r
445**/\r
446VOID\r
447DestroyExpression (\r
448 IN FORM_EXPRESSION *Expression\r
449 )\r
450{\r
451 LIST_ENTRY *Link;\r
452 EXPRESSION_OPCODE *OpCode;\r
453 LIST_ENTRY *SubExpressionLink;\r
454 FORM_EXPRESSION *SubExpression;\r
455\r
456 while (!IsListEmpty (&Expression->OpCodeListHead)) {\r
457 Link = GetFirstNode (&Expression->OpCodeListHead);\r
458 OpCode = EXPRESSION_OPCODE_FROM_LINK (Link);\r
459 RemoveEntryList (&OpCode->Link);\r
460\r
461 if (OpCode->ValueList != NULL) {\r
462 FreePool (OpCode->ValueList);\r
463 }\r
464\r
465 if (OpCode->ValueName != NULL) {\r
466 FreePool (OpCode->ValueName);\r
467 }\r
468\r
469 if (OpCode->MapExpressionList.ForwardLink != NULL) {\r
470 while (!IsListEmpty (&OpCode->MapExpressionList)) {\r
471 SubExpressionLink = GetFirstNode(&OpCode->MapExpressionList);\r
472 SubExpression = FORM_EXPRESSION_FROM_LINK (SubExpressionLink);\r
473 RemoveEntryList(&SubExpression->Link);\r
474 DestroyExpression (SubExpression);\r
475 }\r
476 }\r
477 }\r
478\r
479 //\r
480 // Free this Expression\r
481 //\r
482 FreePool (Expression);\r
483}\r
484\r
485\r
486/**\r
487 Free resources of a storage.\r
488\r
489 @param Storage Pointer of the storage\r
490\r
491**/\r
492VOID\r
493DestroyStorage (\r
494 IN FORMSET_STORAGE *Storage\r
495 )\r
496{\r
497 LIST_ENTRY *Link;\r
498 NAME_VALUE_NODE *NameValueNode;\r
499\r
500 if (Storage == NULL) {\r
501 return;\r
502 }\r
503\r
504 if (Storage->Name != NULL) {\r
505 FreePool (Storage->Name);\r
506 }\r
507 if (Storage->Buffer != NULL) {\r
508 FreePool (Storage->Buffer);\r
509 }\r
510 if (Storage->EditBuffer != NULL) {\r
511 FreePool (Storage->EditBuffer);\r
512 }\r
513\r
514 while (!IsListEmpty (&Storage->NameValueListHead)) {\r
515 Link = GetFirstNode (&Storage->NameValueListHead);\r
516 NameValueNode = NAME_VALUE_NODE_FROM_LINK (Link);\r
517 RemoveEntryList (&NameValueNode->Link);\r
518\r
519 if (NameValueNode->Name != NULL) {\r
520 FreePool (NameValueNode->Name);\r
521 }\r
522 if (NameValueNode->Value != NULL) {\r
523 FreePool (NameValueNode->Value);\r
524 }\r
525 if (NameValueNode->EditValue != NULL) {\r
526 FreePool (NameValueNode->EditValue);\r
527 }\r
528 FreePool (NameValueNode);\r
529 }\r
530\r
531 if (Storage->ConfigHdr != NULL) {\r
532 FreePool (Storage->ConfigHdr);\r
533 }\r
534 if (Storage->ConfigRequest != NULL) {\r
535 FreePool (Storage->ConfigRequest);\r
536 }\r
537\r
538 FreePool (Storage);\r
539}\r
540\r
541\r
542/**\r
543 Free resources of a Statement.\r
544\r
545 @param Statement Pointer of the Statement\r
546\r
547**/\r
548VOID\r
549DestroyStatement (\r
550 IN OUT FORM_BROWSER_STATEMENT *Statement\r
551 )\r
552{\r
553 LIST_ENTRY *Link;\r
554 QUESTION_DEFAULT *Default;\r
555 QUESTION_OPTION *Option;\r
556 FORM_EXPRESSION *Expression;\r
557\r
558 //\r
559 // Free Default value List\r
560 //\r
561 while (!IsListEmpty (&Statement->DefaultListHead)) {\r
562 Link = GetFirstNode (&Statement->DefaultListHead);\r
563 Default = QUESTION_DEFAULT_FROM_LINK (Link);\r
564 RemoveEntryList (&Default->Link);\r
565\r
566 FreePool (Default);\r
567 }\r
568\r
569 //\r
570 // Free Options List\r
571 //\r
572 while (!IsListEmpty (&Statement->OptionListHead)) {\r
573 Link = GetFirstNode (&Statement->OptionListHead);\r
574 Option = QUESTION_OPTION_FROM_LINK (Link);\r
575 RemoveEntryList (&Option->Link);\r
576\r
577 FreePool (Option);\r
578 }\r
579\r
580 //\r
581 // Free Inconsistent List\r
582 //\r
583 while (!IsListEmpty (&Statement->InconsistentListHead)) {\r
584 Link = GetFirstNode (&Statement->InconsistentListHead);\r
585 Expression = FORM_EXPRESSION_FROM_LINK (Link);\r
586 RemoveEntryList (&Expression->Link);\r
587\r
588 DestroyExpression (Expression);\r
589 }\r
590\r
591 //\r
592 // Free NoSubmit List\r
593 //\r
594 while (!IsListEmpty (&Statement->NoSubmitListHead)) {\r
595 Link = GetFirstNode (&Statement->NoSubmitListHead);\r
596 Expression = FORM_EXPRESSION_FROM_LINK (Link);\r
597 RemoveEntryList (&Expression->Link);\r
598\r
599 DestroyExpression (Expression);\r
600 }\r
601\r
602 if (Statement->VariableName != NULL) {\r
603 FreePool (Statement->VariableName);\r
604 }\r
605 if (Statement->BlockName != NULL) {\r
606 FreePool (Statement->BlockName);\r
607 }\r
608 if (Statement->BufferValue != NULL) {\r
609 FreePool (Statement->BufferValue);\r
610 }\r
611}\r
612\r
613\r
614/**\r
615 Free resources of a Form.\r
616\r
617 @param Form Pointer of the Form.\r
618\r
619**/\r
620VOID\r
621DestroyForm (\r
622 IN OUT FORM_BROWSER_FORM *Form\r
623 )\r
624{\r
625 LIST_ENTRY *Link;\r
626 FORM_EXPRESSION *Expression;\r
627 FORM_BROWSER_STATEMENT *Statement;\r
628\r
629 //\r
630 // Free Form Expressions\r
631 //\r
632 while (!IsListEmpty (&Form->ExpressionListHead)) {\r
633 Link = GetFirstNode (&Form->ExpressionListHead);\r
634 Expression = FORM_EXPRESSION_FROM_LINK (Link);\r
635 RemoveEntryList (&Expression->Link);\r
636\r
637 DestroyExpression (Expression);\r
638 }\r
639\r
640 //\r
641 // Free Statements/Questions\r
642 //\r
643 while (!IsListEmpty (&Form->StatementListHead)) {\r
644 Link = GetFirstNode (&Form->StatementListHead);\r
645 Statement = FORM_BROWSER_STATEMENT_FROM_LINK (Link);\r
646 RemoveEntryList (&Statement->Link);\r
647\r
648 DestroyStatement (Statement);\r
649 }\r
650\r
651 //\r
652 // Free this Form\r
653 //\r
654 FreePool (Form);\r
655}\r
656\r
657\r
658/**\r
659 Free resources allocated for a FormSet.\r
660\r
661 @param FormSet Pointer of the FormSet\r
662\r
663**/\r
664VOID\r
665DestroyFormSet (\r
666 IN OUT FORM_BROWSER_FORMSET *FormSet\r
667 )\r
668{\r
669 LIST_ENTRY *Link;\r
670 FORMSET_STORAGE *Storage;\r
671 FORMSET_DEFAULTSTORE *DefaultStore;\r
672 FORM_EXPRESSION *Expression;\r
673 FORM_BROWSER_FORM *Form;\r
674\r
675 if (FormSet->IfrBinaryData == NULL) {\r
676 //\r
677 // Uninitialized FormSet\r
678 //\r
679 FreePool (FormSet);\r
680 return;\r
681 }\r
682\r
683 //\r
684 // Free IFR binary buffer\r
685 //\r
686 FreePool (FormSet->IfrBinaryData);\r
687\r
688 //\r
689 // Free FormSet Storage\r
690 //\r
691 if (FormSet->StorageListHead.ForwardLink != NULL) {\r
692 while (!IsListEmpty (&FormSet->StorageListHead)) {\r
693 Link = GetFirstNode (&FormSet->StorageListHead);\r
694 Storage = FORMSET_STORAGE_FROM_LINK (Link);\r
695 RemoveEntryList (&Storage->Link);\r
696\r
697 DestroyStorage (Storage);\r
698 }\r
699 }\r
700\r
701 //\r
702 // Free FormSet Default Store\r
703 //\r
704 if (FormSet->DefaultStoreListHead.ForwardLink != NULL) {\r
705 while (!IsListEmpty (&FormSet->DefaultStoreListHead)) {\r
706 Link = GetFirstNode (&FormSet->DefaultStoreListHead);\r
707 DefaultStore = FORMSET_DEFAULTSTORE_FROM_LINK (Link);\r
708 RemoveEntryList (&DefaultStore->Link);\r
709\r
710 FreePool (DefaultStore);\r
711 }\r
712 }\r
713\r
714 //\r
715 // Free Formset Expressions\r
716 //\r
717 while (!IsListEmpty (&FormSet->ExpressionListHead)) {\r
718 Link = GetFirstNode (&FormSet->ExpressionListHead);\r
719 Expression = FORM_EXPRESSION_FROM_LINK (Link);\r
720 RemoveEntryList (&Expression->Link);\r
721\r
722 DestroyExpression (Expression);\r
723 }\r
724\r
725 //\r
726 // Free Forms\r
727 //\r
728 if (FormSet->FormListHead.ForwardLink != NULL) {\r
729 while (!IsListEmpty (&FormSet->FormListHead)) {\r
730 Link = GetFirstNode (&FormSet->FormListHead);\r
731 Form = FORM_BROWSER_FORM_FROM_LINK (Link);\r
732 RemoveEntryList (&Form->Link);\r
733\r
734 DestroyForm (Form);\r
735 }\r
736 }\r
737\r
738 if (FormSet->StatementBuffer != NULL) {\r
739 FreePool (FormSet->StatementBuffer);\r
740 }\r
741 if (FormSet->ExpressionBuffer != NULL) {\r
742 FreePool (FormSet->ExpressionBuffer);\r
743 }\r
744\r
745 FreePool (FormSet);\r
746}\r
747\r
748\r
749/**\r
750 Tell whether this Operand is an Expression OpCode or not\r
751\r
752 @param Operand Operand of an IFR OpCode.\r
753\r
754 @retval TRUE This is an Expression OpCode.\r
755 @retval FALSE Not an Expression OpCode.\r
756\r
757**/\r
758BOOLEAN\r
759IsExpressionOpCode (\r
760 IN UINT8 Operand\r
761 )\r
762{\r
763 if (((Operand >= EFI_IFR_EQ_ID_VAL_OP) && (Operand <= EFI_IFR_NOT_OP)) ||\r
764 ((Operand >= EFI_IFR_MATCH_OP) && (Operand <= EFI_IFR_SET_OP)) ||\r
765 ((Operand >= EFI_IFR_EQUAL_OP) && (Operand <= EFI_IFR_SPAN_OP)) ||\r
766 (Operand == EFI_IFR_CATENATE_OP) ||\r
767 (Operand == EFI_IFR_TO_LOWER_OP) ||\r
768 (Operand == EFI_IFR_TO_UPPER_OP) ||\r
769 (Operand == EFI_IFR_MAP_OP) ||\r
770 (Operand == EFI_IFR_VERSION_OP) ||\r
771 (Operand == EFI_IFR_SECURITY_OP)) {\r
772 return TRUE;\r
773 } else {\r
774 return FALSE;\r
775 }\r
776}\r
777\r
778\r
779/**\r
780 Calculate number of Statemens(Questions) and Expression OpCodes.\r
781\r
782 @param FormSet The FormSet to be counted.\r
783 @param NumberOfStatement Number of Statemens(Questions)\r
784 @param NumberOfExpression Number of Expression OpCodes\r
785\r
786**/\r
787VOID\r
788CountOpCodes (\r
789 IN FORM_BROWSER_FORMSET *FormSet,\r
790 IN OUT UINT16 *NumberOfStatement,\r
791 IN OUT UINT16 *NumberOfExpression\r
792 )\r
793{\r
794 UINT16 StatementCount;\r
795 UINT16 ExpressionCount;\r
796 UINT8 *OpCodeData;\r
797 UINTN Offset;\r
798 UINTN OpCodeLen;\r
799\r
800 Offset = 0;\r
801 StatementCount = 0;\r
802 ExpressionCount = 0;\r
803\r
804 while (Offset < FormSet->IfrBinaryLength) {\r
805 OpCodeData = FormSet->IfrBinaryData + Offset;\r
806 OpCodeLen = ((EFI_IFR_OP_HEADER *) OpCodeData)->Length;\r
807 Offset += OpCodeLen;\r
808\r
809 if (IsExpressionOpCode (((EFI_IFR_OP_HEADER *) OpCodeData)->OpCode)) {\r
810 ExpressionCount++;\r
811 } else {\r
812 StatementCount++;\r
813 }\r
814 }\r
815\r
816 *NumberOfStatement = StatementCount;\r
817 *NumberOfExpression = ExpressionCount;\r
818}\r
819\r
820\r
821\r
822/**\r
823 Parse opcodes in the formset IFR binary.\r
824\r
825 @param FormSet Pointer of the FormSet data structure.\r
826\r
827 @retval EFI_SUCCESS Opcode parse success.\r
828 @retval Other Opcode parse fail.\r
829\r
830**/\r
831EFI_STATUS\r
832ParseOpCodes (\r
833 IN FORM_BROWSER_FORMSET *FormSet\r
834 )\r
835{\r
836 EFI_STATUS Status;\r
837 UINT16 Index;\r
838 FORM_BROWSER_FORM *CurrentForm;\r
839 FORM_BROWSER_STATEMENT *CurrentStatement;\r
840 EXPRESSION_OPCODE *ExpressionOpCode;\r
841 FORM_EXPRESSION *CurrentExpression;\r
842 UINT8 Operand;\r
843 UINT8 Scope;\r
844 UINTN OpCodeOffset;\r
845 UINTN OpCodeLength;\r
846 UINT8 *OpCodeData;\r
847 UINT8 ScopeOpCode;\r
848 FORMSET_STORAGE *Storage;\r
849 FORMSET_DEFAULTSTORE *DefaultStore;\r
850 QUESTION_DEFAULT *CurrentDefault;\r
851 QUESTION_OPTION *CurrentOption;\r
852 UINT8 Width;\r
853 CHAR8 *AsciiString;\r
854 UINT16 NumberOfStatement;\r
855 UINT16 NumberOfExpression;\r
856 EFI_IMAGE_ID *ImageId;\r
857 BOOLEAN SuppressForQuestion;\r
858 BOOLEAN SuppressForOption;\r
859 BOOLEAN InScopeOptionSuppress;\r
860 FORM_EXPRESSION *OptionSuppressExpression;\r
861 BOOLEAN InScopeFormSuppress;\r
862 FORM_EXPRESSION *FormSuppressExpression;\r
863 UINT16 DepthOfDisable;\r
864 BOOLEAN OpCodeDisabled;\r
865 BOOLEAN SingleOpCodeExpression;\r
866 BOOLEAN InScopeDefault;\r
867 EFI_HII_VALUE *Value;\r
868 EFI_IFR_FORM_MAP_METHOD *MapMethod;\r
869 UINT8 MapScopeDepth;\r
870 LIST_ENTRY *Link;\r
871 FORMSET_STORAGE *VarStorage;\r
872 LIST_ENTRY *MapExpressionList;\r
873 EFI_VARSTORE_ID TempVarstoreId;\r
874\r
875 mInScopeSubtitle = FALSE;\r
876 SuppressForQuestion = FALSE;\r
877 SuppressForOption = FALSE;\r
878 InScopeFormSuppress = FALSE;\r
879 mInScopeSuppress = FALSE;\r
880 InScopeOptionSuppress = FALSE;\r
881 mInScopeGrayOut = FALSE;\r
882 mInScopeDisable = FALSE;\r
883 DepthOfDisable = 0;\r
884 OpCodeDisabled = FALSE;\r
885 SingleOpCodeExpression = FALSE;\r
886 InScopeDefault = FALSE;\r
887 CurrentExpression = NULL;\r
888 CurrentDefault = NULL;\r
889 CurrentOption = NULL;\r
890 OptionSuppressExpression = NULL;\r
891 FormSuppressExpression = NULL;\r
892 ImageId = NULL;\r
893 MapMethod = NULL;\r
894 MapScopeDepth = 0;\r
895 Link = NULL;\r
896 VarStorage = NULL;\r
897 MapExpressionList = NULL;\r
898 TempVarstoreId = 0;\r
899\r
900 //\r
901 // Get the number of Statements and Expressions\r
902 //\r
903 CountOpCodes (FormSet, &NumberOfStatement, &NumberOfExpression);\r
904\r
905 mStatementIndex = 0;\r
906 FormSet->StatementBuffer = AllocateZeroPool (NumberOfStatement * sizeof (FORM_BROWSER_STATEMENT));\r
907 if (FormSet->StatementBuffer == NULL) {\r
908 return EFI_OUT_OF_RESOURCES;\r
909 }\r
910\r
911 mExpressionOpCodeIndex = 0;\r
912 FormSet->ExpressionBuffer = AllocateZeroPool (NumberOfExpression * sizeof (EXPRESSION_OPCODE));\r
913 if (FormSet->ExpressionBuffer == NULL) {\r
914 return EFI_OUT_OF_RESOURCES;\r
915 }\r
916\r
917 InitializeListHead (&FormSet->StorageListHead);\r
918 InitializeListHead (&FormSet->DefaultStoreListHead);\r
919 InitializeListHead (&FormSet->FormListHead);\r
920 ResetCurrentExpressionStack ();\r
921 ResetMapExpressionListStack ();\r
922\r
923 CurrentForm = NULL;\r
924 CurrentStatement = NULL;\r
925\r
926 ResetScopeStack ();\r
927\r
928 OpCodeOffset = 0;\r
929 while (OpCodeOffset < FormSet->IfrBinaryLength) {\r
930 OpCodeData = FormSet->IfrBinaryData + OpCodeOffset;\r
931\r
932 OpCodeLength = ((EFI_IFR_OP_HEADER *) OpCodeData)->Length;\r
933 OpCodeOffset += OpCodeLength;\r
934 Operand = ((EFI_IFR_OP_HEADER *) OpCodeData)->OpCode;\r
935 Scope = ((EFI_IFR_OP_HEADER *) OpCodeData)->Scope;\r
936\r
937 //\r
938 // If scope bit set, push onto scope stack\r
939 //\r
940 if (Scope != 0) {\r
941 PushScope (Operand);\r
942 }\r
943\r
944 if (OpCodeDisabled) {\r
945 //\r
946 // DisableIf Expression is evaluated to be TRUE, try to find its end.\r
947 // Here only cares the EFI_IFR_DISABLE_IF and EFI_IFR_END\r
948 //\r
949 if (Operand == EFI_IFR_DISABLE_IF_OP) {\r
950 DepthOfDisable++;\r
951 } else if (Operand == EFI_IFR_END_OP) {\r
952 Status = PopScope (&ScopeOpCode);\r
953 if (EFI_ERROR (Status)) {\r
954 return Status;\r
955 }\r
956\r
957 if (ScopeOpCode == EFI_IFR_DISABLE_IF_OP) {\r
958 if (DepthOfDisable == 0) {\r
959 mInScopeDisable = FALSE;\r
960 OpCodeDisabled = FALSE;\r
961 } else {\r
962 DepthOfDisable--;\r
963 }\r
964 }\r
965 }\r
966 continue;\r
967 }\r
968\r
969 if (IsExpressionOpCode (Operand)) {\r
970 ExpressionOpCode = &FormSet->ExpressionBuffer[mExpressionOpCodeIndex];\r
971 mExpressionOpCodeIndex++;\r
972\r
973 ExpressionOpCode->Signature = EXPRESSION_OPCODE_SIGNATURE;\r
974 ExpressionOpCode->Operand = Operand;\r
975 Value = &ExpressionOpCode->Value;\r
976\r
977 switch (Operand) {\r
978 case EFI_IFR_EQ_ID_VAL_OP:\r
979 CopyMem (&ExpressionOpCode->QuestionId, &((EFI_IFR_EQ_ID_VAL *) OpCodeData)->QuestionId, sizeof (EFI_QUESTION_ID));\r
980\r
981 Value->Type = EFI_IFR_TYPE_NUM_SIZE_16;\r
982 CopyMem (&Value->Value.u16, &((EFI_IFR_EQ_ID_VAL *) OpCodeData)->Value, sizeof (UINT16));\r
983 break;\r
984\r
985 case EFI_IFR_EQ_ID_ID_OP:\r
986 CopyMem (&ExpressionOpCode->QuestionId, &((EFI_IFR_EQ_ID_ID *) OpCodeData)->QuestionId1, sizeof (EFI_QUESTION_ID));\r
987 CopyMem (&ExpressionOpCode->QuestionId2, &((EFI_IFR_EQ_ID_ID *) OpCodeData)->QuestionId2, sizeof (EFI_QUESTION_ID));\r
988 break;\r
989\r
990 case EFI_IFR_EQ_ID_LIST_OP:\r
991 CopyMem (&ExpressionOpCode->QuestionId, &((EFI_IFR_EQ_ID_VAL_LIST *) OpCodeData)->QuestionId, sizeof (EFI_QUESTION_ID));\r
992 CopyMem (&ExpressionOpCode->ListLength, &((EFI_IFR_EQ_ID_VAL_LIST *) OpCodeData)->ListLength, sizeof (UINT16));\r
993 ExpressionOpCode->ValueList = AllocateCopyPool (ExpressionOpCode->ListLength * sizeof (UINT16), &((EFI_IFR_EQ_ID_VAL_LIST *) OpCodeData)->ValueList);\r
994 break;\r
995\r
996 case EFI_IFR_TO_STRING_OP:\r
997 case EFI_IFR_FIND_OP:\r
998 ExpressionOpCode->Format = (( EFI_IFR_TO_STRING *) OpCodeData)->Format;\r
999 break;\r
1000\r
1001 case EFI_IFR_STRING_REF1_OP:\r
1002 Value->Type = EFI_IFR_TYPE_STRING;\r
1003 CopyMem (&Value->Value.string, &(( EFI_IFR_STRING_REF1 *) OpCodeData)->StringId, sizeof (EFI_STRING_ID));\r
1004 break;\r
1005\r
1006 case EFI_IFR_RULE_REF_OP:\r
1007 ExpressionOpCode->RuleId = (( EFI_IFR_RULE_REF *) OpCodeData)->RuleId;\r
1008 break;\r
1009\r
1010 case EFI_IFR_SPAN_OP:\r
1011 ExpressionOpCode->Flags = (( EFI_IFR_SPAN *) OpCodeData)->Flags;\r
1012 break;\r
1013\r
1014 case EFI_IFR_THIS_OP:\r
1015 ASSERT (CurrentStatement != NULL);\r
1016 ExpressionOpCode->QuestionId = CurrentStatement->QuestionId;\r
1017 break;\r
1018\r
1019 case EFI_IFR_SECURITY_OP:\r
1020 CopyMem (&ExpressionOpCode->Guid, &((EFI_IFR_SECURITY *) OpCodeData)->Permissions, sizeof (EFI_GUID));\r
1021 break;\r
1022\r
1023 case EFI_IFR_GET_OP:\r
1024 case EFI_IFR_SET_OP:\r
1025 CopyMem (&TempVarstoreId, &((EFI_IFR_GET *) OpCodeData)->VarStoreId, sizeof (TempVarstoreId));\r
1026 if (TempVarstoreId != 0) {\r
1027 if (FormSet->StorageListHead.ForwardLink != NULL) {\r
1028 Link = GetFirstNode (&FormSet->StorageListHead);\r
1029 while (!IsNull (&FormSet->StorageListHead, Link)) {\r
1030 VarStorage = FORMSET_STORAGE_FROM_LINK (Link);\r
1031 if (VarStorage->VarStoreId == ((EFI_IFR_GET *) OpCodeData)->VarStoreId) {\r
1032 ExpressionOpCode->VarStorage = VarStorage;\r
1033 break;\r
1034 }\r
1035 Link = GetNextNode (&FormSet->StorageListHead, Link);\r
1036 }\r
1037 }\r
1038 if (ExpressionOpCode->VarStorage == NULL) {\r
1039 //\r
1040 // VarStorage is not found.\r
1041 //\r
1042 return EFI_INVALID_PARAMETER;\r
1043 }\r
1044 }\r
1045 ExpressionOpCode->ValueType = ((EFI_IFR_GET *) OpCodeData)->VarStoreType;\r
1046 switch (ExpressionOpCode->ValueType) {\r
1047 case EFI_IFR_TYPE_BOOLEAN:\r
1048 case EFI_IFR_TYPE_NUM_SIZE_8: \r
1049 ExpressionOpCode->ValueWidth = 1;\r
1050 break;\r
1051\r
1052 case EFI_IFR_TYPE_NUM_SIZE_16:\r
1053 case EFI_IFR_TYPE_STRING:\r
1054 ExpressionOpCode->ValueWidth = 2;\r
1055 break;\r
1056\r
1057 case EFI_IFR_TYPE_NUM_SIZE_32:\r
1058 ExpressionOpCode->ValueWidth = 4;\r
1059 break;\r
1060\r
1061 case EFI_IFR_TYPE_NUM_SIZE_64:\r
1062 ExpressionOpCode->ValueWidth = 8;\r
1063 break;\r
1064\r
1065 case EFI_IFR_TYPE_DATE:\r
1066 ExpressionOpCode->ValueWidth = (UINT8) sizeof (EFI_IFR_DATE);\r
1067 break;\r
1068\r
1069 case EFI_IFR_TYPE_TIME:\r
1070 ExpressionOpCode->ValueWidth = (UINT8) sizeof (EFI_IFR_TIME);\r
1071 break;\r
1072\r
1073 case EFI_IFR_TYPE_OTHER:\r
1074 case EFI_IFR_TYPE_UNDEFINED:\r
1075 case EFI_IFR_TYPE_ACTION:\r
1076 case EFI_IFR_TYPE_BUFFER:\r
1077 default:\r
1078 //\r
1079 // Invalid value type for Get/Set opcode.\r
1080 //\r
1081 return EFI_INVALID_PARAMETER;\r
1082 }\r
1083 CopyMem (&ExpressionOpCode->VarStoreInfo.VarName, &((EFI_IFR_GET *) OpCodeData)->VarStoreInfo.VarName, sizeof (EFI_STRING_ID));\r
1084 CopyMem (&ExpressionOpCode->VarStoreInfo.VarOffset, &((EFI_IFR_GET *) OpCodeData)->VarStoreInfo.VarOffset, sizeof (UINT16));\r
1085 if ((ExpressionOpCode->VarStorage != NULL) && \r
1086 (ExpressionOpCode->VarStorage->Type == EFI_HII_VARSTORE_NAME_VALUE || \r
1087 ExpressionOpCode->VarStorage->Type == EFI_HII_VARSTORE_EFI_VARIABLE)) {\r
1088 ExpressionOpCode->ValueName = GetToken (ExpressionOpCode->VarStoreInfo.VarName, FormSet->HiiHandle);\r
1089 if (ExpressionOpCode->ValueName == NULL) {\r
1090 //\r
1091 // String ID is invalid.\r
1092 //\r
1093 return EFI_INVALID_PARAMETER;\r
1094 }\r
1095 }\r
1096 break;\r
1097\r
1098 case EFI_IFR_QUESTION_REF1_OP:\r
1099 CopyMem (&ExpressionOpCode->QuestionId, &((EFI_IFR_EQ_ID_VAL_LIST *) OpCodeData)->QuestionId, sizeof (EFI_QUESTION_ID));\r
1100 break;\r
1101\r
1102 case EFI_IFR_QUESTION_REF3_OP:\r
1103 if (OpCodeLength >= sizeof (EFI_IFR_QUESTION_REF3_2)) {\r
1104 CopyMem (&ExpressionOpCode->DevicePath, &(( EFI_IFR_QUESTION_REF3_2 *) OpCodeData)->DevicePath, sizeof (EFI_STRING_ID));\r
1105\r
1106 if (OpCodeLength >= sizeof (EFI_IFR_QUESTION_REF3_3)) {\r
1107 CopyMem (&ExpressionOpCode->Guid, &(( EFI_IFR_QUESTION_REF3_3 *) OpCodeData)->Guid, sizeof (EFI_GUID));\r
1108 }\r
1109 }\r
1110 break;\r
1111\r
1112 //\r
1113 // constant\r
1114 //\r
1115 case EFI_IFR_TRUE_OP:\r
1116 Value->Type = EFI_IFR_TYPE_BOOLEAN;\r
1117 Value->Value.b = TRUE;\r
1118 break;\r
1119\r
1120 case EFI_IFR_FALSE_OP:\r
1121 Value->Type = EFI_IFR_TYPE_BOOLEAN;\r
1122 Value->Value.b = FALSE;\r
1123 break;\r
1124\r
1125 case EFI_IFR_ONE_OP:\r
1126 Value->Type = EFI_IFR_TYPE_NUM_SIZE_8;\r
1127 Value->Value.u8 = 1;\r
1128 break;\r
1129\r
1130 case EFI_IFR_ZERO_OP:\r
1131 Value->Type = EFI_IFR_TYPE_NUM_SIZE_8;\r
1132 Value->Value.u8 = 0;\r
1133 break;\r
1134\r
1135 case EFI_IFR_ONES_OP:\r
1136 Value->Type = EFI_IFR_TYPE_NUM_SIZE_64;\r
1137 Value->Value.u64 = 0xffffffffffffffffULL;\r
1138 break;\r
1139\r
1140 case EFI_IFR_UINT8_OP:\r
1141 Value->Type = EFI_IFR_TYPE_NUM_SIZE_8;\r
1142 Value->Value.u8 = (( EFI_IFR_UINT8 *) OpCodeData)->Value;\r
1143 break;\r
1144\r
1145 case EFI_IFR_UINT16_OP:\r
1146 Value->Type = EFI_IFR_TYPE_NUM_SIZE_16;\r
1147 CopyMem (&Value->Value.u16, &(( EFI_IFR_UINT16 *) OpCodeData)->Value, sizeof (UINT16));\r
1148 break;\r
1149\r
1150 case EFI_IFR_UINT32_OP:\r
1151 Value->Type = EFI_IFR_TYPE_NUM_SIZE_32;\r
1152 CopyMem (&Value->Value.u32, &(( EFI_IFR_UINT32 *) OpCodeData)->Value, sizeof (UINT32));\r
1153 break;\r
1154\r
1155 case EFI_IFR_UINT64_OP:\r
1156 Value->Type = EFI_IFR_TYPE_NUM_SIZE_64;\r
1157 CopyMem (&Value->Value.u64, &(( EFI_IFR_UINT64 *) OpCodeData)->Value, sizeof (UINT64));\r
1158 break;\r
1159\r
1160 case EFI_IFR_UNDEFINED_OP:\r
1161 Value->Type = EFI_IFR_TYPE_UNDEFINED;\r
1162 break;\r
1163\r
1164 case EFI_IFR_VERSION_OP:\r
1165 Value->Type = EFI_IFR_TYPE_NUM_SIZE_16;\r
1166 Value->Value.u16 = EFI_IFR_SPECIFICATION_VERSION;\r
1167 break;\r
1168\r
1169 default:\r
1170 break;\r
1171 }\r
1172 //\r
1173 // Create sub expression nested in MAP opcode\r
1174 //\r
1175 if (CurrentExpression == NULL && MapScopeDepth > 0) {\r
1176 CurrentExpression = CreateExpression (CurrentForm);\r
1177 ASSERT (MapExpressionList != NULL);\r
1178 InsertTailList (MapExpressionList, &CurrentExpression->Link);\r
1179 if (Scope == 0) {\r
1180 SingleOpCodeExpression = TRUE;\r
1181 }\r
1182 }\r
1183 ASSERT (CurrentExpression != NULL);\r
1184 InsertTailList (&CurrentExpression->OpCodeListHead, &ExpressionOpCode->Link);\r
1185 if (Operand == EFI_IFR_MAP_OP) {\r
1186 //\r
1187 // Store current Map Expression List.\r
1188 //\r
1189 if (MapExpressionList != NULL) {\r
1190 PushMapExpressionList (MapExpressionList);\r
1191 }\r
1192 //\r
1193 // Initialize new Map Expression List.\r
1194 //\r
1195 MapExpressionList = &ExpressionOpCode->MapExpressionList;\r
1196 InitializeListHead (MapExpressionList);\r
1197 //\r
1198 // Store current expression.\r
1199 //\r
1200 PushCurrentExpression (CurrentExpression);\r
1201 CurrentExpression = NULL;\r
1202 MapScopeDepth ++;\r
1203 } else if (SingleOpCodeExpression) {\r
1204 //\r
1205 // There are two cases to indicate the end of an Expression:\r
1206 // for single OpCode expression: one Expression OpCode\r
1207 // for expression consists of more than one OpCode: EFI_IFR_END\r
1208 //\r
1209 SingleOpCodeExpression = FALSE;\r
1210\r
1211 if (mInScopeDisable && CurrentForm == NULL) {\r
1212 //\r
1213 // This is DisableIf expression for Form, it should be a constant expression\r
1214 //\r
1215 Status = EvaluateExpression (FormSet, CurrentForm, CurrentExpression);\r
1216 if (EFI_ERROR (Status)) {\r
1217 return Status;\r
1218 }\r
1219\r
1220 if (CurrentExpression->Result.Type != EFI_IFR_TYPE_BOOLEAN) {\r
1221 return EFI_INVALID_PARAMETER;\r
1222 }\r
1223\r
1224 OpCodeDisabled = CurrentExpression->Result.Value.b;\r
1225 }\r
1226\r
1227 CurrentExpression = NULL;\r
1228 }\r
1229\r
1230 continue;\r
1231 }\r
1232\r
1233 //\r
1234 // Parse the Opcode\r
1235 //\r
1236 switch (Operand) {\r
1237\r
1238 case EFI_IFR_FORM_SET_OP:\r
1239 //\r
1240 // Check the formset GUID\r
1241 //\r
1242 if (CompareMem (&FormSet->Guid, &((EFI_IFR_FORM_SET *) OpCodeData)->Guid, sizeof (EFI_GUID)) != 0) {\r
1243 return EFI_INVALID_PARAMETER;\r
1244 }\r
1245\r
1246 CopyMem (&FormSet->FormSetTitle, &((EFI_IFR_FORM_SET *) OpCodeData)->FormSetTitle, sizeof (EFI_STRING_ID));\r
1247 CopyMem (&FormSet->Help, &((EFI_IFR_FORM_SET *) OpCodeData)->Help, sizeof (EFI_STRING_ID));\r
1248\r
1249 if (OpCodeLength > OFFSET_OF (EFI_IFR_FORM_SET, Flags)) {\r
1250 //\r
1251 // The formset OpCode contains ClassGuid\r
1252 //\r
1253 FormSet->NumberOfClassGuid = (UINT8) (((EFI_IFR_FORM_SET *) OpCodeData)->Flags & 0x3);\r
1254 CopyMem (FormSet->ClassGuid, OpCodeData + sizeof (EFI_IFR_FORM_SET), FormSet->NumberOfClassGuid * sizeof (EFI_GUID));\r
1255 }\r
1256\r
1257 InitializeListHead (&FormSet->ExpressionListHead);\r
1258 break;\r
1259\r
1260 case EFI_IFR_FORM_OP:\r
1261 //\r
1262 // Create a new Form for this FormSet\r
1263 //\r
1264 CurrentForm = AllocateZeroPool (sizeof (FORM_BROWSER_FORM));\r
1265 ASSERT (CurrentForm != NULL);\r
1266 CurrentForm->Signature = FORM_BROWSER_FORM_SIGNATURE;\r
1267 InitializeListHead (&CurrentForm->ExpressionListHead);\r
1268 InitializeListHead (&CurrentForm->StatementListHead);\r
1269\r
1270 CurrentForm->FormType = STANDARD_MAP_FORM_TYPE;\r
1271 CopyMem (&CurrentForm->FormId, &((EFI_IFR_FORM *) OpCodeData)->FormId, sizeof (UINT16));\r
1272 CopyMem (&CurrentForm->FormTitle, &((EFI_IFR_FORM *) OpCodeData)->FormTitle, sizeof (EFI_STRING_ID));\r
1273\r
1274 if (InScopeFormSuppress) {\r
1275 //\r
1276 // Form is inside of suppressif\r
1277 //\r
1278 CurrentForm->SuppressExpression = FormSuppressExpression;\r
1279 }\r
1280\r
1281 if (Scope != 0) {\r
1282 //\r
1283 // Enter scope of a Form, suppressif will be used for Question or Option\r
1284 //\r
1285 SuppressForQuestion = TRUE;\r
1286 }\r
1287\r
1288 //\r
1289 // Insert into Form list of this FormSet\r
1290 //\r
1291 InsertTailList (&FormSet->FormListHead, &CurrentForm->Link);\r
1292 break;\r
1293\r
1294 case EFI_IFR_FORM_MAP_OP:\r
1295 //\r
1296 // Create a new Form for this FormSet\r
1297 //\r
1298 CurrentForm = AllocateZeroPool (sizeof (FORM_BROWSER_FORM));\r
1299 ASSERT (CurrentForm != NULL);\r
1300 CurrentForm->Signature = FORM_BROWSER_FORM_SIGNATURE;\r
1301 InitializeListHead (&CurrentForm->ExpressionListHead);\r
1302 InitializeListHead (&CurrentForm->StatementListHead);\r
1303 CopyMem (&CurrentForm->FormId, &((EFI_IFR_FORM *) OpCodeData)->FormId, sizeof (UINT16));\r
1304\r
1305 MapMethod = (EFI_IFR_FORM_MAP_METHOD *) (OpCodeData + sizeof (EFI_IFR_FORM_MAP));\r
1306 //\r
1307 // FormMap Form must contain at least one Map Method.\r
1308 //\r
1309 if (((EFI_IFR_OP_HEADER *) OpCodeData)->Length < ((UINTN) (UINT8 *) (MapMethod + 1) - (UINTN) OpCodeData)) {\r
1310 return EFI_INVALID_PARAMETER;\r
1311 }\r
1312 //\r
1313 // Try to find the standard form map method.\r
1314 //\r
1315 while (((UINTN) (UINT8 *) MapMethod - (UINTN) OpCodeData) < ((EFI_IFR_OP_HEADER *) OpCodeData)->Length) {\r
1316 if (CompareGuid ((EFI_GUID *) (VOID *) &MapMethod->MethodIdentifier, &gEfiHiiStandardFormGuid)) {\r
1317 CopyMem (&CurrentForm->FormTitle, &MapMethod->MethodTitle, sizeof (EFI_STRING_ID));\r
1318 CurrentForm->FormType = STANDARD_MAP_FORM_TYPE;\r
1319 break;\r
1320 }\r
1321 MapMethod ++;\r
1322 }\r
1323 //\r
1324 // If the standard form map method is not found, the first map method title will be used.\r
1325 //\r
1326 if (CurrentForm->FormTitle == 0) {\r
1327 MapMethod = (EFI_IFR_FORM_MAP_METHOD *) (OpCodeData + sizeof (EFI_IFR_FORM_MAP));\r
1328 CopyMem (&CurrentForm->FormTitle, &MapMethod->MethodTitle, sizeof (EFI_STRING_ID));\r
1329 }\r
1330\r
1331 if (InScopeFormSuppress) {\r
1332 //\r
1333 // Form is inside of suppressif\r
1334 //\r
1335 CurrentForm->SuppressExpression = FormSuppressExpression;\r
1336 }\r
1337\r
1338 if (Scope != 0) {\r
1339 //\r
1340 // Enter scope of a Form, suppressif will be used for Question or Option\r
1341 //\r
1342 SuppressForQuestion = TRUE;\r
1343 }\r
1344\r
1345 //\r
1346 // Insert into Form list of this FormSet\r
1347 //\r
1348 InsertTailList (&FormSet->FormListHead, &CurrentForm->Link);\r
1349 break;\r
1350\r
1351 //\r
1352 // Storage\r
1353 //\r
1354 case EFI_IFR_VARSTORE_OP:\r
1355 //\r
1356 // Create a buffer Storage for this FormSet\r
1357 //\r
1358 Storage = CreateStorage (FormSet);\r
1359 Storage->Type = EFI_HII_VARSTORE_BUFFER;\r
1360\r
1361 CopyMem (&Storage->VarStoreId, &((EFI_IFR_VARSTORE *) OpCodeData)->VarStoreId, sizeof (EFI_VARSTORE_ID));\r
1362 CopyMem (&Storage->Guid, &((EFI_IFR_VARSTORE *) OpCodeData)->Guid, sizeof (EFI_GUID));\r
1363 CopyMem (&Storage->Size, &((EFI_IFR_VARSTORE *) OpCodeData)->Size, sizeof (UINT16));\r
1364\r
1365 Storage->Buffer = AllocateZeroPool (Storage->Size);\r
1366 Storage->EditBuffer = AllocateZeroPool (Storage->Size);\r
1367\r
1368 AsciiString = (CHAR8 *) ((EFI_IFR_VARSTORE *) OpCodeData)->Name;\r
1369 Storage->Name = AllocateZeroPool (AsciiStrSize (AsciiString) * 2);\r
1370 ASSERT (Storage->Name != NULL);\r
1371 for (Index = 0; AsciiString[Index] != 0; Index++) {\r
1372 Storage->Name[Index] = (CHAR16) AsciiString[Index];\r
1373 }\r
1374\r
1375 //\r
1376 // Initialize <ConfigHdr>\r
1377 //\r
1378 InitializeConfigHdr (FormSet, Storage);\r
1379 break;\r
1380\r
1381 case EFI_IFR_VARSTORE_NAME_VALUE_OP:\r
1382 //\r
1383 // Create a name/value Storage for this FormSet\r
1384 //\r
1385 Storage = CreateStorage (FormSet);\r
1386 Storage->Type = EFI_HII_VARSTORE_NAME_VALUE;\r
1387\r
1388 CopyMem (&Storage->VarStoreId, &((EFI_IFR_VARSTORE_NAME_VALUE *) OpCodeData)->VarStoreId, sizeof (EFI_VARSTORE_ID));\r
1389 CopyMem (&Storage->Guid, &((EFI_IFR_VARSTORE_NAME_VALUE *) OpCodeData)->Guid, sizeof (EFI_GUID));\r
1390\r
1391 //\r
1392 // Initialize <ConfigHdr>\r
1393 //\r
1394 InitializeConfigHdr (FormSet, Storage);\r
1395 break;\r
1396\r
1397 case EFI_IFR_VARSTORE_EFI_OP:\r
1398 //\r
1399 // Create a EFI variable Storage for this FormSet\r
1400 //\r
1401 Storage = CreateStorage (FormSet);\r
1402 Storage->Type = EFI_HII_VARSTORE_EFI_VARIABLE;\r
1403\r
1404 CopyMem (&Storage->VarStoreId, &((EFI_IFR_VARSTORE_EFI *) OpCodeData)->VarStoreId, sizeof (EFI_VARSTORE_ID));\r
1405 CopyMem (&Storage->Guid, &((EFI_IFR_VARSTORE_EFI *) OpCodeData)->Guid, sizeof (EFI_GUID));\r
1406 CopyMem (&Storage->Attributes, &((EFI_IFR_VARSTORE_EFI *) OpCodeData)->Attributes, sizeof (UINT32));\r
1407 break;\r
1408\r
1409 //\r
1410 // DefaultStore\r
1411 //\r
1412 case EFI_IFR_DEFAULTSTORE_OP:\r
1413 DefaultStore = AllocateZeroPool (sizeof (FORMSET_DEFAULTSTORE));\r
1414 ASSERT (DefaultStore != NULL);\r
1415 DefaultStore->Signature = FORMSET_DEFAULTSTORE_SIGNATURE;\r
1416\r
1417 CopyMem (&DefaultStore->DefaultId, &((EFI_IFR_DEFAULTSTORE *) OpCodeData)->DefaultId, sizeof (UINT16));\r
1418 CopyMem (&DefaultStore->DefaultName, &((EFI_IFR_DEFAULTSTORE *) OpCodeData)->DefaultName, sizeof (EFI_STRING_ID));\r
1419\r
1420 //\r
1421 // Insert to DefaultStore list of this Formset\r
1422 //\r
1423 InsertTailList (&FormSet->DefaultStoreListHead, &DefaultStore->Link);\r
1424 break;\r
1425\r
1426 //\r
1427 // Statements\r
1428 //\r
1429 case EFI_IFR_SUBTITLE_OP:\r
1430 CurrentStatement = CreateStatement (OpCodeData, FormSet, CurrentForm);\r
1431 ASSERT (CurrentStatement != NULL);\r
1432\r
1433 CurrentStatement->Flags = ((EFI_IFR_SUBTITLE *) OpCodeData)->Flags;\r
1434\r
1435 if (Scope != 0) {\r
1436 mInScopeSubtitle = TRUE;\r
1437 }\r
1438 break;\r
1439\r
1440 case EFI_IFR_TEXT_OP:\r
1441 CurrentStatement = CreateStatement (OpCodeData, FormSet, CurrentForm);\r
1442 ASSERT (CurrentStatement != NULL);\r
1443\r
1444 CopyMem (&CurrentStatement->TextTwo, &((EFI_IFR_TEXT *) OpCodeData)->TextTwo, sizeof (EFI_STRING_ID));\r
1445 break;\r
1446\r
1447 case EFI_IFR_RESET_BUTTON_OP:\r
1448 CurrentStatement = CreateStatement (OpCodeData, FormSet, CurrentForm);\r
1449 ASSERT (CurrentStatement != NULL);\r
1450 CopyMem (&CurrentStatement->DefaultId, &((EFI_IFR_RESET_BUTTON *) OpCodeData)->DefaultId, sizeof (EFI_DEFAULT_ID));\r
1451 break;\r
1452\r
1453 //\r
1454 // Questions\r
1455 //\r
1456 case EFI_IFR_ACTION_OP:\r
1457 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1458 ASSERT (CurrentStatement != NULL);\r
1459 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_ACTION;\r
1460\r
1461 if (OpCodeLength == sizeof (EFI_IFR_ACTION_1)) {\r
1462 //\r
1463 // No QuestionConfig present, so no configuration string will be processed\r
1464 //\r
1465 CurrentStatement->QuestionConfig = 0;\r
1466 } else {\r
1467 CopyMem (&CurrentStatement->QuestionConfig, &((EFI_IFR_ACTION *) OpCodeData)->QuestionConfig, sizeof (EFI_STRING_ID));\r
1468 }\r
1469 break;\r
1470\r
1471 case EFI_IFR_REF_OP:\r
1472 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1473 ASSERT (CurrentStatement != NULL);\r
1474 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_UNDEFINED;\r
1475 CopyMem (&CurrentStatement->RefFormId, &((EFI_IFR_REF *) OpCodeData)->FormId, sizeof (EFI_FORM_ID));\r
1476 if (OpCodeLength >= sizeof (EFI_IFR_REF2)) {\r
1477 CopyMem (&CurrentStatement->RefQuestionId, &((EFI_IFR_REF2 *) OpCodeData)->QuestionId, sizeof (EFI_QUESTION_ID));\r
1478\r
1479 if (OpCodeLength >= sizeof (EFI_IFR_REF3)) {\r
1480 CopyMem (&CurrentStatement->RefFormSetId, &((EFI_IFR_REF3 *) OpCodeData)->FormSetId, sizeof (EFI_GUID));\r
1481\r
1482 if (OpCodeLength >= sizeof (EFI_IFR_REF4)) {\r
1483 CopyMem (&CurrentStatement->RefDevicePath, &((EFI_IFR_REF4 *) OpCodeData)->DevicePath, sizeof (EFI_STRING_ID));\r
1484 }\r
1485 }\r
1486 }\r
1487 break;\r
1488\r
1489 case EFI_IFR_ONE_OF_OP:\r
1490 case EFI_IFR_NUMERIC_OP:\r
1491 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1492 ASSERT(CurrentStatement != NULL);\r
1493\r
1494 CurrentStatement->Flags = ((EFI_IFR_ONE_OF *) OpCodeData)->Flags;\r
1495 Value = &CurrentStatement->HiiValue;\r
1496\r
1497 switch (CurrentStatement->Flags & EFI_IFR_NUMERIC_SIZE) {\r
1498 case EFI_IFR_NUMERIC_SIZE_1:\r
1499 CurrentStatement->Minimum = ((EFI_IFR_NUMERIC *) OpCodeData)->data.u8.MinValue;\r
1500 CurrentStatement->Maximum = ((EFI_IFR_NUMERIC *) OpCodeData)->data.u8.MaxValue;\r
1501 CurrentStatement->Step = ((EFI_IFR_NUMERIC *) OpCodeData)->data.u8.Step;\r
1502 CurrentStatement->StorageWidth = (UINT16) sizeof (UINT8);\r
1503 Value->Type = EFI_IFR_TYPE_NUM_SIZE_8;\r
1504 break;\r
1505\r
1506 case EFI_IFR_NUMERIC_SIZE_2:\r
1507 CopyMem (&CurrentStatement->Minimum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u16.MinValue, sizeof (UINT16));\r
1508 CopyMem (&CurrentStatement->Maximum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u16.MaxValue, sizeof (UINT16));\r
1509 CopyMem (&CurrentStatement->Step, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u16.Step, sizeof (UINT16));\r
1510 CurrentStatement->StorageWidth = (UINT16) sizeof (UINT16);\r
1511 Value->Type = EFI_IFR_TYPE_NUM_SIZE_16;\r
1512 break;\r
1513\r
1514 case EFI_IFR_NUMERIC_SIZE_4:\r
1515 CopyMem (&CurrentStatement->Minimum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u32.MinValue, sizeof (UINT32));\r
1516 CopyMem (&CurrentStatement->Maximum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u32.MaxValue, sizeof (UINT32));\r
1517 CopyMem (&CurrentStatement->Step, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u32.Step, sizeof (UINT32));\r
1518 CurrentStatement->StorageWidth = (UINT16) sizeof (UINT32);\r
1519 Value->Type = EFI_IFR_TYPE_NUM_SIZE_32;\r
1520 break;\r
1521\r
1522 case EFI_IFR_NUMERIC_SIZE_8:\r
1523 CopyMem (&CurrentStatement->Minimum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u64.MinValue, sizeof (UINT64));\r
1524 CopyMem (&CurrentStatement->Maximum, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u64.MaxValue, sizeof (UINT64));\r
1525 CopyMem (&CurrentStatement->Step, &((EFI_IFR_NUMERIC *) OpCodeData)->data.u64.Step, sizeof (UINT64));\r
1526 CurrentStatement->StorageWidth = (UINT16) sizeof (UINT64);\r
1527 Value->Type = EFI_IFR_TYPE_NUM_SIZE_64;\r
1528 break;\r
1529\r
1530 default:\r
1531 break;\r
1532 }\r
1533\r
1534 InitializeRequestElement (FormSet, CurrentStatement);\r
1535\r
1536 if ((Operand == EFI_IFR_ONE_OF_OP) && Scope != 0) {\r
1537 SuppressForOption = TRUE;\r
1538 }\r
1539 break;\r
1540\r
1541 case EFI_IFR_ORDERED_LIST_OP:\r
1542 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1543 ASSERT(CurrentStatement != NULL);\r
1544\r
1545 CurrentStatement->Flags = ((EFI_IFR_ORDERED_LIST *) OpCodeData)->Flags;\r
1546 CurrentStatement->MaxContainers = ((EFI_IFR_ORDERED_LIST *) OpCodeData)->MaxContainers;\r
1547\r
1548 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_BUFFER;\r
1549 CurrentStatement->BufferValue = NULL;\r
1550\r
1551 if (Scope != 0) {\r
1552 SuppressForOption = TRUE;\r
1553 }\r
1554 break;\r
1555\r
1556 case EFI_IFR_CHECKBOX_OP:\r
1557 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1558 ASSERT(CurrentStatement != NULL);\r
1559\r
1560 CurrentStatement->Flags = ((EFI_IFR_CHECKBOX *) OpCodeData)->Flags;\r
1561 CurrentStatement->StorageWidth = (UINT16) sizeof (BOOLEAN);\r
1562 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_BOOLEAN;\r
1563\r
1564 InitializeRequestElement (FormSet, CurrentStatement);\r
1565\r
1566 break;\r
1567\r
1568 case EFI_IFR_STRING_OP:\r
1569 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1570 ASSERT (CurrentStatement != NULL);\r
1571 //\r
1572 // MinSize is the minimum number of characters that can be accepted for this opcode,\r
1573 // MaxSize is the maximum number of characters that can be accepted for this opcode.\r
1574 // The characters are stored as Unicode, so the storage width should multiply 2.\r
1575 //\r
1576 CurrentStatement->Minimum = ((EFI_IFR_STRING *) OpCodeData)->MinSize;\r
1577 CurrentStatement->Maximum = ((EFI_IFR_STRING *) OpCodeData)->MaxSize;\r
1578 CurrentStatement->StorageWidth = (UINT16)((UINTN) CurrentStatement->Maximum * sizeof (CHAR16));\r
1579 CurrentStatement->Flags = ((EFI_IFR_STRING *) OpCodeData)->Flags;\r
1580\r
1581 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_STRING;\r
1582 CurrentStatement->BufferValue = AllocateZeroPool (CurrentStatement->StorageWidth + sizeof (CHAR16));\r
1583\r
1584 InitializeRequestElement (FormSet, CurrentStatement);\r
1585 break;\r
1586\r
1587 case EFI_IFR_PASSWORD_OP:\r
1588 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1589 ASSERT (CurrentStatement != NULL);\r
1590 //\r
1591 // MinSize is the minimum number of characters that can be accepted for this opcode,\r
1592 // MaxSize is the maximum number of characters that can be accepted for this opcode.\r
1593 // The characters are stored as Unicode, so the storage width should multiply 2.\r
1594 //\r
1595 CopyMem (&CurrentStatement->Minimum, &((EFI_IFR_PASSWORD *) OpCodeData)->MinSize, sizeof (UINT16));\r
1596 CopyMem (&CurrentStatement->Maximum, &((EFI_IFR_PASSWORD *) OpCodeData)->MaxSize, sizeof (UINT16));\r
1597 CurrentStatement->StorageWidth = (UINT16)((UINTN) CurrentStatement->Maximum * sizeof (CHAR16));\r
1598\r
1599 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_STRING;\r
1600 CurrentStatement->BufferValue = AllocateZeroPool ((CurrentStatement->StorageWidth + sizeof (CHAR16)));\r
1601\r
1602 InitializeRequestElement (FormSet, CurrentStatement);\r
1603 break;\r
1604\r
1605 case EFI_IFR_DATE_OP:\r
1606 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1607 ASSERT(CurrentStatement != NULL);\r
1608\r
1609 CurrentStatement->Flags = ((EFI_IFR_DATE *) OpCodeData)->Flags;\r
1610 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_DATE;\r
1611\r
1612 if ((CurrentStatement->Flags & EFI_QF_DATE_STORAGE) == QF_DATE_STORAGE_NORMAL) {\r
1613 CurrentStatement->StorageWidth = (UINT16) sizeof (EFI_HII_DATE);\r
1614\r
1615 InitializeRequestElement (FormSet, CurrentStatement);\r
1616 } else {\r
1617 //\r
1618 // Don't assign storage for RTC type of date/time\r
1619 //\r
1620 CurrentStatement->Storage = NULL;\r
1621 CurrentStatement->StorageWidth = 0;\r
1622 }\r
1623 break;\r
1624\r
1625 case EFI_IFR_TIME_OP:\r
1626 CurrentStatement = CreateQuestion (OpCodeData, FormSet, CurrentForm);\r
1627 ASSERT(CurrentStatement != NULL);\r
1628\r
1629 CurrentStatement->Flags = ((EFI_IFR_TIME *) OpCodeData)->Flags;\r
1630 CurrentStatement->HiiValue.Type = EFI_IFR_TYPE_TIME;\r
1631\r
1632 if ((CurrentStatement->Flags & QF_TIME_STORAGE) == QF_TIME_STORAGE_NORMAL) {\r
1633 CurrentStatement->StorageWidth = (UINT16) sizeof (EFI_IFR_TIME);\r
1634\r
1635 InitializeRequestElement (FormSet, CurrentStatement);\r
1636 } else {\r
1637 //\r
1638 // Don't assign storage for RTC type of date/time\r
1639 //\r
1640 CurrentStatement->Storage = NULL;\r
1641 CurrentStatement->StorageWidth = 0;\r
1642 }\r
1643 break;\r
1644\r
1645 //\r
1646 // Default\r
1647 //\r
1648 case EFI_IFR_DEFAULT_OP:\r
1649 //\r
1650 // EFI_IFR_DEFAULT appear in scope of a Question,\r
1651 // It creates a default value for the current question.\r
1652 // A Question may have more than one Default value which have different default types.\r
1653 //\r
1654 CurrentDefault = AllocateZeroPool (sizeof (QUESTION_DEFAULT));\r
1655 ASSERT (CurrentDefault != NULL);\r
1656 CurrentDefault->Signature = QUESTION_DEFAULT_SIGNATURE;\r
1657\r
1658 CurrentDefault->Value.Type = ((EFI_IFR_DEFAULT *) OpCodeData)->Type;\r
1659 CopyMem (&CurrentDefault->DefaultId, &((EFI_IFR_DEFAULT *) OpCodeData)->DefaultId, sizeof (UINT16));\r
1660 CopyMem (&CurrentDefault->Value.Value, &((EFI_IFR_DEFAULT *) OpCodeData)->Value, sizeof (EFI_IFR_TYPE_VALUE));\r
1661 ExtendValueToU64 (&CurrentDefault->Value);\r
1662\r
1663 //\r
1664 // Insert to Default Value list of current Question\r
1665 //\r
1666 InsertTailList (&CurrentStatement->DefaultListHead, &CurrentDefault->Link);\r
1667\r
1668 if (Scope != 0) {\r
1669 InScopeDefault = TRUE;\r
1670 }\r
1671 break;\r
1672\r
1673 //\r
1674 // Option\r
1675 //\r
1676 case EFI_IFR_ONE_OF_OPTION_OP:\r
1677 //\r
1678 // EFI_IFR_ONE_OF_OPTION appear in scope of a Question.\r
1679 // It create a selection for use in current Question.\r
1680 //\r
1681 CurrentOption = AllocateZeroPool (sizeof (QUESTION_OPTION));\r
1682 ASSERT (CurrentOption != NULL);\r
1683 CurrentOption->Signature = QUESTION_OPTION_SIGNATURE;\r
1684\r
1685 CurrentOption->Flags = ((EFI_IFR_ONE_OF_OPTION *) OpCodeData)->Flags;\r
1686 CurrentOption->Value.Type = ((EFI_IFR_ONE_OF_OPTION *) OpCodeData)->Type;\r
1687 CopyMem (&CurrentOption->Text, &((EFI_IFR_ONE_OF_OPTION *) OpCodeData)->Option, sizeof (EFI_STRING_ID));\r
1688 CopyMem (&CurrentOption->Value.Value, &((EFI_IFR_ONE_OF_OPTION *) OpCodeData)->Value, sizeof (EFI_IFR_TYPE_VALUE));\r
1689 ExtendValueToU64 (&CurrentOption->Value);\r
1690\r
1691 if (InScopeOptionSuppress) {\r
1692 CurrentOption->SuppressExpression = OptionSuppressExpression;\r
1693 }\r
1694\r
1695 //\r
1696 // Insert to Option list of current Question\r
1697 //\r
1698 InsertTailList (&CurrentStatement->OptionListHead, &CurrentOption->Link);\r
1699\r
1700 //\r
1701 // Now we know the Storage width of nested Ordered List\r
1702 //\r
1703 ASSERT (CurrentStatement != NULL);\r
1704 if ((CurrentStatement->Operand == EFI_IFR_ORDERED_LIST_OP) && (CurrentStatement->BufferValue == NULL)) {\r
1705 Width = 1;\r
1706 switch (CurrentOption->Value.Type) {\r
1707 case EFI_IFR_TYPE_NUM_SIZE_8:\r
1708 Width = 1;\r
1709 break;\r
1710\r
1711 case EFI_IFR_TYPE_NUM_SIZE_16:\r
1712 Width = 2;\r
1713 break;\r
1714\r
1715 case EFI_IFR_TYPE_NUM_SIZE_32:\r
1716 Width = 4;\r
1717 break;\r
1718\r
1719 case EFI_IFR_TYPE_NUM_SIZE_64:\r
1720 Width = 8;\r
1721 break;\r
1722\r
1723 default:\r
1724 //\r
1725 // Invalid type for Ordered List\r
1726 //\r
1727 break;\r
1728 }\r
1729\r
1730 CurrentStatement->StorageWidth = (UINT16) (CurrentStatement->MaxContainers * Width);\r
1731 CurrentStatement->BufferValue = AllocateZeroPool (CurrentStatement->StorageWidth);\r
1732 CurrentStatement->ValueType = CurrentOption->Value.Type;\r
1733\r
1734 InitializeRequestElement (FormSet, CurrentStatement);\r
1735 }\r
1736 break;\r
1737\r
1738 //\r
1739 // Conditional\r
1740 //\r
1741 case EFI_IFR_NO_SUBMIT_IF_OP:\r
1742 case EFI_IFR_INCONSISTENT_IF_OP:\r
1743 //\r
1744 // Create an Expression node\r
1745 //\r
1746 CurrentExpression = CreateExpression (CurrentForm);\r
1747 CopyMem (&CurrentExpression->Error, &((EFI_IFR_INCONSISTENT_IF *) OpCodeData)->Error, sizeof (EFI_STRING_ID));\r
1748\r
1749 if (Operand == EFI_IFR_NO_SUBMIT_IF_OP) {\r
1750 CurrentExpression->Type = EFI_HII_EXPRESSION_NO_SUBMIT_IF;\r
1751 InsertTailList (&CurrentStatement->NoSubmitListHead, &CurrentExpression->Link);\r
1752 } else {\r
1753 CurrentExpression->Type = EFI_HII_EXPRESSION_INCONSISTENT_IF;\r
1754 InsertTailList (&CurrentStatement->InconsistentListHead, &CurrentExpression->Link);\r
1755 }\r
1756\r
1757 //\r
1758 // Take a look at next OpCode to see whether current expression consists\r
1759 // of single OpCode\r
1760 //\r
1761 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1762 SingleOpCodeExpression = TRUE;\r
1763 }\r
1764 break;\r
1765\r
1766 case EFI_IFR_SUPPRESS_IF_OP:\r
1767 //\r
1768 // Question and Option will appear in scope of this OpCode\r
1769 //\r
1770 CurrentExpression = CreateExpression (CurrentForm);\r
1771 CurrentExpression->Type = EFI_HII_EXPRESSION_SUPPRESS_IF;\r
1772\r
1773 if (CurrentForm == NULL) {\r
1774 InsertTailList (&FormSet->ExpressionListHead, &CurrentExpression->Link);\r
1775 } else {\r
1776 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1777 }\r
1778\r
1779 if (SuppressForOption) {\r
1780 InScopeOptionSuppress = TRUE;\r
1781 OptionSuppressExpression = CurrentExpression;\r
1782 } else if (SuppressForQuestion) {\r
1783 mInScopeSuppress = TRUE;\r
1784 mSuppressExpression = CurrentExpression;\r
1785 } else {\r
1786 InScopeFormSuppress = TRUE;\r
1787 FormSuppressExpression = CurrentExpression;\r
1788 }\r
1789\r
1790 //\r
1791 // Take a look at next OpCode to see whether current expression consists\r
1792 // of single OpCode\r
1793 //\r
1794 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1795 SingleOpCodeExpression = TRUE;\r
1796 }\r
1797 break;\r
1798\r
1799 case EFI_IFR_GRAY_OUT_IF_OP:\r
1800 //\r
1801 // Questions will appear in scope of this OpCode\r
1802 //\r
1803 CurrentExpression = CreateExpression (CurrentForm);\r
1804 CurrentExpression->Type = EFI_HII_EXPRESSION_GRAY_OUT_IF;\r
1805 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1806\r
1807 mInScopeGrayOut = TRUE;\r
1808 mGrayOutExpression = CurrentExpression;\r
1809\r
1810 //\r
1811 // Take a look at next OpCode to see whether current expression consists\r
1812 // of single OpCode\r
1813 //\r
1814 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1815 SingleOpCodeExpression = TRUE;\r
1816 }\r
1817 break;\r
1818\r
1819 case EFI_IFR_DISABLE_IF_OP:\r
1820 //\r
1821 // The DisableIf expression should only rely on constant, so it could be\r
1822 // evaluated at initialization and it will not be queued\r
1823 //\r
1824 CurrentExpression = AllocateZeroPool (sizeof (FORM_EXPRESSION));\r
1825 ASSERT (CurrentExpression != NULL);\r
1826 CurrentExpression->Signature = FORM_EXPRESSION_SIGNATURE;\r
1827 CurrentExpression->Type = EFI_HII_EXPRESSION_DISABLE_IF;\r
1828 InitializeListHead (&CurrentExpression->OpCodeListHead);\r
1829\r
1830 if (CurrentForm != NULL) {\r
1831 //\r
1832 // This is DisableIf for Question, enqueue it to Form expression list\r
1833 //\r
1834 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1835 }\r
1836\r
1837 mDisableExpression = CurrentExpression;\r
1838 mInScopeDisable = TRUE;\r
1839 OpCodeDisabled = FALSE;\r
1840\r
1841 //\r
1842 // Take a look at next OpCode to see whether current expression consists\r
1843 // of single OpCode\r
1844 //\r
1845 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1846 SingleOpCodeExpression = TRUE;\r
1847 }\r
1848 break;\r
1849\r
1850 //\r
1851 // Expression\r
1852 //\r
1853 case EFI_IFR_VALUE_OP:\r
1854 CurrentExpression = CreateExpression (CurrentForm);\r
1855 CurrentExpression->Type = EFI_HII_EXPRESSION_VALUE;\r
1856 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1857\r
1858 if (InScopeDefault) {\r
1859 //\r
1860 // Used for default (EFI_IFR_DEFAULT)\r
1861 //\r
1862 CurrentDefault->ValueExpression = CurrentExpression;\r
1863 } else {\r
1864 //\r
1865 // If used for a question, then the question will be read-only\r
1866 //\r
1867 //\r
1868 // Make sure CurrentStatement is not NULL.\r
1869 // If it is NULL, 1) ParseOpCodes functions may parse the IFR wrongly. Or 2) the IFR\r
1870 // file is wrongly generated by tools such as VFR Compiler. There may be a bug in VFR Compiler.\r
1871 //\r
1872 ASSERT (CurrentStatement != NULL);\r
1873 CurrentStatement->ValueExpression = CurrentExpression;\r
1874 }\r
1875\r
1876 //\r
1877 // Take a look at next OpCode to see whether current expression consists\r
1878 // of single OpCode\r
1879 //\r
1880 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1881 SingleOpCodeExpression = TRUE;\r
1882 }\r
1883 break;\r
1884\r
1885 case EFI_IFR_RULE_OP:\r
1886 CurrentExpression = CreateExpression (CurrentForm);\r
1887 CurrentExpression->Type = EFI_HII_EXPRESSION_RULE;\r
1888\r
1889 CurrentExpression->RuleId = ((EFI_IFR_RULE *) OpCodeData)->RuleId;\r
1890 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1891\r
1892 //\r
1893 // Take a look at next OpCode to see whether current expression consists\r
1894 // of single OpCode\r
1895 //\r
1896 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1897 SingleOpCodeExpression = TRUE;\r
1898 }\r
1899 break;\r
1900\r
1901 case EFI_IFR_READ_OP:\r
1902 CurrentExpression = CreateExpression (CurrentForm);\r
1903 CurrentExpression->Type = EFI_HII_EXPRESSION_READ;\r
1904 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1905\r
1906 //\r
1907 // Make sure CurrentStatement is not NULL.\r
1908 // If it is NULL, 1) ParseOpCodes functions may parse the IFR wrongly. Or 2) the IFR\r
1909 // file is wrongly generated by tools such as VFR Compiler. There may be a bug in VFR Compiler.\r
1910 //\r
1911 ASSERT (CurrentStatement != NULL);\r
1912 CurrentStatement->ReadExpression = CurrentExpression;\r
1913\r
1914 //\r
1915 // Take a look at next OpCode to see whether current expression consists\r
1916 // of single OpCode\r
1917 //\r
1918 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1919 SingleOpCodeExpression = TRUE;\r
1920 }\r
1921 break;\r
1922\r
1923 case EFI_IFR_WRITE_OP:\r
1924 CurrentExpression = CreateExpression (CurrentForm);\r
1925 CurrentExpression->Type = EFI_HII_EXPRESSION_WRITE;\r
1926 InsertTailList (&CurrentForm->ExpressionListHead, &CurrentExpression->Link);\r
1927\r
1928 //\r
1929 // Make sure CurrentStatement is not NULL.\r
1930 // If it is NULL, 1) ParseOpCodes functions may parse the IFR wrongly. Or 2) the IFR\r
1931 // file is wrongly generated by tools such as VFR Compiler. There may be a bug in VFR Compiler.\r
1932 //\r
1933 ASSERT (CurrentStatement != NULL);\r
1934 CurrentStatement->WriteExpression = CurrentExpression;\r
1935\r
1936 //\r
1937 // Take a look at next OpCode to see whether current expression consists\r
1938 // of single OpCode\r
1939 //\r
1940 if (((EFI_IFR_OP_HEADER *) (OpCodeData + OpCodeLength))->Scope == 0) {\r
1941 SingleOpCodeExpression = TRUE;\r
1942 }\r
1943 break;\r
1944\r
1945 //\r
1946 // Image\r
1947 //\r
1948 case EFI_IFR_IMAGE_OP:\r
1949 //\r
1950 // Get ScopeOpcode from top of stack\r
1951 //\r
1952 PopScope (&ScopeOpCode);\r
1953 PushScope (ScopeOpCode);\r
1954\r
1955 switch (ScopeOpCode) {\r
1956 case EFI_IFR_FORM_SET_OP:\r
1957 ImageId = &FormSet->ImageId;\r
1958 break;\r
1959\r
1960 case EFI_IFR_FORM_OP:\r
1961 case EFI_IFR_FORM_MAP_OP:\r
1962 ASSERT (CurrentForm != NULL);\r
1963 ImageId = &CurrentForm->ImageId;\r
1964 break;\r
1965\r
1966 case EFI_IFR_ONE_OF_OPTION_OP:\r
1967 ImageId = &CurrentOption->ImageId;\r
1968 break;\r
1969\r
1970 default:\r
1971 //\r
1972 // Make sure CurrentStatement is not NULL.\r
1973 // If it is NULL, 1) ParseOpCodes functions may parse the IFR wrongly. Or 2) the IFR\r
1974 // file is wrongly generated by tools such as VFR Compiler.\r
1975 //\r
1976 ASSERT (CurrentStatement != NULL);\r
1977 ImageId = &CurrentStatement->ImageId;\r
1978 break;\r
1979 }\r
1980\r
1981 ASSERT (ImageId != NULL);\r
1982 CopyMem (ImageId, &((EFI_IFR_IMAGE *) OpCodeData)->Id, sizeof (EFI_IMAGE_ID));\r
1983 break;\r
1984\r
1985 //\r
1986 // Refresh\r
1987 //\r
1988 case EFI_IFR_REFRESH_OP:\r
1989 ASSERT (CurrentStatement != NULL);\r
1990 CurrentStatement->RefreshInterval = ((EFI_IFR_REFRESH *) OpCodeData)->RefreshInterval;\r
1991 break;\r
1992\r
1993 //\r
1994 // Vendor specific\r
1995 //\r
1996 case EFI_IFR_GUID_OP:\r
1997 if (CompareGuid (&gEfiIfrTianoGuid, (EFI_GUID *)(OpCodeData + sizeof (EFI_IFR_OP_HEADER)))) {\r
1998 //\r
1999 // Tiano specific GUIDed opcodes\r
2000 //\r
2001 switch (((EFI_IFR_GUID_LABEL *) OpCodeData)->ExtendOpCode) {\r
2002 case EFI_IFR_EXTEND_OP_LABEL:\r
2003 //\r
2004 // just ignore label\r
2005 //\r
2006 break;\r
2007\r
2008 case EFI_IFR_EXTEND_OP_BANNER:\r
2009 //\r
2010 // By SubClass to get Banner Data from Front Page\r
2011 //\r
2012 if (FormSet->SubClass == EFI_FRONT_PAGE_SUBCLASS) {\r
2013 CopyMem (\r
2014 &gBannerData->Banner[((EFI_IFR_GUID_BANNER *) OpCodeData)->LineNumber][\r
2015 ((EFI_IFR_GUID_BANNER *) OpCodeData)->Alignment],\r
2016 &((EFI_IFR_GUID_BANNER *) OpCodeData)->Title,\r
2017 sizeof (EFI_STRING_ID)\r
2018 );\r
2019 }\r
2020 break;\r
2021\r
2022 case EFI_IFR_EXTEND_OP_CLASS:\r
2023 CopyMem (&FormSet->Class, &((EFI_IFR_GUID_CLASS *) OpCodeData)->Class, sizeof (UINT16));\r
2024 break;\r
2025\r
2026 case EFI_IFR_EXTEND_OP_SUBCLASS:\r
2027 CopyMem (&FormSet->SubClass, &((EFI_IFR_GUID_SUBCLASS *) OpCodeData)->SubClass, sizeof (UINT16));\r
2028 break;\r
2029\r
2030 default:\r
2031 break;\r
2032 }\r
2033 }\r
2034\r
2035 break;\r
2036\r
2037 //\r
2038 // Scope End\r
2039 //\r
2040 case EFI_IFR_END_OP:\r
2041 Status = PopScope (&ScopeOpCode);\r
2042 if (EFI_ERROR (Status)) {\r
2043 ResetScopeStack ();\r
2044 return Status;\r
2045 }\r
2046\r
2047 switch (ScopeOpCode) {\r
2048 case EFI_IFR_FORM_SET_OP:\r
2049 //\r
2050 // End of FormSet, update FormSet IFR binary length\r
2051 // to stop parsing substantial OpCodes\r
2052 //\r
2053 FormSet->IfrBinaryLength = OpCodeOffset;\r
2054 break;\r
2055\r
2056 case EFI_IFR_FORM_OP:\r
2057 case EFI_IFR_FORM_MAP_OP:\r
2058 //\r
2059 // End of Form\r
2060 //\r
2061 CurrentForm = NULL;\r
2062 SuppressForQuestion = FALSE;\r
2063 break;\r
2064\r
2065 case EFI_IFR_ONE_OF_OPTION_OP:\r
2066 //\r
2067 // End of Option\r
2068 //\r
2069 CurrentOption = NULL;\r
2070 break;\r
2071\r
2072 case EFI_IFR_SUBTITLE_OP:\r
2073 mInScopeSubtitle = FALSE;\r
2074 break;\r
2075\r
2076 case EFI_IFR_NO_SUBMIT_IF_OP:\r
2077 case EFI_IFR_INCONSISTENT_IF_OP:\r
2078 //\r
2079 // Ignore end of EFI_IFR_NO_SUBMIT_IF and EFI_IFR_INCONSISTENT_IF\r
2080 //\r
2081 break;\r
2082\r
2083 case EFI_IFR_SUPPRESS_IF_OP:\r
2084 if (SuppressForOption) {\r
2085 InScopeOptionSuppress = FALSE;\r
2086 } else if (SuppressForQuestion) {\r
2087 mInScopeSuppress = FALSE;\r
2088 } else {\r
2089 InScopeFormSuppress = FALSE;\r
2090 }\r
2091 break;\r
2092\r
2093 case EFI_IFR_GRAY_OUT_IF_OP:\r
2094 mInScopeGrayOut = FALSE;\r
2095 break;\r
2096\r
2097 case EFI_IFR_DISABLE_IF_OP:\r
2098 mInScopeDisable = FALSE;\r
2099 OpCodeDisabled = FALSE;\r
2100 break;\r
2101\r
2102 case EFI_IFR_ONE_OF_OP:\r
2103 case EFI_IFR_ORDERED_LIST_OP:\r
2104 SuppressForOption = FALSE;\r
2105 break;\r
2106\r
2107 case EFI_IFR_DEFAULT_OP:\r
2108 InScopeDefault = FALSE;\r
2109 break;\r
2110\r
2111 case EFI_IFR_MAP_OP:\r
2112 //\r
2113 // Get current Map Expression List.\r
2114 //\r
2115 Status = PopMapExpressionList ((VOID **) &MapExpressionList);\r
2116 if (Status == EFI_ACCESS_DENIED) {\r
2117 MapExpressionList = NULL;\r
2118 }\r
2119 //\r
2120 // Get current expression.\r
2121 //\r
2122 Status = PopCurrentExpression ((VOID **) &CurrentExpression);\r
2123 ASSERT_EFI_ERROR (Status);\r
2124 ASSERT (MapScopeDepth > 0);\r
2125 MapScopeDepth --;\r
2126 break;\r
2127\r
2128 default:\r
2129 if (IsExpressionOpCode (ScopeOpCode)) {\r
2130 if (mInScopeDisable && CurrentForm == NULL) {\r
2131 //\r
2132 // This is DisableIf expression for Form, it should be a constant expression\r
2133 //\r
2134 ASSERT (CurrentExpression != NULL);\r
2135 Status = EvaluateExpression (FormSet, CurrentForm, CurrentExpression);\r
2136 if (EFI_ERROR (Status)) {\r
2137 return Status;\r
2138 }\r
2139\r
2140 if (CurrentExpression->Result.Type != EFI_IFR_TYPE_BOOLEAN) {\r
2141 return EFI_INVALID_PARAMETER;\r
2142 }\r
2143\r
2144 OpCodeDisabled = CurrentExpression->Result.Value.b;\r
2145 //\r
2146 // DisableIf Expression is only used once and not queued, free it\r
2147 //\r
2148 DestroyExpression (CurrentExpression);\r
2149 }\r
2150\r
2151 //\r
2152 // End of current Expression\r
2153 //\r
2154 CurrentExpression = NULL;\r
2155 }\r
2156 break;\r
2157 }\r
2158 break;\r
2159\r
2160 default:\r
2161 break;\r
2162 }\r
2163 }\r
2164\r
2165 return EFI_SUCCESS;\r
2166}\r