Add 2 new Bds features

1. Lazy ConIn
  2. OsIndicationsSupported & OsIndications

Signed-off-by: Chao Zhang<chao.b.zhang@intel.com>
Reviewed-by: Hot Tian<Hot.Tian@intel.com>

git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@13567 6f19259b-4bc3-4df7-8a09-765794883524
This commit is contained in:
czhang46 2012-07-30 06:04:13 +00:00
parent 18cf395022
commit 838a9c58c9
4 changed files with 282 additions and 3 deletions

View File

@ -633,7 +633,7 @@
# boundary as close to the top of memory as feasible.
#
gEfiMdeModulePkgTokenSpaceGuid.PcdMaxEfiSystemTablePointerAddress|0x0|UINT64|0x30001027
[PcdsPatchableInModule, PcdsDynamic, PcdsDynamicEx]
## This PCD defines the Console output column and the default value is 25 according to UEFI spec.
# This PCD could be set to 0 then console output could be at max column and max row.
@ -814,6 +814,11 @@
# the extension FPDT boot records got after ReadyToBoot and before ExitBootService.
gEfiMdeModulePkgTokenSpaceGuid.PcdExtFpdtBootRecordPadSize|0x0|UINT32|0x0001005F
## This PCD specifies whether ConIn device are connected on demand. If TRUE, ConIn
# device are not connected during BDS and ReadKeyStroke/ReadKeyStrokeEx produced
# by Consplitter should be called before any real key read operation.
gEfiMdeModulePkgTokenSpaceGuid.PcdConInConnectOnDemand|FALSE|BOOLEAN|0x10000060
## This PCD specified whether the S.M.A.R.T feature of attached ATA hard disks are enabled.
gEfiMdeModulePkgTokenSpaceGuid.PcdAtaSmartEnable|TRUE|BOOLEAN|0x00010065

View File

