+ if (EFI_ERROR (Status)) {\r
+ DEBUG ((EFI_D_ERROR, "UsbMassInitMultiLun: InstallMultipleProtocolInterfaces (%r)\n", Status));\r
+ FreePool (UsbMass->DevicePath);\r
+ FreePool (UsbMass);\r
+ continue;\r
+ }\r
+\r
+ //\r
+ // Open USB I/O Protocol by child to setup a parent-child relationship.\r
+ //\r
+ Status = gBS->OpenProtocol (\r
+ Controller,\r
+ &gEfiUsbIoProtocolGuid,\r
+ (VOID **) &UsbIo,\r
+ This->DriverBindingHandle,\r
+ UsbMass->Controller,\r
+ EFI_OPEN_PROTOCOL_BY_CHILD_CONTROLLER\r
+ );\r
+\r
+ if (EFI_ERROR (Status)) {\r
+ DEBUG ((EFI_D_ERROR, "UsbMassInitMultiLun: OpenUsbIoProtocol By Child (%r)\n", Status));\r
+ gBS->UninstallMultipleProtocolInterfaces (\r
+ &UsbMass->Controller,\r
+ &gEfiDevicePathProtocolGuid,\r
+ UsbMass->DevicePath,\r
+ &gEfiBlockIoProtocolGuid,\r
+ &UsbMass->BlockIo,\r
+ &gEfiDiskInfoProtocolGuid,\r
+ &UsbMass->DiskInfo,\r
+ NULL\r
+ );\r
+ FreePool (UsbMass->DevicePath);\r
+ FreePool (UsbMass);\r
+ continue;\r
+ }\r
+ ReturnStatus = EFI_SUCCESS;\r
+ DEBUG ((EFI_D_INFO, "UsbMassInitMultiLun: Success to initialize No.%d logic unit\n", Index));\r
+ }\r
+\r
+ return ReturnStatus;\r
+}\r
+\r
+/**\r
+ Initialize data for device that does not support multiple LUNSs.\r
+\r
+ @param This The Driver Binding Protocol instance.\r
+ @param Controller The device to initialize.\r
+ @param Transport Pointer to USB_MASS_TRANSPORT.\r
+ @param Context Parameter for USB_MASS_DEVICE.Context.\r
+\r
+ @retval EFI_SUCCESS Initialization succeeds.\r
+ @retval Other Initialization fails.\r
+\r
+**/\r
+EFI_STATUS\r
+UsbMassInitNonLun (\r
+ IN EFI_DRIVER_BINDING_PROTOCOL *This,\r
+ IN EFI_HANDLE Controller,\r
+ IN USB_MASS_TRANSPORT *Transport,\r
+ IN VOID *Context\r
+ )\r
+{\r
+ USB_MASS_DEVICE *UsbMass;\r
+ EFI_USB_IO_PROTOCOL *UsbIo;\r
+ EFI_STATUS Status;\r
+\r
+ UsbIo = NULL;\r
+ UsbMass = AllocateZeroPool (sizeof (USB_MASS_DEVICE));\r
+ ASSERT (UsbMass != NULL);\r
+\r
+ Status = gBS->OpenProtocol (\r
+ Controller,\r
+ &gEfiUsbIoProtocolGuid,\r
+ (VOID **) &UsbIo,\r
+ This->DriverBindingHandle,\r
+ Controller,\r
+ EFI_OPEN_PROTOCOL_BY_DRIVER\r
+ );\r
+\r
+ if (EFI_ERROR (Status)) {\r
+ DEBUG ((EFI_D_ERROR, "UsbMassInitNonLun: OpenUsbIoProtocol By Driver (%r)\n", Status));\r
+ goto ON_ERROR;\r
+ }\r
+\r
+ UsbMass->Signature = USB_MASS_SIGNATURE;\r
+ UsbMass->Controller = Controller;\r
+ UsbMass->UsbIo = UsbIo;\r
+ UsbMass->BlockIo.Media = &UsbMass->BlockIoMedia;\r
+ UsbMass->BlockIo.Reset = UsbMassReset;\r
+ UsbMass->BlockIo.ReadBlocks = UsbMassReadBlocks;\r
+ UsbMass->BlockIo.WriteBlocks = UsbMassWriteBlocks;\r
+ UsbMass->BlockIo.FlushBlocks = UsbMassFlushBlocks;\r
+ UsbMass->OpticalStorage = FALSE;\r
+ UsbMass->Transport = Transport;\r
+ UsbMass->Context = Context;\r
+\r
+ //\r
+ // Initialize the media parameter data for EFI_BLOCK_IO_MEDIA of Block I/O Protocol.\r
+ //\r
+ Status = UsbMassInitMedia (UsbMass);\r
+ if ((EFI_ERROR (Status)) && (Status != EFI_NO_MEDIA)) {\r
+ DEBUG ((EFI_D_ERROR, "UsbMassInitNonLun: UsbMassInitMedia (%r)\n", Status));\r
+ goto ON_ERROR;\r
+ }\r
+\r
+ InitializeDiskInfo (UsbMass);\r
+\r
+ Status = gBS->InstallMultipleProtocolInterfaces (\r
+ &Controller,\r
+ &gEfiBlockIoProtocolGuid,\r
+ &UsbMass->BlockIo,\r
+ &gEfiDiskInfoProtocolGuid,\r
+ &UsbMass->DiskInfo,\r
+ NULL\r
+ );\r
+ if (EFI_ERROR (Status)) {\r
+ goto ON_ERROR;\r
+ }\r
+\r
+ return EFI_SUCCESS;\r
+\r
+ON_ERROR:\r
+ if (UsbMass != NULL) {\r
+ FreePool (UsbMass);\r
+ }\r
+ if (UsbIo != NULL) {\r
+ gBS->CloseProtocol (\r
+ Controller,\r
+ &gEfiUsbIoProtocolGuid,\r
+ This->DriverBindingHandle,\r
+ Controller\r
+ );\r
+ }\r