d1edef3d7ed9cadfda0d91af70c12977e071c099
[people/mcb30/edk2.git] / edk2 / EdkUnixPkg / Dxe / PlatformBds / BdsPlatform.c
1 /*++\r
2 \r
3 Copyright (c) 2006, Intel Corporation                                                         \r
4 All rights reserved. This program and the accompanying materials                          \r
5 are licensed and made available under the terms and conditions of the BSD License         \r
6 which accompanies this distribution.  The full text of the license may be found at        \r
7 http://opensource.org/licenses/bsd-license.php                                            \r
8                                                                                           \r
9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,                     \r
10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.             \r
11 \r
12 Module Name:\r
13 \r
14   BdsPlatform.c\r
15 \r
16 Abstract:\r
17 \r
18   This file include all platform action which can be customized\r
19   by IBV/OEM.\r
20 \r
21 --*/\r
22 \r
23 #include "Generic/Bds.h"\r
24 #include "BdsPlatform.h"\r
25 #include "Generic/String.h"\r
26 #include "Generic/Language.h"\r
27 #include "Generic/FrontPage.h"\r
28 \r
29 CHAR16  mFirmwareVendor[] = L"TianoCore.org";\r
30 \r
31 //\r
32 // BDS Platform Functions\r
33 //\r
34 VOID\r
35 PlatformBdsInit (\r
36   IN EFI_BDS_ARCH_PROTOCOL_INSTANCE  *PrivateData\r
37   )\r
38 /*++\r
39 \r
40 Routine Description:\r
41 \r
42   Platform Bds init. Incude the platform firmware vendor, revision\r
43   and so crc check.\r
44 \r
45 Arguments:\r
46 \r
47   PrivateData  - The EFI_BDS_ARCH_PROTOCOL_INSTANCE instance\r
48 \r
49 Returns:\r
50 \r
51   None.\r
52 \r
53 --*/\r
54 {\r
55   //\r
56   // set firmwarevendor, here can be IBV/OEM customize\r
57   //\r
58   gST->FirmwareVendor = AllocateRuntimeCopyPool (\r
59                           sizeof (mFirmwareVendor),\r
60                           &mFirmwareVendor\r
61                           );\r
62   ASSERT (gST->FirmwareVendor != NULL);\r
63 \r
64   gST->FirmwareRevision = EFI_FIRMWARE_REVISION;\r
65 \r
66   //\r
67   // Fixup Tasble CRC after we updated Firmware Vendor and Revision\r
68   //\r
69   gBS->CalculateCrc32 ((VOID *) gST, sizeof (EFI_SYSTEM_TABLE), &gST->Hdr.CRC32);\r
70 \r
71   //\r
72   // Initialize the platform specific string and language\r
73   //\r
74   InitializeStringSupport ();\r
75   InitializeLanguage (TRUE);\r
76   InitializeFrontPage (FALSE);\r
77 \r
78 }\r
79 \r
80 EFI_STATUS\r
81 PlatformBdsConnectConsole (\r
82   IN BDS_CONSOLE_CONNECT_ENTRY   *PlatformConsole\r
83   )\r
84 /*++\r
85 \r
86 Routine Description:\r
87 \r
88   Connect the predefined platform default console device. Always try to find\r
89   and enable the vga device if have.\r
90 \r
91 Arguments:\r
92 \r
93   PlatformConsole         - Predfined platform default console device array.\r
94  \r
95 Returns:\r
96 \r
97   EFI_SUCCESS             - Success connect at least one ConIn and ConOut \r
98                             device, there must have one ConOut device is \r
99                             active vga device.\r
100   \r
101   EFI_STATUS              - Return the status of \r
102                             BdsLibConnectAllDefaultConsoles ()\r
103 \r
104 --*/\r
105 {\r
106   EFI_STATUS  Status;\r
107   UINTN       Index;\r
108 \r
109   Index   = 0;\r
110   Status  = EFI_SUCCESS;\r
111 \r
112   //\r
113   // Have chance to connect the platform default console,\r
114   // the platform default console is the minimue device group\r
115   // the platform should support\r
116   //\r
117   while (PlatformConsole[Index].DevicePath != NULL) {\r
118     //\r
119     // Update the console variable with the connect type\r
120     //\r
121     if ((PlatformConsole[Index].ConnectType & CONSOLE_IN) == CONSOLE_IN) {\r
122       BdsLibUpdateConsoleVariable (L"ConIn", PlatformConsole[Index].DevicePath, NULL);\r
123     }\r
124 \r
125     if ((PlatformConsole[Index].ConnectType & CONSOLE_OUT) == CONSOLE_OUT) {\r
126       BdsLibUpdateConsoleVariable (L"ConOut", PlatformConsole[Index].DevicePath, NULL);\r
127     }\r
128 \r
129     if ((PlatformConsole[Index].ConnectType & STD_ERROR) == STD_ERROR) {\r
130       BdsLibUpdateConsoleVariable (L"ErrOut", PlatformConsole[Index].DevicePath, NULL);\r
131     }\r
132 \r
133     Index++;\r
134   }\r
135   //\r
136   // Connect the all the default console with current cosole variable\r
137   //\r
138   Status = BdsLibConnectAllDefaultConsoles ();\r
139   if (EFI_ERROR (Status)) {\r
140     return Status;\r
141   }\r
142 \r
143   return EFI_SUCCESS;\r
144 }\r
145 \r
146 VOID\r
147 PlatformBdsConnectSequence (\r
148   VOID\r
149   )\r
150 /*++\r
151 \r
152 Routine Description:\r
153 \r
154   Connect with predeined platform connect sequence, \r
155   the OEM/IBV can customize with their own connect sequence.\r
156   \r
157 Arguments:\r
158 \r
159   None.\r
160  \r
161 Returns:\r
162 \r
163   None.\r
164   \r
165 --*/\r
166 {\r
167   UINTN Index;\r
168 \r
169   Index = 0;\r
170 \r
171   //\r
172   // Here we can get the customized platform connect sequence\r
173   // Notes: we can connect with new variable which record the\r
174   // last time boots connect device path sequence\r
175   //\r
176   while (gPlatformConnectSequence[Index] != NULL) {\r
177     //\r
178     // Build the platform boot option\r
179     //\r
180     BdsLibConnectDevicePath (gPlatformConnectSequence[Index]);\r
181     Index++;\r
182   }\r
183 \r
184 }\r
185 \r
186 VOID\r
187 PlatformBdsGetDriverOption (\r
188   IN OUT LIST_ENTRY              *BdsDriverLists\r
189   )\r
190 /*++\r
191 \r
192 Routine Description:\r
193 \r
194   Load the predefined driver option, OEM/IBV can customize this\r
195   to load their own drivers\r
196   \r
197 Arguments:\r
198 \r
199   BdsDriverLists  - The header of the driver option link list.\r
200  \r
201 Returns:\r
202 \r
203   None.\r
204   \r
205 --*/\r
206 {\r
207   UINTN Index;\r
208 \r
209   Index = 0;\r
210 \r
211   //\r
212   // Here we can get the customized platform driver option\r
213   //\r
214   while (gPlatformDriverOption[Index] != NULL) {\r
215     //\r
216     // Build the platform boot option\r
217     //\r
218     BdsLibRegisterNewOption (BdsDriverLists, gPlatformDriverOption[Index], NULL, L"DriverOrder");\r
219     Index++;\r
220   }\r
221 \r
222 }\r
223 \r
224 VOID\r
225 PlatformBdsDiagnostics (\r
226   IN EXTENDMEM_COVERAGE_LEVEL    MemoryTestLevel,\r
227   IN BOOLEAN                     QuietBoot\r
228   )\r
229 /*++\r
230 \r
231 Routine Description:\r
232 \r
233   Perform the platform diagnostic, such like test memory. OEM/IBV also\r
234   can customize this fuction to support specific platform diagnostic.\r
235   \r
236 Arguments:\r
237 \r
238   MemoryTestLevel  - The memory test intensive level\r
239   \r
240   QuietBoot        - Indicate if need to enable the quiet boot\r
241  \r
242 Returns:\r
243 \r
244   None.\r
245   \r
246 --*/\r
247 {\r
248   EFI_STATUS  Status;\r
249 \r
250   //\r
251   // Here we can decide if we need to show\r
252   // the diagnostics screen\r
253   // Notes: this quiet boot code should be remove\r
254   // from the graphic lib\r
255   //\r
256   if (QuietBoot) {\r
257     EnableQuietBoot (&gEfiUgaSplashProtocolGuid);\r
258     //\r
259     // Perform system diagnostic\r
260     //\r
261     Status = BdsMemoryTest (MemoryTestLevel);\r
262     if (EFI_ERROR (Status)) {\r
263       DisableQuietBoot ();\r
264     }\r
265 \r
266     return ;\r
267   }\r
268   //\r
269   // Perform system diagnostic\r
270   //\r
271   Status = BdsMemoryTest (MemoryTestLevel);\r
272 }\r
273 \r
274 VOID\r
275 PlatformBdsPolicyBehavior (\r
276   IN EFI_BDS_ARCH_PROTOCOL_INSTANCE  *PrivateData,\r
277   IN OUT LIST_ENTRY                  *DriverOptionList,\r
278   IN OUT LIST_ENTRY                  *BootOptionList\r
279   )\r
280 /*++\r
281 \r
282 Routine Description:\r
283 \r
284   The function will excute with as the platform policy, current policy\r
285   is driven by boot mode. IBV/OEM can customize this code for their specific\r
286   policy action.\r
287   \r
288 Arguments:\r
289 \r
290   PrivateData      - The EFI_BDS_ARCH_PROTOCOL_INSTANCE instance\r
291   \r
292   DriverOptionList - The header of the driver option link list\r
293   \r
294   BootOptionList   - The header of the boot option link list\r
295  \r
296 Returns:\r
297 \r
298   None.\r
299   \r
300 --*/\r
301 {\r
302   EFI_STATUS  Status;\r
303   UINT16      Timeout;\r
304 \r
305   //\r
306   // Init the time out value\r
307   //\r
308   Timeout = BdsLibGetTimeout ();\r
309 \r
310   //\r
311   // Load the driver option as the driver option list\r
312   //\r
313   PlatformBdsGetDriverOption (DriverOptionList);\r
314 \r
315   //\r
316   // Get current Boot Mode\r
317   //\r
318   Status = BdsLibGetBootMode (&PrivateData->BootMode);\r
319 \r
320   //\r
321   // Go the different platform policy with different boot mode\r
322   // Notes: this part code can be change with the table policy\r
323   //\r
324   switch (PrivateData->BootMode) {\r
325 \r
326   case BOOT_ASSUMING_NO_CONFIGURATION_CHANGES:\r
327   case BOOT_WITH_MINIMAL_CONFIGURATION:\r
328     //\r
329     // In no-configuration boot mode, we can connect the\r
330     // console directly.\r
331     //\r
332     BdsLibConnectAllDefaultConsoles ();\r
333     PlatformBdsDiagnostics (IGNORE, TRUE);\r
334 \r
335     //\r
336     // Perform some platform specific connect sequence\r
337     //\r
338     PlatformBdsConnectSequence ();\r
339 \r
340     //\r
341     // Notes: current time out = 0 can not enter the\r
342     // front page\r
343     //\r
344     PlatformBdsEnterFrontPage (Timeout, FALSE);\r
345 \r
346     //\r
347     // Check the boot option with the boot option list\r
348     //\r
349     BdsLibBuildOptionFromVar (BootOptionList, L"BootOrder");\r
350     break;\r
351 \r
352   case BOOT_ON_FLASH_UPDATE:\r
353     //\r
354     // Boot with the specific configuration\r
355     //\r
356     PlatformBdsConnectConsole (gPlatformConsole);\r
357     PlatformBdsDiagnostics (EXTENSIVE, FALSE);\r
358     BdsLibConnectAll ();\r
359     ProcessCapsules (BOOT_ON_FLASH_UPDATE);\r
360     break;\r
361 \r
362   case BOOT_IN_RECOVERY_MODE:\r
363     //\r
364     // In recovery mode, just connect platform console\r
365     // and show up the front page\r
366     //\r
367     PlatformBdsConnectConsole (gPlatformConsole);\r
368     PlatformBdsDiagnostics (EXTENSIVE, FALSE);\r
369 \r
370     //\r
371     // In recovery boot mode, we still enter to the\r
372     // frong page now\r
373     //\r
374     PlatformBdsEnterFrontPage (Timeout, FALSE);\r
375     break;\r
376 \r
377   case BOOT_WITH_FULL_CONFIGURATION:\r
378   case BOOT_WITH_FULL_CONFIGURATION_PLUS_DIAGNOSTICS:\r
379   case BOOT_WITH_DEFAULT_SETTINGS:\r
380   default:\r
381     //\r
382     // Connect platform console\r
383     //\r
384     Status = PlatformBdsConnectConsole (gPlatformConsole);\r
385     if (EFI_ERROR (Status)) {\r
386       //\r
387       // Here OEM/IBV can customize with defined action\r
388       //\r
389       PlatformBdsNoConsoleAction ();\r
390     }\r
391 \r
392     PlatformBdsDiagnostics (IGNORE, TRUE);\r
393 \r
394     //\r
395     // Perform some platform specific connect sequence\r
396     //\r
397     PlatformBdsConnectSequence ();\r
398 \r
399     //\r
400     // Give one chance to enter the setup if we\r
401     // have the time out\r
402     //\r
403     PlatformBdsEnterFrontPage (Timeout, FALSE);\r
404 \r
405     //\r
406     // Here we have enough time to do the enumeration of boot device\r
407     //\r
408     BdsLibEnumerateAllBootOption (BootOptionList);\r
409     break;\r
410   }\r
411 \r
412   return ;\r
413 \r
414 }\r
415 \r
416 VOID\r
417 PlatformBdsBootSuccess (\r
418   IN  BDS_COMMON_OPTION *Option\r
419   )\r
420 /*++\r
421 \r
422 Routine Description:\r
423   \r
424   Hook point after a boot attempt succeeds. We don't expect a boot option to\r
425   return, so the EFI 1.0 specification defines that you will default to an\r
426   interactive mode and stop processing the BootOrder list in this case. This\r
427   is alos a platform implementation and can be customized by IBV/OEM.\r
428 \r
429 Arguments:\r
430 \r
431   Option - Pointer to Boot Option that succeeded to boot.\r
432 \r
433 Returns:\r
434   \r
435   None.\r
436 \r
437 --*/\r
438 {\r
439   CHAR16  *TmpStr;\r
440 \r
441   //\r
442   // If Boot returned with EFI_SUCCESS and there is not in the boot device\r
443   // select loop then we need to pop up a UI and wait for user input.\r
444   //\r
445   TmpStr = GetStringById (STRING_TOKEN (STR_BOOT_SUCCEEDED));\r
446   if (TmpStr != NULL) {\r
447     BdsLibOutputStrings (gST->ConOut, TmpStr, Option->Description, L"\n\r", NULL);\r
448     gBS->FreePool (TmpStr);\r
449   }\r
450 }\r
451 \r
452 VOID\r
453 PlatformBdsBootFail (\r
454   IN  BDS_COMMON_OPTION  *Option,\r
455   IN  EFI_STATUS         Status,\r
456   IN  CHAR16             *ExitData,\r
457   IN  UINTN              ExitDataSize\r
458   )\r
459 /*++\r
460 \r
461 Routine Description:\r
462   \r
463   Hook point after a boot attempt fails.\r
464 \r
465 Arguments:\r
466   \r
467   Option - Pointer to Boot Option that failed to boot.\r
468 \r
469   Status - Status returned from failed boot.\r
470 \r
471   ExitData - Exit data returned from failed boot.\r
472 \r
473   ExitDataSize - Exit data size returned from failed boot.\r
474 \r
475 Returns:\r
476   \r
477   None.\r
478 \r
479 --*/\r
480 {\r
481   CHAR16  *TmpStr;\r
482 \r
483   //\r
484   // If Boot returned with failed status then we need to pop up a UI and wait\r
485   // for user input.\r
486   //\r
487   TmpStr = GetStringById (STRING_TOKEN (STR_BOOT_FAILED));\r
488   if (TmpStr != NULL) {\r
489     BdsLibOutputStrings (gST->ConOut, TmpStr, Option->Description, L"\n\r", NULL);\r
490     gBS->FreePool (TmpStr);\r
491   }\r
492 \r
493 }\r
494 \r
495 EFI_STATUS\r
496 PlatformBdsNoConsoleAction (\r
497   VOID\r
498   )\r
499 /*++\r
500 \r
501 Routine Description:\r
502   \r
503   This function is remained for IBV/OEM to do some platform action,\r
504   if there no console device can be connected.\r
505 \r
506 Arguments:\r
507   \r
508   None.\r
509   \r
510 Returns:\r
511   \r
512   EFI_SUCCESS      - Direct return success now.\r
513 \r
514 --*/\r
515 {\r
516   return EFI_SUCCESS;\r
517 }\r