-----Original Message-----
From: Laszlo Ersek [mailto:[email protected]] 
Sent: Tuesday, May 03, 2016 1:15 PM
To: Shaveta Leekha <[email protected]>
Cc: [email protected] <[email protected]>
Subject: Re: [edk2] Two PCI IO protocols getting produced by same GUID, how to 
open correct one?

On 05/03/16 08:54, Shaveta Leekha wrote:
> Hi,
> 
> I have a scenario where two separate drivers are installing/producing "PCI 
> IO" protocol with same GUID (gEfiPciIoProtocolGuid).
> 
> Where:
> 
> (1)    One of the PCI Io protocol instance is produced by 
> "MdeModulePkg/Bus/Pci/PciBus" driver for real PCI devices to use( like 
> E1000/NIC card to use)
> 
> (2)    Other PCI Io protocol instance is produced by "Pci Emulation" layer 
> created for USB and SATA kind of controllers. This protocol (APIs) is 
> intended to be used by USB and SATA controller drivers.
> 
> Now when I use "OpenProtocol" in my "Platform specific Sata controller 
> driver" using:
> 
> Status = gBS->OpenProtocol (
>                   Controller,
>                   &gEfiPciIoProtocolGuid,
>                   (VOID **) &PciIo,
>                   This->DriverBindingHandle,
>                   Controller,
>                   EFI_OPEN_PROTOCOL_GET_PROTOCOL
>                   );
> 
> How can I make sure that PCI Io protocol that is produced by "PciEmulation" 
> layer driver is getting opened?
> 
> As "gEfiPciIoProtocolGuid" is same for both protocol instances.
> 
> How to handle such scenarios?

The UEFI spec forbids installing more than one protocol interface with the same 
GUID on the same handle. See
EFI_BOOT_SERVICES.InstallProtocolInterface():

  [... The same GUID cannot be installed more than once onto the same
  handle. If installation of a duplicate GUID on a handle is attempted,
  an EFI_INVALID_PARAMETER will result. [...]

  EFI_INVALID_PARAMETER  Protocol is already installed on the handle
                         specified by Handle.

If you have two separate UEFI drivers that install PciIo interfaces on handles, 
then their EFI_DRIVER_BINDING_PROTOCOL.Supported() methods may report success 
only on distinct sets of handles. There must be no overlap.

But, in any case, I think it's very unusual to have two drivers that produce 
PciIo interfaces. According to the "Driver Writer's Guide for UEFI 2.3.1" 
(03/08/2012, Version 1.01), section "18.2 PCI Bus Drivers":

  TIP:  PCI Bus Driver customizations are *strongly discouraged*
        because the PCI Bus Driver is designed to be conformant with
        the /PCI Specification/. Instead, focus platform specific
        customizations on the Root Bridge Driver that produced
        EFI_PCI_ROOT_BRIDGE_IO_PROTOCOL and its PCI Device Drivers.


[Shaveta] 
Yes, it is un-usual and we had discussed over it also.

So the scenario is:
================
On LS2080 platform, we have real PCI controllers that have E1000 card on 
them(used for networking purposes) And USB and SATA controllers are on-board.
So to provide SATA and USB, a PCIe emulation layer, a PCI IO protocol is 
installed in PciEmulation code.
PciEmulation code is very thin layer that simply produce PciRootBridgeIo 
protocol and hence PCI IO protocol,
Hence bypass the need of "real Pci Bus" code.

Reference is taken from ArmJune platform code in EDK2. In it, it install :
(1) PCI IO protocol using "gEfiPciIoProtocolGuid" in 
ArmPlatformPkg/ArmJunoPkg/Drivers/ArmJunoDxe/PciEmulation.c
(2) It also install " gEfiPciRootBridgeIoProtocolGuid" protocol, using which 
"PciBusDxe" will produce PciIo protocol

The same we are doing for our platform.
For real PCI controller, we have " installed Root Bridge PCI IO protocol with 
gEfiPciRootBridgeIoProtocolGuid"
And for emulation layer, the code direcly install PCI IO protocol with 
gEfiPciIoProtocolGuid"

Regards,
Shaveta

Laszlo

_______________________________________________
edk2-devel mailing list
[email protected]
https://lists.01.org/mailman/listinfo/edk2-devel

Reply via email to