]> git.proxmox.com Git - mirror_edk2.git/blobdiff - IntelFrameworkModulePkg/Universal/BdsDxe/FrontPage.c
Update for IntelFrameworkModulePkg.
[mirror_edk2.git] / IntelFrameworkModulePkg / Universal / BdsDxe / FrontPage.c
index 4cd0691b91e33c7aaa077ea40b8f61f455d2e605..efecf7bec6018828e765cccb55f49fa0a7152806 100644 (file)
@@ -17,6 +17,12 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
 #include "Language.h"\r
 #include "Hotkey.h"\r
 \r
+BOOLEAN   mSetupModeInitialized = FALSE;\r
+UINT32    mSetupTextModeColumn;\r
+UINT32    mSetupTextModeRow;\r
+UINT32    mSetupHorizontalResolution;\r
+UINT32    mSetupVerticalResolution;\r
+\r
 BOOLEAN   gConnectAllHappened = FALSE;\r
 UINTN     gCallbackKey;\r
 \r
@@ -169,23 +175,26 @@ FrontPageCallback (
   CHAR8                         *PlatformSupportedLanguages;\r
   CHAR8                         *BestLanguage;\r
 \r
-  if (Action == EFI_BROWSER_ACTION_CHANGING) {\r
+  if (Action != EFI_BROWSER_ACTION_CHANGING && Action != EFI_BROWSER_ACTION_CHANGED) {\r
+    //\r
+    // All other action return unsupported.\r
+    //\r
+    return EFI_UNSUPPORTED;\r
+  }\r
+  \r
+  gCallbackKey = QuestionId;\r
+\r
+  if (Action == EFI_BROWSER_ACTION_CHANGED) {\r
     if ((Value == NULL) || (ActionRequest == NULL)) {\r
       return EFI_INVALID_PARAMETER;\r
     }\r
 \r
-    gCallbackKey = QuestionId;\r
-\r
-    //\r
-    // The first 4 entries in the Front Page are to be GUARANTEED to remain constant so IHV's can\r
-    // describe to their customers in documentation how to find their setup information (namely\r
-    // under the device manager and specific buckets)\r
-    //\r
     switch (QuestionId) {\r
     case FRONT_PAGE_KEY_CONTINUE:\r
       //\r
       // This is the continue - clear the screen and return an error to get out of FrontPage loop\r
       //\r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_EXIT;\r
       break;\r
 \r
     case FRONT_PAGE_KEY_LANGUAGE:\r
@@ -244,11 +253,27 @@ FrontPageCallback (
         ASSERT (FALSE);\r
       }\r
 \r
+      *ActionRequest = EFI_BROWSER_ACTION_REQUEST_EXIT;\r
+\r
       FreePool (PlatformSupportedLanguages);\r
       FreePool (Lang);\r
       FreePool (LanguageString);\r
       break;\r
 \r
+    default:\r
+      break;\r
+    }\r
+  } else if (Action == EFI_BROWSER_ACTION_CHANGING) {\r
+    if (Value == NULL) {\r
+      return EFI_INVALID_PARAMETER;\r
+    }\r
+\r
+    //\r
+    // The first 4 entries in the Front Page are to be GUARANTEED to remain constant so IHV's can\r
+    // describe to their customers in documentation how to find their setup information (namely\r
+    // under the device manager and specific buckets)\r
+    //\r
+    switch (QuestionId) {\r
     case FRONT_PAGE_KEY_BOOT_MANAGER:\r
       //\r
       // Boot Manager\r
@@ -271,16 +296,9 @@ FrontPageCallback (
       gCallbackKey = 0;\r
       break;\r
     }\r
-\r
-    *ActionRequest = EFI_BROWSER_ACTION_REQUEST_EXIT;\r
-\r
-    return EFI_SUCCESS;\r
   }\r
 \r
-  //\r
-  // All other action return unsupported.\r
-  //\r
-  return EFI_UNSUPPORTED;\r
+  return EFI_SUCCESS;  \r
 }\r
 \r
 /**\r
@@ -722,7 +740,7 @@ UpdateFrontPageStrings (
                   );\r
   ASSERT_EFI_ERROR (Status);\r
 \r
-  SmbiosHandle = 0;\r
+  SmbiosHandle = SMBIOS_HANDLE_PI_RESERVED;\r
   do {\r
     Status = Smbios->GetNext (Smbios, &SmbiosHandle, NULL, &Record, NULL);\r
     if (EFI_ERROR(Status)) {\r
@@ -939,6 +957,186 @@ ShowProgress (
   return EFI_SUCCESS;\r
 }\r
 \r
+/**\r
+  This function will change video resolution and text mode for setup when setup is launched.\r
+\r
+  @param   None.\r
+\r
+  @retval  EFI_SUCCESS  Mode is changed successfully.\r
+  @retval  Others       Mode failed to changed.\r
+\r
+**/\r
+EFI_STATUS\r
+EFIAPI\r
+ChangeModeForSetup (\r
+  VOID\r
+  )\r
+{\r
+  EFI_GRAPHICS_OUTPUT_PROTOCOL          *GraphicsOutput;\r
+  EFI_SIMPLE_TEXT_OUTPUT_PROTOCOL       *SimpleTextOut;\r
+  UINTN                                 SizeOfInfo;\r
+  EFI_GRAPHICS_OUTPUT_MODE_INFORMATION  *Info;\r
+  UINT32                                MaxGopMode;\r
+  UINT32                                MaxTextMode;\r
+  UINT32                                ModeNumber;\r
+  UINTN                                 HandleCount;\r
+  EFI_HANDLE                            *HandleBuffer;\r
+  EFI_STATUS                            Status;\r
+  UINTN                                 Index;\r
+  UINTN                                 CurrentColumn;\r
+  UINTN                                 CurrentRow;  \r
+\r
+  Status = gBS->HandleProtocol (\r
+                  gST->ConsoleOutHandle,\r
+                  &gEfiGraphicsOutputProtocolGuid,\r
+                  (VOID**)&GraphicsOutput\r
+                  );\r
+  if (EFI_ERROR (Status)) {\r
+    GraphicsOutput = NULL;\r
+  }\r
+\r
+  Status = gBS->HandleProtocol (\r
+                  gST->ConsoleOutHandle,\r
+                  &gEfiSimpleTextOutProtocolGuid,\r
+                  (VOID**)&SimpleTextOut\r
+                  );\r
+  if (EFI_ERROR (Status)) {\r
+    SimpleTextOut = NULL;\r
+  }  \r
+\r
+  if ((GraphicsOutput == NULL) || (SimpleTextOut == NULL)) {\r
+    return EFI_UNSUPPORTED;\r
+  }\r
+\r
+  //\r
+  // Get user defined text mode for setup only once.\r
+  //  \r
+  if (!mSetupModeInitialized) {\r
+    mSetupHorizontalResolution = PcdGet32 (PcdSetupVideoHorizontalResolution);\r
+    mSetupVerticalResolution   = PcdGet32 (PcdSetupVideoVerticalResolution);      \r
+    mSetupTextModeColumn       = PcdGet32 (PcdSetupConOutColumn);\r
+    mSetupTextModeRow          = PcdGet32 (PcdSetupConOutRow);\r
+    mSetupModeInitialized     = TRUE;\r
+  }\r
+\r
+  MaxGopMode  = GraphicsOutput->Mode->MaxMode;\r
+  MaxTextMode = SimpleTextOut->Mode->MaxMode;\r
+\r
+  //\r
+  // 1. If current video resolution is same with setup video resolution,\r
+  //    video resolution need not be changed.\r
+  //    1.1. If current text mode is same with setup text mode, text mode need not be changed.\r
+  //    1.2. If current text mode is different with setup text mode, text mode need be changed to setup text mode.\r
+  // 2. If current video resolution is different with setup video resolution, we need restart whole console drivers.\r
+  //\r
+  for (ModeNumber = 0; ModeNumber < MaxGopMode; ModeNumber++) {\r
+    Status = GraphicsOutput->QueryMode (\r
+                       GraphicsOutput,\r
+                       ModeNumber,\r
+                       &SizeOfInfo,\r
+                       &Info\r
+                       );\r
+    if (!EFI_ERROR (Status)) {\r
+      if ((Info->HorizontalResolution == mSetupHorizontalResolution) &&\r
+          (Info->VerticalResolution == mSetupVerticalResolution)) {\r
+        if ((GraphicsOutput->Mode->Info->HorizontalResolution == mSetupHorizontalResolution) &&\r
+            (GraphicsOutput->Mode->Info->VerticalResolution == mSetupVerticalResolution)) {\r
+          //\r
+          // If current video resolution is same with setup video resolution, \r
+          // then check if current text mode is same with setup text mode.\r
+          //\r
+          Status = SimpleTextOut->QueryMode (SimpleTextOut, SimpleTextOut->Mode->Mode, &CurrentColumn, &CurrentRow);\r
+          ASSERT_EFI_ERROR (Status);\r
+          if (CurrentColumn == mSetupTextModeColumn && CurrentRow == mSetupTextModeRow) {\r
+            //\r
+            // Current text mode is same with setup text mode, text mode need not be change.\r
+            //\r
+            FreePool (Info);\r
+            return EFI_SUCCESS;\r
+          } else {\r
+            //\r
+            // Current text mode is different with setup text mode, text mode need be change to new text mode.\r
+            //\r
+            for (Index = 0; Index < MaxTextMode; Index++) {\r
+              Status = SimpleTextOut->QueryMode (SimpleTextOut, Index, &CurrentColumn, &CurrentRow);\r
+              if (!EFI_ERROR(Status)) {\r
+                if ((CurrentColumn == mSetupTextModeColumn) && (CurrentRow == mSetupTextModeRow)) {\r
+                  //\r
+                  // setup text mode is supported, set it.\r
+                  //\r
+                  Status = SimpleTextOut->SetMode (SimpleTextOut, Index);\r
+                  ASSERT_EFI_ERROR (Status);\r
+                  //\r
+                  // Update text mode PCD.\r
+                  //\r
+                  PcdSet32 (PcdConOutColumn, mSetupTextModeColumn);\r
+                  PcdSet32 (PcdConOutRow, mSetupTextModeRow);\r
+                  FreePool (Info);\r
+                  return EFI_SUCCESS;\r
+                }\r
+              }\r
+            }\r
+            if (Index == MaxTextMode) {\r
+              //\r
+              // If setup text mode is not supported, return error.\r
+              //\r
+              FreePool (Info);\r
+              return EFI_UNSUPPORTED;\r
+            }\r
+          }\r
+        } else {\r
+          FreePool (Info);\r
+          //\r
+          // If current video resolution is not same with the setup video resolution, set new video resolution.\r
+          // In this case, the drivers which produce simple text out need be restarted.\r
+          //\r
+          Status = GraphicsOutput->SetMode (GraphicsOutput, ModeNumber);\r
+          if (!EFI_ERROR (Status)) {\r
+            //\r
+            // Set PCD to restart GraphicsConsole and Consplitter to change video resolution \r
+            // and produce new text mode based on new resolution.\r
+            //\r
+            PcdSet32 (PcdVideoHorizontalResolution, mSetupHorizontalResolution);\r
+            PcdSet32 (PcdVideoVerticalResolution, mSetupVerticalResolution);\r
+            PcdSet32 (PcdConOutColumn, mSetupTextModeColumn);\r
+            PcdSet32 (PcdConOutRow, mSetupTextModeRow);\r
+            \r
+            Status = gBS->LocateHandleBuffer (\r
+                             ByProtocol,\r
+                             &gEfiSimpleTextOutProtocolGuid,\r
+                             NULL,\r
+                             &HandleCount,\r
+                             &HandleBuffer\r
+                             );\r
+            if (!EFI_ERROR (Status)) {\r
+              for (Index = 0; Index < HandleCount; Index++) {\r
+                gBS->DisconnectController (HandleBuffer[Index], NULL, NULL);\r
+              }\r
+              for (Index = 0; Index < HandleCount; Index++) {\r
+                gBS->ConnectController (HandleBuffer[Index], NULL, NULL, TRUE);\r
+              }\r
+              if (HandleBuffer != NULL) {\r
+                FreePool (HandleBuffer);\r
+              }\r
+              break;\r
+            }\r
+          }\r
+        }\r
+      }\r
+      FreePool (Info);\r
+    }\r
+  }\r
+\r
+  if (ModeNumber == MaxGopMode) {\r
+    //\r
+    // If the new resolution is not supported, return error.\r
+    //\r
+    return EFI_UNSUPPORTED;\r
+  }\r
+\r
+  return EFI_SUCCESS;\r
+}\r
+\r
 /**\r
   This function is the main entry of the platform setup entry.\r
   The function will present the main menu of the system setup,\r
@@ -995,8 +1193,13 @@ PlatformBdsEnterFrontPage (
     BootLogo->SetBootLogo (BootLogo, NULL, 0, 0, 0, 0);\r
   }\r
 \r
+  Status = EFI_SUCCESS;\r
   do {\r
-\r
+    //\r
+    // Set proper video resolution and text mode for setup\r
+    //\r
+    ChangeModeForSetup ();\r
+    \r
     InitializeFrontPage (FALSE);\r
 \r
     //\r
@@ -1005,7 +1208,7 @@ PlatformBdsEnterFrontPage (
     UpdateFrontPageStrings ();\r
 \r
     gCallbackKey = 0;\r
-    Status = CallFrontPage ();\r
+    CallFrontPage ();\r
 \r
     //\r
     // If gCallbackKey is greater than 1 and less or equal to 5,\r