From mboxrd@z Thu Jan 1 00:00:00 1970 Received: from NAM10-MW2-obe.outbound.protection.outlook.com (NAM10-MW2-obe.outbound.protection.outlook.com [40.107.94.58]) by mx.groups.io with SMTP id smtpd.web10.8902.1689112156563880869 for ; Tue, 11 Jul 2023 14:49:16 -0700 Authentication-Results: mx.groups.io; dkim=pass header.i=@nvidia.com header.s=selector2 header.b=g188FHrU; spf=permerror, err=parse error for token &{10 18 %{i}._ip.%{h}._ehlo.%{d}._spf.vali.email}: invalid domain name (domain: nvidia.com, ip: 40.107.94.58, mailfrom: jbrasen@nvidia.com) ARC-Seal: i=1; a=rsa-sha256; s=arcselector9901; d=microsoft.com; cv=none; b=AyO+0mn2nTSiU5X+uunPEztqwc0PuWtOfXBZkPacdC02BWO21Q2syp2dS/nqKXt4nF4SbPSzHi6j0YQFOiPFJC6vo/Sc4XWwnskR2ezLuJjDG5P0KiCK8zrqE3ITeuksXsWqb/9awDJ3S38t0Lp2Pf7rsstMbWJ42H1FzCLQi8NN4Ma7Rx9djvWq5CgdW0iIbTLO1p6iApcDGkna88lfziyFr9LSW0ImnUxGGzDf8jz1uAu1ko+md2y19yr5PWyiQ5slzQDPl5cfrVdCpI7icNoqnM6Zpw11gTJqn4gxaHjeG5hb8pN9kxtEFSVMXTq79qe9O+N8T0K188oLeKsCpQ== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=microsoft.com; s=arcselector9901; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-AntiSpam-MessageData-ChunkCount:X-MS-Exchange-AntiSpam-MessageData-0:X-MS-Exchange-AntiSpam-MessageData-1; bh=GrdaB63HegTMMQy1ZibH0GbPYBOWW+lj0bWpke/TsbM=; b=f9Bu1cvlK0qOAINJZPJsGDCynXzyqsI4ohrJzD4hPfQqWoJ5TeoPDKuoCH6wM/E3K+igufHc25dudzC5RxZEa0lFLF/h+wI8MDhJ8WY9Y+5wtLLgANHHNA12WwvWHaa1Uobj4HiQx2NLajpQvp6Ssyzq1jGsO8CHAqsXXZtlZj/IvJuPvOwrJ+ipUpdtNuWx7wQpFeKyptwTX84bPxy0j3ayyuQldukEhgju69uyunH9V/0C8X5AuBwJew87E+nPMbq6tA2B/rNo/7CvP9QnNdjX99R/RGxka1WpO1AQOSgZp9vEpJkC9nq/WQsDrFonl+JRAxbLTBxgQ0UVGZrYyg== ARC-Authentication-Results: i=1; mx.microsoft.com 1; spf=pass smtp.mailfrom=nvidia.com; dmarc=pass action=none header.from=nvidia.com; dkim=pass header.d=nvidia.com; arc=none DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=Nvidia.com; s=selector2; h=From:Date:Subject:Message-ID:Content-Type:MIME-Version:X-MS-Exchange-SenderADCheck; bh=GrdaB63HegTMMQy1ZibH0GbPYBOWW+lj0bWpke/TsbM=; b=g188FHrUojq+fSdW7OROimA7R+WFzZ/k0vCJ47Xay0UiscSip9lziEcTiHaPmMWGh+9hQ+0WY6VT24y29vSGHcJCv+w8ZL4p8fImQ7qQVvYA9j8bjVqloxZXOjwR9NIs4OtYLkyL42fD2upQY7GzBHfDEYU4Vgq2DLxTfrihOvuQVGFbNqoq5Cka9TU8pZZE//ad3OqFMP8olFuhlWvFyA6Cqf3HY8JBJ6IcP0EdneOrJ+MRwIaSI5TkcWLTNn6kyPjlJjd3IUdd+B6fzO2P8nUpFgyVJxU5Lxwm6YG7dpbkLLV5FO14ucrmDyO/aLX0RjuzqGIOLiBwIAG38RlkGg== Received: from DS7PR12MB5789.namprd12.prod.outlook.com (2603:10b6:8:74::21) by SJ2PR12MB8181.namprd12.prod.outlook.com (2603:10b6:a03:4f6::18) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384) id 15.20.6565.31; Tue, 11 Jul 2023 21:49:13 +0000 Received: from DS7PR12MB5789.namprd12.prod.outlook.com ([fe80::a5f2:5641:7bf8:84a4]) by DS7PR12MB5789.namprd12.prod.outlook.com ([fe80::a5f2:5641:7bf8:84a4%4]) with mapi id 15.20.6565.028; Tue, 11 Jul 2023 21:49:13 +0000 From: "Jeff Brasen" To: "Ni, Ray" , "devel@edk2.groups.io" CC: "Wang, Jian J" , "Gao, Liming" , "Wu, Hao A" Subject: Re: [PATCH] MdeModulePkg/PciHostBridge: Add support for driver binding Thread-Topic: [PATCH] MdeModulePkg/PciHostBridge: Add support for driver binding Thread-Index: AQHZqsva1IIzn7T6d0y/htmTfHXEKq+in76AgAANIdCAAAv4gIAAx2jggBGsc0A= Date: Tue, 11 Jul 2023 21:49:13 +0000 Message-ID: References: <6add8a5bbb40cd1602acc09345496043ac47fc3e.1688071965.git.jbrasen@nvidia.com> In-Reply-To: Accept-Language: en-US X-MS-Has-Attach: X-MS-TNEF-Correlator: authentication-results: dkim=none (message not signed) header.d=none;dmarc=none action=none header.from=nvidia.com; x-ms-publictraffictype: Email x-ms-traffictypediagnostic: DS7PR12MB5789:EE_|SJ2PR12MB8181:EE_ x-ms-office365-filtering-correlation-id: 64e453ef-8b3c-4e91-56da-08db8258aa8a x-ms-exchange-senderadcheck: 1 x-ms-exchange-antispam-relay: 0 x-microsoft-antispam: BCL:0; x-microsoft-antispam-message-info: 6jHJMljaduJZUcy17cnd/hiEEcqFyCyoivDn1GhjnEy5gitgXTGY2EfIaD0/ThPQPBQzHqVp6JWdxziZW8Nl76cSxO9IcF+7NNWIMlqQnsckzQzSqNWpnn+WpV5a9JcjCle9R5EmdaXs7BSw6FBxRtFtvtqhdVxQznCAIJc7Or42D/ZvUCh2+6nMAt4qNUiblvVYBflPftNJV6DhHuq2ISOSGyL76dMxeVo2szmgORYHmJy5TICLrrh+PNOUk9Ua7OcgyP0JiFtg4fVDzXW0jHR2UalIF8h1fnKkE/3cplzTedPLD1gRynOZsL8AkCw95spdTcjeSEnLAlpOV9ZDwmjNhLkZ8zebZYLwZXVXPaJmnV8O5XDvkFX6SdekZGC7jb/MCc35dUjEk6coxGbb/L9EqoZfNK3V0QNS+JdT0zotZ8KIFs85rJe44AUHs8AtkLauyCqhyPJOGp31gzXOn+PBbkHzvby+WRnOiTQiX2Plh9vBEfnISYpaaVpQEgJWRyoGp+CuTsfWeOTg557jKJtHGet+6uHVs7NQiWIvgnAaGPc0mtfjmusthqq7swrPTu+cRZWYGn0j5++n3JdmAtmIT82Fcjh0oks1kvqJvC13e5PwB9l6iFZZqmd1SdNx7RlODdsZrDVF5lkc9lmrhSYGD3+R6PV4KlZYtH3dPDM= x-forefront-antispam-report: CIP:255.255.255.255;CTRY:;LANG:en;SCL:1;SRV:;IPV:NLI;SFV:NSPM;H:DS7PR12MB5789.namprd12.prod.outlook.com;PTR:;CAT:NONE;SFS:(13230028)(4636009)(376002)(366004)(39860400002)(396003)(346002)(136003)(451199021)(5660300002)(52536014)(8676002)(64756008)(66476007)(66446008)(66556008)(8936002)(76116006)(2906002)(316002)(4326008)(66946007)(71200400001)(7696005)(19627235002)(9686003)(54906003)(53546011)(26005)(186003)(83380400001)(6506007)(30864003)(41300700001)(66899021)(38100700002)(478600001)(110136005)(122000001)(38070700005)(33656002)(55016003)(86362001)(579004)(559001)(44824005)(14943795004);DIR:OUT;SFP:1101; x-ms-exchange-antispam-messagedata-chunkcount: 1 x-ms-exchange-antispam-messagedata-0: =?us-ascii?Q?wlGMqt38X+OqfdK8bbvA9aKwQEnhfN11XaiqmiV4vHxHw9D7Ejh8v1/mgv+I?= =?us-ascii?Q?od9sTVlxt3cO9+v6M0R9AtX30qR062yMqfNmagdNFQ1JT87i+0L+OEJFxZ+o?= =?us-ascii?Q?BoDEOWpsYx/M0X24RSBLjmOvxsoB1MHxt34PN6cIhSGLLwmK61IAgMXAIo7v?= =?us-ascii?Q?HE8cY2a8deEbueK8VfU4qOniEHs4kemQ8Kvnc9qbtzBmlfyoTgcH9CmAapM5?= =?us-ascii?Q?7QasG6/xAkBH1iQsjbkh3d7tzZ7zGvV23hXJDainzrUlYCifTdKbWwoN+JbC?= =?us-ascii?Q?DLVpocO4XyXYK8EEF4lf4+QpTETsdjItI84R/hQo4TSxUp3W3nA7SdbmVysT?= =?us-ascii?Q?lSf0FMYfe5YzU3HhZMzJQm2ShGgsYGzLWxGbDQZhWz69cLcCNPIKTCG9nSXm?= =?us-ascii?Q?6LuPJRo9I5WOzhWJGgDQuVKHrVYmTZ7YBei5zP/WRJlHd+B+BoY6K9DwibFe?= =?us-ascii?Q?zco53WoEUvOSk+tlFH1Iua4ZFYn8DCJY/mVnUUTBEh8Ah74pfXTWrs/4gOe8?= =?us-ascii?Q?4Ua25mwG43wqu9ba1MW756dEXSWXpckLiffcjD2LSZmJu6+68/dO/agN7QJX?= =?us-ascii?Q?Mroz2DZcuR2TTSwCBl+26+HAe3mMfBloL32Q7HUhTQxzZs8DCx6VpIEFVjOt?= =?us-ascii?Q?onHJDtbTYiCsZycoJjeSqpKBQGXby7bMzqnRIPi9dCo+Q/UpWZdl4y+wpCPW?= =?us-ascii?Q?FD6DH77w4+vCAoaOSs2PyAo5yJFW46h91CtryxyJdUbzXPoXvcLj1CUAD5yG?= =?us-ascii?Q?bcl2nO9Ze+jY3/fLBl/cSqa+r6xqtmIIlh3hC4uii30SBiGvoX8YUOfVLNNl?= =?us-ascii?Q?UV50hzEl1APgFarNNb20fSoXRPWBpIYZwb3a/pCJwinXxQyZCCCQmHriR9J4?= =?us-ascii?Q?OjeL8MNLLFrfwEJXRq83OjjsDoETrNLgwRLwivkWtNfaM4mbQZpMi7YFoI90?= =?us-ascii?Q?TThEFhLlDJ8FodE59MrTQzEdvj0I2J0yd230AVsOlMi71/J+pHXzvn8zuxsy?= =?us-ascii?Q?bBVkg8DmsUnkIRBOgR54DE3YKseVCtU/74f2plCxzLm5AvoOqfRgQIIaQMon?= =?us-ascii?Q?fBQahjSdi5suHOM7SPRLewz0+qlC9O+d9FPi70E47CrbdmhLVo7H+V9I95qg?= =?us-ascii?Q?/egK1jEXYYhEzKJVhdLo2DkSIyjxuajn1163qNaCdZLXjWKVcBSy06eIxupx?= =?us-ascii?Q?qkK3UOazQ0w5yxBgm5Vvo46GYc9tb/PboyJ0zthkxNyAttzp0ctDE1ZWYttE?= =?us-ascii?Q?LW0ZLYskcic+14y3rRTpYxOK58b1iHnNZOjFoa7lvKI9p+yhLSfcf7KTyIZr?= =?us-ascii?Q?4PJagYA7ZBWABk5zayAiq5nE2QpHVmnMY455bDMTkn5hRBcp5fEXtDgCEqA4?= =?us-ascii?Q?+BoHNsNfCqXdfG6i2FpqlPboIvdWcsT01vHlAdXeMzlhqQ6cEWtnATH4lTI/?= =?us-ascii?Q?nULXnBr14KXqAlzY/UXymqThOnZFx5cUvzKGUQF0tW/s7RdCR+oLuLp8IaF8?= =?us-ascii?Q?X+5wEb77FcmvjQB35ZrP+luem4gESe58/K+i+yQEZX67Goxv3sFjoEoK8p1D?= =?us-ascii?Q?DViprEaxj1NyNaBxJ+5O4lMZiM0+/rgSQlwW2kzX?= MIME-Version: 1.0 X-OriginatorOrg: Nvidia.com X-MS-Exchange-CrossTenant-AuthAs: Internal X-MS-Exchange-CrossTenant-AuthSource: DS7PR12MB5789.namprd12.prod.outlook.com X-MS-Exchange-CrossTenant-Network-Message-Id: 64e453ef-8b3c-4e91-56da-08db8258aa8a X-MS-Exchange-CrossTenant-originalarrivaltime: 11 Jul 2023 21:49:13.2546 (UTC) X-MS-Exchange-CrossTenant-fromentityheader: Hosted X-MS-Exchange-CrossTenant-id: 43083d15-7273-40c1-b7db-39efd9ccc17a X-MS-Exchange-CrossTenant-mailboxtype: HOSTED X-MS-Exchange-CrossTenant-userprincipalname: g/++C3VEjFTtXdUk6Gxh9sUvZKQiyrjERpf+MR9/OFIE130+DH4HoI+kDuCrgxHMco1kIL9yLFCwsEq/igQNgQ== X-MS-Exchange-Transport-CrossTenantHeadersStamped: SJ2PR12MB8181 Content-Language: en-US Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: quoted-printable Ray, Would you prefer this sort of use would be done by an extra dispatch afte= r the wait for everything being completed and the connect controller call i= n BDS as opposed to the driver binding approach? Basically using a depex o= n the library as we are currently doing.=20 -Jeff > -----Original Message----- > From: Jeff Brasen > Sent: Friday, June 30, 2023 9:57 AM > To: Ni, Ray ; devel@edk2.groups.io > Cc: Wang, Jian J ; Gao, Liming > ; Wu, Hao A > Subject: RE: [PATCH] MdeModulePkg/PciHostBridge: Add support for driver > binding >=20 >=20 >=20 > > -----Original Message----- > > From: Ni, Ray > > Sent: Thursday, June 29, 2023 9:59 PM > > To: Jeff Brasen ; devel@edk2.groups.io > > Cc: Wang, Jian J ; Gao, Liming > > ; Wu, Hao A > > Subject: RE: [PATCH] MdeModulePkg/PciHostBridge: Add support for > > driver binding > > > > External email: Use caution opening links or attachments > > > > > > > -----Original Message----- > > > From: Jeff Brasen > > > Sent: Friday, June 30, 2023 11:21 AM > > > To: Ni, Ray ; devel@edk2.groups.io > > > Cc: Wang, Jian J ; Gao, Liming > > > ; Wu, Hao A > > > Subject: RE: [PATCH] MdeModulePkg/PciHostBridge: Add support for > > > driver binding > > > > > > Not sure why the patch failed to apply I'll see if there is > > > something wrong with my gitconfig tomorrow. The path you suggested > > > below is exactly what our current implementation does. However, I am > > > trying to make our pcie controller driver do async initialization so > > > that using a depex is less ideal as we may have to postpone driver > > > load to after end of dxe instead of just the connection. It seemed > > > that a driver binding > > type approach was a good approach for this. > > > > I am curious how the pcie root (root complex) initialization is done > > in async way? > > Does it use a timer callback to poll the initialization status every > > certain interval? > > >=20 > [JB] That is correct, we use a timer when we expect sleeps or polling loo= ps. >=20 > > On the other hand, even you make PciHostBridge as a UEFI driver-model > > driver, you still require some code to initiate the > > "ConnectController()". How is that done? > > > > Comparing the two paths (today's =3D my proposal, new way =3D your patc= h), > > both require some code to explicitly call "ConnectController()". > > >=20 > [JB] We have a sync point in BDS prior to the ConnectController call that= is > made. I could put that and a dispatch call prior to EndOfDxe signal but w= as > hoping to not trigger any of the driver seen but not loaded debug message= s > from the main dispatch loop if possible as that can be a useful message t= o > trigger something might be wrong. >=20 > > > > > > On a less important implementation if the pieces that live under the > > > library are driver binding we have to reject any stop requests as > > > there is no driver linkage between the two layers. > > > > In x86, root complex (pcie root) is almost the root of all > > peripherals. I cannot see a value to Stop () the pcie root. > > If you check the PciBus implementation, it supports Stop() but the > > Stop() only succeeds when all upper layer drivers succeed to Stop(). > > (usually it's not the > > case.) And even PciBus.Stop() succeeds, the resource(MMIO/IO/BUS) > > allocation is not un-done. It's only the PciIo handles that are > > destroyed in software level. > > >=20 > [JB] Yeah, not allowing stop to work on this isn't a big deal (and what w= e > currently have implemented) but it was something we noticed a while ago i= s > that we couldn't implement this even if we wanted to as there was no way = to > stop the host bridge driver. >=20 > > Thanks, > > Ray > > > > > > > > > > -Jeff > > > > > > > > > -----Original Message----- > > > From: Ni, Ray > > > Sent: Thursday, June 29, 2023 8:29 PM > > > To: Jeff Brasen ; devel@edk2.groups.io > > > Cc: Wang, Jian J ; Gao, Liming > > > ; Wu, Hao A > > > Subject: RE: [PATCH] MdeModulePkg/PciHostBridge: Add support for > > > driver binding > > > > > > External email: Use caution opening links or attachments > > > > > > > > > I failed to apply the patch in my local tree. > > > > > > It seems you invented a new EdkiiRootBridgeIo protocol and a certain > > > proprietary driver would produce this protocol instance. > > > Then the open source PciHostBridge driver starts on that. > > > > > > Then, why not implement your own PciHostBridgeLib and let it depends > > > on some "AllRootBridgeIoInformationIsReady" protocol. > > > So that the PciHostBridge driver could still call PciHostBridgeLib > > > and all your implementation in this patch can be in that lib. > > > > > > Thanks, > > > Ray > > > > > > > -----Original Message----- > > > > From: Jeff Brasen > > > > Sent: Friday, June 30, 2023 4:54 AM > > > > To: devel@edk2.groups.io > > > > Cc: Wang, Jian J ; Gao, Liming > > > > ; Wu, Hao A ; Ni, > > > > Ray ; Jeff Brasen > > > > Subject: [PATCH] MdeModulePkg/PciHostBridge: Add support for > > > > driver binding > > > > > > > > If the platform does not support any PCIe devices using the > > > > library > > > > > > > > method allow devices to connect to host bridge via driver binding. > > > > > > > > > > > > > > > > Signed-off-by: Jeff Brasen > > > > > > > > --- > > > > > > > > .../Bus/Pci/PciHostBridgeDxe/PciHostBridge.c | 649 > > > > ++++++++++++++---- > > > > > > > > .../Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf | 1 + > > > > > > > > .../Bus/Pci/PciHostBridgeDxe/PciRootBridge.h | 13 + > > > > > > > > .../Pci/PciHostBridgeDxe/PciRootBridgeIo.c | 24 + > > > > > > > > MdeModulePkg/MdeModulePkg.dec | 4 + > > > > > > > > 5 files changed, 562 insertions(+), 129 deletions(-) > > > > > > > > > > > > > > > > diff --git a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridge.c > > > > b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridge.c > > > > > > > > index d573e532ba..506c6660ae 100644 > > > > > > > > --- a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridge.c > > > > > > > > +++ b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridge.c > > > > > > > > @@ -422,167 +422,320 @@ IoMmuProtocolCallback ( > > > > > > > > } > > > > > > > > > > > > > > > > /** > > > > > > > > + PCI Root Bridge Memory setup. > > > > > > > > > > > > > > > > - Entry point of this driver. > > > > > > > > + @param RootBridge Root Bridge instance. > > > > > > > > > > > > > > > > - @param ImageHandle Image handle of this driver. > > > > > > > > - @param SystemTable Pointer to standard EFI system table. > > > > > > > > - > > > > > > > > - @retval EFI_SUCCESS Succeed. > > > > > > > > - @retval EFI_DEVICE_ERROR Fail to install PCI_ROOT_BRIDGE_IO > > protocol. > > > > > > > > + @retval EFI_SUCCESS Memory was setup correctly > > > > > > > > + @retval others Error in setup > > > > > > > > > > > > > > > > **/ > > > > > > > > EFI_STATUS > > > > > > > > EFIAPI > > > > > > > > -InitializePciHostBridge ( > > > > > > > > - IN EFI_HANDLE ImageHandle, > > > > > > > > - IN EFI_SYSTEM_TABLE *SystemTable > > > > > > > > +PciRootBridgeMemorySetup ( > > > > > > > > + IN PCI_ROOT_BRIDGE *RootBridge > > > > > > > > ) > > > > > > > > { > > > > > > > > EFI_STATUS Status; > > > > > > > > - PCI_HOST_BRIDGE_INSTANCE *HostBridge; > > > > > > > > - PCI_ROOT_BRIDGE_INSTANCE *RootBridge; > > > > > > > > - PCI_ROOT_BRIDGE *RootBridges; > > > > > > > > - UINTN RootBridgeCount; > > > > > > > > - UINTN Index; > > > > > > > > + UINT64 HostAddress; > > > > > > > > PCI_ROOT_BRIDGE_APERTURE *MemApertures[4]; > > > > > > > > UINTN MemApertureIndex; > > > > > > > > - BOOLEAN ResourceAssigned; > > > > > > > > - LIST_ENTRY *Link; > > > > > > > > - UINT64 HostAddress; > > > > > > > > > > > > > > > > - RootBridges =3D PciHostBridgeGetRootBridges (&RootBridgeCount); > > > > > > > > - if ((RootBridges =3D=3D NULL) || (RootBridgeCount =3D=3D 0)) { > > > > > > > > - return EFI_UNSUPPORTED; > > > > > > > > - } > > > > > > > > - > > > > > > > > - Status =3D gBS->LocateProtocol (&gEfiCpuIo2ProtocolGuid, NULL, > > > > (VOID **)&mCpuIo); > > > > > > > > - ASSERT_EFI_ERROR (Status); > > > > > > > > - > > > > > > > > - // > > > > > > > > - // Most systems in the world including complex servers have > > > > only one Host Bridge. > > > > > > > > - // > > > > > > > > - HostBridge =3D AllocateZeroPool (sizeof > > > > (PCI_HOST_BRIDGE_INSTANCE)); > > > > > > > > - ASSERT (HostBridge !=3D NULL); > > > > > > > > - > > > > > > > > - HostBridge->Signature =3D PCI_HOST_BRIDGE_SIGNATURE; > > > > > > > > - HostBridge->CanRestarted =3D TRUE; > > > > > > > > - InitializeListHead (&HostBridge->RootBridges); > > > > > > > > - ResourceAssigned =3D FALSE; > > > > > > > > - > > > > > > > > - // > > > > > > > > - // Create Root Bridge Device Handle in this Host Bridge > > > > > > > > - // > > > > > > > > - for (Index =3D 0; Index < RootBridgeCount; Index++) { > > > > > > > > + if (RootBridge->Io.Base <=3D RootBridge->Io.Limit) { > > > > > > > > // > > > > > > > > - // Create Root Bridge Handle Instance > > > > > > > > + // Base and Limit in PCI_ROOT_BRIDGE_APERTURE are device addre= ss. > > > > > > > > + // For GCD resource manipulation, we need to use host address. > > > > > > > > // > > > > > > > > - RootBridge =3D CreateRootBridge (&RootBridges[Index]); > > > > > > > > - ASSERT (RootBridge !=3D NULL); > > > > > > > > - if (RootBridge =3D=3D NULL) { > > > > > > > > - continue; > > > > > > > > + HostAddress =3D TO_HOST_ADDRESS ( > > > > > > > > + RootBridge->Io.Base, > > > > > > > > + RootBridge->Io.Translation > > > > > > > > + ); > > > > > > > > + > > > > > > > > + Status =3D AddIoSpace ( > > > > > > > > + HostAddress, > > > > > > > > + RootBridge->Io.Limit - RootBridge->Io.Base + 1 > > > > > > > > + ); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > } > > > > > > > > > > > > > > > > - // > > > > > > > > - // Make sure all root bridges share the same ResourceAssigned = value. > > > > > > > > - // > > > > > > > > - if (Index =3D=3D 0) { > > > > > > > > - ResourceAssigned =3D RootBridges[Index].ResourceAssigned; > > > > > > > > - } else { > > > > > > > > - ASSERT (ResourceAssigned =3D=3D > RootBridges[Index].ResourceAssigned); > > > > > > > > + if (RootBridge->ResourceAssigned) { > > > > > > > > + Status =3D gDS->AllocateIoSpace ( > > > > > > > > + EfiGcdAllocateAddress, > > > > > > > > + EfiGcdIoTypeIo, > > > > > > > > + 0, > > > > > > > > + RootBridge->Io.Limit - RootBridge->Io.Base > > > > + + 1, > > > > > > > > + &HostAddress, > > > > > > > > + gImageHandle, > > > > > > > > + NULL > > > > > > > > + ); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > } > > > > > > > > + } > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Add all the Mem/PMem aperture to GCD > > > > > > > > + // Mem/PMem shouldn't overlap with each other > > > > > > > > + // Root bridge which needs to combine MEM and PMEM should only > > > > + report > > > > > > > > + // the MEM aperture in Mem > > > > > > > > + // > > > > > > > > + MemApertures[0] =3D &RootBridge->Mem; > > > > > > > > + MemApertures[1] =3D &RootBridge->MemAbove4G; > > > > > > > > + MemApertures[2] =3D &RootBridge->PMem; > > > > > > > > + MemApertures[3] =3D &RootBridge->PMemAbove4G; > > > > > > > > > > > > > > > > - if (RootBridges[Index].Io.Base <=3D RootBridges[Index].Io.Limi= t) { > > > > > > > > + for (MemApertureIndex =3D 0; MemApertureIndex < ARRAY_SIZE > > > > (MemApertures); MemApertureIndex++) { > > > > > > > > + if (MemApertures[MemApertureIndex]->Base <=3D > > > > MemApertures[MemApertureIndex]->Limit) { > > > > > > > > // > > > > > > > > // Base and Limit in PCI_ROOT_BRIDGE_APERTURE are device > address. > > > > > > > > // For GCD resource manipulation, we need to use host addres= s. > > > > > > > > // > > > > > > > > HostAddress =3D TO_HOST_ADDRESS ( > > > > > > > > - RootBridges[Index].Io.Base, > > > > > > > > - RootBridges[Index].Io.Translation > > > > > > > > + MemApertures[MemApertureIndex]->Base, > > > > > > > > + MemApertures[MemApertureIndex]->Translation > > > > > > > > ); > > > > > > > > - > > > > > > > > - Status =3D AddIoSpace ( > > > > > > > > + Status =3D AddMemoryMappedIoSpace ( > > > > > > > > HostAddress, > > > > > > > > - RootBridges[Index].Io.Limit - RootBridges[Index].= Io.Base + 1 > > > > > > > > + MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > + EFI_MEMORY_UC > > > > > > > > ); > > > > > > > > ASSERT_EFI_ERROR (Status); > > > > > > > > - if (ResourceAssigned) { > > > > > > > > - Status =3D gDS->AllocateIoSpace ( > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + > > > > > > > > + Status =3D gDS->SetMemorySpaceAttributes ( > > > > > > > > + HostAddress, > > > > > > > > + MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > + EFI_MEMORY_UC > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + DEBUG ((DEBUG_WARN, "PciHostBridge driver failed to set > > > > EFI_MEMORY_UC to MMIO aperture - %r.\n", Status)); > > > > > > > > + } > > > > > > > > + > > > > > > > > + if (RootBridge->ResourceAssigned) { > > > > > > > > + Status =3D gDS->AllocateMemorySpace ( > > > > > > > > EfiGcdAllocateAddress, > > > > > > > > - EfiGcdIoTypeIo, > > > > > > > > + EfiGcdMemoryTypeMemoryMappedIo, > > > > > > > > 0, > > > > > > > > - RootBridges[Index].Io.Limit - RootBridges[= Index].Io.Base + > 1, > > > > > > > > + MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > &HostAddress, > > > > > > > > gImageHandle, > > > > > > > > NULL > > > > > > > > ); > > > > > > > > ASSERT_EFI_ERROR (Status); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > } > > > > > > > > } > > > > > > > > + } > > > > > > > > + > > > > > > > > + return EFI_SUCCESS; > > > > > > > > +} > > > > > > > > > > > > > > > > +/** > > > > > > > > + PCI Root Bridge Memory free. > > > > > > > > + > > > > > > > > + @param RootBridge Root Bridge instance. > > > > > > > > + > > > > > > > > + @retval EFI_SUCCESS Memory was setup correctly > > > > > > > > + @retval others Error in setup > > > > > > > > + > > > > > > > > +**/ > > > > > > > > +EFI_STATUS > > > > > > > > +EFIAPI > > > > > > > > +PciRootBridgeMemoryFree ( > > > > > > > > + IN PCI_ROOT_BRIDGE *RootBridge > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + EFI_STATUS Status; > > > > > > > > + UINT64 HostAddress; > > > > > > > > + PCI_ROOT_BRIDGE_APERTURE *MemApertures[4]; > > > > > > > > + UINTN MemApertureIndex; > > > > > > > > + > > > > > > > > + if (RootBridge->Io.Base <=3D RootBridge->Io.Limit) { > > > > > > > > // > > > > > > > > - // Add all the Mem/PMem aperture to GCD > > > > > > > > - // Mem/PMem shouldn't overlap with each other > > > > > > > > - // Root bridge which needs to combine MEM and PMEM should only > > report > > > > > > > > - // the MEM aperture in Mem > > > > > > > > + // Base and Limit in PCI_ROOT_BRIDGE_APERTURE are device addre= ss. > > > > > > > > + // For GCD resource manipulation, we need to use host address. > > > > > > > > // > > > > > > > > - MemApertures[0] =3D &RootBridges[Index].Mem; > > > > > > > > - MemApertures[1] =3D &RootBridges[Index].MemAbove4G; > > > > > > > > - MemApertures[2] =3D &RootBridges[Index].PMem; > > > > > > > > - MemApertures[3] =3D &RootBridges[Index].PMemAbove4G; > > > > > > > > - > > > > > > > > - for (MemApertureIndex =3D 0; MemApertureIndex < ARRAY_SIZE > > > > (MemApertures); MemApertureIndex++) { > > > > > > > > - if (MemApertures[MemApertureIndex]->Base <=3D > > > > MemApertures[MemApertureIndex]->Limit) { > > > > > > > > - // > > > > > > > > - // Base and Limit in PCI_ROOT_BRIDGE_APERTURE are device > address. > > > > > > > > - // For GCD resource manipulation, we need to use host addr= ess. > > > > > > > > - // > > > > > > > > - HostAddress =3D TO_HOST_ADDRESS ( > > > > > > > > - MemApertures[MemApertureIndex]->Base, > > > > > > > > - MemApertures[MemApertureIndex]->Translatio= n > > > > > > > > - ); > > > > > > > > - Status =3D AddMemoryMappedIoSpace ( > > > > > > > > - HostAddress, > > > > > > > > - MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > - EFI_MEMORY_UC > > > > > > > > - ); > > > > > > > > + HostAddress =3D TO_HOST_ADDRESS ( > > > > > > > > + RootBridge->Io.Base, > > > > > > > > + RootBridge->Io.Translation > > > > > > > > + ); > > > > > > > > + > > > > > > > > + if (RootBridge->ResourceAssigned) { > > > > > > > > + Status =3D gDS->FreeIoSpace (HostAddress, > > > > + RootBridge->Io.Limit > > > > + - > > > > + RootBridge- > > > > >Io.Base + 1); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + } > > > > > > > > + } > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Add all the Mem/PMem aperture to GCD > > > > > > > > + // Mem/PMem shouldn't overlap with each other > > > > > > > > + // Root bridge which needs to combine MEM and PMEM should only > > > > + report > > > > > > > > + // the MEM aperture in Mem > > > > > > > > + // > > > > > > > > + MemApertures[0] =3D &RootBridge->Mem; > > > > > > > > + MemApertures[1] =3D &RootBridge->MemAbove4G; > > > > > > > > + MemApertures[2] =3D &RootBridge->PMem; > > > > > > > > + MemApertures[3] =3D &RootBridge->PMemAbove4G; > > > > > > > > + > > > > > > > > + for (MemApertureIndex =3D 0; MemApertureIndex < ARRAY_SIZE > > > > (MemApertures); MemApertureIndex++) { > > > > > > > > + if (MemApertures[MemApertureIndex]->Base <=3D > > > > MemApertures[MemApertureIndex]->Limit) { > > > > > > > > + // > > > > > > > > + // Base and Limit in PCI_ROOT_BRIDGE_APERTURE are device > address. > > > > > > > > + // For GCD resource manipulation, we need to use host addres= s. > > > > > > > > + // > > > > > > > > + HostAddress =3D TO_HOST_ADDRESS ( > > > > > > > > + MemApertures[MemApertureIndex]->Base, > > > > > > > > + MemApertures[MemApertureIndex]->Translation > > > > > > > > + ); > > > > > > > > + if (RootBridge->ResourceAssigned) { > > > > > > > > + Status =3D gDS->FreeMemorySpace (HostAddress, > > > > + RootBridge->Io.Limit - > > > > RootBridge->Io.Base + 1); > > > > > > > > ASSERT_EFI_ERROR (Status); > > > > > > > > - Status =3D gDS->SetMemorySpaceAttributes ( > > > > > > > > - HostAddress, > > > > > > > > - MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > - EFI_MEMORY_UC > > > > > > > > - ); > > > > > > > > if (EFI_ERROR (Status)) { > > > > > > > > - DEBUG ((DEBUG_WARN, "PciHostBridge driver failed to set > > > > EFI_MEMORY_UC to MMIO aperture - %r.\n", Status)); > > > > > > > > - } > > > > > > > > - > > > > > > > > - if (ResourceAssigned) { > > > > > > > > - Status =3D gDS->AllocateMemorySpace ( > > > > > > > > - EfiGcdAllocateAddress, > > > > > > > > - EfiGcdMemoryTypeMemoryMappedIo, > > > > > > > > - 0, > > > > > > > > - MemApertures[MemApertureIndex]->Limit - > > > > MemApertures[MemApertureIndex]->Base + 1, > > > > > > > > - &HostAddress, > > > > > > > > - gImageHandle, > > > > > > > > - NULL > > > > > > > > - ); > > > > > > > > - ASSERT_EFI_ERROR (Status); > > > > > > > > + return Status; > > > > > > > > } > > > > > > > > } > > > > > > > > } > > > > > > > > + } > > > > > > > > > > > > > > > > - // > > > > > > > > - // Insert Root Bridge Handle Instance > > > > > > > > - // > > > > > > > > - InsertTailList (&HostBridge->RootBridges, &RootBridge->Link); > > > > > > > > + return EFI_SUCCESS; > > > > > > > > +} > > > > > > > > + > > > > > > > > +/** > > > > > > > > + Test to see if this driver supports ControllerHandle. Any > > > > + ControllerHandle > > > > > > > > + than contains a gEdkiiPciHostBridgeProtocolGuid protocol can be > > supported. > > > > > > > > + > > > > > > > > + @param This Protocol instance pointer. > > > > > > > > + @param Controller Handle of device to test. > > > > > > > > + @param RemainingDevicePath Optional parameter use to pick a > > > > + specific child > > > > > > > > + device to start. > > > > > > > > + > > > > > > > > + @retval EFI_SUCCESS This driver supports this device. > > > > > > > > + @retval EFI_ALREADY_STARTED This driver is already running on > > > > + this > > device. > > > > > > > > + @retval other This driver does not support this de= vice. > > > > > > > > + > > > > > > > > +**/ > > > > > > > > +EFI_STATUS > > > > > > > > +EFIAPI > > > > > > > > +PciHostBrigeDriverBindingSupported ( > > > > > > > > + IN EFI_DRIVER_BINDING_PROTOCOL *This, > > > > > > > > + IN EFI_HANDLE Controller, > > > > > > > > + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + EFI_STATUS Status; > > > > > > > > + PCI_ROOT_BRIDGE *PciRootBridge; > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Check if Pci Host Bridge protocol is installed by platform > > > > > > > > + // > > > > > > > > + Status =3D gBS->OpenProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + (VOID **)&PciRootBridge, > > > > > > > > + This->DriverBindingHandle, > > > > > > > > + Controller, > > > > > > > > + EFI_OPEN_PROTOCOL_BY_DRIVER > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > } > > > > > > > > > > > > > > > > // > > > > > > > > - // When resources were assigned, it's not needed to expose > > > > > > > > - // PciHostBridgeResourceAllocation protocol. > > > > > > > > + // Close the protocol used to perform the supported test > > > > > > > > + // > > > > > > > > + gBS->CloseProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + This->DriverBindingHandle, > > > > > > > > + Controller > > > > > > > > + ); > > > > > > > > + > > > > > > > > + return EFI_SUCCESS; > > > > > > > > +} > > > > > > > > + > > > > > > > > +/** > > > > > > > > + Start this driver on ControllerHandle and enumerate Pci bus and > > > > + start > > > > > > > > + all device under PCI bus. > > > > > > > > + > > > > > > > > + @param This Protocol instance pointer. > > > > > > > > + @param Controller Handle of device to bind driver to. > > > > > > > > + @param RemainingDevicePath Optional parameter use to pick a > > > > + specific child > > > > > > > > + device to start. > > > > > > > > + > > > > > > > > + @retval EFI_SUCCESS This driver is added to ControllerH= andle. > > > > > > > > + @retval EFI_ALREADY_STARTED This driver is already running on > > > > ControllerHandle. > > > > > > > > + @retval other This driver does not support this d= evice. > > > > > > > > + > > > > > > > > +**/ > > > > > > > > +EFI_STATUS > > > > > > > > +EFIAPI > > > > > > > > +PciHostBrigeDriverBindingStart ( > > > > > > > > + IN EFI_DRIVER_BINDING_PROTOCOL *This, > > > > > > > > + IN EFI_HANDLE Controller, > > > > > > > > + IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + EFI_STATUS Status; > > > > > > > > + PCI_ROOT_BRIDGE *PciRootBridge; > > > > > > > > + PCI_ROOT_BRIDGE_INSTANCE *RootBridge; > > > > > > > > + PCI_HOST_BRIDGE_INSTANCE *HostBridge; > > > > > > > > + BOOLEAN MemorySetupDone; > > > > > > > > + > > > > > > > > + MemorySetupDone =3D FALSE; > > > > > > > > + // > > > > > > > > + // Check if Pci Host Bridge protocol is installed by platform > > > > > > > > // > > > > > > > > - if (!ResourceAssigned) { > > > > > > > > + Status =3D gBS->OpenProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + (VOID **)&PciRootBridge, > > > > > > > > + This->DriverBindingHandle, > > > > > > > > + Controller, > > > > > > > > + EFI_OPEN_PROTOCOL_BY_DRIVER > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + > > > > > > > > + RootBridge =3D CreateRootBridge (PciRootBridge); > > > > > > > > + ASSERT (RootBridge !=3D NULL); > > > > > > > > + if (RootBridge =3D=3D NULL) { > > > > > > > > + Status =3D EFI_DEVICE_ERROR; > > > > > > > > + goto ErrorExit; > > > > > > > > + } > > > > > > > > + > > > > > > > > + Status =3D PciRootBridgeMemorySetup (PciRootBridge); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + goto ErrorExit; > > > > > > > > + } > > > > > > > > + > > > > > > > > + MemorySetupDone =3D TRUE; > > > > > > > > + > > > > > > > > + if (!PciRootBridge->ResourceAssigned) { > > > > > > > > + // Create host bridge > > > > > > > > + HostBridge =3D AllocateZeroPool (sizeof > > > > + (PCI_HOST_BRIDGE_INSTANCE)); > > > > > > > > + ASSERT (HostBridge !=3D NULL); > > > > > > > > + if (HostBridge =3D=3D NULL) { > > > > > > > > + Status =3D EFI_OUT_OF_RESOURCES; > > > > > > > > + goto ErrorExit; > > > > > > > > + } > > > > > > > > + > > > > > > > > + HostBridge->Handle =3D 0; > > > > > > > > + HostBridge->Signature =3D PCI_HOST_BRIDGE_SIGNATURE; > > > > > > > > + HostBridge->CanRestarted =3D TRUE; > > > > > > > > + InitializeListHead (&HostBridge->RootBridges); > > > > > > > > + > > > > > > > > HostBridge->ResAlloc.NotifyPhase =3D NotifyPhase; > > > > > > > > HostBridge->ResAlloc.GetNextRootBridge =3D GetNextRootBridg= e; > > > > > > > > HostBridge->ResAlloc.GetAllocAttributes =3D GetAttributes; > > > > > > > > @@ -599,28 +752,266 @@ InitializePciHostBridge ( > > > > > > > > NULL > > > > > > > > ); > > > > > > > > ASSERT_EFI_ERROR (Status); > > > > > > > > - } > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + goto ErrorExit; > > > > > > > > + } > > > > > > > > > > > > > > > > - for (Link =3D GetFirstNode (&HostBridge->RootBridges) > > > > > > > > - ; !IsNull (&HostBridge->RootBridges, Link) > > > > > > > > - ; Link =3D GetNextNode (&HostBridge->RootBridges, Link) > > > > > > > > - ) > > > > > > > > - { > > > > > > > > - RootBridge =3D ROOT_BRIDGE_FROM_LIN= K (Link); > > > > > > > > + // > > > > > > > > + // Insert Root Bridge Handle Instance > > > > > > > > + // > > > > > > > > + InsertTailList (&HostBridge->RootBridges, &RootBridge->Link); > > > > > > > > RootBridge->RootBridgeIo.ParentHandle =3D HostBridge->Handle; > > > > > > > > + } else { > > > > > > > > + RootBridge->RootBridgeIo.ParentHandle =3D 0; > > > > > > > > + } > > > > > > > > > > > > > > > > - Status =3D gBS->InstallMultipleProtocolInterfaces ( > > > > > > > > - &RootBridge->Handle, > > > > > > > > - &gEfiDevicePathProtocolGuid, > > > > > > > > - RootBridge->DevicePath, > > > > > > > > - &gEfiPciRootBridgeIoProtocolGuid, > > > > > > > > - &RootBridge->RootBridgeIo, > > > > > > > > - NULL > > > > > > > > - ); > > > > > > > > - ASSERT_EFI_ERROR (Status); > > > > > > > > + RootBridge->Handle =3D Controller; > > > > > > > > + Status =3D gBS->InstallMultipleProtocolInterfaces ( > > > > > > > > + &RootBridge->Handle, > > > > > > > > + &gEfiPciRootBridgeIoProtocolGuid, > > > > > > > > + &RootBridge->RootBridgeIo, > > > > > > > > + NULL > > > > > > > > + ); > > > > > > > > + > > > > > > > > +ErrorExit: > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + if (MemorySetupDone) { > > > > > > > > + PciRootBridgeMemoryFree (PciRootBridge); > > > > > > > > + } > > > > > > > > + > > > > > > > > + if (RootBridge !=3D NULL) { > > > > > > > > + if (!IsListEmpty (&RootBridge->Link)) { > > > > > > > > + RemoveEntryList (&RootBridge->Link); > > > > > > > > + } > > > > > > > > + > > > > > > > > + FreeRootBridge (RootBridge); > > > > > > > > + } > > > > > > > > + > > > > > > > > + gBS->CloseProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + This->DriverBindingHandle, > > > > > > > > + Controller > > > > > > > > + ); > > > > > > > > } > > > > > > > > > > > > > > > > - PciHostBridgeFreeRootBridges (RootBridges, RootBridgeCount); > > > > > > > > + return Status; > > > > > > > > +} > > > > > > > > + > > > > > > > > +/** > > > > > > > > + Stop this driver on ControllerHandle. Support stopping any > > > > + child handles > > > > > > > > + created by this driver. > > > > > > > > + > > > > > > > > + @param This Protocol instance pointer. > > > > > > > > + @param Controller Handle of device to stop driver on. > > > > > > > > + @param NumberOfChildren Number of Handles in ChildHandleBuffer= . > > > > + If > > > > number of > > > > > > > > + children is zero stop the entire bus d= river. > > > > > > > > + @param ChildHandleBuffer List of Child Handles to Stop. > > > > > > > > + > > > > > > > > + @retval EFI_SUCCESS This driver is removed ControllerHandl= e. > > > > > > > > + @retval other This driver was not removed from this = device. > > > > > > > > + > > > > > > > > +**/ > > > > > > > > +EFI_STATUS > > > > > > > > +EFIAPI > > > > > > > > +PciHostBrigeDriverBindingStop ( > > > > > > > > + IN EFI_DRIVER_BINDING_PROTOCOL *This, > > > > > > > > + IN EFI_HANDLE Controller, > > > > > > > > + IN UINTN NumberOfChildren, > > > > > > > > + IN EFI_HANDLE *ChildHandleBuffer > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + EFI_STATUS Status; > > > > > > > > + PCI_ROOT_BRIDGE *PciRootBridge; > > > > > > > > + PCI_ROOT_BRIDGE_INSTANCE *RootBridge; > > > > > > > > + EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL *RootBridgeIo; > > > > > > > > + > > > > > > > > + Status =3D gBS->HandleProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEfiPciRootBridgeIoProtocolGuid, > > > > > > > > + (VOID **)&RootBridgeIo > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + > > > > > > > > + RootBridge =3D ROOT_BRIDGE_FROM_THIS (RootBridgeIo); > > > > > > > > + > > > > > > > > + Status =3D gBS->HandleProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + (VOID **)&PciRootBridge > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + > > > > > > > > + Status =3D gBS->UninstallMultipleProtocolInterfaces ( > > > > > > > > + Controller, > > > > > > > > + &gEfiPciRootBridgeIoProtocolGuid, > > > > > > > > + (VOID **)&PciRootBridge > > > > > > > > + ); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + return Status; > > > > > > > > + } > > > > > > > > + > > > > > > > > + if (!IsListEmpty (&RootBridge->Link)) { > > > > > > > > + RemoveEntryList (&RootBridge->Link); > > > > > > > > + } > > > > > > > > + > > > > > > > > + PciRootBridgeMemoryFree (PciRootBridge); > > > > > > > > + > > > > > > > > + FreeRootBridge (RootBridge); > > > > > > > > + gBS->CloseProtocol ( > > > > > > > > + Controller, > > > > > > > > + &gEdkiiPciHostBridgeProtocolGuid, > > > > > > > > + This->DriverBindingHandle, > > > > > > > > + Controller > > > > > > > > + ); > > > > > > > > + return EFI_SUCCESS; > > > > > > > > +} > > > > > > > > + > > > > > > > > +// > > > > > > > > +// PCI Bus Driver Global Variables > > > > > > > > +// > > > > > > > > +EFI_DRIVER_BINDING_PROTOCOL gPciHostBrigeDriverBinding =3D { > > > > > > > > + PciHostBrigeDriverBindingSupported, > > > > > > > > + PciHostBrigeDriverBindingStart, > > > > > > > > + PciHostBrigeDriverBindingStop, > > > > > > > > + 0xa, > > > > > > > > + NULL, > > > > > > > > + NULL > > > > > > > > +}; > > > > > > > > + > > > > > > > > +/** > > > > > > > > + > > > > > > > > + Entry point of this driver. > > > > > > > > + > > > > > > > > + @param ImageHandle Image handle of this driver. > > > > > > > > + @param SystemTable Pointer to standard EFI system table. > > > > > > > > + > > > > > > > > + @retval EFI_SUCCESS Succeed. > > > > > > > > + @retval EFI_DEVICE_ERROR Fail to install PCI_ROOT_BRIDGE_IO > > protocol. > > > > > > > > + > > > > > > > > +**/ > > > > > > > > +EFI_STATUS > > > > > > > > +EFIAPI > > > > > > > > +InitializePciHostBridge ( > > > > > > > > + IN EFI_HANDLE ImageHandle, > > > > > > > > + IN EFI_SYSTEM_TABLE *SystemTable > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + EFI_STATUS Status; > > > > > > > > + PCI_HOST_BRIDGE_INSTANCE *HostBridge; > > > > > > > > + PCI_ROOT_BRIDGE_INSTANCE *RootBridge; > > > > > > > > + PCI_ROOT_BRIDGE *RootBridges; > > > > > > > > + UINTN RootBridgeCount; > > > > > > > > + UINTN Index; > > > > > > > > + BOOLEAN ResourceAssigned; > > > > > > > > + LIST_ENTRY *Link; > > > > > > > > + > > > > > > > > + Status =3D gBS->LocateProtocol (&gEfiCpuIo2ProtocolGuid, NULL, > > > > + (VOID > > > > **)&mCpuIo); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + > > > > > > > > + RootBridges =3D PciHostBridgeGetRootBridges (&RootBridgeCount); > > > > > > > > + if ((RootBridges =3D=3D NULL) || (RootBridgeCount =3D=3D 0)) { > > > > > > > > + // Register for binding protocol if library enumeration is > > > > + not used > > > > > > > > + Status =3D EfiLibInstallDriverBinding ( > > > > > > > > + ImageHandle, > > > > > > > > + SystemTable, > > > > > > > > + &gPciHostBrigeDriverBinding, > > > > > > > > + ImageHandle > > > > > > > > + ); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + } else { > > > > > > > > + // > > > > > > > > + // Most systems in the world including complex servers have > > > > + only one Host > > > > Bridge. > > > > > > > > + // > > > > > > > > + HostBridge =3D AllocateZeroPool (sizeof > > > > + (PCI_HOST_BRIDGE_INSTANCE)); > > > > > > > > + ASSERT (HostBridge !=3D NULL); > > > > > > > > + > > > > > > > > + HostBridge->Signature =3D PCI_HOST_BRIDGE_SIGNATURE; > > > > > > > > + HostBridge->CanRestarted =3D TRUE; > > > > > > > > + InitializeListHead (&HostBridge->RootBridges); > > > > > > > > + ResourceAssigned =3D FALSE; > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Create Root Bridge Device Handle in this Host Bridge > > > > > > > > + // > > > > > > > > + for (Index =3D 0; Index < RootBridgeCount; Index++) { > > > > > > > > + // > > > > > > > > + // Create Root Bridge Handle Instance > > > > > > > > + // > > > > > > > > + RootBridge =3D CreateRootBridge (&RootBridges[Index]); > > > > > > > > + ASSERT (RootBridge !=3D NULL); > > > > > > > > + if (RootBridge =3D=3D NULL) { > > > > > > > > + continue; > > > > > > > > + } > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Make sure all root bridges share the same ResourceAssigne= d value. > > > > > > > > + // > > > > > > > > + if (Index =3D=3D 0) { > > > > > > > > + ResourceAssigned =3D RootBridges[Index].ResourceAssigned; > > > > > > > > + } else { > > > > > > > > + ASSERT (ResourceAssigned =3D=3D > > > > + RootBridges[Index].ResourceAssigned); > > > > > > > > + } > > > > > > > > + > > > > > > > > + Status =3D PciRootBridgeMemorySetup (&RootBridges[Index]); > > > > > > > > + if (EFI_ERROR (Status)) { > > > > > > > > + continue; > > > > > > > > + } > > > > > > > > + > > > > > > > > + // > > > > > > > > + // Insert Root Bridge Handle Instance > > > > > > > > + // > > > > > > > > + InsertTailList (&HostBridge->RootBridges, > > > > + &RootBridge->Link); > > > > > > > > + } > > > > > > > > + > > > > > > > > + // > > > > > > > > + // When resources were assigned, it's not needed to expose > > > > > > > > + // PciHostBridgeResourceAllocation protocol. > > > > > > > > + // > > > > > > > > + if (!ResourceAssigned) { > > > > > > > > + HostBridge->ResAlloc.NotifyPhase =3D NotifyPhase; > > > > > > > > + HostBridge->ResAlloc.GetNextRootBridge =3D GetNextRootBri= dge; > > > > > > > > + HostBridge->ResAlloc.GetAllocAttributes =3D GetAttributes; > > > > > > > > + HostBridge->ResAlloc.StartBusEnumeration =3D > > > > + StartBusEnumeration; > > > > > > > > + HostBridge->ResAlloc.SetBusNumbers =3D SetBusNumbers; > > > > > > > > + HostBridge->ResAlloc.SubmitResources =3D SubmitResource= s; > > > > > > > > + HostBridge->ResAlloc.GetProposedResources =3D > > > > + GetProposedResources; > > > > > > > > + HostBridge->ResAlloc.PreprocessController =3D > > > > + PreprocessController; > > > > > > > > + > > > > > > > > + Status =3D gBS->InstallMultipleProtocolInterfaces ( > > > > > > > > + &HostBridge->Handle, > > > > > > > > + > > > > + &gEfiPciHostBridgeResourceAllocationProtocolGuid, > > > > > > > > + &HostBridge->ResAlloc, > > > > > > > > + NULL > > > > > > > > + ); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + } > > > > > > > > + > > > > > > > > + for (Link =3D GetFirstNode (&HostBridge->RootBridges) > > > > > > > > + ; !IsNull (&HostBridge->RootBridges, Link) > > > > > > > > + ; Link =3D GetNextNode (&HostBridge->RootBridges, Link) > > > > > > > > + ) > > > > > > > > + { > > > > > > > > + RootBridge =3D ROOT_BRIDGE_FROM_L= INK (Link); > > > > > > > > + RootBridge->RootBridgeIo.ParentHandle =3D HostBridge->Handle= ; > > > > > > > > + > > > > > > > > + Status =3D gBS->InstallMultipleProtocolInterfaces ( > > > > > > > > + &RootBridge->Handle, > > > > > > > > + &gEfiDevicePathProtocolGuid, > > > > > > > > + RootBridge->DevicePath, > > > > > > > > + &gEfiPciRootBridgeIoProtocolGuid, > > > > > > > > + &RootBridge->RootBridgeIo, > > > > > > > > + NULL > > > > > > > > + ); > > > > > > > > + ASSERT_EFI_ERROR (Status); > > > > > > > > + } > > > > > > > > + > > > > > > > > + PciHostBridgeFreeRootBridges (RootBridges, RootBridgeCount); > > > > > > > > + } > > > > > > > > > > > > > > > > if (!EFI_ERROR (Status)) { > > > > > > > > mIoMmuEvent =3D EfiCreateProtocolNotifyEvent ( > > > > > > > > diff --git > > > > a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf > > > > b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf > > > > > > > > index 9c24cacc30..ee4740b14f 100644 > > > > > > > > --- a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf > > > > > > > > +++ b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciHostBridgeDxe.inf > > > > > > > > @@ -46,6 +46,7 @@ > > > > > > > > gEfiPciRootBridgeIoProtocolGuid ## BY_START > > > > > > > > gEfiPciHostBridgeResourceAllocationProtocolGuid ## BY_START > > > > > > > > gEdkiiIoMmuProtocolGuid ## SOMETIMES_CON= SUMES > > > > > > > > + gEdkiiPciHostBridgeProtocolGuid ## SOMETIMES_CON= SUMES > > > > > > > > > > > > > > > > [Depex] > > > > > > > > gEfiCpuIo2ProtocolGuid AND > > > > > > > > diff --git a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridge.h > > > > b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridge.h > > > > > > > > index 10a6200719..7923c4677b 100644 > > > > > > > > --- a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridge.h > > > > > > > > +++ b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridge.h > > > > > > > > @@ -93,6 +93,19 @@ CreateRootBridge ( > > > > > > > > IN PCI_ROOT_BRIDGE *Bridge > > > > > > > > ); > > > > > > > > > > > > > > > > +/** > > > > > > > > + Free the Pci Root Bridge instance. > > > > > > > > + > > > > > > > > + @param Bridge The root bridge instance. > > > > > > > > + > > > > > > > > + @return The pointer to PCI_ROOT_BRIDGE_INSTANCE just created > > > > > > > > + or NULL if creation fails. > > > > > > > > +**/ > > > > > > > > +VOID > > > > > > > > +FreeRootBridge ( > > > > > > > > + IN PCI_ROOT_BRIDGE_INSTANCE *Bridge > > > > > > > > + ); > > > > > > > > + > > > > > > > > // > > > > > > > > // Protocol Member Function Prototypes > > > > > > > > // > > > > > > > > diff --git > > > > a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridgeIo.c > > > > b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridgeIo.c > > > > > > > > index 157a0ada80..f0eb465a9d 100644 > > > > > > > > --- a/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridgeIo.c > > > > > > > > +++ b/MdeModulePkg/Bus/Pci/PciHostBridgeDxe/PciRootBridgeIo.c > > > > > > > > @@ -286,6 +286,30 @@ CreateRootBridge ( > > > > > > > > return RootBridge; > > > > > > > > } > > > > > > > > > > > > > > > > +/** > > > > > > > > + Free the Pci Root Bridge instance. > > > > > > > > + > > > > > > > > + @param Bridge The root bridge instance. > > > > > > > > + > > > > > > > > + @return The pointer to PCI_ROOT_BRIDGE_INSTANCE just created > > > > > > > > + or NULL if creation fails. > > > > > > > > +**/ > > > > > > > > +VOID > > > > > > > > +FreeRootBridge ( > > > > > > > > + IN PCI_ROOT_BRIDGE_INSTANCE *Bridge > > > > > > > > + ) > > > > > > > > +{ > > > > > > > > + if (Bridge->ConfigBuffer !=3D NULL) { > > > > > > > > + FreePool (Bridge->ConfigBuffer); > > > > > > > > + } > > > > > > > > + > > > > > > > > + if (Bridge->DevicePath !=3D NULL) { > > > > > > > > + FreePool (Bridge->DevicePath); > > > > > > > > + } > > > > > > > > + > > > > > > > > + FreePool (Bridge); > > > > > > > > +} > > > > > > > > + > > > > > > > > /** > > > > > > > > Check parameters for IO,MMIO,PCI read/write services of PCI > > > > Root > > Bridge IO. > > > > > > > > > > > > > > > > diff --git a/MdeModulePkg/MdeModulePkg.dec > > > > b/MdeModulePkg/MdeModulePkg.dec > > > > > > > > index d65dae18aa..24700fa797 100644 > > > > > > > > --- a/MdeModulePkg/MdeModulePkg.dec > > > > > > > > +++ b/MdeModulePkg/MdeModulePkg.dec > > > > > > > > @@ -692,6 +692,10 @@ > > > > > > > > ## Include/Protocol/VariablePolicy.h > > > > > > > > gEdkiiVariablePolicyProtocolGuid =3D { 0x81D1675C, 0x86F6, > > > > 0x48DF, { 0xBD, 0x95, 0x9A, 0x6E, 0x4F, 0x09, 0x25, 0xC3 } } > > > > > > > > > > > > > > > > + ## Include/Library/PciHostBridgeLib.h > > > > > > > > + # Exposes a PCI_HOST_BRIDGE structure for driver binding usage > > > > > > > > + gEdkiiPciHostBridgeProtocolGuid =3D { 0xaff2b72d, 0x202e, 0x40e3= , > > > > + { 0x82, 0xd5, > > > > 0x9f, 0x6f, 0x61, 0xaf, 0x2a, 0x0b } } > > > > > > > > + > > > > > > > > [PcdsFeatureFlag] > > > > > > > > ## Indicates if the platform can support update capsule across > > > > a system reset.

> > > > > > > > # TRUE - Supports update capsule across a system reset.
> > > > > > > > -- > > > > > > > > 2.25.1 > > > > > > > >