summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--MdeModulePkg/Bus/Pci/EhciDxe/Ehci.c6
-rw-r--r--MdeModulePkg/Bus/Pci/EhciDxe/EhciReg.h29
-rw-r--r--MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBus.c7
-rw-r--r--MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c18
-rw-r--r--MdeModulePkg/Bus/Usb/UsbKbDxe/KeyBoard.c20
-rw-r--r--MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBoot.c15
-rw-r--r--MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBot.c7
-rw-r--r--MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassCbi.c6
8 files changed, 92 insertions, 16 deletions
diff --git a/MdeModulePkg/Bus/Pci/EhciDxe/Ehci.c b/MdeModulePkg/Bus/Pci/EhciDxe/Ehci.c
index c6c7e5a519..e130836216 100644
--- a/MdeModulePkg/Bus/Pci/EhciDxe/Ehci.c
+++ b/MdeModulePkg/Bus/Pci/EhciDxe/Ehci.c
@@ -1864,6 +1864,12 @@ EhcDriverBindingStop (
if (Ehc->ControllerNameTable != NULL) {
FreeUnicodeStringTable (Ehc->ControllerNameTable);
}
+
+ //
+ // Disable routing of all ports to EHCI controller, so all ports are
+ // routed back to the UHCI controller.
+ //
+ EhcClearOpRegBit (Ehc, EHC_CONFIG_FLAG_OFFSET, CONFIGFLAG_ROUTE_EHC);
//
// Restore original PCI attributes
diff --git a/MdeModulePkg/Bus/Pci/EhciDxe/EhciReg.h b/MdeModulePkg/Bus/Pci/EhciDxe/EhciReg.h
index 15fd661e3d..a995dc40c2 100644
--- a/MdeModulePkg/Bus/Pci/EhciDxe/EhciReg.h
+++ b/MdeModulePkg/Bus/Pci/EhciDxe/EhciReg.h
@@ -160,6 +160,35 @@ EhcWriteOpReg (
IN UINT32 Data
);
+/**
+ Set one bit of the operational register while keeping other bits.
+
+ @param Ehc The EHCI device.
+ @param Offset The offset of the operational register.
+ @param Bit The bit mask of the register to set.
+
+**/
+VOID
+EhcSetOpRegBit (
+ IN USB2_HC_DEV *Ehc,
+ IN UINT32 Offset,
+ IN UINT32 Bit
+ );
+
+/**
+ Clear one bit of the operational register while keeping other bits.
+
+ @param Ehc The EHCI device.
+ @param Offset The offset of the operational register.
+ @param Bit The bit mask of the register to clear.
+
+**/
+VOID
+EhcClearOpRegBit (
+ IN USB2_HC_DEV *Ehc,
+ IN UINT32 Offset,
+ IN UINT32 Bit
+ );
/**
Add support for UEFI Over Legacy (UoL) feature, stop
diff --git a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBus.c b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBus.c
index d0def777bd..1b66e75f67 100644
--- a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBus.c
+++ b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbBus.c
@@ -849,8 +849,9 @@ UsbIoPortReset (
Address = Dev->Address;
Dev->Address = 0;
Status = UsbSetAddress (Dev, Address);
- Dev->Address = Address;
-
+
+ gBS->Stall (USB_SET_DEVICE_ADDRESS_STALL);
+
if (EFI_ERROR (Status)) {
DEBUG (( EFI_D_ERROR, "UsbIoPortReset: failed to set address for device %d - %r\n",
Address, Status));
@@ -858,7 +859,7 @@ UsbIoPortReset (
goto ON_EXIT;
}
- gBS->Stall (USB_SET_DEVICE_ADDRESS_STALL);
+ Dev->Address = Address;
DEBUG (( EFI_D_INFO, "UsbIoPortReset: device is now ADDRESSED at %d\n", Address));
diff --git a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
index c1908cf14a..cd8a99d493 100644
--- a/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
+++ b/MdeModulePkg/Bus/Usb/UsbBusDxe/UsbDesc.c
@@ -42,7 +42,12 @@ UsbFreeInterfaceDesc (
}
}
- FreePool (Setting->Endpoints);
+ //
+ // Only call FreePool() if NumEndpoints > 0.
+ //
+ if (Setting->Desc.NumEndpoints > 0) {
+ FreePool (Setting->Endpoints);
+ }
}
FreePool (Setting);
@@ -192,10 +197,13 @@ UsbCreateDesc (
return NULL;
}
- Desc = AllocateCopyPool(CtrlLen, Head);
+ Desc = AllocateZeroPool (CtrlLen);
if (Desc == NULL) {
return NULL;
}
+
+ CopyMem (Desc, Head, DescLen);
+
*Consumed = Offset + Head->Len;
return Desc;
@@ -344,7 +352,11 @@ UsbParseConfigDesc (
DescBuf += Consumed;
Len -= Consumed;
- while (Len > 0) {
+ //
+ // Make allowances for devices that return extra data at the
+ // end of their config descriptors
+ //
+ while (Len >= sizeof (EFI_USB_INTERFACE_DESCRIPTOR)) {
Setting = UsbParseInterfaceDesc (DescBuf, Len, &Consumed);
if ((Setting == NULL)) {
diff --git a/MdeModulePkg/Bus/Usb/UsbKbDxe/KeyBoard.c b/MdeModulePkg/Bus/Usb/UsbKbDxe/KeyBoard.c
index 51ab18223e..80feb4694d 100644
--- a/MdeModulePkg/Bus/Usb/UsbKbDxe/KeyBoard.c
+++ b/MdeModulePkg/Bus/Usb/UsbKbDxe/KeyBoard.c
@@ -799,7 +799,7 @@ InitUSBKeyboard (
IN OUT USB_KB_DEV *UsbKeyboardDevice
)
{
- UINT8 ConfigValue;
+ UINT16 ConfigValue;
UINT8 Protocol;
UINT8 ReportId;
UINT8 Duration;
@@ -815,12 +815,24 @@ InitUSBKeyboard (
InitUSBKeyBuffer (&(UsbKeyboardDevice->KeyboardBuffer));
//
- // Uses default configuration to configure the USB keyboard device.
+ // Use the config out of the descriptor
+ // Assumed the first config is the correct one and this is not always the case
//
- ConfigValue = 0x01;
+ Status = UsbGetConfiguration (
+ UsbKeyboardDevice->UsbIo,
+ &ConfigValue,
+ &TransferResult
+ );
+ if (EFI_ERROR (Status)) {
+ ConfigValue = 0x01;
+ }
+
+ //
+ // Uses default configuration to configure the USB Keyboard device.
+ //
Status = UsbSetConfiguration (
UsbKeyboardDevice->UsbIo,
- (UINT16) ConfigValue,
+ ConfigValue,
&TransferResult
);
if (EFI_ERROR (Status)) {
diff --git a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBoot.c b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBoot.c
index 013b7e2cc3..7f3fb99e50 100644
--- a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBoot.c
+++ b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBoot.c
@@ -235,10 +235,11 @@ UsbBootExecCmdWithRetry (
{
EFI_STATUS Status;
UINTN Retry;
-
+ UINT8 Terminate;
+
Status = EFI_SUCCESS;
- for (Retry = 0; Retry < USB_BOOT_COMMAND_RETRY; Retry++) {
+ for (Retry = 0, Terminate = 0; Retry < USB_BOOT_COMMAND_RETRY; Retry++) {
Status = UsbBootExecCmd (
UsbMass,
@@ -255,8 +256,9 @@ UsbBootExecCmdWithRetry (
//
// If the device isn't ready, just wait for it without limit on retrial times.
//
- if (Status == EFI_NOT_READY) {
+ if (Status == EFI_NOT_READY && Terminate < 3) {
Retry = 0;
+ Terminate++;
}
}
@@ -410,7 +412,10 @@ UsbBootReadCapacity (
BlockSize = SwapBytes32 (ReadUnaligned32 ((CONST UINT32 *) CapacityData.BlockLen));
if (BlockSize == 0) {
- return EFI_NOT_READY;
+ //
+ // Get sense data
+ //
+ return UsbBootRequestSense (UsbMass);
} else {
Media->BlockSize = BlockSize;
}
@@ -418,7 +423,7 @@ UsbBootReadCapacity (
DEBUG ((EFI_D_INFO, "UsbBootReadCapacity Success LBA=%ld BlockSize=%d\n",
Media->LastBlock, Media->BlockSize));
- return EFI_SUCCESS;
+ return Status;
}
/**
diff --git a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBot.c b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBot.c
index ab669463c8..681424883b 100644
--- a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBot.c
+++ b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassBot.c
@@ -273,10 +273,17 @@ UsbBotDataTransfer (
);
if (EFI_ERROR (Status)) {
if (USB_IS_ERROR (Result, EFI_USB_ERR_STALL)) {
+ DEBUG ((EFI_D_INFO, "UsbBotDataTransfer: (%r)\n", Status));
+ DEBUG ((EFI_D_INFO, "UsbBotDataTransfer: DataIn Stall\n"));
UsbClearEndpointStall (UsbBot->UsbIo, Endpoint->EndpointAddress);
} else if (USB_IS_ERROR (Result, EFI_USB_ERR_NAK)) {
Status = EFI_NOT_READY;
+ } else {
+ DEBUG ((EFI_D_ERROR, "UsbBotDataTransfer: (%r)\n", Status));
}
+ if(Status == EFI_TIMEOUT){
+ UsbBotResetDevice(UsbBot, FALSE);
+ }
}
return Status;
diff --git a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassCbi.c b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassCbi.c
index 4de18d4bb9..5b6dfd0fe9 100644
--- a/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassCbi.c
+++ b/MdeModulePkg/Bus/Usb/UsbMassStorageDxe/UsbMassCbi.c
@@ -457,6 +457,7 @@ UsbCbiExecCommand (
//
Status = UsbCbiSendCommand (UsbCbi, Cmd, CmdLen, Timeout);
if (EFI_ERROR (Status)) {
+ gBS->Stall(10 * USB_MASS_1_MILLISECOND);
DEBUG ((EFI_D_ERROR, "UsbCbiExecCommand: UsbCbiSendCommand (%r)\n",Status));
return Status;
}
@@ -486,7 +487,10 @@ UsbCbiExecCommand (
//
// For UFI device, ASC and ASCQ are returned.
//
- if (Result.Type != 0) {
+ // Do not set the USB_MASS_CMD_FAIL for a request sense command
+ // as a bad result type doesn't mean a cmd failure
+ //
+ if (Result.Type != 0 && *(UINT8*)Cmd != 0x03) {
*CmdStatus = USB_MASS_CMD_FAIL;
}