TianoCore EDK2 master
Loading...
Searching...
No Matches
ProcessOptions.c
Go to the documentation of this file.
1
10#include "FormDisplay.h"
11
12#define MAX_TIME_OUT_LEN 0x10
13
23VOID
25 IN OUT CHAR16 *Destination,
26 IN UINTN DestMax,
27 IN CHAR16 *Source
28 )
29{
30 UINTN Length;
31
32 for (Length = 0; Destination[Length] != 0; Length++) {
33 }
34
35 //
36 // We now have the length of the original string
37 // We can safely assume for now that we are concatenating a narrow value to this string.
38 // For instance, the string is "XYZ" and cat'ing ">"
39 // If this assumption changes, we need to make this routine a bit more complex
40 //
41 Destination[Length] = NARROW_CHAR;
42 Length++;
43
44 StrCpyS (Destination + Length, DestMax - Length, Source);
45}
46
55UINT64
57 IN EFI_HII_VALUE *Value
58 )
59{
60 UINT64 RetVal;
61
62 RetVal = 0;
63
64 switch (Value->Type) {
65 case EFI_IFR_TYPE_NUM_SIZE_8:
66 RetVal = Value->Value.u8;
67 break;
68
69 case EFI_IFR_TYPE_NUM_SIZE_16:
70 RetVal = Value->Value.u16;
71 break;
72
73 case EFI_IFR_TYPE_NUM_SIZE_32:
74 RetVal = Value->Value.u32;
75 break;
76
77 case EFI_IFR_TYPE_BOOLEAN:
78 RetVal = Value->Value.b;
79 break;
80
81 case EFI_IFR_TYPE_DATE:
82 RetVal = *(UINT64 *)&Value->Value.date;
83 break;
84
85 case EFI_IFR_TYPE_TIME:
86 RetVal = (*(UINT64 *)&Value->Value.time) & 0xffffff;
87 break;
88
89 default:
90 RetVal = Value->Value.u64;
91 break;
92 }
93
94 return RetVal;
95}
96
109BOOLEAN
111 IN EFI_HII_VALUE *Value
112 )
113{
114 switch (Value->Type) {
115 case EFI_IFR_TYPE_BUFFER:
116 case EFI_IFR_TYPE_DATE:
117 case EFI_IFR_TYPE_TIME:
118 case EFI_IFR_TYPE_REF:
119 return TRUE;
120
121 default:
122 return FALSE;
123 }
124}
125
135BOOLEAN
137 IN EFI_HII_VALUE *Value
138 )
139{
140 switch (Value->Type) {
141 case EFI_IFR_TYPE_NUM_SIZE_8:
142 case EFI_IFR_TYPE_NUM_SIZE_16:
143 case EFI_IFR_TYPE_NUM_SIZE_32:
144 case EFI_IFR_TYPE_NUM_SIZE_64:
145 case EFI_IFR_TYPE_BOOLEAN:
146 return TRUE;
147
148 default:
149 return FALSE;
150 }
151}
152
164VOID
166 IN EFI_HII_VALUE *Value,
167 OUT UINT8 **Buf,
168 OUT UINT16 *BufLen
169 )
170{
171 switch (Value->Type) {
172 case EFI_IFR_TYPE_BUFFER:
173 *Buf = Value->Buffer;
174 *BufLen = Value->BufferLen;
175 break;
176
177 case EFI_IFR_TYPE_DATE:
178 *Buf = (UINT8 *)(&Value->Value.date);
179 *BufLen = (UINT16)sizeof (EFI_HII_DATE);
180 break;
181
182 case EFI_IFR_TYPE_TIME:
183 *Buf = (UINT8 *)(&Value->Value.time);
184 *BufLen = (UINT16)sizeof (EFI_HII_TIME);
185 break;
186
187 case EFI_IFR_TYPE_REF:
188 *Buf = (UINT8 *)(&Value->Value.ref);
189 *BufLen = (UINT16)sizeof (EFI_HII_REF);
190 break;
191
192 default:
193 *Buf = NULL;
194 *BufLen = 0;
195 }
196}
197
215 IN EFI_HII_VALUE *Value1,
216 IN EFI_HII_VALUE *Value2,
217 OUT INTN *Result,
218 IN EFI_HII_HANDLE HiiHandle OPTIONAL
219 )
220{
221 INT64 Temp64;
222 CHAR16 *Str1;
223 CHAR16 *Str2;
224 UINTN Len;
225 UINT8 *Buf1;
226 UINT16 Buf1Len;
227 UINT8 *Buf2;
228 UINT16 Buf2Len;
229
230 if ((Value1->Type == EFI_IFR_TYPE_STRING) && (Value2->Type == EFI_IFR_TYPE_STRING)) {
231 if ((Value1->Value.string == 0) || (Value2->Value.string == 0)) {
232 //
233 // StringId 0 is reserved
234 //
235 return EFI_INVALID_PARAMETER;
236 }
237
238 if (Value1->Value.string == Value2->Value.string) {
239 *Result = 0;
240 return EFI_SUCCESS;
241 }
242
243 Str1 = GetToken (Value1->Value.string, HiiHandle);
244 if (Str1 == NULL) {
245 //
246 // String not found
247 //
248 return EFI_NOT_FOUND;
249 }
250
251 Str2 = GetToken (Value2->Value.string, HiiHandle);
252 if (Str2 == NULL) {
253 FreePool (Str1);
254 return EFI_NOT_FOUND;
255 }
256
257 *Result = StrCmp (Str1, Str2);
258
259 FreePool (Str1);
260 FreePool (Str2);
261
262 return EFI_SUCCESS;
263 }
264
265 //
266 // Take types(date, time, ref, buffer) as buffer
267 //
268 if (IsTypeInBuffer (Value1) && IsTypeInBuffer (Value2)) {
269 GetBufAndLenForValue (Value1, &Buf1, &Buf1Len);
270 GetBufAndLenForValue (Value2, &Buf2, &Buf2Len);
271
272 Len = Buf1Len > Buf2Len ? Buf2Len : Buf1Len;
273 *Result = CompareMem (Buf1, Buf2, Len);
274 if ((*Result == 0) && (Buf1Len != Buf2Len)) {
275 //
276 // In this case, means base on samll number buffer, the data is same
277 // So which value has more data, which value is bigger.
278 //
279 *Result = Buf1Len > Buf2Len ? 1 : -1;
280 }
281
282 return EFI_SUCCESS;
283 }
284
285 //
286 // Take remain types(integer, boolean, date/time) as integer
287 //
288 if (IsTypeInUINT64 (Value1) && IsTypeInUINT64 (Value2)) {
289 Temp64 = HiiValueToUINT64 (Value1) - HiiValueToUINT64 (Value2);
290 if (Temp64 > 0) {
291 *Result = 1;
292 } else if (Temp64 < 0) {
293 *Result = -1;
294 } else {
295 *Result = 0;
296 }
297
298 return EFI_SUCCESS;
299 }
300
301 return EFI_UNSUPPORTED;
302}
303
317 IN EFI_HII_VALUE *OptionValue
318 )
319{
320 LIST_ENTRY *Link;
322 INTN Result;
323 EFI_HII_VALUE Value;
324
325 Link = GetFirstNode (&Question->OptionListHead);
326 while (!IsNull (&Question->OptionListHead, Link)) {
327 Option = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
328
329 ZeroMem (&Value, sizeof (EFI_HII_VALUE));
330 Value.Type = Option->OptionOpCode->Type;
331 CopyMem (&Value.Value, &Option->OptionOpCode->Value, Option->OptionOpCode->Header.Length - OFFSET_OF (EFI_IFR_ONE_OF_OPTION, Value));
332
333 if ((CompareHiiValue (&Value, OptionValue, &Result, NULL) == EFI_SUCCESS) && (Result == 0)) {
334 return Option;
335 }
336
337 Link = GetNextNode (&Question->OptionListHead, Link);
338 }
339
340 return NULL;
341}
342
353UINT64
355 IN VOID *Array,
356 IN UINT8 Type,
357 IN UINTN Index
358 )
359{
360 UINT64 Data;
361
362 ASSERT (Array != NULL);
363
364 Data = 0;
365 switch (Type) {
366 case EFI_IFR_TYPE_NUM_SIZE_8:
367 Data = (UINT64)*(((UINT8 *)Array) + Index);
368 break;
369
370 case EFI_IFR_TYPE_NUM_SIZE_16:
371 Data = (UINT64)*(((UINT16 *)Array) + Index);
372 break;
373
374 case EFI_IFR_TYPE_NUM_SIZE_32:
375 Data = (UINT64)*(((UINT32 *)Array) + Index);
376 break;
377
378 case EFI_IFR_TYPE_NUM_SIZE_64:
379 Data = (UINT64)*(((UINT64 *)Array) + Index);
380 break;
381
382 default:
383 break;
384 }
385
386 return Data;
387}
388
398VOID
400 IN VOID *Array,
401 IN UINT8 Type,
402 IN UINTN Index,
403 IN UINT64 Value
404 )
405{
406 ASSERT (Array != NULL);
407
408 switch (Type) {
409 case EFI_IFR_TYPE_NUM_SIZE_8:
410 *(((UINT8 *)Array) + Index) = (UINT8)Value;
411 break;
412
413 case EFI_IFR_TYPE_NUM_SIZE_16:
414 *(((UINT16 *)Array) + Index) = (UINT16)Value;
415 break;
416
417 case EFI_IFR_TYPE_NUM_SIZE_32:
418 *(((UINT32 *)Array) + Index) = (UINT32)Value;
419 break;
420
421 case EFI_IFR_TYPE_NUM_SIZE_64:
422 *(((UINT64 *)Array) + Index) = (UINT64)Value;
423 break;
424
425 default:
426 break;
427 }
428}
429
442BOOLEAN
444 IN VOID *Array,
445 IN UINT8 Type,
446 IN UINT64 Value,
447 OUT UINTN *Index OPTIONAL
448 )
449{
450 UINTN Count;
451 UINT64 TmpValue;
452 UINT64 ValueComp;
453
454 ASSERT (Array != NULL);
455
456 Count = 0;
457 TmpValue = 0;
458
459 switch (Type) {
460 case EFI_IFR_TYPE_NUM_SIZE_8:
461 ValueComp = (UINT8)Value;
462 break;
463
464 case EFI_IFR_TYPE_NUM_SIZE_16:
465 ValueComp = (UINT16)Value;
466 break;
467
468 case EFI_IFR_TYPE_NUM_SIZE_32:
469 ValueComp = (UINT32)Value;
470 break;
471
472 case EFI_IFR_TYPE_NUM_SIZE_64:
473 ValueComp = (UINT64)Value;
474 break;
475
476 default:
477 ValueComp = 0;
478 break;
479 }
480
481 while ((TmpValue = GetArrayData (Array, Type, Count)) != 0) {
482 if (ValueComp == TmpValue) {
483 if (Index != NULL) {
484 *Index = Count;
485 }
486
487 return TRUE;
488 }
489
490 Count++;
491 }
492
493 return FALSE;
494}
495
510 IN OUT CHAR16 *FormattedNumber,
511 IN UINTN BufferSize
512 )
513{
514 INT64 Value;
515 CHAR16 *Format;
516 EFI_HII_VALUE *QuestionValue;
517 EFI_IFR_NUMERIC *NumericOp;
518
519 if (BufferSize < (21 * sizeof (CHAR16))) {
520 return EFI_BUFFER_TOO_SMALL;
521 }
522
523 QuestionValue = &Question->CurrentValue;
524 NumericOp = (EFI_IFR_NUMERIC *)Question->OpCode;
525
526 Value = (INT64)QuestionValue->Value.u64;
527 switch (NumericOp->Flags & EFI_IFR_DISPLAY) {
528 case EFI_IFR_DISPLAY_INT_DEC:
529 switch (QuestionValue->Type) {
530 case EFI_IFR_NUMERIC_SIZE_1:
531 Value = (INT64)((INT8)QuestionValue->Value.u8);
532 break;
533
534 case EFI_IFR_NUMERIC_SIZE_2:
535 Value = (INT64)((INT16)QuestionValue->Value.u16);
536 break;
537
538 case EFI_IFR_NUMERIC_SIZE_4:
539 Value = (INT64)((INT32)QuestionValue->Value.u32);
540 break;
541
542 case EFI_IFR_NUMERIC_SIZE_8:
543 default:
544 break;
545 }
546
547 if (Value < 0) {
548 Value = -Value;
549 Format = L"-%ld";
550 } else {
551 Format = L"%ld";
552 }
553
554 break;
555
556 case EFI_IFR_DISPLAY_UINT_DEC:
557 Format = L"%ld";
558 break;
559
560 case EFI_IFR_DISPLAY_UINT_HEX:
561 Format = L"%lx";
562 break;
563
564 default:
565 return EFI_UNSUPPORTED;
566 }
567
568 UnicodeSPrint (FormattedNumber, BufferSize, Format, Value);
569
570 return EFI_SUCCESS;
571}
572
582VOID
584 IN UINTN RequestedWidth,
585 IN UINTN NumberOfLines,
586 IN VA_LIST Marker
587 )
588{
589 UINTN Index;
590 UINTN Count;
591 CHAR16 Character;
592 UINTN Start;
593 UINTN End;
594 UINTN Top;
595 UINTN Bottom;
596 CHAR16 *String;
597 UINTN DimensionsWidth;
598 UINTN DimensionsHeight;
599
600 DimensionsWidth = gStatementDimensions.RightColumn - gStatementDimensions.LeftColumn;
601 DimensionsHeight = gStatementDimensions.BottomRow - gStatementDimensions.TopRow;
602
603 gST->ConOut->SetAttribute (gST->ConOut, GetPopupColor ());
604
605 if ((RequestedWidth + 2) > DimensionsWidth) {
606 RequestedWidth = DimensionsWidth - 2;
607 }
608
609 //
610 // Subtract the PopUp width from total Columns, allow for one space extra on
611 // each end plus a border.
612 //
613 Start = (DimensionsWidth - RequestedWidth - 2) / 2 + gStatementDimensions.LeftColumn + 1;
614 End = Start + RequestedWidth + 1;
615
616 Top = ((DimensionsHeight - NumberOfLines - 2) / 2) + gStatementDimensions.TopRow - 1;
617 Bottom = Top + NumberOfLines + 2;
618
619 Character = BOXDRAW_DOWN_RIGHT;
620 PrintCharAt (Start, Top, Character);
621 Character = BOXDRAW_HORIZONTAL;
622 for (Index = Start; Index + 2 < End; Index++) {
623 PrintCharAt ((UINTN)-1, (UINTN)-1, Character);
624 }
625
626 Character = BOXDRAW_DOWN_LEFT;
627 PrintCharAt ((UINTN)-1, (UINTN)-1, Character);
628 Character = BOXDRAW_VERTICAL;
629
630 Count = 0;
631 for (Index = Top; Index + 2 < Bottom; Index++, Count++) {
632 String = VA_ARG (Marker, CHAR16 *);
633
634 //
635 // This will clear the background of the line - we never know who might have been
636 // here before us. This differs from the next clear in that it used the non-reverse
637 // video for normal printing.
638 //
639 if (GetStringWidth (String) / 2 > 1) {
640 ClearLines (Start, End, Index + 1, Index + 1, GetPopupColor ());
641 }
642
643 //
644 // Passing in a space results in the assumption that this is where typing will occur
645 //
646 if (String[0] == L' ') {
647 ClearLines (Start + 1, End - 1, Index + 1, Index + 1, GetPopupInverseColor ());
648 }
649
650 //
651 // Passing in a NULL results in a blank space
652 //
653 if (String[0] == CHAR_NULL) {
654 ClearLines (Start, End, Index + 1, Index + 1, GetPopupColor ());
655 }
656
658 ((DimensionsWidth - GetStringWidth (String) / 2) / 2) + gStatementDimensions.LeftColumn + 1,
659 Index + 1,
660 String
661 );
662 gST->ConOut->SetAttribute (gST->ConOut, GetPopupColor ());
663 PrintCharAt (Start, Index + 1, Character);
664 PrintCharAt (End - 1, Index + 1, Character);
665 }
666
667 Character = BOXDRAW_UP_RIGHT;
668 PrintCharAt (Start, Bottom - 1, Character);
669 Character = BOXDRAW_HORIZONTAL;
670 for (Index = Start; Index + 2 < End; Index++) {
671 PrintCharAt ((UINTN)-1, (UINTN)-1, Character);
672 }
673
674 Character = BOXDRAW_UP_LEFT;
675 PrintCharAt ((UINTN)-1, (UINTN)-1, Character);
676}
677
687VOID
688EFIAPI
690 IN UINTN RequestedWidth,
691 IN UINTN NumberOfLines,
692 ...
693 )
694{
695 VA_LIST Marker;
696
697 VA_START (Marker, NumberOfLines);
698
699 CreateSharedPopUp (RequestedWidth, NumberOfLines, Marker);
700
701 VA_END (Marker);
702}
703
711VOID
712EFIAPI
714 IN EFI_EVENT Event,
715 IN VOID *Context
716 )
717{
718}
719
727VOID
728EFIAPI
730 IN EFI_EVENT Event,
731 IN VOID *Context
732 )
733{
734 WARNING_IF_CONTEXT *EventInfo;
735 CHAR16 TimeOutString[MAX_TIME_OUT_LEN];
736
737 EventInfo = (WARNING_IF_CONTEXT *)Context;
738
739 if (*(EventInfo->TimeOut) == 0) {
740 gBS->CloseEvent (Event);
741
742 gBS->SignalEvent (EventInfo->SyncEvent);
743 return;
744 }
745
746 UnicodeSPrint (TimeOutString, MAX_TIME_OUT_LEN, L"%d", *(EventInfo->TimeOut));
747
748 CreateDialog (NULL, gEmptyString, EventInfo->ErrorInfo, gPressEnter, gEmptyString, TimeOutString, NULL);
749
750 *(EventInfo->TimeOut) -= 1;
751}
752
757VOID
759 VOID
760 )
761{
762 EFI_INPUT_KEY Key;
763
764 //
765 // Invalid password, prompt error message
766 //
767 do {
768 CreateDialog (&Key, gEmptyString, gPassowordInvalid, gPressEnter, gEmptyString, NULL);
769 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
770}
771
783 IN UI_MENU_OPTION *MenuOption
784 )
785{
786 CHAR16 *StringPtr;
787 CHAR16 *TempString;
788 UINTN Maximum;
789 EFI_STATUS Status;
790 EFI_IFR_PASSWORD *PasswordInfo;
792 EFI_INPUT_KEY Key;
793
794 Question = MenuOption->ThisTag;
795 PasswordInfo = (EFI_IFR_PASSWORD *)Question->OpCode;
796 Maximum = PasswordInfo->MaxSize;
797 Status = EFI_SUCCESS;
798
799 StringPtr = AllocateZeroPool ((Maximum + 1) * sizeof (CHAR16));
800 ASSERT (StringPtr);
801
802 //
803 // Use a NULL password to test whether old password is required
804 //
805 *StringPtr = 0;
806 Status = Question->PasswordCheck (gFormData, Question, StringPtr);
807 if ((Status == EFI_NOT_AVAILABLE_YET) || (Status == EFI_UNSUPPORTED)) {
808 //
809 // Password can't be set now.
810 //
811 if (Status == EFI_UNSUPPORTED) {
812 do {
813 CreateDialog (&Key, gEmptyString, gPasswordUnsupported, gPressEnter, gEmptyString, NULL);
814 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
815 }
816
817 FreePool (StringPtr);
818 return EFI_SUCCESS;
819 }
820
821 if (EFI_ERROR (Status)) {
822 //
823 // Old password exist, ask user for the old password
824 //
825 Status = ReadString (MenuOption, gPromptForPassword, StringPtr);
826 if (EFI_ERROR (Status)) {
827 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
828 FreePool (StringPtr);
829 return Status;
830 }
831
832 //
833 // Check user input old password
834 //
835 Status = Question->PasswordCheck (gFormData, Question, StringPtr);
836 if (EFI_ERROR (Status)) {
837 if (Status == EFI_NOT_READY) {
838 //
839 // Typed in old password incorrect
840 //
842 } else {
843 Status = EFI_SUCCESS;
844 }
845
846 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
847 FreePool (StringPtr);
848 return Status;
849 }
850 }
851
852 //
853 // Ask for new password
854 //
855 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
856 Status = ReadString (MenuOption, gPromptForNewPassword, StringPtr);
857 if (EFI_ERROR (Status)) {
858 //
859 // Reset state machine for password
860 //
861 Question->PasswordCheck (gFormData, Question, NULL);
862 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
863 FreePool (StringPtr);
864 return Status;
865 }
866
867 //
868 // Confirm new password
869 //
870 TempString = AllocateZeroPool ((Maximum + 1) * sizeof (CHAR16));
871 ASSERT (TempString);
872 Status = ReadString (MenuOption, gConfirmPassword, TempString);
873 if (EFI_ERROR (Status)) {
874 //
875 // Reset state machine for password
876 //
877 Question->PasswordCheck (gFormData, Question, NULL);
878 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
879 ZeroMem (TempString, (Maximum + 1) * sizeof (CHAR16));
880 FreePool (StringPtr);
881 FreePool (TempString);
882 return Status;
883 }
884
885 //
886 // Compare two typed-in new passwords
887 //
888 if (StrCmp (StringPtr, TempString) == 0) {
889 gUserInput->InputValue.Buffer = AllocateCopyPool (Question->CurrentValue.BufferLen, StringPtr);
890 gUserInput->InputValue.BufferLen = Question->CurrentValue.BufferLen;
891 gUserInput->InputValue.Type = Question->CurrentValue.Type;
892 gUserInput->InputValue.Value.string = HiiSetString (gFormData->HiiHandle, gUserInput->InputValue.Value.string, StringPtr, NULL);
893
894 Status = EFI_SUCCESS;
895 } else {
896 //
897 // Reset state machine for password
898 //
899 Question->PasswordCheck (gFormData, Question, NULL);
900
901 //
902 // Two password mismatch, prompt error message
903 //
904 do {
905 CreateDialog (&Key, gEmptyString, gConfirmError, gPressEnter, gEmptyString, NULL);
906 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
907
908 Status = EFI_INVALID_PARAMETER;
909 }
910
911 ZeroMem (TempString, (Maximum + 1) * sizeof (CHAR16));
912 ZeroMem (StringPtr, (Maximum + 1) * sizeof (CHAR16));
913 FreePool (TempString);
914 FreePool (StringPtr);
915
916 return Status;
917}
918
925VOID
927 IN UI_MENU_OPTION *MenuOption
928 )
929{
930 CHAR16 *FormTitleStr;
931 CHAR16 *FormSetTitleStr;
932 CHAR16 *OneOfOptionStr;
933 CHAR16 *QuestionName;
934 LIST_ENTRY *Link;
936 EFI_IFR_ORDERED_LIST *OrderList;
937 UINT8 Index;
938 EFI_HII_VALUE HiiValue;
939 EFI_HII_VALUE *QuestionValue;
941 UINT8 *ValueArray;
942 UINT8 ValueType;
943 EFI_IFR_FORM_SET *FormsetBuffer;
944 UINTN FormsetBufferSize;
945
946 Question = MenuOption->ThisTag;
947
948 if (!EFI_ERROR (HiiGetFormSetFromHiiHandle (gFormData->HiiHandle, &FormsetBuffer, &FormsetBufferSize))) {
949 FormSetTitleStr = GetToken (FormsetBuffer->FormSetTitle, gFormData->HiiHandle);
950 FormTitleStr = GetToken (gFormData->FormTitle, gFormData->HiiHandle);
951
952 DEBUG ((DEBUG_ERROR, "\n[%a]: Mismatch Formset : Formset Guid = %g, FormSet title = %s\n", gEfiCallerBaseName, &gFormData->FormSetGuid, FormSetTitleStr));
953 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch Form : FormId = %d, Form title = %s.\n", gEfiCallerBaseName, gFormData->FormId, FormTitleStr));
954 }
955
956 if (Question->OpCode->OpCode == EFI_IFR_ORDERED_LIST_OP) {
957 QuestionName = GetToken (((EFI_IFR_ORDERED_LIST *)MenuOption->ThisTag->OpCode)->Question.Header.Prompt, gFormData->HiiHandle);
958 Link = GetFirstNode (&Question->OptionListHead);
959 Option = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
960 ValueType = Option->OptionOpCode->Type;
961 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch Error : OrderedList value in the array doesn't match with option value.\n", gEfiCallerBaseName));
962 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OrderedList: Name = %s.\n", gEfiCallerBaseName, QuestionName));
963 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OrderedList: OrderedList array value :\n", gEfiCallerBaseName));
964
965 OrderList = (EFI_IFR_ORDERED_LIST *)Question->OpCode;
966 for (Index = 0; Index < OrderList->MaxContainers; Index++) {
967 ValueArray = Question->CurrentValue.Buffer;
968 HiiValue.Value.u64 = GetArrayData (ValueArray, ValueType, Index);
969 DEBUG ((DEBUG_ERROR, " Value[%d] =%ld.\n", Index, HiiValue.Value.u64));
970 }
971 } else if (Question->OpCode->OpCode == EFI_IFR_ONE_OF_OP) {
972 QuestionName = GetToken (((EFI_IFR_ONE_OF *)MenuOption->ThisTag->OpCode)->Question.Header.Prompt, gFormData->HiiHandle);
973 QuestionValue = &Question->CurrentValue;
974 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch Error : OneOf value doesn't match with option value.\n", gEfiCallerBaseName));
975 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OneOf : Name = %s.\n", gEfiCallerBaseName, QuestionName));
976 switch (QuestionValue->Type) {
977 case EFI_IFR_TYPE_NUM_SIZE_64:
978 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OneOf : OneOf value = %ld.\n", gEfiCallerBaseName, QuestionValue->Value.u64));
979 break;
980
981 case EFI_IFR_TYPE_NUM_SIZE_32:
982 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OneOf : OneOf value = %d.\n", gEfiCallerBaseName, QuestionValue->Value.u32));
983 break;
984
985 case EFI_IFR_TYPE_NUM_SIZE_16:
986 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OneOf : OneOf value = %d.\n", gEfiCallerBaseName, QuestionValue->Value.u16));
987 break;
988
989 case EFI_IFR_TYPE_NUM_SIZE_8:
990 DEBUG ((DEBUG_ERROR, "[%a]: Mismatch OneOf : OneOf value = %d.\n", gEfiCallerBaseName, QuestionValue->Value.u8));
991 break;
992
993 default:
994 ASSERT (FALSE);
995 break;
996 }
997 }
998
999 Index = 0;
1000 Link = GetFirstNode (&Question->OptionListHead);
1001 while (!IsNull (&Question->OptionListHead, Link)) {
1002 Option = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1003 OneOfOptionStr = GetToken (Option->OptionOpCode->Option, gFormData->HiiHandle);
1004 switch (Option->OptionOpCode->Type) {
1005 case EFI_IFR_TYPE_NUM_SIZE_64:
1006 DEBUG ((DEBUG_ERROR, "[%a]: Option %d : Option Value = %ld, Option Name = %s.\n", gEfiCallerBaseName, Index, Option->OptionOpCode->Value.u64, OneOfOptionStr));
1007 break;
1008
1009 case EFI_IFR_TYPE_NUM_SIZE_32:
1010 DEBUG ((DEBUG_ERROR, "[%a]: Option %d : Option Value = %d, Option Name = %s.\n", gEfiCallerBaseName, Index, Option->OptionOpCode->Value.u32, OneOfOptionStr));
1011 break;
1012
1013 case EFI_IFR_TYPE_NUM_SIZE_16:
1014 DEBUG ((DEBUG_ERROR, "[%a]: Option %d : Option Value = %d, Option Name = %s.\n", gEfiCallerBaseName, Index, Option->OptionOpCode->Value.u16, OneOfOptionStr));
1015 break;
1016
1017 case EFI_IFR_TYPE_NUM_SIZE_8:
1018 DEBUG ((DEBUG_ERROR, "[%a]: Option %d : Option Value = %d, Option Name = %s.\n", gEfiCallerBaseName, Index, Option->OptionOpCode->Value.u8, OneOfOptionStr));
1019 break;
1020
1021 default:
1022 ASSERT (FALSE);
1023 break;
1024 }
1025
1026 Link = GetNextNode (&Question->OptionListHead, Link);
1027 Index++;
1028 }
1029}
1030
1045 IN UI_MENU_OPTION *MenuOption,
1046 IN BOOLEAN Selected,
1047 OUT CHAR16 **OptionString,
1048 IN BOOLEAN SkipErrorValue
1049 )
1050{
1051 EFI_STATUS Status;
1052 CHAR16 *StringPtr;
1053 UINTN Index;
1055 CHAR16 FormattedNumber[21];
1056 UINT16 Number;
1057 CHAR16 Character[2];
1058 EFI_INPUT_KEY Key;
1059 UINTN BufferSize;
1060 DISPLAY_QUESTION_OPTION *OneOfOption;
1061 LIST_ENTRY *Link;
1062 EFI_HII_VALUE HiiValue;
1063 EFI_HII_VALUE *QuestionValue;
1065 UINTN Index2;
1066 UINT8 *ValueArray;
1067 UINT8 ValueType;
1068 EFI_IFR_ORDERED_LIST *OrderList;
1069 BOOLEAN ValueInvalid;
1070 UINTN MaxLen;
1071
1072 Status = EFI_SUCCESS;
1073
1074 StringPtr = NULL;
1075 Character[1] = L'\0';
1076 *OptionString = NULL;
1077 ValueInvalid = FALSE;
1078
1079 ZeroMem (FormattedNumber, 21 * sizeof (CHAR16));
1080 BufferSize = (gOptionBlockWidth + 1) * 2 * gStatementDimensions.BottomRow;
1081
1082 Question = MenuOption->ThisTag;
1083 QuestionValue = &Question->CurrentValue;
1084
1085 switch (Question->OpCode->OpCode) {
1086 case EFI_IFR_ORDERED_LIST_OP:
1087
1088 //
1089 // Check whether there are Options of this OrderedList
1090 //
1091 if (IsListEmpty (&Question->OptionListHead)) {
1092 break;
1093 }
1094
1095 OrderList = (EFI_IFR_ORDERED_LIST *)Question->OpCode;
1096
1097 Link = GetFirstNode (&Question->OptionListHead);
1098 OneOfOption = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1099
1100 ValueType = OneOfOption->OptionOpCode->Type;
1101 ValueArray = Question->CurrentValue.Buffer;
1102
1103 if (Selected) {
1104 //
1105 // Go ask for input
1106 //
1107 Status = GetSelectionInputPopUp (MenuOption);
1108 } else {
1109 //
1110 // We now know how many strings we will have, so we can allocate the
1111 // space required for the array or strings.
1112 //
1113 MaxLen = OrderList->MaxContainers * BufferSize / sizeof (CHAR16);
1114 *OptionString = AllocateZeroPool (MaxLen * sizeof (CHAR16));
1115 ASSERT (*OptionString);
1116
1117 HiiValue.Type = ValueType;
1118 HiiValue.Value.u64 = 0;
1119 for (Index = 0; Index < OrderList->MaxContainers; Index++) {
1120 HiiValue.Value.u64 = GetArrayData (ValueArray, ValueType, Index);
1121 if (HiiValue.Value.u64 == 0) {
1122 //
1123 // Values for the options in ordered lists should never be a 0
1124 //
1125 break;
1126 }
1127
1128 OneOfOption = ValueToOption (Question, &HiiValue);
1129 if (OneOfOption == NULL) {
1130 //
1131 // Print debug msg for the mistach menu.
1132 //
1133 PrintMismatchMenuInfo (MenuOption);
1134
1135 if (SkipErrorValue) {
1136 //
1137 // Just try to get the option string, skip the value which not has option.
1138 //
1139 continue;
1140 }
1141
1142 //
1143 // Show error message
1144 //
1145 do {
1146 CreateDialog (&Key, gEmptyString, gOptionMismatch, gPressEnter, gEmptyString, NULL);
1147 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
1148
1149 //
1150 // The initial value of the orderedlist is invalid, force to be valid value
1151 // Exit current DisplayForm with new value.
1152 //
1153 gUserInput->SelectedStatement = Question;
1154 gMisMatch = TRUE;
1155 ValueArray = AllocateZeroPool (Question->CurrentValue.BufferLen);
1156 ASSERT (ValueArray != NULL);
1157 gUserInput->InputValue.Buffer = ValueArray;
1158 gUserInput->InputValue.BufferLen = Question->CurrentValue.BufferLen;
1159 gUserInput->InputValue.Type = Question->CurrentValue.Type;
1160
1161 Link = GetFirstNode (&Question->OptionListHead);
1162 Index2 = 0;
1163 while (!IsNull (&Question->OptionListHead, Link) && Index2 < OrderList->MaxContainers) {
1164 Option = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1165 Link = GetNextNode (&Question->OptionListHead, Link);
1166 SetArrayData (ValueArray, ValueType, Index2, Option->OptionOpCode->Value.u64);
1167 Index2++;
1168 }
1169
1170 SetArrayData (ValueArray, ValueType, Index2, 0);
1171
1172 FreePool (*OptionString);
1173 *OptionString = NULL;
1174 return EFI_NOT_FOUND;
1175 }
1176
1177 Character[0] = LEFT_ONEOF_DELIMITER;
1178 NewStrCat (OptionString[0], MaxLen, Character);
1179 StringPtr = GetToken (OneOfOption->OptionOpCode->Option, gFormData->HiiHandle);
1180 ASSERT (StringPtr != NULL);
1181 NewStrCat (OptionString[0], MaxLen, StringPtr);
1182 Character[0] = RIGHT_ONEOF_DELIMITER;
1183 NewStrCat (OptionString[0], MaxLen, Character);
1184 Character[0] = CHAR_CARRIAGE_RETURN;
1185 NewStrCat (OptionString[0], MaxLen, Character);
1186 FreePool (StringPtr);
1187 }
1188
1189 //
1190 // If valid option more than the max container, skip these options.
1191 //
1192 if (Index >= OrderList->MaxContainers) {
1193 break;
1194 }
1195
1196 //
1197 // Search the other options, try to find the one not in the container.
1198 //
1199 Link = GetFirstNode (&Question->OptionListHead);
1200 while (!IsNull (&Question->OptionListHead, Link)) {
1201 OneOfOption = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1202 Link = GetNextNode (&Question->OptionListHead, Link);
1203
1204 if (FindArrayData (ValueArray, ValueType, OneOfOption->OptionOpCode->Value.u64, NULL)) {
1205 continue;
1206 }
1207
1208 //
1209 // Print debug msg for the mistach menu.
1210 //
1211 PrintMismatchMenuInfo (MenuOption);
1212
1213 if (SkipErrorValue) {
1214 //
1215 // Not report error, just get the correct option string info.
1216 //
1217 Character[0] = LEFT_ONEOF_DELIMITER;
1218 NewStrCat (OptionString[0], MaxLen, Character);
1219 StringPtr = GetToken (OneOfOption->OptionOpCode->Option, gFormData->HiiHandle);
1220 ASSERT (StringPtr != NULL);
1221 NewStrCat (OptionString[0], MaxLen, StringPtr);
1222 Character[0] = RIGHT_ONEOF_DELIMITER;
1223 NewStrCat (OptionString[0], MaxLen, Character);
1224 Character[0] = CHAR_CARRIAGE_RETURN;
1225 NewStrCat (OptionString[0], MaxLen, Character);
1226 FreePool (StringPtr);
1227
1228 continue;
1229 }
1230
1231 if (!ValueInvalid) {
1232 ValueInvalid = TRUE;
1233 //
1234 // Show error message
1235 //
1236 do {
1237 CreateDialog (&Key, gEmptyString, gOptionMismatch, gPressEnter, gEmptyString, NULL);
1238 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
1239
1240 //
1241 // The initial value of the orderedlist is invalid, force to be valid value
1242 // Exit current DisplayForm with new value.
1243 //
1244 gUserInput->SelectedStatement = Question;
1245 gMisMatch = TRUE;
1246 ValueArray = AllocateCopyPool (Question->CurrentValue.BufferLen, Question->CurrentValue.Buffer);
1247 ASSERT (ValueArray != NULL);
1248 gUserInput->InputValue.Buffer = ValueArray;
1249 gUserInput->InputValue.BufferLen = Question->CurrentValue.BufferLen;
1250 gUserInput->InputValue.Type = Question->CurrentValue.Type;
1251 }
1252
1253 SetArrayData (ValueArray, ValueType, Index++, OneOfOption->OptionOpCode->Value.u64);
1254 }
1255
1256 if (ValueInvalid) {
1257 FreePool (*OptionString);
1258 *OptionString = NULL;
1259 return EFI_NOT_FOUND;
1260 }
1261 }
1262
1263 break;
1264
1265 case EFI_IFR_ONE_OF_OP:
1266 //
1267 // Check whether there are Options of this OneOf
1268 //
1269 if (IsListEmpty (&Question->OptionListHead)) {
1270 break;
1271 }
1272
1273 if (Selected) {
1274 //
1275 // Go ask for input
1276 //
1277 Status = GetSelectionInputPopUp (MenuOption);
1278 } else {
1279 MaxLen = BufferSize / sizeof (CHAR16);
1280 *OptionString = AllocateZeroPool (BufferSize);
1281 ASSERT (*OptionString);
1282
1283 OneOfOption = ValueToOption (Question, QuestionValue);
1284 if (OneOfOption == NULL) {
1285 //
1286 // Print debug msg for the mistach menu.
1287 //
1288 PrintMismatchMenuInfo (MenuOption);
1289
1290 if (SkipErrorValue) {
1291 //
1292 // Not report error, just get the correct option string info.
1293 //
1294 Link = GetFirstNode (&Question->OptionListHead);
1295 OneOfOption = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1296 } else {
1297 //
1298 // Show error message
1299 //
1300 do {
1301 CreateDialog (&Key, gEmptyString, gOptionMismatch, gPressEnter, gEmptyString, NULL);
1302 } while (Key.UnicodeChar != CHAR_CARRIAGE_RETURN);
1303
1304 //
1305 // Force the Question value to be valid
1306 // Exit current DisplayForm with new value.
1307 //
1308 Link = GetFirstNode (&Question->OptionListHead);
1309 Option = DISPLAY_QUESTION_OPTION_FROM_LINK (Link);
1310
1311 gUserInput->InputValue.Type = Option->OptionOpCode->Type;
1312 switch (gUserInput->InputValue.Type) {
1313 case EFI_IFR_TYPE_NUM_SIZE_8:
1314 gUserInput->InputValue.Value.u8 = Option->OptionOpCode->Value.u8;
1315 break;
1316 case EFI_IFR_TYPE_NUM_SIZE_16:
1317 CopyMem (&gUserInput->InputValue.Value.u16, &Option->OptionOpCode->Value.u16, sizeof (UINT16));
1318 break;
1319 case EFI_IFR_TYPE_NUM_SIZE_32:
1320 CopyMem (&gUserInput->InputValue.Value.u32, &Option->OptionOpCode->Value.u32, sizeof (UINT32));
1321 break;
1322 case EFI_IFR_TYPE_NUM_SIZE_64:
1323 CopyMem (&gUserInput->InputValue.Value.u64, &Option->OptionOpCode->Value.u64, sizeof (UINT64));
1324 break;
1325 default:
1326 ASSERT (FALSE);
1327 break;
1328 }
1329
1330 gUserInput->SelectedStatement = Question;
1331 gMisMatch = TRUE;
1332 FreePool (*OptionString);
1333 *OptionString = NULL;
1334 return EFI_NOT_FOUND;
1335 }
1336 }
1337
1338 Character[0] = LEFT_ONEOF_DELIMITER;
1339 NewStrCat (OptionString[0], MaxLen, Character);
1340 StringPtr = GetToken (OneOfOption->OptionOpCode->Option, gFormData->HiiHandle);
1341 ASSERT (StringPtr != NULL);
1342 NewStrCat (OptionString[0], MaxLen, StringPtr);
1343 Character[0] = RIGHT_ONEOF_DELIMITER;
1344 NewStrCat (OptionString[0], MaxLen, Character);
1345
1346 FreePool (StringPtr);
1347 }
1348
1349 break;
1350
1351 case EFI_IFR_CHECKBOX_OP:
1352 if (Selected) {
1353 //
1354 // Since this is a BOOLEAN operation, flip it upon selection
1355 //
1356 gUserInput->InputValue.Type = QuestionValue->Type;
1357 gUserInput->InputValue.Value.b = (BOOLEAN)(QuestionValue->Value.b ? FALSE : TRUE);
1358
1359 //
1360 // Perform inconsistent check
1361 //
1362 return EFI_SUCCESS;
1363 } else {
1364 *OptionString = AllocateZeroPool (BufferSize);
1365 ASSERT (*OptionString);
1366
1367 *OptionString[0] = LEFT_CHECKBOX_DELIMITER;
1368
1369 if (QuestionValue->Value.b) {
1370 *(OptionString[0] + 1) = CHECK_ON;
1371 } else {
1372 *(OptionString[0] + 1) = CHECK_OFF;
1373 }
1374
1375 *(OptionString[0] + 2) = RIGHT_CHECKBOX_DELIMITER;
1376 }
1377
1378 break;
1379
1380 case EFI_IFR_NUMERIC_OP:
1381 if (Selected) {
1382 //
1383 // Go ask for input
1384 //
1385 Status = GetNumericInput (MenuOption);
1386 } else {
1387 *OptionString = AllocateZeroPool (BufferSize);
1388 ASSERT (*OptionString);
1389
1390 *OptionString[0] = LEFT_NUMERIC_DELIMITER;
1391
1392 //
1393 // Formatted print
1394 //
1395 PrintFormattedNumber (Question, FormattedNumber, 21 * sizeof (CHAR16));
1396 Number = (UINT16)GetStringWidth (FormattedNumber);
1397 CopyMem (OptionString[0] + 1, FormattedNumber, Number);
1398
1399 *(OptionString[0] + Number / 2) = RIGHT_NUMERIC_DELIMITER;
1400 }
1401
1402 break;
1403
1404 case EFI_IFR_DATE_OP:
1405 if (Selected) {
1406 //
1407 // This is similar to numerics
1408 //
1409 Status = GetNumericInput (MenuOption);
1410 } else {
1411 *OptionString = AllocateZeroPool (BufferSize);
1412 ASSERT (*OptionString);
1413
1414 switch (MenuOption->Sequence) {
1415 case 0:
1416 *OptionString[0] = LEFT_NUMERIC_DELIMITER;
1417 if (QuestionValue->Value.date.Month == 0xff) {
1418 UnicodeSPrint (OptionString[0] + 1, 21 * sizeof (CHAR16), L"??");
1419 } else {
1420 UnicodeSPrint (OptionString[0] + 1, 21 * sizeof (CHAR16), L"%02d", QuestionValue->Value.date.Month);
1421 }
1422
1423 *(OptionString[0] + 3) = DATE_SEPARATOR;
1424 break;
1425
1426 case 1:
1427 SetUnicodeMem (OptionString[0], 4, L' ');
1428 if (QuestionValue->Value.date.Day == 0xff) {
1429 UnicodeSPrint (OptionString[0] + 4, 21 * sizeof (CHAR16), L"??");
1430 } else {
1431 UnicodeSPrint (OptionString[0] + 4, 21 * sizeof (CHAR16), L"%02d", QuestionValue->Value.date.Day);
1432 }
1433
1434 *(OptionString[0] + 6) = DATE_SEPARATOR;
1435 break;
1436
1437 case 2:
1438 SetUnicodeMem (OptionString[0], 7, L' ');
1439 if (QuestionValue->Value.date.Year == 0xff) {
1440 UnicodeSPrint (OptionString[0] + 7, 21 * sizeof (CHAR16), L"????");
1441 } else {
1442 UnicodeSPrint (OptionString[0] + 7, 21 * sizeof (CHAR16), L"%04d", QuestionValue->Value.date.Year);
1443 }
1444
1445 *(OptionString[0] + 11) = RIGHT_NUMERIC_DELIMITER;
1446 break;
1447 }
1448 }
1449
1450 break;
1451
1452 case EFI_IFR_TIME_OP:
1453 if (Selected) {
1454 //
1455 // This is similar to numerics
1456 //
1457 Status = GetNumericInput (MenuOption);
1458 } else {
1459 *OptionString = AllocateZeroPool (BufferSize);
1460 ASSERT (*OptionString);
1461
1462 switch (MenuOption->Sequence) {
1463 case 0:
1464 *OptionString[0] = LEFT_NUMERIC_DELIMITER;
1465 if (QuestionValue->Value.time.Hour == 0xff) {
1466 UnicodeSPrint (OptionString[0] + 1, 21 * sizeof (CHAR16), L"??");
1467 } else {
1468 UnicodeSPrint (OptionString[0] + 1, 21 * sizeof (CHAR16), L"%02d", QuestionValue->Value.time.Hour);
1469 }
1470
1471 *(OptionString[0] + 3) = TIME_SEPARATOR;
1472 break;
1473
1474 case 1:
1475 SetUnicodeMem (OptionString[0], 4, L' ');
1476 if (QuestionValue->Value.time.Minute == 0xff) {
1477 UnicodeSPrint (OptionString[0] + 4, 21 * sizeof (CHAR16), L"??");
1478 } else {
1479 UnicodeSPrint (OptionString[0] + 4, 21 * sizeof (CHAR16), L"%02d", QuestionValue->Value.time.Minute);
1480 }
1481
1482 *(OptionString[0] + 6) = TIME_SEPARATOR;
1483 break;
1484
1485 case 2:
1486 SetUnicodeMem (OptionString[0], 7, L' ');
1487 if (QuestionValue->Value.time.Second == 0xff) {
1488 UnicodeSPrint (OptionString[0] + 7, 21 * sizeof (CHAR16), L"??");
1489 } else {
1490 UnicodeSPrint (OptionString[0] + 7, 21 * sizeof (CHAR16), L"%02d", QuestionValue->Value.time.Second);
1491 }
1492
1493 *(OptionString[0] + 9) = RIGHT_NUMERIC_DELIMITER;
1494 break;
1495 }
1496 }
1497
1498 break;
1499
1500 case EFI_IFR_STRING_OP:
1501 if (Selected) {
1502 StringPtr = AllocateZeroPool (Question->CurrentValue.BufferLen + sizeof (CHAR16));
1503 ASSERT (StringPtr);
1504 CopyMem (StringPtr, Question->CurrentValue.Buffer, Question->CurrentValue.BufferLen);
1505
1506 Status = ReadString (MenuOption, gPromptForData, StringPtr);
1507 if (EFI_ERROR (Status)) {
1508 FreePool (StringPtr);
1509 return Status;
1510 }
1511
1512 gUserInput->InputValue.Buffer = AllocateCopyPool (Question->CurrentValue.BufferLen, StringPtr);
1513 gUserInput->InputValue.BufferLen = Question->CurrentValue.BufferLen;
1514 gUserInput->InputValue.Type = Question->CurrentValue.Type;
1515 gUserInput->InputValue.Value.string = HiiSetString (gFormData->HiiHandle, gUserInput->InputValue.Value.string, StringPtr, NULL);
1516 FreePool (StringPtr);
1517 return EFI_SUCCESS;
1518 } else {
1519 *OptionString = AllocateZeroPool (BufferSize);
1520 ASSERT (*OptionString);
1521
1522 if (((CHAR16 *)Question->CurrentValue.Buffer)[0] == 0x0000) {
1523 *(OptionString[0]) = '_';
1524 } else {
1525 if (Question->CurrentValue.BufferLen < BufferSize) {
1526 BufferSize = Question->CurrentValue.BufferLen;
1527 }
1528
1529 CopyMem (OptionString[0], (CHAR16 *)Question->CurrentValue.Buffer, BufferSize);
1530 }
1531 }
1532
1533 break;
1534
1535 case EFI_IFR_PASSWORD_OP:
1536 if (Selected) {
1537 Status = PasswordProcess (MenuOption);
1538 }
1539
1540 break;
1541
1542 default:
1543 break;
1544 }
1545
1546 return Status;
1547}
1548
1559UINTN
1561 IN CHAR16 *StringPtr,
1562 OUT CHAR16 **FormattedString,
1563 OUT UINT16 *EachLineWidth,
1564 IN UINTN RowCount
1565 )
1566{
1567 UINTN Index;
1568 CHAR16 *OutputString;
1569 UINTN TotalRowNum;
1570 UINTN CheckedNum;
1571 UINT16 GlyphWidth;
1572 UINT16 LineWidth;
1573 UINT16 MaxStringLen;
1574 UINT16 StringLen;
1575
1576 TotalRowNum = 0;
1577 CheckedNum = 0;
1578 GlyphWidth = 1;
1579 Index = 0;
1580 MaxStringLen = 0;
1581 StringLen = 0;
1582
1583 //
1584 // Set default help string width.
1585 //
1586 LineWidth = (UINT16)(gHelpBlockWidth - 1);
1587
1588 //
1589 // Get row number of the String.
1590 //
1591 while ((StringLen = GetLineByWidth (StringPtr, LineWidth, &GlyphWidth, &Index, &OutputString)) != 0) {
1592 if (StringLen > MaxStringLen) {
1593 MaxStringLen = StringLen;
1594 }
1595
1596 TotalRowNum++;
1597 FreePool (OutputString);
1598 }
1599
1600 *EachLineWidth = MaxStringLen;
1601
1602 *FormattedString = AllocateZeroPool (TotalRowNum * MaxStringLen * sizeof (CHAR16));
1603 ASSERT (*FormattedString != NULL);
1604
1605 //
1606 // Generate formatted help string array.
1607 //
1608 GlyphWidth = 1;
1609 Index = 0;
1610 while ((StringLen = GetLineByWidth (StringPtr, LineWidth, &GlyphWidth, &Index, &OutputString)) != 0) {
1611 CopyMem (*FormattedString + CheckedNum * MaxStringLen, OutputString, StringLen * sizeof (CHAR16));
1612 CheckedNum++;
1613 FreePool (OutputString);
1614 }
1615
1616 return TotalRowNum;
1617}
UINT64 UINTN
INT64 INTN
BOOLEAN EFIAPI IsNull(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
Definition: LinkedList.c:443
BOOLEAN EFIAPI IsListEmpty(IN CONST LIST_ENTRY *ListHead)
Definition: LinkedList.c:403
RETURN_STATUS EFIAPI StrCpyS(OUT CHAR16 *Destination, IN UINTN DestMax, IN CONST CHAR16 *Source)
Definition: SafeString.c:226
LIST_ENTRY *EFIAPI GetNextNode(IN CONST LIST_ENTRY *List, IN CONST LIST_ENTRY *Node)
Definition: LinkedList.c:333
INTN EFIAPI StrCmp(IN CONST CHAR16 *FirstString, IN CONST CHAR16 *SecondString)
Definition: String.c:109
LIST_ENTRY *EFIAPI GetFirstNode(IN CONST LIST_ENTRY *List)
Definition: LinkedList.c:298
INTN EFIAPI CompareMem(IN CONST VOID *DestinationBuffer, IN CONST VOID *SourceBuffer, IN UINTN Length)
VOID *EFIAPI CopyMem(OUT VOID *DestinationBuffer, IN CONST VOID *SourceBuffer, IN UINTN Length)
VOID *EFIAPI ZeroMem(OUT VOID *Buffer, IN UINTN Length)
UINTN PrintCharAt(IN UINTN Column, IN UINTN Row, CHAR16 Character)
UINTN PrintStringAt(IN UINTN Column, IN UINTN Row, IN CHAR16 *String)
VOID EFIAPI CreateDialog(OUT EFI_INPUT_KEY *Key OPTIONAL,...)
UINT8 EFIAPI GetPopupInverseColor(VOID)
UINT8 EFIAPI GetPopupColor(VOID)
VOID EFIAPI ClearLines(IN UINTN LeftColumn, IN UINTN RightColumn, IN UINTN TopRow, IN UINTN BottomRow, IN UINTN TextAttribute)
VOID *EFIAPI AllocateZeroPool(IN UINTN AllocationSize)
VOID EFIAPI FreePool(IN VOID *Buffer)
VOID *EFIAPI AllocateCopyPool(IN UINTN AllocationSize, IN CONST VOID *Buffer)
CHAR16 * GetToken(IN EFI_STRING_ID Token, IN EFI_HII_HANDLE HiiHandle)
Definition: FormDisplay.c:191
UINTN GetStringWidth(IN CHAR16 *String)
Definition: FormDisplay.c:830
UINT16 GetLineByWidth(IN CHAR16 *InputString, IN UINT16 LineWidth, IN OUT UINT16 *GlyphWidth, IN OUT UINTN *Index, OUT CHAR16 **OutputString)
Definition: FormDisplay.c:464
VOID SetUnicodeMem(IN VOID *Buffer, IN UINTN Size, IN CHAR16 Value)
Definition: FormDisplay.c:4210
EFI_STATUS GetNumericInput(IN UI_MENU_OPTION *MenuOption)
Definition: InputHandler.c:487
EFI_STATUS ReadString(IN UI_MENU_OPTION *MenuOption, IN CHAR16 *Prompt, IN OUT CHAR16 *StringPtr)
Definition: InputHandler.c:56
EFI_STATUS GetSelectionInputPopUp(IN UI_MENU_OPTION *MenuOption)
EFI_STRING_ID EFIAPI HiiSetString(IN EFI_HII_HANDLE HiiHandle, IN EFI_STRING_ID StringId OPTIONAL, IN CONST EFI_STRING String, IN CONST CHAR8 *SupportedLanguages OPTIONAL)
Definition: HiiString.c:52
EFI_STATUS EFIAPI HiiGetFormSetFromHiiHandle(IN EFI_HII_HANDLE Handle, OUT EFI_IFR_FORM_SET **Buffer, OUT UINTN *BufferSize)
Definition: HiiLib.c:394
UINTN EFIAPI UnicodeSPrint(OUT CHAR16 *StartOfBuffer, IN UINTN BufferSize, IN CONST CHAR16 *FormatString,...)
Definition: PrintLib.c:408
#define NULL
Definition: Base.h:319
#define VA_ARG(Marker, TYPE)
Definition: Base.h:679
#define VA_START(Marker, Parameter)
Definition: Base.h:661
#define TRUE
Definition: Base.h:301
#define FALSE
Definition: Base.h:307
CHAR8 * VA_LIST
Definition: Base.h:643
#define IN
Definition: Base.h:279
#define OFFSET_OF(TYPE, Field)
Definition: Base.h:758
#define OUT
Definition: Base.h:284
#define VA_END(Marker)
Definition: Base.h:691
#define DEBUG(Expression)
Definition: DebugLib.h:434
#define EFI_NOT_AVAILABLE_YET
Definition: PiMultiPhase.h:54
UINTN ProcessHelpString(IN CHAR16 *StringPtr, OUT CHAR16 **FormattedString, OUT UINT16 *EachLineWidth, IN UINTN RowCount)
VOID EFIAPI RefreshTimeOutProcess(IN EFI_EVENT Event, IN VOID *Context)
EFI_STATUS CompareHiiValue(IN EFI_HII_VALUE *Value1, IN EFI_HII_VALUE *Value2, OUT INTN *Result, IN EFI_HII_HANDLE HiiHandle OPTIONAL)
VOID EFIAPI CreateMultiStringPopUp(IN UINTN RequestedWidth, IN UINTN NumberOfLines,...)
BOOLEAN FindArrayData(IN VOID *Array, IN UINT8 Type, IN UINT64 Value, OUT UINTN *Index OPTIONAL)
VOID EFIAPI EmptyEventProcess(IN EFI_EVENT Event, IN VOID *Context)
EFI_STATUS ProcessOptions(IN UI_MENU_OPTION *MenuOption, IN BOOLEAN Selected, OUT CHAR16 **OptionString, IN BOOLEAN SkipErrorValue)
BOOLEAN IsTypeInUINT64(IN EFI_HII_VALUE *Value)
VOID PasswordInvalid(VOID)
UINT64 HiiValueToUINT64(IN EFI_HII_VALUE *Value)
EFI_STATUS PrintFormattedNumber(IN FORM_DISPLAY_ENGINE_STATEMENT *Question, IN OUT CHAR16 *FormattedNumber, IN UINTN BufferSize)
BOOLEAN IsTypeInBuffer(IN EFI_HII_VALUE *Value)
EFI_STATUS PasswordProcess(IN UI_MENU_OPTION *MenuOption)
VOID CreateSharedPopUp(IN UINTN RequestedWidth, IN UINTN NumberOfLines, IN VA_LIST Marker)
VOID PrintMismatchMenuInfo(IN UI_MENU_OPTION *MenuOption)
UINT64 GetArrayData(IN VOID *Array, IN UINT8 Type, IN UINTN Index)
VOID SetArrayData(IN VOID *Array, IN UINT8 Type, IN UINTN Index, IN UINT64 Value)
VOID GetBufAndLenForValue(IN EFI_HII_VALUE *Value, OUT UINT8 **Buf, OUT UINT16 *BufLen)
DISPLAY_QUESTION_OPTION * ValueToOption(IN FORM_DISPLAY_ENGINE_STATEMENT *Question, IN EFI_HII_VALUE *OptionValue)
VOID NewStrCat(IN OUT CHAR16 *Destination, IN UINTN DestMax, IN CHAR16 *Source)
RETURN_STATUS EFI_STATUS
Definition: UefiBaseType.h:29
VOID * EFI_EVENT
Definition: UefiBaseType.h:37
#define EFI_SUCCESS
Definition: UefiBaseType.h:112
EFI_SYSTEM_TABLE * gST
EFI_BOOT_SERVICES * gBS
VOID * EFI_HII_HANDLE
EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL * ConOut
Definition: UefiSpec.h:2064
EFI_STRING_ID string
EFI_IFR_TYPE_STRING, EFI_IFR_TYPE_ACTION.