]> git.proxmox.com Git - mirror_edk2.git/blame - MdeModulePkg/Application/UiApp/BootMaint/BootMaint.c
UiApp: Update copyright info, cover old code existed in old BdsDxe driver.
[mirror_edk2.git] / MdeModulePkg / Application / UiApp / BootMaint / BootMaint.c
CommitLineData
143f0b1d
ED
1/** @file\r
2 The functions for Boot Maintainence Main menu.\r
3\r
afc244a5 4Copyright (c) 2004 - 2015, Intel Corporation. All rights reserved.<BR>\r
143f0b1d
ED
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 "BootMaint.h"\r
16\r
17EFI_DEVICE_PATH_PROTOCOL EndDevicePath[] = {\r
18 {\r
19 END_DEVICE_PATH_TYPE,\r
20 END_ENTIRE_DEVICE_PATH_SUBTYPE,\r
21 {\r
22 END_DEVICE_PATH_LENGTH,\r
23 0\r
24 }\r
25 }\r
26};\r
27\r
28HII_VENDOR_DEVICE_PATH mBmmHiiVendorDevicePath = {\r
29 {\r
30 {\r
31 HARDWARE_DEVICE_PATH,\r
32 HW_VENDOR_DP,\r
33 {\r
34 (UINT8) (sizeof (VENDOR_DEVICE_PATH)),\r
35 (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8)\r
36 }\r
37 },\r
38 //\r
39 // {165A028F-0BB2-4b5f-8747-77592E3F6499}\r
40 //\r
41 { 0x165a028f, 0xbb2, 0x4b5f, { 0x87, 0x47, 0x77, 0x59, 0x2e, 0x3f, 0x64, 0x99 } }\r
42 },\r
43 {\r
44 END_DEVICE_PATH_TYPE,\r
45 END_ENTIRE_DEVICE_PATH_SUBTYPE,\r
46 { \r
47 (UINT8) (END_DEVICE_PATH_LENGTH),\r
48 (UINT8) ((END_DEVICE_PATH_LENGTH) >> 8)\r
49 }\r
50 }\r
51};\r
52\r
53HII_VENDOR_DEVICE_PATH mFeHiiVendorDevicePath = {\r
54 {\r
55 {\r
56 HARDWARE_DEVICE_PATH,\r
57 HW_VENDOR_DP,\r
58 {\r
59 (UINT8) (sizeof (VENDOR_DEVICE_PATH)),\r
60 (UINT8) ((sizeof (VENDOR_DEVICE_PATH)) >> 8)\r
61 }\r
62 },\r
63 //\r
64 // {91DB4238-B0C8-472e-BBCF-F3A6541010F4}\r
65 //\r
66 { 0x91db4238, 0xb0c8, 0x472e, { 0xbb, 0xcf, 0xf3, 0xa6, 0x54, 0x10, 0x10, 0xf4 } }\r
67 },\r
68 {\r
69 END_DEVICE_PATH_TYPE,\r
70 END_ENTIRE_DEVICE_PATH_SUBTYPE,\r
71 { \r
72 (UINT8) (END_DEVICE_PATH_LENGTH),\r
73 (UINT8) ((END_DEVICE_PATH_LENGTH) >> 8)\r
74 }\r
75 }\r
76};\r
77\r
78EFI_GUID mBootMaintGuid = BOOT_MAINT_FORMSET_GUID;\r
79EFI_GUID mFileExplorerGuid = FILE_EXPLORE_FORMSET_GUID;\r
80\r
81CHAR16 mBootMaintStorageName[] = L"BmmData";\r
82CHAR16 mFileExplorerStorageName[] = L"FeData";\r
83BMM_CALLBACK_DATA *mBmmCallbackInfo = NULL;\r
84BOOLEAN mAllMenuInit = FALSE;\r
85BOOLEAN mEnterFileExplorer = FALSE;\r
86\r
87/**\r
88 Init all memu.\r
89\r
90 @param CallbackData The BMM context data.\r
91\r
92**/\r
93VOID\r
94InitAllMenu (\r
95 IN BMM_CALLBACK_DATA *CallbackData\r
96 );\r
97\r
98/**\r
99 Free up all Menu Option list.\r
100\r
101**/\r
102VOID\r
103FreeAllMenu (\r
104 VOID\r
105 );\r
106\r
107/**\r
108 Create string tokens for a menu from its help strings and display strings\r
109\r
110 @param CallbackData The BMM context data.\r
111 @param HiiHandle Hii Handle of the package to be updated.\r
112 @param MenuOption The Menu whose string tokens need to be created\r
113\r
114 @retval EFI_SUCCESS String tokens created successfully\r
115 @retval others contain some errors\r
116**/\r
117EFI_STATUS\r
118CreateMenuStringToken (\r
119 IN BMM_CALLBACK_DATA *CallbackData,\r
120 IN EFI_HII_HANDLE HiiHandle,\r
121 IN BM_MENU_OPTION *MenuOption\r
122 )\r
123{\r
124 BM_MENU_ENTRY *NewMenuEntry;\r
125 UINTN Index;\r
126\r
127 for (Index = 0; Index < MenuOption->MenuNumber; Index++) {\r
128 NewMenuEntry = BOpt_GetMenuEntry (MenuOption, Index);\r
129\r
130 NewMenuEntry->DisplayStringToken = HiiSetString (\r
131 HiiHandle,\r
132 0,\r
133 NewMenuEntry->DisplayString,\r
134 NULL\r
135 );\r
136\r
137 if (NULL == NewMenuEntry->HelpString) {\r
138 NewMenuEntry->HelpStringToken = NewMenuEntry->DisplayStringToken;\r
139 } else {\r
140 NewMenuEntry->HelpStringToken = HiiSetString (\r
141 HiiHandle,\r
142 0,\r
143 NewMenuEntry->HelpString,\r
144 NULL\r
145 );\r
146 }\r
147 }\r
148\r
149 return EFI_SUCCESS;\r
150}\r
151\r
152/**\r
153 This function allows a caller to extract the current configuration for one\r
154 or more named elements from the target driver.\r
155\r
156\r
157 @param This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.\r
158 @param Request A null-terminated Unicode string in <ConfigRequest> format.\r
159 @param Progress On return, points to a character in the Request string.\r
160 Points to the string's null terminator if request was successful.\r
161 Points to the most recent '&' before the first failing name/value\r
162 pair (or the beginning of the string if the failure is in the\r
163 first name/value pair) if the request was not successful.\r
164 @param Results A null-terminated Unicode string in <ConfigAltResp> format which\r
165 has all values filled in for the names in the Request string.\r
166 String to be allocated by the called function.\r
167\r
168 @retval EFI_SUCCESS The Results is filled with the requested values.\r
169 @retval EFI_OUT_OF_RESOURCES Not enough memory to store the results.\r
170 @retval EFI_INVALID_PARAMETER Request is NULL, illegal syntax, or unknown name.\r
171 @retval EFI_NOT_FOUND Routing data doesn't match any storage in this driver.\r
172\r
173**/\r
174EFI_STATUS\r
175EFIAPI\r
176BootMaintExtractConfig (\r
177 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL *This,\r
178 IN CONST EFI_STRING Request,\r
179 OUT EFI_STRING *Progress,\r
180 OUT EFI_STRING *Results\r
181 )\r
182{\r
183 EFI_STATUS Status;\r
184 UINTN BufferSize;\r
185 BMM_CALLBACK_DATA *Private;\r
186 EFI_STRING ConfigRequestHdr;\r
187 EFI_STRING ConfigRequest;\r
188 BOOLEAN AllocatedRequest;\r
189 UINTN Size;\r
190\r
191 if (Progress == NULL || Results == NULL) {\r
192 return EFI_INVALID_PARAMETER;\r
193 }\r
194\r
195 *Progress = Request;\r
196 if ((Request != NULL) && !HiiIsConfigHdrMatch (Request, &mBootMaintGuid, mBootMaintStorageName)) {\r
197 return EFI_NOT_FOUND;\r
198 }\r
199\r
200 ConfigRequestHdr = NULL;\r
201 ConfigRequest = NULL;\r
202 AllocatedRequest = FALSE;\r
203 Size = 0;\r
204\r
205 Private = BMM_CALLBACK_DATA_FROM_THIS (This);\r
206 //\r
207 // Convert buffer data to <ConfigResp> by helper function BlockToConfig()\r
208 //\r
209 BufferSize = sizeof (BMM_FAKE_NV_DATA);\r
210 ConfigRequest = Request;\r
211 if ((Request == NULL) || (StrStr (Request, L"OFFSET") == NULL)) {\r
212 //\r
213 // Request has no request element, construct full request string.\r
214 // Allocate and fill a buffer large enough to hold the <ConfigHdr> template\r
215 // followed by "&OFFSET=0&WIDTH=WWWWWWWWWWWWWWWW" followed by a Null-terminator\r
216 //\r
217 ConfigRequestHdr = HiiConstructConfigHdr (&mBootMaintGuid, mBootMaintStorageName, Private->BmmDriverHandle);\r
218 Size = (StrLen (ConfigRequestHdr) + 32 + 1) * sizeof (CHAR16);\r
219 ConfigRequest = AllocateZeroPool (Size);\r
220 ASSERT (ConfigRequest != NULL);\r
221 AllocatedRequest = TRUE;\r
222 UnicodeSPrint (ConfigRequest, Size, L"%s&OFFSET=0&WIDTH=%016LX", ConfigRequestHdr, (UINT64)BufferSize);\r
223 FreePool (ConfigRequestHdr);\r
224 }\r
225\r
226 Status = gHiiConfigRouting->BlockToConfig (\r
227 gHiiConfigRouting,\r
228 ConfigRequest,\r
229 (UINT8 *) &Private->BmmFakeNvData,\r
230 BufferSize,\r
231 Results,\r
232 Progress\r
233 );\r
234 //\r
235 // Free the allocated config request string.\r
236 //\r
237 if (AllocatedRequest) {\r
238 FreePool (ConfigRequest);\r
239 ConfigRequest = NULL;\r
240 }\r
241 //\r
242 // Set Progress string to the original request string.\r
243 //\r
244 if (Request == NULL) {\r
245 *Progress = NULL;\r
246 } else if (StrStr (Request, L"OFFSET") == NULL) {\r
247 *Progress = Request + StrLen (Request);\r
248 }\r
249\r
250 return Status;\r
251}\r
252\r
253/**\r
254 This function applies changes in a driver's configuration.\r
255 Input is a Configuration, which has the routing data for this\r
256 driver followed by name / value configuration pairs. The driver\r
257 must apply those pairs to its configurable storage. If the\r
258 driver's configuration is stored in a linear block of data\r
259 and the driver's name / value pairs are in <BlockConfig>\r
260 format, it may use the ConfigToBlock helper function (above) to\r
261 simplify the job. Currently not implemented.\r
262\r
263 @param[in] This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.\r
264 @param[in] Configuration A null-terminated Unicode string in\r
265 <ConfigString> format. \r
266 @param[out] Progress A pointer to a string filled in with the\r
267 offset of the most recent '&' before the\r
268 first failing name / value pair (or the\r
269 beginn ing of the string if the failure\r
270 is in the first name / value pair) or\r
271 the terminating NULL if all was\r
272 successful.\r
273\r
274 @retval EFI_SUCCESS The results have been distributed or are\r
275 awaiting distribution. \r
276 @retval EFI_OUT_OF_RESOURCES Not enough memory to store the\r
277 parts of the results that must be\r
278 stored awaiting possible future\r
279 protocols.\r
280 @retval EFI_INVALID_PARAMETERS Passing in a NULL for the\r
281 Results parameter would result\r
282 in this type of error.\r
283 @retval EFI_NOT_FOUND Target for the specified routing data\r
284 was not found.\r
285**/\r
286EFI_STATUS\r
287EFIAPI\r
288BootMaintRouteConfig (\r
289 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL *This,\r
290 IN CONST EFI_STRING Configuration,\r
291 OUT EFI_STRING *Progress\r
292 )\r
293{\r
294 EFI_STATUS Status;\r
295 UINTN BufferSize;\r
296 EFI_HII_CONFIG_ROUTING_PROTOCOL *ConfigRouting;\r
297 BMM_FAKE_NV_DATA *NewBmmData;\r
298 BMM_FAKE_NV_DATA *OldBmmData;\r
299 BM_MENU_ENTRY *NewMenuEntry;\r
300 BM_LOAD_CONTEXT *NewLoadContext;\r
301 UINT16 Index; \r
302 BMM_CALLBACK_DATA *Private; \r
303\r
304 if (Progress == NULL) {\r
305 return EFI_INVALID_PARAMETER;\r
306 }\r
307 *Progress = Configuration;\r
308\r
309 if (Configuration == NULL) {\r
310 return EFI_INVALID_PARAMETER;\r
311 }\r
312\r
313 //\r
314 // Check routing data in <ConfigHdr>.\r
315 // Note: there is no name for Name/Value storage, only GUID will be checked\r
316 //\r
317 if (!HiiIsConfigHdrMatch (Configuration, &mBootMaintGuid, mBootMaintStorageName)) {\r
318 return EFI_NOT_FOUND;\r
319 }\r
320\r
321 Status = gBS->LocateProtocol (\r
322 &gEfiHiiConfigRoutingProtocolGuid, \r
323 NULL, \r
324 (VOID **)&ConfigRouting\r
325 );\r
326 if (EFI_ERROR (Status)) {\r
327 return Status;\r
328 }\r
329 \r
330 Private = BMM_CALLBACK_DATA_FROM_THIS (This); \r
331 //\r
332 // Get Buffer Storage data from EFI variable\r
333 //\r
334 BufferSize = sizeof (BMM_FAKE_NV_DATA);\r
335 OldBmmData = &Private->BmmOldFakeNVData;\r
336 NewBmmData = &Private->BmmFakeNvData;\r
337 //\r
338 // Convert <ConfigResp> to buffer data by helper function ConfigToBlock()\r
339 //\r
340 Status = ConfigRouting->ConfigToBlock (\r
341 ConfigRouting,\r
342 Configuration,\r
343 (UINT8 *) NewBmmData,\r
344 &BufferSize,\r
345 Progress\r
346 );\r
347 ASSERT_EFI_ERROR (Status); \r
348 //\r
349 // Compare new and old BMM configuration data and only do action for modified item to \r
350 // avoid setting unnecessary non-volatile variable\r
351 //\r
352 \r
353 //\r
354 // Check data which located in BMM main page and save the settings if need\r
355 // \r
356 if (CompareMem (&NewBmmData->BootNext, &OldBmmData->BootNext, sizeof (NewBmmData->BootNext)) != 0) {\r
357 Status = Var_UpdateBootNext (Private);\r
358 }\r
359 \r
360 //\r
361 // Check data which located in Boot Options Menu and save the settings if need\r
362 // \r
363 if (CompareMem (NewBmmData->BootOptionDel, OldBmmData->BootOptionDel, sizeof (NewBmmData->BootOptionDel)) != 0) { \r
364 for (Index = 0; \r
365 ((Index < BootOptionMenu.MenuNumber) && (Index < (sizeof (NewBmmData->BootOptionDel) / sizeof (NewBmmData->BootOptionDel[0])))); \r
366 Index ++) {\r
367 NewMenuEntry = BOpt_GetMenuEntry (&BootOptionMenu, Index);\r
368 NewLoadContext = (BM_LOAD_CONTEXT *) NewMenuEntry->VariableContext;\r
369 NewLoadContext->Deleted = NewBmmData->BootOptionDel[Index];\r
370 NewBmmData->BootOptionDel[Index] = FALSE;\r
371 }\r
372 \r
373 Var_DelBootOption ();\r
374 }\r
375 \r
376 if (CompareMem (NewBmmData->BootOptionOrder, OldBmmData->BootOptionOrder, sizeof (NewBmmData->BootOptionOrder)) != 0) { \r
377 Status = Var_UpdateBootOrder (Private);\r
378 } \r
379\r
380 //\r
381 // Check data which located in Driver Options Menu and save the settings if need\r
382 // \r
383 if (CompareMem (NewBmmData->DriverOptionDel, OldBmmData->DriverOptionDel, sizeof (NewBmmData->DriverOptionDel)) != 0) { \r
384 for (Index = 0; \r
385 ((Index < DriverOptionMenu.MenuNumber) && (Index < (sizeof (NewBmmData->DriverOptionDel) / sizeof (NewBmmData->DriverOptionDel[0])))); \r
386 Index++) {\r
387 NewMenuEntry = BOpt_GetMenuEntry (&DriverOptionMenu, Index);\r
388 NewLoadContext = (BM_LOAD_CONTEXT *) NewMenuEntry->VariableContext;\r
389 NewLoadContext->Deleted = NewBmmData->DriverOptionDel[Index];\r
390 NewBmmData->DriverOptionDel[Index] = FALSE;\r
391 }\r
392 Var_DelDriverOption (); \r
393 }\r
394 \r
395 if (CompareMem (NewBmmData->DriverOptionOrder, OldBmmData->DriverOptionOrder, sizeof (NewBmmData->DriverOptionOrder)) != 0) { \r
396 Status = Var_UpdateDriverOrder (Private);\r
397 } \r
398\r
399 //\r
400 // After user do the save action, need to update OldBmmData.\r
401 //\r
402 CopyMem (OldBmmData, NewBmmData, sizeof (BMM_FAKE_NV_DATA));\r
403\r
404 return EFI_SUCCESS;\r
405}\r
406\r
407/**\r
408 This function processes the results of changes in configuration.\r
409\r
410\r
411 @param This Points to the EFI_HII_CONFIG_ACCESS_PROTOCOL.\r
412 @param Action Specifies the type of action taken by the browser.\r
413 @param QuestionId A unique value which is sent to the original exporting driver\r
414 so that it can identify the type of data to expect.\r
415 @param Type The type of value for the question.\r
416 @param Value A pointer to the data being sent to the original exporting driver.\r
417 @param ActionRequest On return, points to the action requested by the callback function.\r
418\r
419 @retval EFI_SUCCESS The callback successfully handled the action.\r
420 @retval EFI_OUT_OF_RESOURCES Not enough storage is available to hold the variable and its data.\r
421 @retval EFI_DEVICE_ERROR The variable could not be saved.\r
422 @retval EFI_UNSUPPORTED The specified Action is not supported by the callback.\r
423 @retval EFI_INVALID_PARAMETER The parameter of Value or ActionRequest is invalid.\r
424**/\r
425EFI_STATUS\r
426EFIAPI\r
427BootMaintCallback (\r
428 IN CONST EFI_HII_CONFIG_ACCESS_PROTOCOL *This,\r
429 IN EFI_BROWSER_ACTION Action,\r
430 IN EFI_QUESTION_ID QuestionId,\r
431 IN UINT8 Type,\r
432 IN EFI_IFR_TYPE_VALUE *Value,\r
433 OUT EFI_BROWSER_ACTION_REQUEST *ActionRequest\r
434 )\r
435{\r
436 BMM_CALLBACK_DATA *Private;\r
437 BM_MENU_ENTRY *NewMenuEntry;\r
438 BMM_FAKE_NV_DATA *CurrentFakeNVMap;\r
439 EFI_STATUS Status;\r
440 UINTN OldValue;\r
441 UINTN NewValue;\r
442 UINTN Number;\r
443 UINTN Index;\r
444\r
445 //\r
446 //Chech whether exit from FileExplorer and reenter BM,if yes,reclaim string depositories\r
447 //\r
448 if (Action == EFI_BROWSER_ACTION_FORM_OPEN){\r
449 if(mEnterFileExplorer ){\r
450 ReclaimStringDepository();\r
451 mEnterFileExplorer = FALSE;\r
452 }\r
453 }\r
454\r
455 if (Action != EFI_BROWSER_ACTION_CHANGING && Action != EFI_BROWSER_ACTION_CHANGED) {\r
456 //\r
457 // Do nothing for other UEFI Action. Only do call back when data is changed.\r
458 //\r
459 return EFI_UNSUPPORTED;\r
460 }\r
461\r
462 OldValue = 0;\r
463 NewValue = 0;\r
464 Number = 0;\r
465\r
466 Private = BMM_CALLBACK_DATA_FROM_THIS (This);\r
467\r
468 //\r
469 // Retrive uncommitted data from Form Browser\r
470 //\r
471 CurrentFakeNVMap = &Private->BmmFakeNvData;\r
472 HiiGetBrowserData (&mBootMaintGuid, mBootMaintStorageName, sizeof (BMM_FAKE_NV_DATA), (UINT8 *) CurrentFakeNVMap);\r
473\r
474 if (Action == EFI_BROWSER_ACTION_CHANGING) {\r
475 if (Value == NULL) {\r
476 return EFI_INVALID_PARAMETER;\r
477 }\r
478 \r
479 UpdatePageId (Private, QuestionId);\r
480\r
481 if (QuestionId < FILE_OPTION_OFFSET) {\r
482 if (QuestionId < CONFIG_OPTION_OFFSET) {\r
483 switch (QuestionId) {\r
484 case FORM_BOOT_ADD_ID:\r
485 // Leave Bm and enter FileExplorer.\r
486 Private->FeCurrentState = FileExplorerStateAddBootOption;\r
487 Private->FeDisplayContext = FileExplorerDisplayUnknown;\r
488 ReclaimStringDepository (); \r
489 UpdateFileExplorer(Private, 0);\r
490 mEnterFileExplorer = TRUE;\r
491 break;\r
492\r
493 case FORM_DRV_ADD_FILE_ID:\r
494 // Leave Bm and enter FileExplorer.\r
495 Private->FeCurrentState = FileExplorerStateAddDriverOptionState;\r
496 Private->FeDisplayContext = FileExplorerDisplayUnknown;\r
497 ReclaimStringDepository ();\r
498 UpdateFileExplorer(Private, 0);\r
499 mEnterFileExplorer = TRUE;\r
500 break;\r
501\r
502 case FORM_DRV_ADD_HANDLE_ID:\r
503 CleanUpPage (FORM_DRV_ADD_HANDLE_ID, Private);\r
504 UpdateDrvAddHandlePage (Private);\r
505 break;\r
506\r
507 case FORM_BOOT_DEL_ID:\r
508 CleanUpPage (FORM_BOOT_DEL_ID, Private);\r
509 UpdateBootDelPage (Private);\r
510 break;\r
511\r
512 case FORM_BOOT_CHG_ID:\r
513 case FORM_DRV_CHG_ID:\r
514 UpdatePageBody (QuestionId, Private);\r
515 break;\r
516\r
517 case FORM_DRV_DEL_ID:\r
518 CleanUpPage (FORM_DRV_DEL_ID, Private);\r
519 UpdateDrvDelPage (Private);\r
520 break;\r
521\r
522 case FORM_BOOT_NEXT_ID:\r
523 CleanUpPage (FORM_BOOT_NEXT_ID, Private);\r
524 UpdateBootNextPage (Private);\r
525 break;\r
526\r
527 case FORM_TIME_OUT_ID:\r
528 CleanUpPage (FORM_TIME_OUT_ID, Private);\r
529 UpdateTimeOutPage (Private);\r
530 break;\r
531\r
532 case FORM_CON_IN_ID:\r
533 case FORM_CON_OUT_ID:\r
534 case FORM_CON_ERR_ID:\r
535 UpdatePageBody (QuestionId, Private);\r
536 break;\r
537\r
538 case FORM_CON_MODE_ID:\r
539 CleanUpPage (FORM_CON_MODE_ID, Private);\r
540 UpdateConModePage (Private);\r
541 break;\r
542\r
543 case FORM_CON_COM_ID:\r
544 CleanUpPage (FORM_CON_COM_ID, Private);\r
545 UpdateConCOMPage (Private);\r
546 break;\r
547\r
548 default:\r
549 break;\r
550 }\r
551 } else if ((QuestionId >= TERMINAL_OPTION_OFFSET) && (QuestionId < CONSOLE_OPTION_OFFSET)) {\r
552 Index = (UINT16) (QuestionId - TERMINAL_OPTION_OFFSET);\r
553 Private->CurrentTerminal = Index;\r
554\r
555 CleanUpPage (FORM_CON_COM_SETUP_ID, Private);\r
556 UpdateTerminalPage (Private);\r
557\r
558 } else if (QuestionId >= HANDLE_OPTION_OFFSET) {\r
559 Index = (UINT16) (QuestionId - HANDLE_OPTION_OFFSET);\r
560\r
561 NewMenuEntry = BOpt_GetMenuEntry (&DriverMenu, Index);\r
562 ASSERT (NewMenuEntry != NULL);\r
563 Private->HandleContext = (BM_HANDLE_CONTEXT *) NewMenuEntry->VariableContext;\r
564\r
565 CleanUpPage (FORM_DRV_ADD_HANDLE_DESC_ID, Private);\r
566\r
567 Private->MenuEntry = NewMenuEntry;\r
568 Private->LoadContext->FilePathList = Private->HandleContext->DevicePath;\r
569\r
570 UpdateDriverAddHandleDescPage (Private);\r
571 }\r
572 }\r
573 if (QuestionId == KEY_VALUE_BOOT_FROM_FILE){\r
574 // Leave Bm and enter FileExplorer.\r
575 Private->FeCurrentState = FileExplorerStateBootFromFile;\r
576 Private->FeDisplayContext = FileExplorerDisplayUnknown;\r
577 ReclaimStringDepository ();\r
578 UpdateFileExplorer(Private, 0);\r
579 mEnterFileExplorer = TRUE;\r
580 }\r
581 } else if (Action == EFI_BROWSER_ACTION_CHANGED) {\r
582 if ((Value == NULL) || (ActionRequest == NULL)) {\r
583 return EFI_INVALID_PARAMETER;\r
584 }\r
585\r
586 switch (QuestionId) {\r
587 case KEY_VALUE_SAVE_AND_EXIT:\r
588 case KEY_VALUE_NO_SAVE_AND_EXIT:\r
589 if (QuestionId == KEY_VALUE_SAVE_AND_EXIT) {\r
590 Status = ApplyChangeHandler (Private, CurrentFakeNVMap, Private->BmmPreviousPageId);\r
591 if (EFI_ERROR (Status)) {\r
592 return Status;\r
593 }\r
594 } else if (QuestionId == KEY_VALUE_NO_SAVE_AND_EXIT) {\r
595 DiscardChangeHandler (Private, CurrentFakeNVMap);\r
596 }\r
597\r
598 //\r
599 // Tell browser not to ask for confirmation of changes,\r
600 // since we have already applied or discarded.\r
601 //\r
602 *ActionRequest = EFI_BROWSER_ACTION_REQUEST_FORM_SUBMIT_EXIT;\r
603\r
604 break;\r
00db1dfc
ED
605 \r
606 case FORM_RESET:\r
607 gRT->ResetSystem (EfiResetCold, EFI_SUCCESS, 0, NULL);\r
608 return EFI_UNSUPPORTED;\r
143f0b1d
ED
609\r
610 default:\r
611 break;\r
612 }\r
613 }\r
614\r
615 //\r
616 // Pass changed uncommitted data back to Form Browser\r
617 //\r
618 HiiSetBrowserData (&mBootMaintGuid, mBootMaintStorageName, sizeof (BMM_FAKE_NV_DATA), (UINT8 *) CurrentFakeNVMap, NULL);\r
619\r
620 return EFI_SUCCESS;\r
621}\r
622\r
623/**\r
624 Function handling request to apply changes for BMM pages.\r
625\r
626 @param Private Pointer to callback data buffer.\r
627 @param CurrentFakeNVMap Pointer to buffer holding data of various values used by BMM\r
628 @param FormId ID of the form which has sent the request to apply change.\r
629\r
630 @retval EFI_SUCCESS Change successfully applied.\r
631 @retval Other Error occurs while trying to apply changes.\r
632\r
633**/\r
634EFI_STATUS\r
635ApplyChangeHandler (\r
636 IN BMM_CALLBACK_DATA *Private,\r
637 IN BMM_FAKE_NV_DATA *CurrentFakeNVMap,\r
638 IN EFI_FORM_ID FormId\r
639 )\r
640{\r
641 BM_CONSOLE_CONTEXT *NewConsoleContext;\r
642 BM_TERMINAL_CONTEXT *NewTerminalContext;\r
643 BM_LOAD_CONTEXT *NewLoadContext;\r
644 BM_MENU_ENTRY *NewMenuEntry;\r
645 EFI_STATUS Status;\r
646 UINT16 Index;\r
647\r
648 Status = EFI_SUCCESS;\r
649\r
650 switch (FormId) {\r
651 case FORM_BOOT_DEL_ID:\r
652 for (Index = 0; \r
653 ((Index < BootOptionMenu.MenuNumber) && (Index < (sizeof (CurrentFakeNVMap->BootOptionDel) / sizeof (CurrentFakeNVMap->BootOptionDel[0])))); \r
654 Index ++) {\r
655 NewMenuEntry = BOpt_GetMenuEntry (&BootOptionMenu, Index);\r
656 NewLoadContext = (BM_LOAD_CONTEXT *) NewMenuEntry->VariableContext;\r
657 NewLoadContext->Deleted = CurrentFakeNVMap->BootOptionDel[Index];\r
658 CurrentFakeNVMap->BootOptionDel[Index] = FALSE;\r
659 }\r
660\r
661 Var_DelBootOption ();\r
662 break;\r
663\r
664 case FORM_DRV_DEL_ID:\r
665 for (Index = 0; \r
666 ((Index < DriverOptionMenu.MenuNumber) && (Index < (sizeof (CurrentFakeNVMap->DriverOptionDel) / sizeof (CurrentFakeNVMap->DriverOptionDel[0])))); \r
667 Index++) {\r
668 NewMenuEntry = BOpt_GetMenuEntry (&DriverOptionMenu, Index);\r
669 NewLoadContext = (BM_LOAD_CONTEXT *) NewMenuEntry->VariableContext;\r
670 NewLoadContext->Deleted = CurrentFakeNVMap->DriverOptionDel[Index];\r
671 CurrentFakeNVMap->DriverOptionDel[Index] = FALSE;\r
672 }\r
673\r
674 Var_DelDriverOption ();\r
675 break;\r
676\r
677 case FORM_BOOT_CHG_ID:\r
678 Status = Var_UpdateBootOrder (Private);\r
679 break;\r
680\r
681 case FORM_DRV_CHG_ID:\r
682 Status = Var_UpdateDriverOrder (Private);\r
683 break;\r
684\r
685 case FORM_TIME_OUT_ID:\r
686 Status = gRT->SetVariable (\r
687 L"Timeout",\r
688 &gEfiGlobalVariableGuid,\r
689 EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_RUNTIME_ACCESS | EFI_VARIABLE_NON_VOLATILE,\r
690 sizeof (UINT16),\r
691 &(CurrentFakeNVMap->BootTimeOut)\r
692 );\r
693 ASSERT_EFI_ERROR(Status);\r
694\r
695 Private->BmmOldFakeNVData.BootTimeOut = CurrentFakeNVMap->BootTimeOut;\r
696 break;\r
697\r
698 case FORM_BOOT_NEXT_ID:\r
699 Status = Var_UpdateBootNext (Private);\r
700 break;\r
701\r
702 case FORM_CON_MODE_ID:\r
703 Status = Var_UpdateConMode (Private);\r
704 break;\r
705\r
706 case FORM_CON_COM_SETUP_ID:\r
707 NewMenuEntry = BOpt_GetMenuEntry (&TerminalMenu, Private->CurrentTerminal);\r
708\r
709 ASSERT (NewMenuEntry != NULL);\r
710\r
711 NewTerminalContext = (BM_TERMINAL_CONTEXT *) NewMenuEntry->VariableContext;\r
712\r
713 NewTerminalContext->BaudRateIndex = CurrentFakeNVMap->COMBaudRate;\r
714 ASSERT (CurrentFakeNVMap->COMBaudRate < (sizeof (BaudRateList) / sizeof (BaudRateList[0])));\r
715 NewTerminalContext->BaudRate = BaudRateList[CurrentFakeNVMap->COMBaudRate].Value;\r
716 NewTerminalContext->DataBitsIndex = CurrentFakeNVMap->COMDataRate;\r
717 ASSERT (CurrentFakeNVMap->COMDataRate < (sizeof (DataBitsList) / sizeof (DataBitsList[0])));\r
718 NewTerminalContext->DataBits = (UINT8) DataBitsList[CurrentFakeNVMap->COMDataRate].Value;\r
719 NewTerminalContext->StopBitsIndex = CurrentFakeNVMap->COMStopBits;\r
720 ASSERT (CurrentFakeNVMap->COMStopBits < (sizeof (StopBitsList) / sizeof (StopBitsList[0])));\r
721 NewTerminalContext->StopBits = (UINT8) StopBitsList[CurrentFakeNVMap->COMStopBits].Value;\r
722 NewTerminalContext->ParityIndex = CurrentFakeNVMap->COMParity;\r
723 ASSERT (CurrentFakeNVMap->COMParity < (sizeof (ParityList) / sizeof (ParityList[0])));\r
724 NewTerminalContext->Parity = (UINT8) ParityList[CurrentFakeNVMap->COMParity].Value;\r
725 NewTerminalContext->TerminalType = CurrentFakeNVMap->COMTerminalType;\r
726\r
727 ChangeTerminalDevicePath (\r
728 NewTerminalContext->DevicePath,\r
729 FALSE\r
730 );\r
731\r
732 Var_UpdateConsoleInpOption ();\r
733 Var_UpdateConsoleOutOption ();\r
734 Var_UpdateErrorOutOption ();\r
735 break;\r
736\r
737 case FORM_CON_IN_ID:\r
738 for (Index = 0; Index < ConsoleInpMenu.MenuNumber; Index++) {\r
739 NewMenuEntry = BOpt_GetMenuEntry (&ConsoleInpMenu, Index);\r
740 NewConsoleContext = (BM_CONSOLE_CONTEXT *) NewMenuEntry->VariableContext;\r
741 ASSERT (Index < MAX_MENU_NUMBER);\r
742 NewConsoleContext->IsActive = CurrentFakeNVMap->ConsoleCheck[Index];\r
743 }\r
744\r
745 for (Index = 0; Index < TerminalMenu.MenuNumber; Index++) {\r
746 NewMenuEntry = BOpt_GetMenuEntry (&TerminalMenu, Index);\r
747 NewTerminalContext = (BM_TERMINAL_CONTEXT *) NewMenuEntry->VariableContext;\r
748 ASSERT (Index + ConsoleInpMenu.MenuNumber < MAX_MENU_NUMBER);\r
749 NewTerminalContext->IsConIn = CurrentFakeNVMap->ConsoleCheck[Index + ConsoleInpMenu.MenuNumber];\r
750 }\r
751\r
752 Var_UpdateConsoleInpOption ();\r
753 break;\r
754\r
755 case FORM_CON_OUT_ID:\r
756 for (Index = 0; Index < ConsoleOutMenu.MenuNumber; Index++) {\r
757 NewMenuEntry = BOpt_GetMenuEntry (&ConsoleOutMenu, Index);\r
758 NewConsoleContext = (BM_CONSOLE_CONTEXT *) NewMenuEntry->VariableContext;\r
759 ASSERT (Index < MAX_MENU_NUMBER);\r
760 NewConsoleContext->IsActive = CurrentFakeNVMap->ConsoleCheck[Index];\r
761 }\r
762\r
763 for (Index = 0; Index < TerminalMenu.MenuNumber; Index++) {\r
764 NewMenuEntry = BOpt_GetMenuEntry (&TerminalMenu, Index);\r
765 NewTerminalContext = (BM_TERMINAL_CONTEXT *) NewMenuEntry->VariableContext;\r
766 ASSERT (Index + ConsoleOutMenu.MenuNumber < MAX_MENU_NUMBER);\r
767 NewTerminalContext->IsConOut = CurrentFakeNVMap->ConsoleCheck[Index + ConsoleOutMenu.MenuNumber];\r
768 }\r
769\r
770 Var_UpdateConsoleOutOption ();\r
771 break;\r
772\r
773 case FORM_CON_ERR_ID:\r
774 for (Index = 0; Index < ConsoleErrMenu.MenuNumber; Index++) {\r
775 NewMenuEntry = BOpt_GetMenuEntry (&ConsoleErrMenu, Index);\r
776 NewConsoleContext = (BM_CONSOLE_CONTEXT *) NewMenuEntry->VariableContext;\r
777 ASSERT (Index < MAX_MENU_NUMBER);\r
778 NewConsoleContext->IsActive = CurrentFakeNVMap->ConsoleCheck[Index];\r
779 }\r
780\r
781 for (Index = 0; Index < TerminalMenu.MenuNumber; Index++) {\r
782 NewMenuEntry = BOpt_GetMenuEntry (&TerminalMenu, Index);\r
783 NewTerminalContext = (BM_TERMINAL_CONTEXT *) NewMenuEntry->VariableContext;\r
784 ASSERT (Index + ConsoleErrMenu.MenuNumber < MAX_MENU_NUMBER);\r
785 NewTerminalContext->IsStdErr = CurrentFakeNVMap->ConsoleCheck[Index + ConsoleErrMenu.MenuNumber];\r
786 }\r
787\r
788 Var_UpdateErrorOutOption ();\r
789 break;\r
790\r
791 case FORM_DRV_ADD_HANDLE_DESC_ID:\r
792 Status = Var_UpdateDriverOption (\r
793 Private,\r
794 Private->BmmHiiHandle,\r
795 CurrentFakeNVMap->DriverAddHandleDesc,\r
796 CurrentFakeNVMap->DriverAddHandleOptionalData,\r
797 CurrentFakeNVMap->DriverAddForceReconnect\r
798 );\r
799 if (EFI_ERROR (Status)) {\r
800 goto Error;\r
801 }\r
802\r
803 BOpt_GetDriverOptions (Private);\r
804 CreateMenuStringToken (Private, Private->BmmHiiHandle, &DriverOptionMenu);\r
805 break;\r
806\r
807 default:\r
808 break;\r
809 }\r
810\r
811Error:\r
812 return Status;\r
813}\r
814\r
815/**\r
816 Discard all changes done to the BMM pages such as Boot Order change,\r
817 Driver order change.\r
818\r
819 @param Private The BMM context data.\r
820 @param CurrentFakeNVMap The current Fack NV Map.\r
821\r
822**/\r
823VOID\r
824DiscardChangeHandler (\r
825 IN BMM_CALLBACK_DATA *Private,\r
826 IN BMM_FAKE_NV_DATA *CurrentFakeNVMap\r
827 )\r
828{\r
829 UINT16 Index;\r
830\r
831 switch (Private->BmmPreviousPageId) {\r
832 case FORM_BOOT_CHG_ID:\r
833 CopyMem (CurrentFakeNVMap->BootOptionOrder, Private->BmmOldFakeNVData.BootOptionOrder, sizeof (CurrentFakeNVMap->BootOptionOrder));\r
834 break;\r
835 \r
836 case FORM_DRV_CHG_ID:\r
837 CopyMem (CurrentFakeNVMap->DriverOptionOrder, Private->BmmOldFakeNVData.DriverOptionOrder, sizeof (CurrentFakeNVMap->DriverOptionOrder));\r
838 break;\r
839\r
840 case FORM_BOOT_DEL_ID:\r
841 ASSERT (BootOptionMenu.MenuNumber <= (sizeof (CurrentFakeNVMap->BootOptionDel) / sizeof (CurrentFakeNVMap->BootOptionDel[0])));\r
842 for (Index = 0; Index < BootOptionMenu.MenuNumber; Index++) {\r
843 CurrentFakeNVMap->BootOptionDel[Index] = FALSE;\r
844 }\r
845 break;\r
846\r
847 case FORM_DRV_DEL_ID:\r
848 ASSERT (DriverOptionMenu.MenuNumber <= (sizeof (CurrentFakeNVMap->DriverOptionDel) / sizeof (CurrentFakeNVMap->DriverOptionDel[0])));\r
849 for (Index = 0; Index < DriverOptionMenu.MenuNumber; Index++) {\r
850 CurrentFakeNVMap->DriverOptionDel[Index] = FALSE;\r
851 }\r
852 break;\r
853\r
854 case FORM_BOOT_NEXT_ID:\r
855 CurrentFakeNVMap->BootNext = Private->BmmOldFakeNVData.BootNext;\r
856 break;\r
857\r
858 case FORM_TIME_OUT_ID:\r
859 CurrentFakeNVMap->BootTimeOut = Private->BmmOldFakeNVData.BootTimeOut;\r
860 break;\r
861\r
862 case FORM_DRV_ADD_HANDLE_DESC_ID:\r
863 case FORM_DRV_ADD_FILE_ID:\r
864 case FORM_DRV_ADD_HANDLE_ID:\r
865 CurrentFakeNVMap->DriverAddHandleDesc[0] = 0x0000;\r
866 CurrentFakeNVMap->DriverAddHandleOptionalData[0] = 0x0000;\r
867 break;\r
868\r
869 default:\r
870 break;\r
871 }\r
872}\r
873\r
874\r
875/**\r
876 Create dynamic code for BMM.\r
877\r
878 @param BmmCallbackInfo The BMM context data.\r
879\r
880**/\r
881VOID\r
882InitializeDrivers(\r
883 IN BMM_CALLBACK_DATA *BmmCallbackInfo\r
884 )\r
885{\r
886 EFI_HII_HANDLE HiiHandle;\r
887 VOID *StartOpCodeHandle;\r
888 VOID *EndOpCodeHandle;\r
889 EFI_IFR_GUID_LABEL *StartLabel;\r
890 EFI_IFR_GUID_LABEL *EndLabel;\r
891 UINTN Index; \r
892 EFI_STRING_ID FormSetTitle;\r
893 EFI_STRING_ID FormSetHelp; \r
894 EFI_STRING String;\r
895 EFI_STRING_ID Token;\r
896 EFI_STRING_ID TokenHelp; \r
897 EFI_HII_HANDLE *HiiHandles;\r
898 UINTN SkipCount;\r
899 EFI_GUID FormSetGuid;\r
900 CHAR16 *DevicePathStr;\r
901 EFI_STRING_ID DevicePathId;\r
902\r
903 HiiHandle = BmmCallbackInfo->BmmHiiHandle;\r
904 //\r
905 // Allocate space for creation of UpdateData Buffer\r
906 //\r
907 StartOpCodeHandle = HiiAllocateOpCodeHandle ();\r
908 ASSERT (StartOpCodeHandle != NULL);\r
909\r
910 EndOpCodeHandle = HiiAllocateOpCodeHandle ();\r
911 ASSERT (EndOpCodeHandle != NULL);\r
912\r
913 //\r
914 // Create Hii Extend Label OpCode as the start opcode\r
915 //\r
916 StartLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (StartOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL));\r
917 StartLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL;\r
918 StartLabel->Number = LABEL_BMM_PLATFORM_INFORMATION;\r
919\r
920 //\r
921 // Create Hii Extend Label OpCode as the end opcode\r
922 //\r
923 EndLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (EndOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL));\r
924 EndLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL;\r
925 EndLabel->Number = LABEL_END;\r
926\r
927 //\r
928 // Get all the Hii handles\r
929 //\r
930 HiiHandles = HiiGetHiiHandles (NULL);\r
931 ASSERT (HiiHandles != NULL);\r
932\r
933 //\r
934 // Search for formset of each class type\r
935 //\r
936 SkipCount = 0;\r
937 for (Index = 0; HiiHandles[Index] != NULL; Index++) {\r
938 if (!ExtractDisplayedHiiFormFromHiiHandle (HiiHandles[Index], &gEfiIfrBootMaintenanceGuid, SkipCount, &FormSetTitle, &FormSetHelp, &FormSetGuid)) {\r
939 SkipCount = 0;\r
940 continue;\r
941 }\r
942 String = HiiGetString (HiiHandles[Index], FormSetTitle, NULL);\r
943 if (String == NULL) {\r
944 String = HiiGetString (HiiHandle, STR_MISSING_STRING, NULL);\r
945 ASSERT (String != NULL);\r
946 }\r
947 Token = HiiSetString (HiiHandle, 0, String, NULL);\r
948 FreePool (String);\r
949\r
950 String = HiiGetString (HiiHandles[Index], FormSetHelp, NULL);\r
951 if (String == NULL) {\r
952 String = HiiGetString (HiiHandle, STR_MISSING_STRING, NULL);\r
953 ASSERT (String != NULL);\r
954 }\r
955 TokenHelp = HiiSetString (HiiHandle, 0, String, NULL);\r
956 FreePool (String);\r
957\r
958 DevicePathStr = ExtractDevicePathFromHiiHandle(HiiHandles[Index]);\r
959 DevicePathId = 0;\r
960 if (DevicePathStr != NULL){\r
961 DevicePathId = HiiSetString (HiiHandle, 0, DevicePathStr, NULL);\r
962 FreePool (DevicePathStr);\r
963 }\r
964\r
965 HiiCreateGotoExOpCode (\r
966 StartOpCodeHandle,\r
967 0,\r
968 Token,\r
969 TokenHelp,\r
970 0,\r
971 (EFI_QUESTION_ID) (Index + FRONT_PAGE_KEY_OFFSET),\r
972 0,\r
973 &FormSetGuid,\r
974 DevicePathId\r
975 );\r
976 //\r
977 //One packagelist may has more than one form package,\r
978 //Index-- means keep current HiiHandle and still extract from the packagelist, \r
979 //SkipCount++ means skip the formset which was found before in the same form package. \r
980 //\r
981 SkipCount++;\r
982 Index--;\r
983 }\r
984\r
985 HiiUpdateForm (\r
986 HiiHandle,\r
987 &mBootMaintGuid,\r
988 FORM_MAIN_ID,\r
989 StartOpCodeHandle,\r
990 EndOpCodeHandle\r
991 );\r
992\r
993 HiiFreeOpCodeHandle (StartOpCodeHandle);\r
994 HiiFreeOpCodeHandle (EndOpCodeHandle); \r
995 FreePool (HiiHandles);\r
996}\r
997\r
998\r
999/**\r
1000 Create dynamic code for BMM.\r
1001\r
1002 @param BmmCallbackInfo The BMM context data.\r
1003\r
1004**/\r
1005VOID\r
1006InitializeBmmConfig(\r
1007 IN BMM_CALLBACK_DATA *BmmCallbackInfo\r
1008 )\r
1009{\r
1010 UpdateBootDelPage (BmmCallbackInfo);\r
1011 UpdateDrvDelPage (BmmCallbackInfo);\r
1012\r
1013 if (TerminalMenu.MenuNumber > 0) {\r
1014 BmmCallbackInfo->CurrentTerminal = 0;\r
1015 UpdateTerminalPage (BmmCallbackInfo);\r
1016 }\r
1017\r
1018 InitializeDrivers (BmmCallbackInfo);\r
1019}\r
1020\r
1021/**\r
1022 Initialize the Boot Maintenance Utitliy.\r
1023\r
1024**/\r
1025VOID\r
1026InitializeBM (\r
1027 VOID\r
1028 )\r
1029{\r
1030 BMM_CALLBACK_DATA *BmmCallbackInfo;\r
1031\r
1032 BmmCallbackInfo = mBmmCallbackInfo;\r
1033 BmmCallbackInfo->BmmPreviousPageId = FORM_MAIN_ID;\r
1034 BmmCallbackInfo->BmmCurrentPageId = FORM_MAIN_ID;\r
1035 BmmCallbackInfo->FeCurrentState = FileExplorerStateInActive;\r
1036 BmmCallbackInfo->FeDisplayContext = FileExplorerDisplayUnknown;\r
1037\r
1038 InitAllMenu (BmmCallbackInfo);\r
1039\r
1040 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &ConsoleInpMenu);\r
1041 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &ConsoleOutMenu);\r
1042 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &ConsoleErrMenu);\r
1043 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &BootOptionMenu);\r
1044 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &DriverOptionMenu);\r
1045 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &TerminalMenu);\r
1046 CreateMenuStringToken (BmmCallbackInfo, BmmCallbackInfo->BmmHiiHandle, &DriverMenu);\r
1047\r
1048 InitializeBmmConfig(BmmCallbackInfo);\r
1049}\r
1050\r
1051/**\r
1052 Initialized all Menu Option List.\r
1053\r
1054 @param CallbackData The BMM context data.\r
1055\r
1056**/\r
1057VOID\r
1058InitAllMenu (\r
1059 IN BMM_CALLBACK_DATA *CallbackData\r
1060 )\r
1061{\r
1062 InitializeListHead (&BootOptionMenu.Head);\r
1063 InitializeListHead (&DriverOptionMenu.Head);\r
1064 BOpt_GetBootOptions (CallbackData);\r
1065 BOpt_GetDriverOptions (CallbackData);\r
1066 InitializeListHead (&FsOptionMenu.Head);\r
1067 BOpt_FindDrivers ();\r
1068 InitializeListHead (&DirectoryMenu.Head);\r
1069 InitializeListHead (&ConsoleInpMenu.Head);\r
1070 InitializeListHead (&ConsoleOutMenu.Head);\r
1071 InitializeListHead (&ConsoleErrMenu.Head);\r
1072 InitializeListHead (&TerminalMenu.Head);\r
1073 LocateSerialIo ();\r
1074 GetAllConsoles ();\r
1075 mAllMenuInit = TRUE;\r
1076}\r
1077\r
1078/**\r
1079 Free up all Menu Option list.\r
1080\r
1081**/\r
1082VOID\r
1083FreeAllMenu (\r
1084 VOID\r
1085 )\r
1086{\r
1087 if (!mAllMenuInit){\r
1088 return;\r
1089 }\r
1090 BOpt_FreeMenu (&DirectoryMenu);\r
1091 BOpt_FreeMenu (&FsOptionMenu);\r
1092 BOpt_FreeMenu (&BootOptionMenu);\r
1093 BOpt_FreeMenu (&DriverOptionMenu);\r
1094 BOpt_FreeMenu (&DriverMenu);\r
1095 FreeAllConsoles ();\r
1096 mAllMenuInit = FALSE;\r
1097}\r
1098\r
1099/**\r
1100 Initialize all the string depositories.\r
1101\r
1102**/\r
1103VOID\r
1104InitializeStringDepository (\r
1105 VOID\r
1106 )\r
1107{\r
1108 STRING_DEPOSITORY *StringDepository;\r
1109 StringDepository = AllocateZeroPool (sizeof (STRING_DEPOSITORY) * STRING_DEPOSITORY_NUMBER);\r
1110 FileOptionStrDepository = StringDepository++;\r
1111 ConsoleOptionStrDepository = StringDepository++;\r
1112 BootOptionStrDepository = StringDepository++;\r
1113 BootOptionHelpStrDepository = StringDepository++;\r
1114 DriverOptionStrDepository = StringDepository++;\r
1115 DriverOptionHelpStrDepository = StringDepository++;\r
1116 TerminalStrDepository = StringDepository;\r
1117}\r
1118\r
1119/**\r
1120 Fetch a usable string node from the string depository and return the string token.\r
1121\r
1122 @param CallbackData The BMM context data.\r
1123 @param StringDepository The string repository.\r
1124\r
1125 @retval EFI_STRING_ID String token.\r
1126\r
1127**/\r
1128EFI_STRING_ID\r
1129GetStringTokenFromDepository (\r
1130 IN BMM_CALLBACK_DATA *CallbackData,\r
1131 IN STRING_DEPOSITORY *StringDepository\r
1132 )\r
1133{\r
1134 STRING_LIST_NODE *CurrentListNode;\r
1135 STRING_LIST_NODE *NextListNode;\r
1136\r
1137 CurrentListNode = StringDepository->CurrentNode;\r
1138\r
1139 if ((NULL != CurrentListNode) && (NULL != CurrentListNode->Next)) {\r
1140 //\r
1141 // Fetch one reclaimed node from the list.\r
1142 //\r
1143 NextListNode = StringDepository->CurrentNode->Next;\r
1144 } else {\r
1145 //\r
1146 // If there is no usable node in the list, update the list.\r
1147 //\r
1148 NextListNode = AllocateZeroPool (sizeof (STRING_LIST_NODE));\r
1149 ASSERT (NextListNode != NULL);\r
1150 NextListNode->StringToken = HiiSetString (CallbackData->BmmHiiHandle, 0, L" ", NULL);\r
1151 ASSERT (NextListNode->StringToken != 0);\r
1152\r
1153 StringDepository->TotalNodeNumber++;\r
1154\r
1155 if (NULL == CurrentListNode) {\r
1156 StringDepository->ListHead = NextListNode;\r
1157 } else {\r
1158 CurrentListNode->Next = NextListNode;\r
1159 }\r
1160 }\r
1161\r
1162 StringDepository->CurrentNode = NextListNode;\r
1163\r
1164 return StringDepository->CurrentNode->StringToken;\r
1165}\r
1166\r
1167/**\r
1168 Reclaim string depositories by moving the current node pointer to list head..\r
1169\r
1170**/\r
1171VOID\r
1172ReclaimStringDepository (\r
1173 VOID\r
1174 )\r
1175{\r
1176 UINTN DepositoryIndex;\r
1177 STRING_DEPOSITORY *StringDepository;\r
1178\r
1179 StringDepository = FileOptionStrDepository;\r
1180 for (DepositoryIndex = 0; DepositoryIndex < STRING_DEPOSITORY_NUMBER; DepositoryIndex++) {\r
1181 StringDepository->CurrentNode = StringDepository->ListHead;\r
1182 StringDepository++;\r
1183 }\r
1184}\r
1185\r
1186/**\r
1187 Release resource for all the string depositories.\r
1188\r
1189**/\r
1190VOID\r
1191CleanUpStringDepository (\r
1192 VOID\r
1193 )\r
1194{\r
1195 UINTN NodeIndex;\r
1196 UINTN DepositoryIndex;\r
1197 STRING_LIST_NODE *CurrentListNode;\r
1198 STRING_LIST_NODE *NextListNode;\r
1199 STRING_DEPOSITORY *StringDepository;\r
1200\r
1201 //\r
1202 // Release string list nodes.\r
1203 //\r
1204 StringDepository = FileOptionStrDepository;\r
1205 for (DepositoryIndex = 0; DepositoryIndex < STRING_DEPOSITORY_NUMBER; DepositoryIndex++) {\r
1206 CurrentListNode = StringDepository->ListHead;\r
1207 for (NodeIndex = 0; NodeIndex < StringDepository->TotalNodeNumber; NodeIndex++) {\r
1208 NextListNode = CurrentListNode->Next;\r
1209 FreePool (CurrentListNode);\r
1210 CurrentListNode = NextListNode;\r
1211 }\r
1212\r
1213 StringDepository++;\r
1214 }\r
1215 //\r
1216 // Release string depository.\r
1217 //\r
1218 FreePool (FileOptionStrDepository);\r
1219}\r
1220\r
1221/**\r
1222 Install BootMaint and FileExplorer HiiPackages.\r
1223\r
1224**/\r
1225VOID\r
1226InitBootMaintenance(\r
1227 VOID\r
1228 )\r
1229{\r
1230 BMM_CALLBACK_DATA *BmmCallbackInfo;\r
1231 EFI_STATUS Status;\r
1232 UINT8 *Ptr;\r
1233\r
1234 Status = EFI_SUCCESS;\r
1235\r
1236 if (!gConnectAllHappened){\r
1237 EfiBootManagerConnectAll();\r
1238 gConnectAllHappened = TRUE;\r
1239 }\r
1240\r
1241 EfiBootManagerRefreshAllBootOption ();\r
1242\r
1243 //\r
1244 // Create CallbackData structures for Driver Callback\r
1245 //\r
1246 BmmCallbackInfo = AllocateZeroPool (sizeof (BMM_CALLBACK_DATA));\r
1247 ASSERT (BmmCallbackInfo != NULL);\r
1248\r
1249 //\r
1250 // Create LoadOption in BmmCallbackInfo for Driver Callback\r
1251 //\r
1252 Ptr = AllocateZeroPool (sizeof (BM_LOAD_CONTEXT) + sizeof (BM_FILE_CONTEXT) + sizeof (BM_HANDLE_CONTEXT) + sizeof (BM_MENU_ENTRY));\r
1253 ASSERT (Ptr != NULL);\r
1254\r
1255 //\r
1256 // Initialize Bmm callback data.\r
1257 //\r
1258 BmmCallbackInfo->LoadContext = (BM_LOAD_CONTEXT *) Ptr;\r
1259 Ptr += sizeof (BM_LOAD_CONTEXT);\r
1260\r
1261 BmmCallbackInfo->FileContext = (BM_FILE_CONTEXT *) Ptr;\r
1262 Ptr += sizeof (BM_FILE_CONTEXT);\r
1263\r
1264 BmmCallbackInfo->HandleContext = (BM_HANDLE_CONTEXT *) Ptr;\r
1265 Ptr += sizeof (BM_HANDLE_CONTEXT);\r
1266\r
1267 BmmCallbackInfo->MenuEntry = (BM_MENU_ENTRY *) Ptr;\r
1268\r
1269 BmmCallbackInfo->Signature = BMM_CALLBACK_DATA_SIGNATURE;\r
1270 BmmCallbackInfo->BmmConfigAccess.ExtractConfig = BootMaintExtractConfig;\r
1271 BmmCallbackInfo->BmmConfigAccess.RouteConfig = BootMaintRouteConfig;\r
1272 BmmCallbackInfo->BmmConfigAccess.Callback = BootMaintCallback;\r
1273 BmmCallbackInfo->BmmPreviousPageId = FORM_MAIN_ID;\r
1274 BmmCallbackInfo->BmmCurrentPageId = FORM_MAIN_ID;\r
1275 BmmCallbackInfo->FeConfigAccess.ExtractConfig = FakeExtractConfig;\r
1276 BmmCallbackInfo->FeConfigAccess.RouteConfig = FakeRouteConfig;\r
1277 BmmCallbackInfo->FeConfigAccess.Callback = FileExplorerCallback;\r
1278 BmmCallbackInfo->FeCurrentState = FileExplorerStateInActive;\r
1279 BmmCallbackInfo->FeDisplayContext = FileExplorerDisplayUnknown;\r
1280\r
1281 //\r
1282 // Install Device Path Protocol and Config Access protocol to driver handle\r
1283 //\r
1284 Status = gBS->InstallMultipleProtocolInterfaces (\r
1285 &BmmCallbackInfo->BmmDriverHandle,\r
1286 &gEfiDevicePathProtocolGuid,\r
1287 &mBmmHiiVendorDevicePath,\r
1288 &gEfiHiiConfigAccessProtocolGuid,\r
1289 &BmmCallbackInfo->BmmConfigAccess,\r
1290 NULL\r
1291 );\r
1292 ASSERT_EFI_ERROR (Status);\r
1293\r
1294 //\r
1295 // Install Device Path Protocol and Config Access protocol to driver handle\r
1296 //\r
1297 Status = gBS->InstallMultipleProtocolInterfaces (\r
1298 &BmmCallbackInfo->FeDriverHandle,\r
1299 &gEfiDevicePathProtocolGuid,\r
1300 &mFeHiiVendorDevicePath,\r
1301 &gEfiHiiConfigAccessProtocolGuid,\r
1302 &BmmCallbackInfo->FeConfigAccess,\r
1303 NULL\r
1304 );\r
1305 ASSERT_EFI_ERROR (Status);\r
1306\r
1307 //\r
1308 // Post our Boot Maint VFR binary to the HII database.\r
1309 //\r
1310 BmmCallbackInfo->BmmHiiHandle = HiiAddPackages (\r
1311 &mBootMaintGuid,\r
1312 BmmCallbackInfo->BmmDriverHandle,\r
1313 BmBin,\r
1314 UiAppStrings,\r
1315 NULL\r
1316 );\r
1317 ASSERT (BmmCallbackInfo->BmmHiiHandle != NULL);\r
1318\r
1319 //\r
1320 // Post our File Explorer VFR binary to the HII database.\r
1321 //\r
1322 BmmCallbackInfo->FeHiiHandle = HiiAddPackages (\r
1323 &mFileExplorerGuid,\r
1324 BmmCallbackInfo->FeDriverHandle,\r
1325 FEBin,\r
1326 UiAppStrings,\r
1327 NULL\r
1328 );\r
1329 ASSERT (BmmCallbackInfo->FeHiiHandle != NULL);\r
1330\r
1331 //\r
1332 // Init OpCode Handle and Allocate space for creation of Buffer\r
1333 //\r
1334 mStartOpCodeHandle = HiiAllocateOpCodeHandle ();\r
1335 ASSERT (mStartOpCodeHandle != NULL);\r
1336\r
1337 mEndOpCodeHandle = HiiAllocateOpCodeHandle ();\r
1338 ASSERT (mEndOpCodeHandle != NULL);\r
1339\r
1340 //\r
1341 // Create Hii Extend Label OpCode as the start opcode\r
1342 //\r
1343 mStartLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (mStartOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL));\r
1344 mStartLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL;\r
1345\r
1346 //\r
1347 // Create Hii Extend Label OpCode as the end opcode\r
1348 //\r
1349 mEndLabel = (EFI_IFR_GUID_LABEL *) HiiCreateGuidOpCode (mEndOpCodeHandle, &gEfiIfrTianoGuid, NULL, sizeof (EFI_IFR_GUID_LABEL));\r
1350 mEndLabel->ExtendOpCode = EFI_IFR_EXTEND_OP_LABEL;\r
1351 mEndLabel->Number = LABEL_END;\r
1352\r
1353 mBmmCallbackInfo = BmmCallbackInfo;\r
1354\r
1355 InitializeStringDepository ();\r
1356\r
1357}\r
1358\r
1359/**\r
1360 Remove the installed BootMaint and FileExplorer HiiPackages.\r
1361\r
1362**/\r
143f0b1d
ED
1363VOID\r
1364FreeBMPackage(\r
1365 VOID\r
1366 )\r
1367{\r
1368 BMM_CALLBACK_DATA *BmmCallbackInfo;\r
1369\r
1370 if (mStartOpCodeHandle != NULL) {\r
1371 HiiFreeOpCodeHandle (mStartOpCodeHandle);\r
1372 }\r
1373\r
1374 if (mEndOpCodeHandle != NULL) {\r
1375 HiiFreeOpCodeHandle (mEndOpCodeHandle);\r
1376 }\r
1377\r
1378 FreeAllMenu ();\r
1379 CleanUpStringDepository ();\r
1380\r
1381 BmmCallbackInfo = mBmmCallbackInfo;\r
1382\r
1383 //\r
1384 // Remove our IFR data from HII database\r
1385 //\r
1386 HiiRemovePackages (BmmCallbackInfo->BmmHiiHandle);\r
1387 HiiRemovePackages (BmmCallbackInfo->FeHiiHandle);\r
1388\r
1389 gBS->UninstallMultipleProtocolInterfaces (\r
1390 BmmCallbackInfo->FeDriverHandle,\r
1391 &gEfiDevicePathProtocolGuid,\r
1392 &mFeHiiVendorDevicePath,\r
1393 &gEfiHiiConfigAccessProtocolGuid,\r
1394 &BmmCallbackInfo->FeConfigAccess,\r
1395 NULL\r
1396 );\r
1397\r
1398 gBS->UninstallMultipleProtocolInterfaces (\r
1399 BmmCallbackInfo->BmmDriverHandle,\r
1400 &gEfiDevicePathProtocolGuid,\r
1401 &mBmmHiiVendorDevicePath,\r
1402 &gEfiHiiConfigAccessProtocolGuid,\r
1403 &BmmCallbackInfo->BmmConfigAccess,\r
1404 NULL\r
1405 );\r
1406\r
1407 FreePool (BmmCallbackInfo->LoadContext);\r
1408 FreePool (BmmCallbackInfo);\r
1409}\r
1410\r