From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: from mail02.groups.io (mail02.groups.io [66.175.222.108]) by spool.mail.gandi.net (Postfix) with ESMTPS id 546F99419EE for ; Tue, 10 Oct 2023 15:07:10 +0000 (UTC) DKIM-Signature: a=rsa-sha256; bh=p5zaue4Vbh0/u+4hN+YfS+qt5y7oQHbH7DHmKeeoa4U=; c=relaxed/simple; d=groups.io; h=From:To:Subject:Date:Message-Id:MIME-Version:Precedence:List-Subscribe:List-Help:Sender:List-Id:Mailing-List:Delivered-To:Reply-To:List-Unsubscribe-Post:List-Unsubscribe:Content-Transfer-Encoding; s=20140610; t=1696950428; v=1; b=Rz1vHquqZzFpbqcalUWJyAj3hP01xpgAHlKcHzpy6k78JSGoC2hsoxPnNhcMu3m7uqJUJgjb r0Tqg8G9PmmOotL0Z4Hye3GkqZJKZ3X14f4YGS8GJB6IHvXJIWbxjf1j0byYmOaTsZIU8uJ4q55 54XQYJnVfdLRB0U6NZB31ggs= X-Received: by 127.0.0.2 with SMTP id ugWZYY7687511xzQdrQ9BASl; Tue, 10 Oct 2023 08:07:08 -0700 X-Received: from mx0a-00069f02.pphosted.com (mx0a-00069f02.pphosted.com [205.220.165.32]) by mx.groups.io with SMTP id smtpd.web11.93767.1696950428397025784 for ; Tue, 10 Oct 2023 08:07:08 -0700 X-Received: from pps.filterd (m0246627.ppops.net [127.0.0.1]) by mx0b-00069f02.pphosted.com (8.17.1.19/8.17.1.19) with ESMTP id 39AExSFH012624 for ; Tue, 10 Oct 2023 15:07:08 GMT X-Received: from phxpaimrmta02.imrmtpd1.prodappphxaev1.oraclevcn.com (phxpaimrmta02.appoci.oracle.com [147.154.114.232]) by mx0b-00069f02.pphosted.com (PPS) with ESMTPS id 3tjwx25fga-1 (version=TLSv1.2 cipher=ECDHE-RSA-AES256-GCM-SHA384 bits=256 verify=OK) for ; Tue, 10 Oct 2023 15:07:06 +0000 X-Received: from pps.filterd (phxpaimrmta02.imrmtpd1.prodappphxaev1.oraclevcn.com [127.0.0.1]) by phxpaimrmta02.imrmtpd1.prodappphxaev1.oraclevcn.com (8.17.1.19/8.17.1.19) with ESMTP id 39AEO3xI004730 for ; Tue, 10 Oct 2023 15:07:05 GMT X-Received: from dhcp-10-159-238-159.vpn.oracle.com (dhcp-10-159-238-159.vpn.oracle.com [10.159.238.159]) by phxpaimrmta02.imrmtpd1.prodappphxaev1.oraclevcn.com (PPS) with ESMTP id 3tjws6s78d-1 for ; Tue, 10 Oct 2023 15:07:05 +0000 From: "Aaron Young" To: devel@edk2.groups.io Subject: [edk2-devel] [PATCH 1/1] MdeModulePkg: Optimize BmExpandPartitionDevicePath Date: Tue, 10 Oct 2023 08:06:44 -0700 Message-Id: <20231010150644.37857-1-Aaron.Young@oracle.com> MIME-Version: 1.0 X-Proofpoint-GUID: olkG5cDyUBF1L7uBKtAe-9AwAGC3cWzj X-Proofpoint-ORIG-GUID: olkG5cDyUBF1L7uBKtAe-9AwAGC3cWzj Precedence: Bulk List-Subscribe: List-Help: Sender: devel@edk2.groups.io List-Id: Mailing-List: list devel@edk2.groups.io; contact devel+owner@edk2.groups.io Reply-To: devel@edk2.groups.io,aaron.young@oracle.com List-Unsubscribe-Post: List-Unsubscribe=One-Click List-Unsubscribe: X-Gm-Message-State: Znft29gjKndXLIS2DarymxRvx7686176AA= Content-Transfer-Encoding: quoted-printable X-GND-Status: LEGIT Authentication-Results: spool.mail.gandi.net; dkim=pass header.d=groups.io header.s=20140610 header.b=Rz1vHquq; dmarc=fail reason="SPF not aligned (relaxed), DKIM not aligned (relaxed)" header.from=oracle.com (policy=none); spf=pass (spool.mail.gandi.net: domain of bounce@groups.io designates 66.175.222.108 as permitted sender) smtp.mailfrom=bounce@groups.io Reference: https://github.com/tianocore/edk2/pull/4892 BmExpandPartitionDevicePath is called to expand "short-form" device paths which are commonly used with OS boot options. To expand a device path, it calls EfiBootManagerConnectAll to connect all the possible BlockIo devices in the system to search for a matching partition. However, this is sometimes unnecessary on certain platforms (such as OVMF/QEMU) because the boot devices are previously explicity connected (See: ConnectDevicesFromQemu). EfiBootManagerConnectAll calls are extremely costly in terms of boot time and resources and should be avoided whenever feasible. Therefore optimize BmExpandPartitionDevicePath to first search the existing BlockIo handles for a match. If a match is not found, then fallback to the original code to call EfiBootManagerConnectAll and search again. Thus, this optimization should be extremely low-risk given the fallback to previous behavior. NOTE: The existing optimization in the code to use a "HDDP" variable to save the last matched device paths does not cover the first time a boot option is expanded (i.e. before the "HDDP" is created) nor when the device configuration has changed (resulting in the boot device moving to a different location in the PCI Bus/Dev hierarchy). This new optimization covers both of these cases on requisite platforms which explicity connect boot devices. In our testing on OVMF/QEMU VMs with dozens of configured vnic devices, these extraneous calls to EfiBootManagerConnectAll from BmExpandPartitionDevicePath were found to cause many seconds (or even minutes) of additional VM boot time in some cases - due to the vnics being unnecessarily connected. Cc: Zhichao Gao zhichao.gao@intel.com Cc: Ray Ni ray.ni@intel.com Signed-off-by: Aaron Young --- MdeModulePkg/Library/UefiBootManagerLib/BmBoot.c | 90 ++++++++++++-------- 1 file changed, 56 insertions(+), 34 deletions(-) diff --git a/MdeModulePkg/Library/UefiBootManagerLib/BmBoot.c b/MdeModulePk= g/Library/UefiBootManagerLib/BmBoot.c index c3763c4483c7..7a97f7cdcc6b 100644 --- a/MdeModulePkg/Library/UefiBootManagerLib/BmBoot.c +++ b/MdeModulePkg/Library/UefiBootManagerLib/BmBoot.c @@ -880,6 +880,8 @@ BmExpandPartitionDevicePath ( BOOLEAN NeedAdjust;=0D EFI_DEVICE_PATH_PROTOCOL *Instance;=0D UINTN Size;=0D + BOOLEAN MatchFound;=0D + BOOLEAN ConnectAllAttempted;=0D =0D //=0D // Check if there is prestore 'HDDP' variable.=0D @@ -974,49 +976,69 @@ BmExpandPartitionDevicePath ( // If we get here we fail to find or 'HDDP' not exist, and now we need=0D // to search all devices in the system for a matched partition=0D //=0D - EfiBootManagerConnectAll ();=0D - Status =3D gBS->LocateHandleBuffer (ByProtocol, &gEfiBlockIoProtocolGuid= , NULL, &BlockIoHandleCount, &BlockIoBuffer);=0D - if (EFI_ERROR (Status)) {=0D - BlockIoHandleCount =3D 0;=0D - BlockIoBuffer =3D NULL;=0D - }=0D -=0D - //=0D - // Loop through all the device handles that support the BLOCK_IO Protoco= l=0D - //=0D - for (Index =3D 0; Index < BlockIoHandleCount; Index++) {=0D - BlockIoDevicePath =3D DevicePathFromHandle (BlockIoBuffer[Index]);=0D - if (BlockIoDevicePath =3D=3D NULL) {=0D - continue;=0D + BlockIoBuffer =3D NULL;=0D + MatchFound =3D FALSE;=0D + ConnectAllAttempted =3D FALSE;=0D + do {=0D + if (BlockIoBuffer !=3D NULL) {=0D + FreePool (BlockIoBuffer);=0D }=0D =0D - if (BmMatchPartitionDevicePathNode (BlockIoDevicePath, (HARDDRIVE_DEVI= CE_PATH *)FilePath)) {=0D - //=0D - // Find the matched partition device path=0D - //=0D - TempDevicePath =3D AppendDevicePath (BlockIoDevicePath, NextDevicePa= thNode (FilePath));=0D - FullPath =3D BmGetNextLoadOptionDevicePath (TempDevicePath, NU= LL);=0D - FreePool (TempDevicePath);=0D + Status =3D gBS->LocateHandleBuffer (ByProtocol, &gEfiBlockIoProtocolGu= id, NULL, &BlockIoHandleCount, &BlockIoBuffer);=0D + if (EFI_ERROR (Status)) {=0D + BlockIoHandleCount =3D 0;=0D + BlockIoBuffer =3D NULL;=0D + }=0D =0D - if (FullPath !=3D NULL) {=0D - BmCachePartitionDevicePath (&CachedDevicePath, BlockIoDevicePath);= =0D + //=0D + // Loop through all the device handles that support the BLOCK_IO Proto= col=0D + //=0D + for (Index =3D 0; Index < BlockIoHandleCount; Index++) {=0D + BlockIoDevicePath =3D DevicePathFromHandle (BlockIoBuffer[Index]);=0D + if (BlockIoDevicePath =3D=3D NULL) {=0D + continue;=0D + }=0D =0D + if (BmMatchPartitionDevicePathNode (BlockIoDevicePath, (HARDDRIVE_DE= VICE_PATH *)FilePath)) {=0D //=0D - // Save the matching Device Path so we don't need to do a connect = all next time=0D - // Failing to save only impacts performance next time expanding th= e short-form device path=0D + // Find the matched partition device path=0D //=0D - Status =3D gRT->SetVariable (=0D - L"HDDP",=0D - &mBmHardDriveBootVariableGuid,=0D - EFI_VARIABLE_BOOTSERVICE_ACCESS | EFI_VARIABLE_NON= _VOLATILE,=0D - GetDevicePathSize (CachedDevicePath),=0D - CachedDevicePath=0D - );=0D + TempDevicePath =3D AppendDevicePath (BlockIoDevicePath, NextDevice= PathNode (FilePath));=0D + FullPath =3D BmGetNextLoadOptionDevicePath (TempDevicePath, = NULL);=0D + FreePool (TempDevicePath);=0D +=0D + if (FullPath !=3D NULL) {=0D + BmCachePartitionDevicePath (&CachedDevicePath, BlockIoDevicePath= );=0D =0D - break;=0D + //=0D + // Save the matching Device Path so we don't need to do a connec= t all next time=0D + // Failing to save only impacts performance next time expanding = the short-form device path=0D + //=0D + Status =3D gRT->SetVariable (=0D + L"HDDP",=0D + &mBmHardDriveBootVariableGuid,=0D + EFI_VARIABLE_BOOTSERVICE_ACCESS |=0D + EFI_VARIABLE_NON_VOLATILE,=0D + GetDevicePathSize (CachedDevicePath),=0D + CachedDevicePath=0D + );=0D + MatchFound =3D TRUE;=0D + break;=0D + }=0D }=0D }=0D - }=0D +=0D + //=0D + // If we found a matching BLOCK_IO handle or we've already=0D + // tried a ConnectAll, we are done searching.=0D + //=0D + if (MatchFound || ConnectAllAttempted) {=0D + break;=0D + }=0D +=0D + EfiBootManagerConnectAll ();=0D + ConnectAllAttempted =3D TRUE;=0D + } while (1);=0D =0D if (CachedDevicePath !=3D NULL) {=0D FreePool (CachedDevicePath);=0D --=20 2.39.3 -=-=-=-=-=-=-=-=-=-=-=- Groups.io Links: You receive all messages sent to this group. View/Reply Online (#109496): https://edk2.groups.io/g/devel/message/109496 Mute This Topic: https://groups.io/mt/101876973/7686176 Group Owner: devel+owner@edk2.groups.io Unsubscribe: https://edk2.groups.io/g/devel/unsub [rebecca@openfw.io] -=-=-=-=-=-=-=-=-=-=-=-