MdeModulePkg/Bus/Usb/UsbNetwork/UsbCdcNcm: Add USB Cdc NCM devices support
This driver provides UEFI driver for USB CDC NCM device Signed-off-by: Richard Ho <richardho@ami.com> Cc: Andrew Fish <afish@apple.com> Cc: Leif Lindholm <quic_llindhol@quicinc.com> Cc: Michael D Kinney <michael.d.kinney@intel.com> Cc: Michael Kubacki <mikuback@linux.microsoft.com> Cc: Zhiguang Liu <zhiguang.liu@intel.com> Cc: Liming Gao <gaoliming@byosoft.com.cn> Cc: Hao A Wu <hao.a.wu@intel.com> Cc: Ray Ni <ray.ni@intel.com> Tested-by: Tinh Nguyen <tinhnguyen@os.amperecomputing.com> Acked-by: Hao A Wu <hao.a.wu@intel.com> Reviewed-by: Rebecca Cran <rebecca@bsdio.com> Reviewed-by: Tony Lo <tonylo@ami.com>
This commit is contained in:
506
MdeModulePkg/Bus/Usb/UsbNetwork/UsbCdcNcm/UsbCdcNcm.c
Normal file
506
MdeModulePkg/Bus/Usb/UsbNetwork/UsbCdcNcm/UsbCdcNcm.c
Normal file
@@ -0,0 +1,506 @@
|
||||
/** @file
|
||||
This file contains code for USB Network Control Model
|
||||
binding driver
|
||||
|
||||
Copyright (c) 2023, American Megatrends International LLC. All rights reserved.<BR>
|
||||
SPDX-License-Identifier: BSD-2-Clause-Patent
|
||||
**/
|
||||
|
||||
#include "UsbCdcNcm.h"
|
||||
|
||||
EFI_DRIVER_BINDING_PROTOCOL gUsbNcmDriverBinding = {
|
||||
UsbNcmDriverSupported,
|
||||
UsbNcmDriverStart,
|
||||
UsbNcmDriverStop,
|
||||
USB_NCM_DRIVER_VERSION,
|
||||
NULL,
|
||||
NULL
|
||||
};
|
||||
|
||||
/**
|
||||
Check if this interface is USB NCM SubType
|
||||
|
||||
@param[in] UsbIo A pointer to the EFI_USB_IO_PROTOCOL instance.
|
||||
|
||||
@retval TRUE USB NCM SubType.
|
||||
@retval FALSE Not USB NCM SubType.
|
||||
|
||||
**/
|
||||
BOOLEAN
|
||||
IsSupportedDevice (
|
||||
IN EFI_USB_IO_PROTOCOL *UsbIo
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_USB_INTERFACE_DESCRIPTOR InterfaceDescriptor;
|
||||
|
||||
Status = UsbIo->UsbGetInterfaceDescriptor (UsbIo, &InterfaceDescriptor);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
if ((InterfaceDescriptor.InterfaceClass == USB_CDC_CLASS) &&
|
||||
(InterfaceDescriptor.InterfaceSubClass == USB_CDC_NCM_SUBCLASS) &&
|
||||
(InterfaceDescriptor.InterfaceProtocol == USB_NO_CLASS_PROTOCOL))
|
||||
{
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/**
|
||||
USB NCM Driver Binding Support.
|
||||
|
||||
@param[in] This Protocol instance pointer.
|
||||
@param[in] ControllerHandle Handle of device to test.
|
||||
@param[in] 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 device.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
UsbNcmDriverSupported (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EFI_USB_IO_PROTOCOL *UsbIo;
|
||||
|
||||
Status = gBS->OpenProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
(VOID **)&UsbIo,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_BY_DRIVER
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = IsSupportedDevice (UsbIo) ? EFI_SUCCESS : EFI_UNSUPPORTED;
|
||||
|
||||
gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Check if the USB NCM and USB CDC Data interfaces are from the same device.
|
||||
|
||||
@param[in] UsbEthPath A pointer to the EFI_DEVICE_PATH_PROTOCOL instance.
|
||||
@param[in] UsbCdcDataPath A pointer to the EFI_DEVICE_PATH_PROTOCOL instance.
|
||||
|
||||
@retval EFI_SUCCESS Is the same device.
|
||||
@retval EFI_NOT_FOUND Is not the same device.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
IsSameDevice (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *UsbEthPath,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *UsbCdcDataPath
|
||||
)
|
||||
{
|
||||
while (1) {
|
||||
if ((UsbEthPath->Type == ACPI_DEVICE_PATH) && (UsbEthPath->SubType == ACPI_DP)) {
|
||||
if (CompareMem ((ACPI_HID_DEVICE_PATH *)UsbCdcDataPath, (ACPI_HID_DEVICE_PATH *)UsbEthPath, sizeof (ACPI_HID_DEVICE_PATH))) {
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
}
|
||||
|
||||
if ((UsbEthPath->Type == HARDWARE_DEVICE_PATH) && (UsbEthPath->SubType == HW_PCI_DP)) {
|
||||
if (CompareMem ((PCI_DEVICE_PATH *)UsbCdcDataPath, (PCI_DEVICE_PATH *)UsbEthPath, sizeof (PCI_DEVICE_PATH))) {
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
}
|
||||
|
||||
if ((UsbEthPath->Type == MESSAGING_DEVICE_PATH) && (UsbEthPath->SubType == MSG_USB_DP)) {
|
||||
if (IsDevicePathEnd (NextDevicePathNode (UsbEthPath))) {
|
||||
if (((USB_DEVICE_PATH *)UsbEthPath)->ParentPortNumber ==
|
||||
((USB_DEVICE_PATH *)UsbCdcDataPath)->ParentPortNumber)
|
||||
{
|
||||
return EFI_SUCCESS;
|
||||
} else {
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
} else {
|
||||
if (CompareMem ((USB_DEVICE_PATH *)UsbCdcDataPath, (USB_DEVICE_PATH *)UsbEthPath, sizeof (USB_DEVICE_PATH))) {
|
||||
return EFI_NOT_FOUND;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
UsbEthPath = NextDevicePathNode (UsbEthPath);
|
||||
UsbCdcDataPath = NextDevicePathNode (UsbCdcDataPath);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
Check if the USB CDC Data(UsbIo) installed and return USB CDC Data Handle.
|
||||
|
||||
@param[in] UsbEthPath A pointer to the EFI_DEVICE_PATH_PROTOCOL instance.
|
||||
@param[in, out] UsbCdcDataHandle A pointer to the EFI_HANDLE for USB CDC Data.
|
||||
|
||||
@retval TRUE USB CDC Data(UsbIo) installed.
|
||||
@retval FALSE USB CDC Data(UsbIo) did not installed.
|
||||
|
||||
**/
|
||||
BOOLEAN
|
||||
IsUsbCdcData (
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *UsbEthPath,
|
||||
IN OUT EFI_HANDLE *UsbCdcDataHandle
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINTN Index;
|
||||
UINTN HandleCount;
|
||||
EFI_HANDLE *HandleBuffer;
|
||||
EFI_USB_IO_PROTOCOL *UsbIo;
|
||||
EFI_USB_INTERFACE_DESCRIPTOR Interface;
|
||||
EFI_DEVICE_PATH_PROTOCOL *UsbCdcDataPath;
|
||||
|
||||
Status = gBS->LocateHandleBuffer (
|
||||
ByProtocol,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
NULL,
|
||||
&HandleCount,
|
||||
&HandleBuffer
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
for (Index = 0; Index < HandleCount; Index++) {
|
||||
Status = gBS->HandleProtocol (
|
||||
HandleBuffer[Index],
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
(VOID **)&UsbIo
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
Status = UsbIo->UsbGetInterfaceDescriptor (UsbIo, &Interface);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
if ((Interface.InterfaceClass == USB_CDC_DATA_CLASS) &&
|
||||
(Interface.InterfaceSubClass == USB_CDC_DATA_SUBCLASS) &&
|
||||
(Interface.InterfaceProtocol == USB_NCM_NTB_PROTOCOL))
|
||||
{
|
||||
Status = gBS->HandleProtocol (
|
||||
HandleBuffer[Index],
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
(VOID **)&UsbCdcDataPath
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
Status = IsSameDevice (UsbEthPath, UsbCdcDataPath);
|
||||
if (!EFI_ERROR (Status)) {
|
||||
CopyMem (UsbCdcDataHandle, &HandleBuffer[Index], sizeof (EFI_HANDLE));
|
||||
FreePool (HandleBuffer);
|
||||
return TRUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
FreePool (HandleBuffer);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/**
|
||||
Call Back Function.
|
||||
|
||||
@param[in] Event Event whose notification function is being invoked.
|
||||
@param[in] Context The pointer to the notification function's context,
|
||||
which is implementation-dependent.
|
||||
|
||||
**/
|
||||
VOID
|
||||
EFIAPI
|
||||
CallbackFunction (
|
||||
IN EFI_EVENT Event,
|
||||
IN VOID *Context
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
UINTN Index;
|
||||
UINTN HandleCount;
|
||||
EFI_HANDLE *HandleBuffer;
|
||||
EFI_USB_IO_PROTOCOL *UsbIo;
|
||||
EFI_USB_INTERFACE_DESCRIPTOR Interface;
|
||||
|
||||
Status = gBS->LocateHandleBuffer (
|
||||
ByProtocol,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
NULL,
|
||||
&HandleCount,
|
||||
&HandleBuffer
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return;
|
||||
}
|
||||
|
||||
for (Index = 0; Index < HandleCount; Index++) {
|
||||
Status = gBS->HandleProtocol (
|
||||
HandleBuffer[Index],
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
(VOID **)&UsbIo
|
||||
);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
Status = UsbIo->UsbGetInterfaceDescriptor (UsbIo, &Interface);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
if ((Interface.InterfaceClass == USB_CDC_CLASS) &&
|
||||
(Interface.InterfaceSubClass == USB_CDC_NCM_SUBCLASS) &&
|
||||
(Interface.InterfaceProtocol == USB_NO_CLASS_PROTOCOL))
|
||||
{
|
||||
gBS->ConnectController (HandleBuffer[Index], NULL, NULL, TRUE);
|
||||
}
|
||||
}
|
||||
|
||||
FreePool (HandleBuffer);
|
||||
gBS->CloseEvent (Event);
|
||||
}
|
||||
|
||||
/**
|
||||
USB NCM Driver Binding Start.
|
||||
|
||||
@param[in] This Protocol instance pointer.
|
||||
@param[in] ControllerHandle Handle of device to bind driver to.
|
||||
@param[in] RemainingDevicePath Optional parameter use to pick a specific child
|
||||
device to start.
|
||||
|
||||
@retval EFI_SUCCESS This driver is added to ControllerHandle
|
||||
@retval EFI_DEVICE_ERROR This driver could not be started due to a device error
|
||||
@retval EFI_OUT_OF_RESOURCES The driver could not install successfully due to a lack of resources.
|
||||
@retval other This driver does not support this device
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
UsbNcmDriverStart (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE ControllerHandle,
|
||||
IN EFI_DEVICE_PATH_PROTOCOL *RemainingDevicePath
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
VOID *Reg;
|
||||
EFI_EVENT Event;
|
||||
USB_ETHERNET_DRIVER *UsbEthDriver;
|
||||
EFI_DEVICE_PATH_PROTOCOL *UsbEthPath;
|
||||
EFI_HANDLE UsbCdcDataHandle;
|
||||
EFI_USB_IO_PROTOCOL *UsbIo;
|
||||
EFI_USB_INTERFACE_DESCRIPTOR Interface;
|
||||
|
||||
Status = gBS->OpenProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
(VOID **)&UsbIo,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_BY_DRIVER
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = gBS->OpenProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiDevicePathProtocolGuid,
|
||||
(VOID **)&UsbEthPath,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_GET_PROTOCOL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = IsUsbCdcData (UsbEthPath, &UsbCdcDataHandle) ? EFI_SUCCESS : EFI_UNSUPPORTED;
|
||||
if (EFI_ERROR (Status)) {
|
||||
gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
|
||||
Status = gBS->CreateEvent (EVT_NOTIFY_SIGNAL, TPL_CALLBACK, CallbackFunction, NULL, &Event);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = gBS->RegisterProtocolNotify (&gEfiUsbIoProtocolGuid, Event, &Reg);
|
||||
return Status;
|
||||
}
|
||||
|
||||
UsbEthDriver = AllocateZeroPool (sizeof (USB_ETHERNET_DRIVER));
|
||||
if (!UsbEthDriver) {
|
||||
gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
return EFI_OUT_OF_RESOURCES;
|
||||
}
|
||||
|
||||
Status = LoadAllDescriptor (UsbIo, &UsbEthDriver->Config);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
GetEndpoint (UsbIo, UsbEthDriver);
|
||||
|
||||
Status = UsbIo->UsbGetInterfaceDescriptor (UsbIo, &Interface);
|
||||
ASSERT_EFI_ERROR (Status);
|
||||
|
||||
UsbEthDriver->Signature = USB_ETHERNET_SIGNATURE;
|
||||
UsbEthDriver->NumOfInterface = Interface.InterfaceNumber;
|
||||
UsbEthDriver->UsbCdcDataHandle = UsbCdcDataHandle;
|
||||
UsbEthDriver->UsbIo = UsbIo;
|
||||
UsbEthDriver->UsbEth.UsbEthReceive = UsbEthNcmReceive;
|
||||
UsbEthDriver->UsbEth.UsbEthTransmit = UsbEthNcmTransmit;
|
||||
UsbEthDriver->UsbEth.UsbEthInterrupt = UsbEthNcmInterrupt;
|
||||
UsbEthDriver->UsbEth.UsbEthMacAddress = GetUsbEthMacAddress;
|
||||
UsbEthDriver->UsbEth.UsbEthMaxBulkSize = UsbEthNcmBulkSize;
|
||||
UsbEthDriver->UsbEth.UsbHeaderFunDescriptor = GetUsbHeaderFunDescriptor;
|
||||
UsbEthDriver->UsbEth.UsbUnionFunDescriptor = GetUsbUnionFunDescriptor;
|
||||
UsbEthDriver->UsbEth.UsbEthFunDescriptor = GetUsbEthFunDescriptor;
|
||||
UsbEthDriver->UsbEth.SetUsbEthMcastFilter = SetUsbEthMcastFilter;
|
||||
UsbEthDriver->UsbEth.SetUsbEthPowerPatternFilter = SetUsbEthPowerFilter;
|
||||
UsbEthDriver->UsbEth.GetUsbEthPowerPatternFilter = GetUsbEthPowerFilter;
|
||||
UsbEthDriver->UsbEth.SetUsbEthPacketFilter = SetUsbEthPacketFilter;
|
||||
UsbEthDriver->UsbEth.GetUsbEthStatistic = GetUsbEthStatistic;
|
||||
|
||||
UsbEthDriver->BulkBuffer = AllocateZeroPool (USB_NCM_MAX_NTB_SIZE);
|
||||
|
||||
Status = gBS->InstallProtocolInterface (
|
||||
&ControllerHandle,
|
||||
&gEdkIIUsbEthProtocolGuid,
|
||||
EFI_NATIVE_INTERFACE,
|
||||
&(UsbEthDriver->UsbEth)
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
FreePool (UsbEthDriver);
|
||||
return Status;
|
||||
}
|
||||
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
USB NCM Driver Binding Stop.
|
||||
|
||||
@param[in] This Protocol instance pointer.
|
||||
@param[in] ControllerHandle Handle of device to stop driver on
|
||||
@param[in] NumberOfChildren Number of Handles in ChildHandleBuffer. If number of
|
||||
children is zero stop the entire bus driver.
|
||||
@param[in] ChildHandleBuffer List of Child Handles to Stop.
|
||||
|
||||
@retval EFI_SUCCESS This driver is removed ControllerHandle
|
||||
@retval other This driver was not removed from this device
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
UsbNcmDriverStop (
|
||||
IN EFI_DRIVER_BINDING_PROTOCOL *This,
|
||||
IN EFI_HANDLE ControllerHandle,
|
||||
IN UINTN NumberOfChildren,
|
||||
IN EFI_HANDLE *ChildHandleBuffer
|
||||
)
|
||||
{
|
||||
EFI_STATUS Status;
|
||||
EDKII_USB_ETHERNET_PROTOCOL *UsbEthProtocol;
|
||||
USB_ETHERNET_DRIVER *UsbEthDriver;
|
||||
|
||||
Status = gBS->OpenProtocol (
|
||||
ControllerHandle,
|
||||
&gEdkIIUsbEthProtocolGuid,
|
||||
(VOID **)&UsbEthProtocol,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle,
|
||||
EFI_OPEN_PROTOCOL_GET_PROTOCOL
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
UsbEthDriver = USB_ETHERNET_DEV_FROM_THIS (UsbEthProtocol);
|
||||
|
||||
Status = gBS->UninstallProtocolInterface (
|
||||
ControllerHandle,
|
||||
&gEdkIIUsbEthProtocolGuid,
|
||||
UsbEthProtocol
|
||||
);
|
||||
if (EFI_ERROR (Status)) {
|
||||
return Status;
|
||||
}
|
||||
|
||||
Status = gBS->CloseProtocol (
|
||||
ControllerHandle,
|
||||
&gEfiUsbIoProtocolGuid,
|
||||
This->DriverBindingHandle,
|
||||
ControllerHandle
|
||||
);
|
||||
FreePool (UsbEthDriver->Config);
|
||||
FreePool (UsbEthDriver->BulkBuffer);
|
||||
FreePool (UsbEthDriver);
|
||||
return Status;
|
||||
}
|
||||
|
||||
/**
|
||||
Entrypoint of NCM Driver.
|
||||
|
||||
This function is the entrypoint of NCM Driver. It installs Driver Binding
|
||||
Protocols together with Component Name Protocols.
|
||||
|
||||
@param[in] ImageHandle The firmware allocated handle for the EFI image.
|
||||
@param[in] SystemTable A pointer to the EFI System Table.
|
||||
|
||||
@retval EFI_SUCCESS The entry point is executed successfully.
|
||||
|
||||
**/
|
||||
EFI_STATUS
|
||||
EFIAPI
|
||||
UsbNcmEntry (
|
||||
IN EFI_HANDLE ImageHandle,
|
||||
IN EFI_SYSTEM_TABLE *SystemTable
|
||||
)
|
||||
{
|
||||
gUsbNcmDriverBinding.DriverBindingHandle = ImageHandle;
|
||||
gUsbNcmDriverBinding.ImageHandle = ImageHandle;
|
||||
|
||||
return gBS->InstallMultipleProtocolInterfaces (
|
||||
&gUsbNcmDriverBinding.DriverBindingHandle,
|
||||
&gEfiDriverBindingProtocolGuid,
|
||||
&gUsbNcmDriverBinding,
|
||||
&gEfiComponentName2ProtocolGuid,
|
||||
&gUsbNcmComponentName2,
|
||||
NULL
|
||||
);
|
||||
}
|
Reference in New Issue
Block a user