]> git.ipfire.org Git - thirdparty/ipxe.git/commitdiff
[efi] Disconnect controllers before uninstalling EFI_USB_IO_PROTOCOL
authorMichael Brown <mcb30@ipxe.org>
Tue, 29 Sep 2020 20:13:10 +0000 (21:13 +0100)
committerMichael Brown <mcb30@ipxe.org>
Tue, 29 Sep 2020 20:21:04 +0000 (21:21 +0100)
The call to UninstallMultipleProtocolInterfaces() will implicitly
disconnect any relevant controllers, and there is no specified
requirement to explicitly call DisconnectController() prior to
callling UninstallMultipleProtocolInterfaces().

However, some UEFI implementations (observed with the USB keyboard
driver on a Microsoft Surface Go) will fail to implicitly disconnect
the controller and will consequently fail to uninstall the protocols.

The net effect is that unplugging and replugging a USB keyboard may
leave the keyboard in a non-functional state.

Work around these broken UEFI implementations by including an
unnecessary call to DisconnectController() before the call to
UninstallMultipleProtocolInterfaces().

Signed-off-by: Michael Brown <mcb30@ipxe.org>
src/interface/efi/efi_usb.c

index f280a681b005c86e4ff8dd52b882c44fe1ffbee8..bac2d053af5b5dc4ac6b9c4022e59a3268c7ade0 100644 (file)
@@ -1193,6 +1193,12 @@ static void efi_usb_uninstall ( struct efi_usb_interface *usbintf ) {
        DBGC ( usbdev, "USBDEV %s uninstalling %s\n",
               usbintf->name, efi_handle_name ( usbintf->handle ) );
 
+       /* Disconnect controllers.  This should not be necessary, but
+        * seems to be required on some platforms to avoid failures
+        * when uninstalling protocols.
+        */
+       bs->DisconnectController ( usbintf->handle, NULL, NULL );
+
        /* Uninstall protocols */
        bs->UninstallMultipleProtocolInterfaces (
                        usbintf->handle,