Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

USB: xHCI: PCI power management implementation

This patch implements the PCI suspend/resume.

Please refer to xHCI spec for doing the suspend/resume operation.

For S3, CSS/SRS in USBCMD is used to save/restore the internal state.
However, an error maybe occurs while restoring the internal state.
In this case, it means that HC internal state is wrong and HC will be
re-initialized.

Signed-off-by: Libin Yang <libin.yang@amd.com>
Signed-off-by: Dong Nguyen <dong.nguyen@amd.com>
Signed-off-by: Andiry Xu <andiry.xu@amd.com>
Signed-off-by: Sarah Sharp <sarah.a.sharp@linux.intel.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>

authored by

Andiry Xu and committed by
Greg Kroah-Hartman
5535b1d5 9777e3ce

+258 -2
+33 -1
drivers/usb/host/xhci-pci.c
··· 116 116 return xhci_pci_reinit(xhci, pdev); 117 117 } 118 118 119 + #ifdef CONFIG_PM 120 + static int xhci_pci_suspend(struct usb_hcd *hcd, bool do_wakeup) 121 + { 122 + struct xhci_hcd *xhci = hcd_to_xhci(hcd); 123 + int retval = 0; 124 + 125 + if (hcd->state != HC_STATE_SUSPENDED) 126 + return -EINVAL; 127 + 128 + retval = xhci_suspend(xhci); 129 + 130 + return retval; 131 + } 132 + 133 + static int xhci_pci_resume(struct usb_hcd *hcd, bool hibernated) 134 + { 135 + struct xhci_hcd *xhci = hcd_to_xhci(hcd); 136 + int retval = 0; 137 + 138 + retval = xhci_resume(xhci, hibernated); 139 + return retval; 140 + } 141 + #endif /* CONFIG_PM */ 142 + 119 143 static const struct hc_driver xhci_pci_hc_driver = { 120 144 .description = hcd_name, 121 145 .product_desc = "xHCI Host Controller", ··· 156 132 */ 157 133 .reset = xhci_pci_setup, 158 134 .start = xhci_run, 159 - /* suspend and resume implemented later */ 135 + #ifdef CONFIG_PM 136 + .pci_suspend = xhci_pci_suspend, 137 + .pci_resume = xhci_pci_resume, 138 + #endif 160 139 .stop = xhci_stop, 161 140 .shutdown = xhci_shutdown, 162 141 ··· 215 188 /* suspend and resume implemented later */ 216 189 217 190 .shutdown = usb_hcd_pci_shutdown, 191 + #ifdef CONFIG_PM_SLEEP 192 + .driver = { 193 + .pm = &usb_hcd_pci_pm_ops 194 + }, 195 + #endif 218 196 }; 219 197 220 198 int xhci_register_pci(void)
+210
drivers/usb/host/xhci.c
··· 551 551 xhci_readl(xhci, &xhci->op_regs->status)); 552 552 } 553 553 554 + static void xhci_save_registers(struct xhci_hcd *xhci) 555 + { 556 + xhci->s3.command = xhci_readl(xhci, &xhci->op_regs->command); 557 + xhci->s3.dev_nt = xhci_readl(xhci, &xhci->op_regs->dev_notification); 558 + xhci->s3.dcbaa_ptr = xhci_read_64(xhci, &xhci->op_regs->dcbaa_ptr); 559 + xhci->s3.config_reg = xhci_readl(xhci, &xhci->op_regs->config_reg); 560 + xhci->s3.irq_pending = xhci_readl(xhci, &xhci->ir_set->irq_pending); 561 + xhci->s3.irq_control = xhci_readl(xhci, &xhci->ir_set->irq_control); 562 + xhci->s3.erst_size = xhci_readl(xhci, &xhci->ir_set->erst_size); 563 + xhci->s3.erst_base = xhci_read_64(xhci, &xhci->ir_set->erst_base); 564 + xhci->s3.erst_dequeue = xhci_read_64(xhci, &xhci->ir_set->erst_dequeue); 565 + } 566 + 567 + static void xhci_restore_registers(struct xhci_hcd *xhci) 568 + { 569 + xhci_writel(xhci, xhci->s3.command, &xhci->op_regs->command); 570 + xhci_writel(xhci, xhci->s3.dev_nt, &xhci->op_regs->dev_notification); 571 + xhci_write_64(xhci, xhci->s3.dcbaa_ptr, &xhci->op_regs->dcbaa_ptr); 572 + xhci_writel(xhci, xhci->s3.config_reg, &xhci->op_regs->config_reg); 573 + xhci_writel(xhci, xhci->s3.irq_pending, &xhci->ir_set->irq_pending); 574 + xhci_writel(xhci, xhci->s3.irq_control, &xhci->ir_set->irq_control); 575 + xhci_writel(xhci, xhci->s3.erst_size, &xhci->ir_set->erst_size); 576 + xhci_write_64(xhci, xhci->s3.erst_base, &xhci->ir_set->erst_base); 577 + } 578 + 579 + /* 580 + * Stop HC (not bus-specific) 581 + * 582 + * This is called when the machine transition into S3/S4 mode. 583 + * 584 + */ 585 + int xhci_suspend(struct xhci_hcd *xhci) 586 + { 587 + int rc = 0; 588 + struct usb_hcd *hcd = xhci_to_hcd(xhci); 589 + u32 command; 590 + 591 + spin_lock_irq(&xhci->lock); 592 + clear_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags); 593 + /* step 1: stop endpoint */ 594 + /* skipped assuming that port suspend has done */ 595 + 596 + /* step 2: clear Run/Stop bit */ 597 + command = xhci_readl(xhci, &xhci->op_regs->command); 598 + command &= ~CMD_RUN; 599 + xhci_writel(xhci, command, &xhci->op_regs->command); 600 + if (handshake(xhci, &xhci->op_regs->status, 601 + STS_HALT, STS_HALT, 100*100)) { 602 + xhci_warn(xhci, "WARN: xHC CMD_RUN timeout\n"); 603 + spin_unlock_irq(&xhci->lock); 604 + return -ETIMEDOUT; 605 + } 606 + 607 + /* step 3: save registers */ 608 + xhci_save_registers(xhci); 609 + 610 + /* step 4: set CSS flag */ 611 + command = xhci_readl(xhci, &xhci->op_regs->command); 612 + command |= CMD_CSS; 613 + xhci_writel(xhci, command, &xhci->op_regs->command); 614 + if (handshake(xhci, &xhci->op_regs->status, STS_SAVE, 0, 10*100)) { 615 + xhci_warn(xhci, "WARN: xHC CMD_CSS timeout\n"); 616 + spin_unlock_irq(&xhci->lock); 617 + return -ETIMEDOUT; 618 + } 619 + /* step 5: remove core well power */ 620 + xhci_cleanup_msix(xhci); 621 + spin_unlock_irq(&xhci->lock); 622 + 623 + return rc; 624 + } 625 + 626 + /* 627 + * start xHC (not bus-specific) 628 + * 629 + * This is called when the machine transition from S3/S4 mode. 630 + * 631 + */ 632 + int xhci_resume(struct xhci_hcd *xhci, bool hibernated) 633 + { 634 + u32 command, temp = 0; 635 + struct usb_hcd *hcd = xhci_to_hcd(xhci); 636 + struct pci_dev *pdev = to_pci_dev(hcd->self.controller); 637 + u64 val_64; 638 + int old_state, retval; 639 + 640 + old_state = hcd->state; 641 + if (time_before(jiffies, xhci->next_statechange)) 642 + msleep(100); 643 + 644 + spin_lock_irq(&xhci->lock); 645 + 646 + if (!hibernated) { 647 + /* step 1: restore register */ 648 + xhci_restore_registers(xhci); 649 + /* step 2: initialize command ring buffer */ 650 + val_64 = xhci_read_64(xhci, &xhci->op_regs->cmd_ring); 651 + val_64 = (val_64 & (u64) CMD_RING_RSVD_BITS) | 652 + (xhci_trb_virt_to_dma(xhci->cmd_ring->deq_seg, 653 + xhci->cmd_ring->dequeue) & 654 + (u64) ~CMD_RING_RSVD_BITS) | 655 + xhci->cmd_ring->cycle_state; 656 + xhci_dbg(xhci, "// Setting command ring address to 0x%llx\n", 657 + (long unsigned long) val_64); 658 + xhci_write_64(xhci, val_64, &xhci->op_regs->cmd_ring); 659 + /* step 3: restore state and start state*/ 660 + /* step 3: set CRS flag */ 661 + command = xhci_readl(xhci, &xhci->op_regs->command); 662 + command |= CMD_CRS; 663 + xhci_writel(xhci, command, &xhci->op_regs->command); 664 + if (handshake(xhci, &xhci->op_regs->status, 665 + STS_RESTORE, 0, 10*100)) { 666 + xhci_dbg(xhci, "WARN: xHC CMD_CSS timeout\n"); 667 + spin_unlock_irq(&xhci->lock); 668 + return -ETIMEDOUT; 669 + } 670 + temp = xhci_readl(xhci, &xhci->op_regs->status); 671 + } 672 + 673 + /* If restore operation fails, re-initialize the HC during resume */ 674 + if ((temp & STS_SRE) || hibernated) { 675 + usb_root_hub_lost_power(hcd->self.root_hub); 676 + 677 + xhci_dbg(xhci, "Stop HCD\n"); 678 + xhci_halt(xhci); 679 + xhci_reset(xhci); 680 + if (hibernated) 681 + xhci_cleanup_msix(xhci); 682 + spin_unlock_irq(&xhci->lock); 683 + 684 + #ifdef CONFIG_USB_XHCI_HCD_DEBUGGING 685 + /* Tell the event ring poll function not to reschedule */ 686 + xhci->zombie = 1; 687 + del_timer_sync(&xhci->event_ring_timer); 688 + #endif 689 + 690 + xhci_dbg(xhci, "// Disabling event ring interrupts\n"); 691 + temp = xhci_readl(xhci, &xhci->op_regs->status); 692 + xhci_writel(xhci, temp & ~STS_EINT, &xhci->op_regs->status); 693 + temp = xhci_readl(xhci, &xhci->ir_set->irq_pending); 694 + xhci_writel(xhci, ER_IRQ_DISABLE(temp), 695 + &xhci->ir_set->irq_pending); 696 + xhci_print_ir_set(xhci, xhci->ir_set, 0); 697 + 698 + xhci_dbg(xhci, "cleaning up memory\n"); 699 + xhci_mem_cleanup(xhci); 700 + xhci_dbg(xhci, "xhci_stop completed - status = %x\n", 701 + xhci_readl(xhci, &xhci->op_regs->status)); 702 + 703 + xhci_dbg(xhci, "Initialize the HCD\n"); 704 + retval = xhci_init(hcd); 705 + if (retval) 706 + return retval; 707 + 708 + xhci_dbg(xhci, "Start the HCD\n"); 709 + retval = xhci_run(hcd); 710 + if (!retval) 711 + set_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags); 712 + hcd->state = HC_STATE_SUSPENDED; 713 + return retval; 714 + } 715 + 716 + /* Re-setup MSI-X */ 717 + if (hcd->irq) 718 + free_irq(hcd->irq, hcd); 719 + hcd->irq = -1; 720 + 721 + retval = xhci_setup_msix(xhci); 722 + if (retval) 723 + /* fall back to msi*/ 724 + retval = xhci_setup_msi(xhci); 725 + 726 + if (retval) { 727 + /* fall back to legacy interrupt*/ 728 + retval = request_irq(pdev->irq, &usb_hcd_irq, IRQF_SHARED, 729 + hcd->irq_descr, hcd); 730 + if (retval) { 731 + xhci_err(xhci, "request interrupt %d failed\n", 732 + pdev->irq); 733 + return retval; 734 + } 735 + hcd->irq = pdev->irq; 736 + } 737 + 738 + /* step 4: set Run/Stop bit */ 739 + command = xhci_readl(xhci, &xhci->op_regs->command); 740 + command |= CMD_RUN; 741 + xhci_writel(xhci, command, &xhci->op_regs->command); 742 + handshake(xhci, &xhci->op_regs->status, STS_HALT, 743 + 0, 250 * 1000); 744 + 745 + /* step 5: walk topology and initialize portsc, 746 + * portpmsc and portli 747 + */ 748 + /* this is done in bus_resume */ 749 + 750 + /* step 6: restart each of the previously 751 + * Running endpoints by ringing their doorbells 752 + */ 753 + 754 + set_bit(HCD_FLAG_HW_ACCESSIBLE, &hcd->flags); 755 + if (!hibernated) 756 + hcd->state = old_state; 757 + else 758 + hcd->state = HC_STATE_SUSPENDED; 759 + 760 + spin_unlock_irq(&xhci->lock); 761 + return 0; 762 + } 763 + 554 764 /*-------------------------------------------------------------------------*/ 555 765 556 766 /**
+15 -1
drivers/usb/host/xhci.h
··· 191 191 /* bits 4:6 are reserved (and should be preserved on writes). */ 192 192 /* light reset (port status stays unchanged) - reset completed when this is 0 */ 193 193 #define CMD_LRESET (1 << 7) 194 - /* FIXME: ignoring host controller save/restore state for now. */ 194 + /* host controller save/restore state. */ 195 195 #define CMD_CSS (1 << 8) 196 196 #define CMD_CRS (1 << 9) 197 197 /* Enable Wrap Event - '1' means xHC generates an event when MFINDEX wraps. */ ··· 1130 1130 #define XHCI_STOP_EP_CMD_TIMEOUT 5 1131 1131 /* XXX: Make these module parameters */ 1132 1132 1133 + struct s3_save { 1134 + u32 command; 1135 + u32 dev_nt; 1136 + u64 dcbaa_ptr; 1137 + u32 config_reg; 1138 + u32 irq_pending; 1139 + u32 irq_control; 1140 + u32 erst_size; 1141 + u64 erst_base; 1142 + u64 erst_dequeue; 1143 + }; 1133 1144 1134 1145 /* There is one ehci_hci structure per controller */ 1135 1146 struct xhci_hcd { ··· 1209 1198 unsigned long next_statechange; 1210 1199 1211 1200 u32 command; 1201 + struct s3_save s3; 1212 1202 /* Host controller is dying - not responding to commands. "I'm not dead yet!" 1213 1203 * 1214 1204 * xHC interrupts have been disabled and a watchdog timer will (or has already) ··· 1405 1393 int xhci_run(struct usb_hcd *hcd); 1406 1394 void xhci_stop(struct usb_hcd *hcd); 1407 1395 void xhci_shutdown(struct usb_hcd *hcd); 1396 + int xhci_suspend(struct xhci_hcd *xhci); 1397 + int xhci_resume(struct xhci_hcd *xhci, bool hibernated); 1408 1398 int xhci_get_frame(struct usb_hcd *hcd); 1409 1399 irqreturn_t xhci_irq(struct usb_hcd *hcd); 1410 1400 irqreturn_t xhci_msi_irq(int irq, struct usb_hcd *hcd);