Skip to content

Commit 0b0a229

Browse files
Puma Hsugregkh
authored andcommitted
xhci: re-initialize the HC during resume if HCE was set
commit 8b328f8 upstream. When HCE(Host Controller Error) is set, it means an internal error condition has been detected. Software needs to re-initialize the HC, so add this check in xhci resume. Cc: stable@vger.kernel.org Signed-off-by: Puma Hsu <pumahsu@google.com> Signed-off-by: Mathias Nyman <mathias.nyman@linux.intel.com> Link: https://lore.kernel.org/r/20220215123320.1253947-2-mathias.nyman@linux.intel.com Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
1 parent 328faee commit 0b0a229

1 file changed

Lines changed: 13 additions & 6 deletions

File tree

drivers/usb/host/xhci.c

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1091,6 +1091,7 @@ int xhci_resume(struct xhci_hcd *xhci, bool hibernated)
10911091
int retval = 0;
10921092
bool comp_timer_running = false;
10931093
bool pending_portevent = false;
1094+
bool reinit_xhc = false;
10941095

10951096
if (!hcd->state)
10961097
return 0;
@@ -1107,10 +1108,11 @@ int xhci_resume(struct xhci_hcd *xhci, bool hibernated)
11071108
set_bit(HCD_FLAG_HW_ACCESSIBLE, &xhci->shared_hcd->flags);
11081109

11091110
spin_lock_irq(&xhci->lock);
1110-
if ((xhci->quirks & XHCI_RESET_ON_RESUME) || xhci->broken_suspend)
1111-
hibernated = true;
11121111

1113-
if (!hibernated) {
1112+
if (hibernated || xhci->quirks & XHCI_RESET_ON_RESUME || xhci->broken_suspend)
1113+
reinit_xhc = true;
1114+
1115+
if (!reinit_xhc) {
11141116
/*
11151117
* Some controllers might lose power during suspend, so wait
11161118
* for controller not ready bit to clear, just as in xHC init.
@@ -1143,12 +1145,17 @@ int xhci_resume(struct xhci_hcd *xhci, bool hibernated)
11431145
spin_unlock_irq(&xhci->lock);
11441146
return -ETIMEDOUT;
11451147
}
1146-
temp = readl(&xhci->op_regs->status);
11471148
}
11481149

1149-
/* If restore operation fails, re-initialize the HC during resume */
1150-
if ((temp & STS_SRE) || hibernated) {
1150+
temp = readl(&xhci->op_regs->status);
1151+
1152+
/* re-initialize the HC on Restore Error, or Host Controller Error */
1153+
if (temp & (STS_SRE | STS_HCE)) {
1154+
reinit_xhc = true;
1155+
xhci_warn(xhci, "xHC error in resume, USBSTS 0x%x, Reinit\n", temp);
1156+
}
11511157

1158+
if (reinit_xhc) {
11521159
if ((xhci->quirks & XHCI_COMP_MODE_QUIRK) &&
11531160
!(xhci_all_ports_seen_u0(xhci))) {
11541161
del_timer_sync(&xhci->comp_mode_recovery_timer);

0 commit comments

Comments
 (0)