2 Function and Macro defintions for to extract default values from UEFI Form package.
4 Copyright (c) 2008 - 2010, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
15 #include "HiiDatabase.h"
16 #include "UefiIfrParser.h"
17 #include "UefiIfrDefault.h"
22 extern CONST EFI_HII_DATABASE_PROTOCOL
*mHiiDatabase
;
23 extern CONST EFI_HII_IMAGE_PROTOCOL
*mHiiImageProtocol
;
24 extern CONST EFI_HII_STRING_PROTOCOL
*mHiiStringProtocol
;
25 extern CONST EFI_HII_CONFIG_ROUTING_PROTOCOL
*mHiiConfigRoutingProtocol
;
28 Set the data position at Offset with Width in Node->Buffer based
31 @param Node The Buffer Storage Node.
32 @param Value The input value.
33 @param Offset The offset in Node->Buffer for the update.
34 @param Width The length of the Value.
39 OUT UEFI_IFR_BUFFER_STORAGE_NODE
*Node
,
40 IN CONST EFI_HII_VALUE
*Value
,
45 ASSERT (Node
->Signature
== UEFI_IFR_BUFFER_STORAGE_NODE_SIGNATURE
);
46 ASSERT (Offset
+ Width
<= Node
->Size
);
48 CopyMem (Node
->Buffer
+ Offset
, &Value
->Value
.u8
, Width
);
53 Get question default value, and set it into the match var storage.
55 Note Framework 0.92's HII Implementation does not support for default value for these opcodes:
56 EFI_IFR_ORDERED_LIST_OP:
60 @param Question Question to be set to its default value.
61 @param DefaultId The Class of the default.
62 @param VarStoreId Id of var storage.
63 @param Node Var storage buffer to store the got default value.
65 @retval EFI_SUCCESS Question is reset to default value.
70 IN FORM_BROWSER_STATEMENT
*Question
,
73 OUT UEFI_IFR_BUFFER_STORAGE_NODE
*Node
78 QUESTION_DEFAULT
*Default
;
79 QUESTION_OPTION
*Option
;
80 EFI_HII_VALUE
*HiiValue
;
85 // Statement don't have storage, skip them
87 if (Question
->QuestionId
== 0) {
91 if (Question
->VarStoreId
!= VarStoreId
) {
95 ASSERT (Question
->Storage
->Type
== EFI_HII_VARSTORE_BUFFER
);
98 // There are three ways to specify default value for a Question:
99 // 1, use nested EFI_IFR_DEFAULT (highest priority)
100 // 2, set flags of EFI_ONE_OF_OPTION (provide Standard and Manufacturing default)
101 // 3, set flags of EFI_IFR_CHECKBOX (provide Standard and Manufacturing default) (lowest priority)
103 HiiValue
= &Question
->HiiValue
;
106 // EFI_IFR_DEFAULT has highest priority
108 if (!IsListEmpty (&Question
->DefaultListHead
)) {
109 Link
= GetFirstNode (&Question
->DefaultListHead
);
110 while (!IsNull (&Question
->DefaultListHead
, Link
)) {
111 Default
= QUESTION_DEFAULT_FROM_LINK (Link
);
113 if (Default
->DefaultId
== DefaultId
) {
115 // Default value is embedded in EFI_IFR_DEFAULT
117 CopyMem (HiiValue
, &Default
->Value
, sizeof (EFI_HII_VALUE
));
119 SetNodeBuffer (Node
, HiiValue
, Question
->VarStoreInfo
.VarOffset
, Question
->StorageWidth
);
123 Link
= GetNextNode (&Question
->DefaultListHead
, Link
);
130 if ((Question
->Operand
== EFI_IFR_ONE_OF_OP
) && !IsListEmpty (&Question
->OptionListHead
)) {
131 if (DefaultId
<= EFI_HII_DEFAULT_CLASS_MANUFACTURING
) {
133 // OneOfOption could only provide Standard and Manufacturing default
135 Link
= GetFirstNode (&Question
->OptionListHead
);
136 while (!IsNull (&Question
->OptionListHead
, Link
)) {
137 Option
= QUESTION_OPTION_FROM_LINK (Link
);
139 if (((DefaultId
== EFI_HII_DEFAULT_CLASS_STANDARD
) && ((Option
->Flags
& EFI_IFR_OPTION_DEFAULT
) == EFI_IFR_OPTION_DEFAULT
)) ||
140 ((DefaultId
== EFI_HII_DEFAULT_CLASS_MANUFACTURING
) && ((Option
->Flags
& EFI_IFR_OPTION_DEFAULT_MFG
) == EFI_IFR_OPTION_DEFAULT_MFG
))
142 CopyMem (HiiValue
, &Option
->Value
, sizeof (EFI_HII_VALUE
));
144 SetNodeBuffer (Node
, HiiValue
, Question
->VarStoreInfo
.VarOffset
, Question
->StorageWidth
);
148 Link
= GetNextNode (&Question
->OptionListHead
, Link
);
154 // EFI_IFR_CHECKBOX - lowest priority
156 if (Question
->Operand
== EFI_IFR_CHECKBOX_OP
) {
157 if (DefaultId
<= EFI_HII_DEFAULT_CLASS_MANUFACTURING
) {
159 // Checkbox could only provide Standard and Manufacturing default
161 if (((DefaultId
== EFI_HII_DEFAULT_CLASS_STANDARD
) && ((Question
->Flags
& EFI_IFR_CHECKBOX_DEFAULT
) == EFI_IFR_CHECKBOX_DEFAULT
)) ||
162 ((DefaultId
== EFI_HII_DEFAULT_CLASS_MANUFACTURING
) && ((Question
->Flags
& EFI_IFR_CHECKBOX_DEFAULT_MFG
) == EFI_IFR_CHECKBOX_DEFAULT_MFG
))
164 HiiValue
->Value
.b
= TRUE
;
166 HiiValue
->Value
.b
= FALSE
;
169 SetNodeBuffer (Node
, HiiValue
, Question
->VarStoreInfo
.VarOffset
, Question
->StorageWidth
);
179 Extract the default values from all questions in the input Form,
180 and set default value into the matched var storage.
182 @param Form The Form which to be reset.
183 @param DefaultId The Class of the default.
184 @param VarStoreId Id of var storage.
185 @param Node Var storage buffer to store the got default value.
187 @retval EFI_SUCCESS The function completed successfully.
192 IN FORM_BROWSER_FORM
*Form
,
194 IN UINT16 VarStoreId
,
195 OUT UEFI_IFR_BUFFER_STORAGE_NODE
*Node
200 FORM_BROWSER_STATEMENT
*Question
;
202 Link
= GetFirstNode (&Form
->StatementListHead
);
203 while (!IsNull (&Form
->StatementListHead
, Link
)) {
204 Question
= FORM_BROWSER_STATEMENT_FROM_LINK (Link
);
206 // Reset Question to its default value
208 Status
= GetQuestionDefault (Question
, DefaultId
, VarStoreId
, Node
);
209 if (EFI_ERROR (Status
)) {
213 Link
= GetNextNode (&Form
->StatementListHead
, Link
);
220 Destroy all the buffer allocated for the fileds of
221 UEFI_IFR_BUFFER_STORAGE_NODE. The Node itself
224 @param Node Var storage buffer.
229 IN UEFI_IFR_BUFFER_STORAGE_NODE
*Node
232 FreePool (Node
->Buffer
);
233 FreePool (Node
->Name
);
239 Get the default value for Buffer Type storage named by
240 a Default Store and a Storage Store from a FormSet.
241 The result is in the a instance of UEFI_IFR_BUFFER_STORAGE_NODE
242 allocated by this function. It is inserted to the link list.
244 @param DefaultStore The Default Store.
245 @param Storage The Storage.
246 @param FormSet The Form Set.
247 @param UefiDefaultsListHead The head of link list for the output.
249 @retval EFI_SUCCESS Successful.
253 GetBufferTypeDefaultIdAndStorageId (
254 IN FORMSET_DEFAULTSTORE
*DefaultStore
,
255 IN FORMSET_STORAGE
*Storage
,
256 IN FORM_BROWSER_FORMSET
*FormSet
,
257 OUT LIST_ENTRY
*UefiDefaultsListHead
260 UEFI_IFR_BUFFER_STORAGE_NODE
*Node
;
262 FORM_BROWSER_FORM
*Form
;
265 Node
= AllocateZeroPool (sizeof (UEFI_IFR_BUFFER_STORAGE_NODE
));
266 ASSERT (Node
!= NULL
);
268 Node
->Signature
= UEFI_IFR_BUFFER_STORAGE_NODE_SIGNATURE
;
269 Node
->Name
= AllocateCopyPool (StrSize (Storage
->Name
), Storage
->Name
);
270 Node
->DefaultId
= DefaultStore
->DefaultId
;
271 Node
->StoreId
= Storage
->VarStoreId
;
272 CopyGuid (&Node
->Guid
, &Storage
->Guid
);
273 Node
->Size
= Storage
->Size
;
274 Node
->Buffer
= AllocateZeroPool (Node
->Size
);
276 // Extract default from IFR binary
278 Link
= GetFirstNode (&FormSet
->FormListHead
);
279 while (!IsNull (&FormSet
->FormListHead
, Link
)) {
280 Form
= FORM_BROWSER_FORM_FROM_LINK (Link
);
282 Status
= ExtractFormDefault (Form
, DefaultStore
->DefaultId
, Storage
->VarStoreId
, Node
);
283 ASSERT_EFI_ERROR (Status
);
285 Link
= GetNextNode (&FormSet
->FormListHead
, Link
);
288 InsertTailList (UefiDefaultsListHead
, &Node
->List
);
295 Get the default value for Buffer Type storage named by
296 a Default Store from a FormSet.
297 The result is in the a instance of UEFI_IFR_BUFFER_STORAGE_NODE
298 allocated by this function. The output can be multiple instances
299 of UEFI_IFR_BUFFER_STORAGE_NODE. It is inserted to the link list.
301 @param DefaultStore The Default Store.
302 @param FormSet The Form Set.
303 @param UefiDefaultsListHead The head of link list for the output.
305 @retval EFI_SUCCESS Successful.
309 GetBufferTypeDefaultId (
310 IN FORMSET_DEFAULTSTORE
*DefaultStore
,
311 IN FORM_BROWSER_FORMSET
*FormSet
,
312 OUT LIST_ENTRY
*UefiDefaultsListHead
315 LIST_ENTRY
*StorageLink
;
316 FORMSET_STORAGE
*Storage
;
319 StorageLink
= GetFirstNode (&FormSet
->StorageListHead
);
321 while (!IsNull (&FormSet
->StorageListHead
, StorageLink
)) {
322 Storage
= FORMSET_STORAGE_FROM_LINK(StorageLink
);
324 if (Storage
->Type
== EFI_HII_VARSTORE_BUFFER
) {
325 Status
= GetBufferTypeDefaultIdAndStorageId (DefaultStore
, Storage
, FormSet
, UefiDefaultsListHead
);
326 ASSERT_EFI_ERROR (Status
);
329 StorageLink
= GetNextNode (&FormSet
->StorageListHead
, StorageLink
);
337 Get the default value for Buffer Type storage from the FormSet in ThunkContext.
339 The results can be multiple instances of UEFI_IFR_BUFFER_STORAGE_NODE.
340 They are inserted to the link list.
342 @param ThunkContext Hii thunk context.
343 @param UefiDefaults The head of link list for the output.
345 @retval EFI_SUCCESS Successful.
349 UefiIfrGetBufferTypeDefaults (
350 IN HII_THUNK_CONTEXT
*ThunkContext
,
351 OUT LIST_ENTRY
**UefiDefaults
354 LIST_ENTRY
*DefaultLink
;
355 FORMSET_DEFAULTSTORE
*DefaultStore
;
358 ASSERT (UefiDefaults
!= NULL
);
360 *UefiDefaults
= AllocateZeroPool (sizeof (LIST_ENTRY
));
361 ASSERT (*UefiDefaults
!= NULL
);
362 InitializeListHead (*UefiDefaults
);
364 DefaultLink
= GetFirstNode (&ThunkContext
->FormSet
->DefaultStoreListHead
);
365 while (!IsNull (&ThunkContext
->FormSet
->DefaultStoreListHead
, DefaultLink
)) {
366 DefaultStore
= FORMSET_DEFAULTSTORE_FROM_LINK(DefaultLink
);
368 Status
= GetBufferTypeDefaultId (DefaultStore
, ThunkContext
->FormSet
, *UefiDefaults
);
369 ASSERT_EFI_ERROR (Status
);
371 DefaultLink
= GetNextNode (&ThunkContext
->FormSet
->DefaultStoreListHead
, DefaultLink
);
379 Convert the UEFI Buffer Type default values to a Framework HII default
380 values specified by a EFI_HII_VARIABLE_PACK_LIST structure.
382 @param ListHead The link list of UEFI_IFR_BUFFER_STORAGE_NODE
383 which contains the default values retrived from a UEFI form set.
384 @param DefaultMask The default mask.
385 The valid values are EFI_IFR_FLAG_DEFAULT and EFI_IFR_FLAG_MANUFACTURING.
386 UEFI spec only map EFI_IFR_FLAG_DEFAULT and EFI_IFR_FLAG_MANUFACTURING
387 from specification to valid default class.
388 @param UefiFormSetDefaultVarStoreId
389 ID of the default varstore in FormSet.
390 @param VariablePackList The output default value in a format defined in Framework.
392 @retval EFI_SUCCESS Successful.
393 @retval EFI_INVALID_PARAMETER The default mask is not EFI_IFR_FLAG_DEFAULT or
394 EFI_IFR_FLAG_MANUFACTURING.
397 UefiDefaultsToFwDefaults (
398 IN LIST_ENTRY
*ListHead
,
399 IN UINTN DefaultMask
,
400 IN EFI_VARSTORE_ID UefiFormSetDefaultVarStoreId
,
401 OUT EFI_HII_VARIABLE_PACK_LIST
**VariablePackList
405 UEFI_IFR_BUFFER_STORAGE_NODE
*Node
;
409 EFI_HII_VARIABLE_PACK
*Pack
;
410 EFI_HII_VARIABLE_PACK_LIST
*PackList
;
413 if (DefaultMask
== EFI_IFR_FLAG_DEFAULT
) {
414 DefaultId
= EFI_HII_DEFAULT_CLASS_STANDARD
;
415 } else if (DefaultMask
== EFI_IFR_FLAG_MANUFACTURING
) {
416 DefaultId
= EFI_HII_DEFAULT_CLASS_MANUFACTURING
;
419 // UEFI spec only map EFI_IFR_FLAG_DEFAULT and EFI_IFR_FLAG_MANUFACTURING
420 // from specification to valid default class.
423 return EFI_INVALID_PARAMETER
;
427 // Calculate the size of the output EFI_HII_VARIABLE_PACK_LIST structure
431 List
= GetFirstNode (ListHead
);
432 while (!IsNull (ListHead
, List
)) {
433 Node
= UEFI_IFR_BUFFER_STORAGE_NODE_FROM_LIST(List
);
435 if (Node
->DefaultId
== DefaultId
) {
437 Size
+= StrSize (Node
->Name
);
442 List
= GetNextNode (ListHead
, List
);
446 *VariablePackList
= NULL
;
447 return EFI_NOT_FOUND
;
450 Size
= Size
+ Count
* (sizeof (EFI_HII_VARIABLE_PACK_LIST
) + sizeof (EFI_HII_VARIABLE_PACK
));
452 *VariablePackList
= AllocateZeroPool (Size
);
453 ASSERT (*VariablePackList
!= NULL
);
455 List
= GetFirstNode (ListHead
);
457 PackList
= (EFI_HII_VARIABLE_PACK_LIST
*) *VariablePackList
;
458 Pack
= (EFI_HII_VARIABLE_PACK
*) (PackList
+ 1);
460 while (!IsNull (ListHead
, List
)) {
461 Node
= UEFI_IFR_BUFFER_STORAGE_NODE_FROM_LIST(List
);
464 if (Node
->DefaultId
== DefaultId
) {
466 Size
+= sizeof (EFI_HII_VARIABLE_PACK
);
468 Pack
->VariableNameLength
= (UINT32
) StrSize (Node
->Name
);
470 if (Node
->StoreId
== UefiFormSetDefaultVarStoreId
) {
472 // The default VARSTORE in VFR from a Framework module has Varstore ID of 0.
474 Pack
->VariableId
= 0;
476 Pack
->VariableId
= Node
->StoreId
;
479 CopyMem ((UINT8
*) Pack
+ sizeof (EFI_HII_VARIABLE_PACK
), Node
->Name
, StrSize (Node
->Name
));
480 Size
+= Pack
->VariableNameLength
;
483 // Initialize EFI_HII_VARIABLE_PACK
485 Pack
->Header
.Type
= 0;
486 Pack
->Header
.Length
= (UINT32
) Size
;
487 CopyMem (&Pack
->VariableGuid
, &Node
->Guid
, sizeof (EFI_GUID
));
489 CopyMem ((UINT8
*) Pack
+ sizeof (EFI_HII_VARIABLE_PACK
) + Pack
->VariableNameLength
, Node
->Buffer
, Node
->Size
);
491 Size
+= sizeof (EFI_HII_VARIABLE_PACK_LIST
);
494 // Initialize EFI_HII_VARIABLE_PACK_LIST
496 PackList
->VariablePack
= Pack
;
499 PackList
->NextVariablePack
= (EFI_HII_VARIABLE_PACK_LIST
*)((UINT8
*) PackList
+ Size
);
501 PackList
= PackList
->NextVariablePack
;
502 Pack
= (EFI_HII_VARIABLE_PACK
*) (PackList
+ 1);
507 List
= GetNextNode (ListHead
, List
);
516 Free up all buffer allocated for the link list of UEFI_IFR_BUFFER_STORAGE_NODE.
518 @param ListHead The link list of UEFI_IFR_BUFFER_STORAGE_NODE
519 which contains the default values retrived from
525 IN LIST_ENTRY
*ListHead
529 UEFI_IFR_BUFFER_STORAGE_NODE
*Default
;
531 while (!IsListEmpty (ListHead
)) {
532 Link
= GetFirstNode (ListHead
);
534 Default
= UEFI_IFR_BUFFER_STORAGE_NODE_FROM_LIST(Link
);
536 RemoveEntryList (Link
);
538 DestroyDefaultNode (Default
);