@ -29,6 +29,12 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#include "ConSplitter.h"
//
// Identify if ConIn is connected in PcdConInConnectOnDemand enabled mode.
// default not connect
//
BOOLEAN mConInIsConnect = FALSE;
//
// Text In Splitter Private Data template
//
@ -3304,6 +3310,246 @@ ConSplitterTextInPrivateReadKeyStroke (
return EFI_NOT_READY;
}
/*
Connect the specific Usb device which match the short form device path,
and whose bus is determined by Host Controller.
@param DevicePath A short-form device path that starts with the first
element being a USB WWID or a USB Class device
path
@return EFI_INVALID_PARAMETER DevicePath is NULL pointer.
DevicePath is not a USB device path.
@return EFI_SUCCESS Success to connect USB device
@return EFI_NOT_FOUND Fail to find handle for USB controller to connect.
**/
EFI_STATUS
EFIAPI
ConSplitterConnectUsbShortFormDevicePath (
IN EFI_DEVICE_PATH_PROTOCOL *DevicePath
)
{
EFI_STATUS Status;
EFI_HANDLE *Handles;
UINTN HandleCount;
UINTN Index;
EFI_PCI_IO_PROTOCOL *PciIo;
UINT8 Class[3];
BOOLEAN AtLeastOneConnected;
//
// Check the passed in parameters
//
if (DevicePath == NULL) {
return EFI_INVALID_PARAMETER;
}
if ((DevicePathType (DevicePath) != MESSAGING_DEVICE_PATH) ||
((DevicePathSubType (DevicePath) != MSG_USB_CLASS_DP) && (DevicePathSubType (DevicePath) != MSG_USB_WWID_DP))
) {
return EFI_INVALID_PARAMETER;
}
//
// Find the usb host controller firstly, then connect with the remaining device path
//
AtLeastOneConnected = FALSE;
Status = gBS->LocateHandleBuffer (
ByProtocol,
&gEfiPciIoProtocolGuid,
NULL,
&HandleCount,
&Handles
);
for (Index = 0; Index < HandleCount; Index++) {
Status = gBS->HandleProtocol (
Handles[Index],
&gEfiPciIoProtocolGuid,
(VOID **) &PciIo
);
if (!EFI_ERROR (Status)) {
//
// Check whether the Pci device is the wanted usb host controller
//
Status = PciIo->Pci.Read (PciIo, EfiPciIoWidthUint8, 0x09, 3, &Class);
if (!EFI_ERROR (Status) &&
((PCI_CLASS_SERIAL == Class[2]) && (PCI_CLASS_SERIAL_USB == Class[1]))
) {
Status = gBS->ConnectController (
Handles[Index],
NULL,
DevicePath,
FALSE
);
if (!EFI_ERROR(Status)) {
AtLeastOneConnected = TRUE;
}
}
}
}
return AtLeastOneConnected ? EFI_SUCCESS : EFI_NOT_FOUND;
}
/**
This function will create all handles associate with every device
path node. If the handle associate with one device path node can not
be created successfully, then still give one chance to do the dispatch,
which load the missing drivers if possible.
@param DevicePathToConnect The device path which will be connected, it CANNOT be
a multi-instance device path
@param MatchingHandle Return the controller handle closest to the DevicePathToConnect
@retval EFI_INVALID_PARAMETER DevicePathToConnect is NULL.
@retval EFI_NOT_FOUND Failed to create all handles associate with every device path node.
@retval EFI_SUCCESS Successful to create all handles associate with every device path node.
**/
EFI_STATUS
EFIAPI
ConSplitterConnectDevicePath (
IN EFI_DEVICE_PATH_PROTOCOL *DevicePathToConnect,
OUT EFI_HANDLE *MatchingHandle OPTIONAL
)
{
EFI_STATUS Status;
EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath;
EFI_HANDLE Handle;
EFI_HANDLE PreviousHandle;
if (DevicePathToConnect == NULL) {
return EFI_INVALID_PARAMETER;
}
//
// Start the real work of connect with RemainingDevicePath
//
PreviousHandle = NULL;
do {
//
// Find the handle that best matches the Device Path. If it is only a
// partial match the remaining part of the device path is returned in
// RemainingDevicePath.
//
RemainingDevicePath = DevicePathToConnect;
Status = gBS->LocateDevicePath (&gEfiDevicePathProtocolGuid, &RemainingDevicePath, &Handle);
if (!EFI_ERROR (Status)) {
if (Handle == PreviousHandle) {
//
// If no forward progress is made try invoking the Dispatcher.
// A new FV may have been added to the system an new drivers
// may now be found.
// Status == EFI_SUCCESS means a driver was dispatched
// Status == EFI_NOT_FOUND means no new drivers were dispatched
//
Status = gDS->Dispatch ();
}
if (!EFI_ERROR (Status)) {
PreviousHandle = Handle;
//
// Connect all drivers that apply to Handle and RemainingDevicePath,
// the Recursive flag is FALSE so only one level will be expanded.
//
// Do not check the connect status here, if the connect controller fail,
// then still give the chance to do dispatch, because partial
// RemainingDevicepath may be in the new FV
//
// 1. If the connect fail, RemainingDevicepath and handle will not
// change, so next time will do the dispatch, then dispatch's status
// will take effect
// 2. If the connect success, the RemainingDevicepath and handle will
// change, then avoid the dispatch, we have chance to continue the
// next connection
//
gBS->ConnectController (Handle, NULL, RemainingDevicePath, FALSE);
if (MatchingHandle != NULL) {
*MatchingHandle = Handle;
}
}
}
//
// Loop until RemainingDevicePath is an empty device path
//
} while (!EFI_ERROR (Status) && !IsDevicePathEnd (RemainingDevicePath));
ASSERT (EFI_ERROR (Status) || IsDevicePathEnd (RemainingDevicePath));
return Status;
}
/**
Connect to all ConIn device which is in the ConIn variable.
@param DevicePath A short-form device path that starts with the first
element being a USB WWID or a USB Class device
path
@return EFI_INVALID_PARAMETER DevicePath is NULL pointer.
DevicePath is not a USB device path.
@return EFI_SUCCESS Success to connect USB device
@return EFI_NOT_FOUND Fail to find handle for USB controller to connect.
**/
EFI_STATUS
EFIAPI
ConSplitterConnectConInDevicePath (
)
{
EFI_DEVICE_PATH_PROTOCOL *DevicePath;
EFI_DEVICE_PATH_PROTOCOL *DevicePathInst;
EFI_DEVICE_PATH_PROTOCOL *CopyDevicePath;
UINTN Size;
EFI_DEVICE_PATH_PROTOCOL *Next;
DevicePath = GetEfiGlobalVariable (L"ConIn");
//
// Check the passed in parameters
//
if (DevicePath == NULL) {
return EFI_NOT_FOUND;
}
CopyDevicePath = DevicePath;
DevicePathInst = GetNextDevicePathInstance (&DevicePath, &Size);
while (DevicePathInst != NULL) {
Next = DevicePathInst;
while (!IsDevicePathEndType (Next)) {
Next = NextDevicePathNode (Next);
}
SetDevicePathEndNode (Next);
//
// Connect the USB console
// USB console device path is a short-form device path that
// starts with the first element being a USB WWID
// or a USB Class device path
//
if ((DevicePathType (DevicePathInst) == MESSAGING_DEVICE_PATH) &&
((DevicePathSubType (DevicePathInst) == MSG_USB_CLASS_DP)
|| (DevicePathSubType (DevicePathInst) == MSG_USB_WWID_DP)
)) {
ConSplitterConnectUsbShortFormDevicePath (DevicePathInst);
} else {
ConSplitterConnectDevicePath (DevicePathInst, NULL);
}
DevicePathInst = GetNextDevicePathInstance (&DevicePath, &Size);
}
return EFI_SUCCESS;
}
/**
Reads the next keystroke from the input device. The WaitForKey Event can
@ -3331,6 +3577,15 @@ ConSplitterTextInReadKeyStroke (
Private->KeyEventSignalState = FALSE;
//
// Connect ConIn when first call in Lazy ConIn mode
//
if (!mConInIsConnect && PcdGetBool (PcdConInConnectOnDemand)) {
DEBUG ((EFI_D_INFO, "Connect ConIn in first ReadKeyStoke in Lazy ConIn mode.\n"));
ConSplitterConnectConInDevicePath ();
mConInIsConnect = TRUE;
}
return ConSplitterTextInPrivateReadKeyStroke (Private, Key);
}
@ -3503,6 +3758,15 @@ ConSplitterTextInReadKeyStrokeEx (
return EFI_INVALID_PARAMETER;
}
//
// Connect ConIn when first call in Lazy ConIn mode
//
if (!mConInIsConnect && PcdGetBool (PcdConInConnectOnDemand)) {
DEBUG ((EFI_D_INFO, "Connect ConIn in first ReadKeyStoke in Lazy ConIn mode.\n"));
ConSplitterConnectConInDevicePath ();
mConInIsConnect = TRUE;
}
Private = TEXT_IN_EX_SPLITTER_PRIVATE_DATA_FROM_THIS (This);
Private->KeyEventSignalState = FALSE;

View File

@ -16,6 +16,9 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#define _CON_SPLITTER_H_
#include <Uefi.h>
#include <PiDxe.h>
#include <IndustryStandard/Pci.h>
#include <Protocol/DevicePath.h>
#include <Protocol/ComponentName.h>
@ -27,6 +30,7 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#include <Protocol/SimpleTextInEx.h>
#include <Protocol/GraphicsOutput.h>
#include <Protocol/UgaDraw.h>
#include <Protocol/PciIo.h>
#include <Guid/ConsoleInDevice.h>
#include <Guid/StandardErrorDevice.h>
@ -41,6 +45,8 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#include <Library/MemoryAllocationLib.h>
#include <Library/UefiBootServicesTableLib.h>
#include <Library/UefiRuntimeServicesTableLib.h>
#include <Library/DevicePathLib.h>
#include <Library/DxeServicesTableLib.h>
//

View File

@ -10,7 +10,7 @@
# Note: If only UGA Draw protocol is installed in system table, PcdUgaConsumeSupport
# should be set to TRUE.
#
# Copyright (c) 2006 - 2010, Intel Corporation. All rights reserved.<BR>
# Copyright (c) 2006 - 2012, Intel Corporation. All rights reserved.<BR>
#
# This program and the accompanying materials
# are licensed and made available under the terms and conditions of the BSD License
@ -68,6 +68,9 @@
UefiDriverEntryPoint
DebugLib
PcdLib
DevicePathLib
DxeServicesLib
DxeServicesTableLib
[Guids]
gEfiConsoleInDeviceGuid ## SOMETIMES_CONSUMES
@ -83,6 +86,7 @@
gEfiSimpleTextOutProtocolGuid ## BY_START
gEfiGraphicsOutputProtocolGuid ## BY_START
gEfiUgaDrawProtocolGuid ## BY_START
gEfiPciIoProtocolGuid ## PROTOCOL CONSUMES
[FeaturePcd]
@ -93,4 +97,4 @@
[Pcd]
gEfiMdeModulePkgTokenSpaceGuid.PcdConOutRow
gEfiMdeModulePkgTokenSpaceGuid.PcdConOutColumn
gEfiMdeModulePkgTokenSpaceGuid.PcdConInConnectOnDemand