From 63894979e0a413a6668b1bd3b7d88a6960522a60 Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Thu, 19 Dec 2019 10:33:01 +0100 Subject: [PATCH] 4.19-stable patches added patches: mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch mmc-block-make-card_busy_detect-a-bit-more-generic.patch pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch pci-fix-intel-acs-quirk-updcr-register-address.patch pci-msi-fix-incorrect-msi-x-masking-on-resume.patch pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch pci-pm-always-return-devices-to-d0-when-thawing.patch pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch --- ...ing-for-mmc-ioctls-with-r1b-response.patch | 211 ++++++++++++++++++ ...-card_busy_detect-a-bit-more-generic.patch | 76 +++++++ ...acs-quirk-to-thunderx2-and-thunderx3.patch | 56 +++++ ...tel-acs-quirk-updcr-register-address.patch | 46 ++++ ...ix-incorrect-msi-x-masking-on-resume.patch | 63 ++++++ ...ning-prematurely-from-sysfs-requests.patch | 95 ++++++++ ...ys-return-devices-to-d0-when-thawing.patch | 87 ++++++++ ...ead-all-64-bits-of-part_event_bitmap.patch | 36 +++ queue-4.19/series | 8 + 9 files changed, 678 insertions(+) create mode 100644 queue-4.19/mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch create mode 100644 queue-4.19/mmc-block-make-card_busy_detect-a-bit-more-generic.patch create mode 100644 queue-4.19/pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch create mode 100644 queue-4.19/pci-fix-intel-acs-quirk-updcr-register-address.patch create mode 100644 queue-4.19/pci-msi-fix-incorrect-msi-x-masking-on-resume.patch create mode 100644 queue-4.19/pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch create mode 100644 queue-4.19/pci-pm-always-return-devices-to-d0-when-thawing.patch create mode 100644 queue-4.19/pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch diff --git a/queue-4.19/mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch b/queue-4.19/mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch new file mode 100644 index 00000000000..e0d019cae8b --- /dev/null +++ b/queue-4.19/mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch @@ -0,0 +1,211 @@ +From a0d4c7eb71dd08a89ad631177bb0cbbabd598f84 Mon Sep 17 00:00:00 2001 +From: Chaotian Jing +Date: Thu, 5 Sep 2019 15:53:18 +0800 +Subject: mmc: block: Add CMD13 polling for MMC IOCTLS with R1B response + +From: Chaotian Jing + +commit a0d4c7eb71dd08a89ad631177bb0cbbabd598f84 upstream. + +MMC IOCTLS with R1B responses may cause the card to enter the busy state, +which means it's not ready to receive a new request. To prevent new +requests from being sent to the card, use a CMD13 polling loop to verify +that the card returns to the transfer state, before completing the request. + +Signed-off-by: Chaotian Jing +Reviewed-by: Avri Altman +Cc: stable@vger.kernel.org +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/core/block.c | 147 +++++++++++++++++------------------------------ + 1 file changed, 55 insertions(+), 92 deletions(-) + +--- a/drivers/mmc/core/block.c ++++ b/drivers/mmc/core/block.c +@@ -409,38 +409,6 @@ static int mmc_blk_ioctl_copy_to_user(st + return 0; + } + +-static int ioctl_rpmb_card_status_poll(struct mmc_card *card, u32 *status, +- u32 retries_max) +-{ +- int err; +- u32 retry_count = 0; +- +- if (!status || !retries_max) +- return -EINVAL; +- +- do { +- err = __mmc_send_status(card, status, 5); +- if (err) +- break; +- +- if (!R1_STATUS(*status) && +- (R1_CURRENT_STATE(*status) != R1_STATE_PRG)) +- break; /* RPMB programming operation complete */ +- +- /* +- * Rechedule to give the MMC device a chance to continue +- * processing the previous command without being polled too +- * frequently. +- */ +- usleep_range(1000, 5000); +- } while (++retry_count < retries_max); +- +- if (retry_count == retries_max) +- err = -EPERM; +- +- return err; +-} +- + static int ioctl_do_sanitize(struct mmc_card *card) + { + int err; +@@ -469,6 +437,58 @@ out: + return err; + } + ++static inline bool mmc_blk_in_tran_state(u32 status) ++{ ++ /* ++ * Some cards mishandle the status bits, so make sure to check both the ++ * busy indication and the card state. ++ */ ++ return status & R1_READY_FOR_DATA && ++ (R1_CURRENT_STATE(status) == R1_STATE_TRAN); ++} ++ ++static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms, ++ u32 *resp_errs) ++{ ++ unsigned long timeout = jiffies + msecs_to_jiffies(timeout_ms); ++ int err = 0; ++ u32 status; ++ ++ do { ++ bool done = time_after(jiffies, timeout); ++ ++ err = __mmc_send_status(card, &status, 5); ++ if (err) { ++ dev_err(mmc_dev(card->host), ++ "error %d requesting status\n", err); ++ return err; ++ } ++ ++ /* Accumulate any response error bits seen */ ++ if (resp_errs) ++ *resp_errs |= status; ++ ++ /* ++ * Timeout if the device never becomes ready for data and never ++ * leaves the program state. ++ */ ++ if (done) { ++ dev_err(mmc_dev(card->host), ++ "Card stuck in wrong state! %s status: %#x\n", ++ __func__, status); ++ return -ETIMEDOUT; ++ } ++ ++ /* ++ * Some cards mishandle the status bits, ++ * so make sure to check both the busy ++ * indication and the card state. ++ */ ++ } while (!mmc_blk_in_tran_state(status)); ++ ++ return err; ++} ++ + static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data *md, + struct mmc_blk_ioc_data *idata) + { +@@ -478,7 +498,6 @@ static int __mmc_blk_ioctl_cmd(struct mm + struct scatterlist sg; + int err; + unsigned int target_part; +- u32 status = 0; + + if (!card || !md || !idata) + return -EINVAL; +@@ -612,16 +631,12 @@ static int __mmc_blk_ioctl_cmd(struct mm + + memcpy(&(idata->ic.response), cmd.resp, sizeof(cmd.resp)); + +- if (idata->rpmb) { ++ if (idata->rpmb || (cmd.flags & MMC_RSP_R1B)) { + /* +- * Ensure RPMB command has completed by polling CMD13 ++ * Ensure RPMB/R1B command has completed by polling CMD13 + * "Send Status". + */ +- err = ioctl_rpmb_card_status_poll(card, &status, 5); +- if (err) +- dev_err(mmc_dev(card->host), +- "%s: Card Status=0x%08X, error %d\n", +- __func__, status, err); ++ err = card_busy_detect(card, MMC_BLK_TIMEOUT_MS, NULL); + } + + return err; +@@ -971,58 +986,6 @@ static unsigned int mmc_blk_data_timeout + return ms; + } + +-static inline bool mmc_blk_in_tran_state(u32 status) +-{ +- /* +- * Some cards mishandle the status bits, so make sure to check both the +- * busy indication and the card state. +- */ +- return status & R1_READY_FOR_DATA && +- (R1_CURRENT_STATE(status) == R1_STATE_TRAN); +-} +- +-static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms, +- u32 *resp_errs) +-{ +- unsigned long timeout = jiffies + msecs_to_jiffies(timeout_ms); +- int err = 0; +- u32 status; +- +- do { +- bool done = time_after(jiffies, timeout); +- +- err = __mmc_send_status(card, &status, 5); +- if (err) { +- dev_err(mmc_dev(card->host), +- "error %d requesting status\n", err); +- return err; +- } +- +- /* Accumulate any response error bits seen */ +- if (resp_errs) +- *resp_errs |= status; +- +- /* +- * Timeout if the device never becomes ready for data and never +- * leaves the program state. +- */ +- if (done) { +- dev_err(mmc_dev(card->host), +- "Card stuck in wrong state! %s status: %#x\n", +- __func__, status); +- return -ETIMEDOUT; +- } +- +- /* +- * Some cards mishandle the status bits, +- * so make sure to check both the busy +- * indication and the card state. +- */ +- } while (!mmc_blk_in_tran_state(status)); +- +- return err; +-} +- + static int mmc_blk_reset(struct mmc_blk_data *md, struct mmc_host *host, + int type) + { diff --git a/queue-4.19/mmc-block-make-card_busy_detect-a-bit-more-generic.patch b/queue-4.19/mmc-block-make-card_busy_detect-a-bit-more-generic.patch new file mode 100644 index 00000000000..41c5c43a383 --- /dev/null +++ b/queue-4.19/mmc-block-make-card_busy_detect-a-bit-more-generic.patch @@ -0,0 +1,76 @@ +From 3869468e0c4800af52bfe1e0b72b338dcdae2cfc Mon Sep 17 00:00:00 2001 +From: Chaotian Jing +Date: Thu, 5 Sep 2019 15:53:17 +0800 +Subject: mmc: block: Make card_busy_detect() a bit more generic + +From: Chaotian Jing + +commit 3869468e0c4800af52bfe1e0b72b338dcdae2cfc upstream. + +To prepare for more users of card_busy_detect(), let's drop the struct +request * as an in-parameter and convert to log the error message via +dev_err() instead of pr_err(). + +Signed-off-by: Chaotian Jing +Reviewed-by: Avri Altman +Cc: stable@vger.kernel.org +Signed-off-by: Ulf Hansson +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/mmc/core/block.c | 16 ++++++++-------- + 1 file changed, 8 insertions(+), 8 deletions(-) + +--- a/drivers/mmc/core/block.c ++++ b/drivers/mmc/core/block.c +@@ -982,7 +982,7 @@ static inline bool mmc_blk_in_tran_state + } + + static int card_busy_detect(struct mmc_card *card, unsigned int timeout_ms, +- struct request *req, u32 *resp_errs) ++ u32 *resp_errs) + { + unsigned long timeout = jiffies + msecs_to_jiffies(timeout_ms); + int err = 0; +@@ -993,8 +993,8 @@ static int card_busy_detect(struct mmc_c + + err = __mmc_send_status(card, &status, 5); + if (err) { +- pr_err("%s: error %d requesting status\n", +- req->rq_disk->disk_name, err); ++ dev_err(mmc_dev(card->host), ++ "error %d requesting status\n", err); + return err; + } + +@@ -1007,9 +1007,9 @@ static int card_busy_detect(struct mmc_c + * leaves the program state. + */ + if (done) { +- pr_err("%s: Card stuck in wrong state! %s %s status: %#x\n", +- mmc_hostname(card->host), +- req->rq_disk->disk_name, __func__, status); ++ dev_err(mmc_dev(card->host), ++ "Card stuck in wrong state! %s status: %#x\n", ++ __func__, status); + return -ETIMEDOUT; + } + +@@ -1678,7 +1678,7 @@ static int mmc_blk_fix_state(struct mmc_ + + mmc_blk_send_stop(card, timeout); + +- err = card_busy_detect(card, timeout, req, NULL); ++ err = card_busy_detect(card, timeout, NULL); + + mmc_retune_release(card->host); + +@@ -1902,7 +1902,7 @@ static int mmc_blk_card_busy(struct mmc_ + if (mmc_host_is_spi(card->host) || rq_data_dir(req) == READ) + return 0; + +- err = card_busy_detect(card, MMC_BLK_TIMEOUT_MS, req, &status); ++ err = card_busy_detect(card, MMC_BLK_TIMEOUT_MS, &status); + + /* + * Do not assume data transferred correctly if there are any error bits diff --git a/queue-4.19/pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch b/queue-4.19/pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch new file mode 100644 index 00000000000..f5423a87c95 --- /dev/null +++ b/queue-4.19/pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch @@ -0,0 +1,56 @@ +From f338bb9f0179cb959977b74e8331b312264d720b Mon Sep 17 00:00:00 2001 +From: George Cherian +Date: Mon, 11 Nov 2019 02:43:03 +0000 +Subject: PCI: Apply Cavium ACS quirk to ThunderX2 and ThunderX3 + +From: George Cherian + +commit f338bb9f0179cb959977b74e8331b312264d720b upstream. + +Enhance the ACS quirk for Cavium Processors. Add the root port vendor IDs +for ThunderX2 and ThunderX3 series of processors. + +[bhelgaas: add Fixes: and stable tag] +Fixes: f2ddaf8dfd4a ("PCI: Apply Cavium ThunderX ACS quirk to more Root Ports") +Link: https://lore.kernel.org/r/20191111024243.GA11408@dc5-eodlnx05.marvell.com +Signed-off-by: George Cherian +Signed-off-by: Bjorn Helgaas +Reviewed-by: Robert Richter +Cc: stable@vger.kernel.org # v4.12+ +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/quirks.c | 20 +++++++++++++------- + 1 file changed, 13 insertions(+), 7 deletions(-) + +--- a/drivers/pci/quirks.c ++++ b/drivers/pci/quirks.c +@@ -4219,15 +4219,21 @@ static int pci_quirk_amd_sb_acs(struct p + + static bool pci_quirk_cavium_acs_match(struct pci_dev *dev) + { ++ if (!pci_is_pcie(dev) || pci_pcie_type(dev) != PCI_EXP_TYPE_ROOT_PORT) ++ return false; ++ ++ switch (dev->device) { + /* +- * Effectively selects all downstream ports for whole ThunderX 1 +- * family by 0xf800 mask (which represents 8 SoCs), while the lower +- * bits of device ID are used to indicate which subdevice is used +- * within the SoC. ++ * Effectively selects all downstream ports for whole ThunderX1 ++ * (which represents 8 SoCs). + */ +- return (pci_is_pcie(dev) && +- (pci_pcie_type(dev) == PCI_EXP_TYPE_ROOT_PORT) && +- ((dev->device & 0xf800) == 0xa000)); ++ case 0xa000 ... 0xa7ff: /* ThunderX1 */ ++ case 0xaf84: /* ThunderX2 */ ++ case 0xb884: /* ThunderX3 */ ++ return true; ++ default: ++ return false; ++ } + } + + static int pci_quirk_cavium_acs(struct pci_dev *dev, u16 acs_flags) diff --git a/queue-4.19/pci-fix-intel-acs-quirk-updcr-register-address.patch b/queue-4.19/pci-fix-intel-acs-quirk-updcr-register-address.patch new file mode 100644 index 00000000000..f4ea6fd6f11 --- /dev/null +++ b/queue-4.19/pci-fix-intel-acs-quirk-updcr-register-address.patch @@ -0,0 +1,46 @@ +From d8558ac8c93d429d65d7490b512a3a67e559d0d4 Mon Sep 17 00:00:00 2001 +From: Steffen Liebergeld +Date: Wed, 18 Sep 2019 15:16:52 +0200 +Subject: PCI: Fix Intel ACS quirk UPDCR register address + +From: Steffen Liebergeld + +commit d8558ac8c93d429d65d7490b512a3a67e559d0d4 upstream. + +According to documentation [0] the correct offset for the Upstream Peer +Decode Configuration Register (UPDCR) is 0x1014. It was previously defined +as 0x1114. + +d99321b63b1f ("PCI: Enable quirks for PCIe ACS on Intel PCH root ports") +intended to enforce isolation between PCI devices allowing them to be put +into separate IOMMU groups. Due to the wrong register offset the intended +isolation was not fully enforced. This is fixed with this patch. + +Please note that I did not test this patch because I have no hardware that +implements this register. + +[0] https://www.intel.com/content/dam/www/public/us/en/documents/datasheets/4th-gen-core-family-mobile-i-o-datasheet.pdf (page 325) +Fixes: d99321b63b1f ("PCI: Enable quirks for PCIe ACS on Intel PCH root ports") +Link: https://lore.kernel.org/r/7a3505df-79ba-8a28-464c-88b83eefffa6@kernkonzept.com +Signed-off-by: Steffen Liebergeld +Signed-off-by: Bjorn Helgaas +Reviewed-by: Andrew Murray +Acked-by: Ashok Raj +Cc: stable@vger.kernel.org # v3.15+ +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/quirks.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/pci/quirks.c ++++ b/drivers/pci/quirks.c +@@ -4576,7 +4576,7 @@ int pci_dev_specific_acs_enabled(struct + #define INTEL_BSPR_REG_BPPD (1 << 9) + + /* Upstream Peer Decode Configuration Register */ +-#define INTEL_UPDCR_REG 0x1114 ++#define INTEL_UPDCR_REG 0x1014 + /* 5:0 Peer Decode Enable bits */ + #define INTEL_UPDCR_REG_MASK 0x3f + diff --git a/queue-4.19/pci-msi-fix-incorrect-msi-x-masking-on-resume.patch b/queue-4.19/pci-msi-fix-incorrect-msi-x-masking-on-resume.patch new file mode 100644 index 00000000000..4ef7c69a32c --- /dev/null +++ b/queue-4.19/pci-msi-fix-incorrect-msi-x-masking-on-resume.patch @@ -0,0 +1,63 @@ +From e045fa29e89383c717e308609edd19d2fd29e1be Mon Sep 17 00:00:00 2001 +From: Jian-Hong Pan +Date: Tue, 8 Oct 2019 11:42:39 +0800 +Subject: PCI/MSI: Fix incorrect MSI-X masking on resume + +From: Jian-Hong Pan + +commit e045fa29e89383c717e308609edd19d2fd29e1be upstream. + +When a driver enables MSI-X, msix_program_entries() reads the MSI-X Vector +Control register for each vector and saves it in desc->masked. Each +register is 32 bits and bit 0 is the actual Mask bit. + +When we restored these registers during resume, we previously set the Mask +bit if *any* bit in desc->masked was set instead of when the Mask bit +itself was set: + + pci_restore_state + pci_restore_msi_state + __pci_restore_msix_state + for_each_pci_msi_entry + msix_mask_irq(entry, entry->masked) <-- entire u32 word + __pci_msix_desc_mask_irq(desc, flag) + mask_bits = desc->masked & ~PCI_MSIX_ENTRY_CTRL_MASKBIT + if (flag) <-- testing entire u32, not just bit 0 + mask_bits |= PCI_MSIX_ENTRY_CTRL_MASKBIT + writel(mask_bits, desc_addr + PCI_MSIX_ENTRY_VECTOR_CTRL) + +This means that after resume, MSI-X vectors were masked when they shouldn't +be, which leads to timeouts like this: + + nvme nvme0: I/O 978 QID 3 timeout, completion polled + +On resume, set the Mask bit only when the saved Mask bit from suspend was +set. + +This should remove the need for 19ea025e1d28 ("nvme: Add quirk for Kingston +NVME SSD running FW E8FK11.T"). + +[bhelgaas: commit log, move fix to __pci_msix_desc_mask_irq()] +Link: https://bugzilla.kernel.org/show_bug.cgi?id=204887 +Link: https://lore.kernel.org/r/20191008034238.2503-1-jian-hong@endlessm.com +Fixes: f2440d9acbe8 ("PCI MSI: Refactor interrupt masking code") +Signed-off-by: Jian-Hong Pan +Signed-off-by: Bjorn Helgaas +Cc: stable@vger.kernel.org +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/msi.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/pci/msi.c ++++ b/drivers/pci/msi.c +@@ -211,7 +211,7 @@ u32 __pci_msix_desc_mask_irq(struct msi_ + return 0; + + mask_bits &= ~PCI_MSIX_ENTRY_CTRL_MASKBIT; +- if (flag) ++ if (flag & PCI_MSIX_ENTRY_CTRL_MASKBIT) + mask_bits |= PCI_MSIX_ENTRY_CTRL_MASKBIT; + writel(mask_bits, pci_msix_desc_addr(desc) + PCI_MSIX_ENTRY_VECTOR_CTRL); + diff --git a/queue-4.19/pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch b/queue-4.19/pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch new file mode 100644 index 00000000000..7dc481872ab --- /dev/null +++ b/queue-4.19/pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch @@ -0,0 +1,95 @@ +From 157c1062fcd86ade3c674503705033051fd3d401 Mon Sep 17 00:00:00 2001 +From: Lukas Wunner +Date: Fri, 9 Aug 2019 12:28:43 +0200 +Subject: PCI: pciehp: Avoid returning prematurely from sysfs requests + +From: Lukas Wunner + +commit 157c1062fcd86ade3c674503705033051fd3d401 upstream. + +A sysfs request to enable or disable a PCIe hotplug slot should not +return before it has been carried out. That is sought to be achieved by +waiting until the controller's "pending_events" have been cleared. + +However the IRQ thread pciehp_ist() clears the "pending_events" before +it acts on them. If pciehp_sysfs_enable_slot() / _disable_slot() happen +to check the "pending_events" after they have been cleared but while +pciehp_ist() is still running, the functions may return prematurely +with an incorrect return value. + +Fix by introducing an "ist_running" flag which must be false before a sysfs +request is allowed to return. + +Fixes: 32a8cef274fe ("PCI: pciehp: Enable/disable exclusively from IRQ thread") +Link: https://lore.kernel.org/linux-pci/1562226638-54134-1-git-send-email-wangxiongfeng2@huawei.com +Link: https://lore.kernel.org/r/4174210466e27eb7e2243dd1d801d5f75baaffd8.1565345211.git.lukas@wunner.de +Reported-and-tested-by: Xiongfeng Wang +Signed-off-by: Lukas Wunner +Signed-off-by: Bjorn Helgaas +Cc: stable@vger.kernel.org # v4.19+ +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/hotplug/pciehp.h | 2 ++ + drivers/pci/hotplug/pciehp_ctrl.c | 6 ++++-- + drivers/pci/hotplug/pciehp_hpc.c | 2 ++ + 3 files changed, 8 insertions(+), 2 deletions(-) + +--- a/drivers/pci/hotplug/pciehp.h ++++ b/drivers/pci/hotplug/pciehp.h +@@ -106,6 +106,7 @@ struct slot { + * that has not yet been cleared by the user + * @pending_events: used by the IRQ handler to save events retrieved from the + * Slot Status register for later consumption by the IRQ thread ++ * @ist_running: flag to keep user request waiting while IRQ thread is running + * @request_result: result of last user request submitted to the IRQ thread + * @requester: wait queue to wake up on completion of user request, + * used for synchronous slot enable/disable request via sysfs +@@ -125,6 +126,7 @@ struct controller { + unsigned int notification_enabled:1; + unsigned int power_fault_detected; + atomic_t pending_events; ++ unsigned int ist_running; + int request_result; + wait_queue_head_t requester; + }; +--- a/drivers/pci/hotplug/pciehp_ctrl.c ++++ b/drivers/pci/hotplug/pciehp_ctrl.c +@@ -383,7 +383,8 @@ int pciehp_sysfs_enable_slot(struct slot + ctrl->request_result = -ENODEV; + pciehp_request(ctrl, PCI_EXP_SLTSTA_PDC); + wait_event(ctrl->requester, +- !atomic_read(&ctrl->pending_events)); ++ !atomic_read(&ctrl->pending_events) && ++ !ctrl->ist_running); + return ctrl->request_result; + case POWERON_STATE: + ctrl_info(ctrl, "Slot(%s): Already in powering on state\n", +@@ -416,7 +417,8 @@ int pciehp_sysfs_disable_slot(struct slo + mutex_unlock(&p_slot->lock); + pciehp_request(ctrl, DISABLE_SLOT); + wait_event(ctrl->requester, +- !atomic_read(&ctrl->pending_events)); ++ !atomic_read(&ctrl->pending_events) && ++ !ctrl->ist_running); + return ctrl->request_result; + case POWEROFF_STATE: + ctrl_info(ctrl, "Slot(%s): Already in powering off state\n", +--- a/drivers/pci/hotplug/pciehp_hpc.c ++++ b/drivers/pci/hotplug/pciehp_hpc.c +@@ -620,6 +620,7 @@ static irqreturn_t pciehp_ist(int irq, v + irqreturn_t ret; + u32 events; + ++ ctrl->ist_running = true; + pci_config_pm_runtime_get(pdev); + + /* rerun pciehp_isr() if the port was inaccessible on interrupt */ +@@ -666,6 +667,7 @@ static irqreturn_t pciehp_ist(int irq, v + up_read(&ctrl->reset_lock); + + pci_config_pm_runtime_put(pdev); ++ ctrl->ist_running = false; + wake_up(&ctrl->requester); + return IRQ_HANDLED; + } diff --git a/queue-4.19/pci-pm-always-return-devices-to-d0-when-thawing.patch b/queue-4.19/pci-pm-always-return-devices-to-d0-when-thawing.patch new file mode 100644 index 00000000000..d2ea91c3c96 --- /dev/null +++ b/queue-4.19/pci-pm-always-return-devices-to-d0-when-thawing.patch @@ -0,0 +1,87 @@ +From f2c33ccacb2d4bbeae2a255a7ca0cbfd03017b7c Mon Sep 17 00:00:00 2001 +From: Dexuan Cui +Date: Wed, 14 Aug 2019 01:06:55 +0000 +Subject: PCI/PM: Always return devices to D0 when thawing + +From: Dexuan Cui + +commit f2c33ccacb2d4bbeae2a255a7ca0cbfd03017b7c upstream. + +pci_pm_thaw_noirq() is supposed to return the device to D0 and restore its +configuration registers, but previously it only did that for devices whose +drivers implemented the new power management ops. + +Hibernation, e.g., via "echo disk > /sys/power/state", involves freezing +devices, creating a hibernation image, thawing devices, writing the image, +and powering off. The fact that thawing did not return devices with legacy +power management to D0 caused errors, e.g., in this path: + + pci_pm_thaw_noirq + if (pci_has_legacy_pm_support(pci_dev)) # true for Mellanox VF driver + return pci_legacy_resume_early(dev) # ... legacy PM skips the rest + pci_set_power_state(pci_dev, PCI_D0) + pci_restore_state(pci_dev) + pci_pm_thaw + if (pci_has_legacy_pm_support(pci_dev)) + pci_legacy_resume + drv->resume + mlx4_resume + ... + pci_enable_msix_range + ... + if (dev->current_state != PCI_D0) # <--- + return -EINVAL; + +which caused these warnings: + + mlx4_core a6d1:00:02.0: INTx is not supported in multi-function mode, aborting + PM: dpm_run_callback(): pci_pm_thaw+0x0/0xd7 returns -95 + PM: Device a6d1:00:02.0 failed to thaw: error -95 + +Return devices to D0 and restore config registers for all devices, not just +those whose drivers support new power management. + +[bhelgaas: also call pci_restore_state() before pci_legacy_resume_early(), +update comment, add stable tag, commit log] +Link: https://lore.kernel.org/r/KU1P153MB016637CAEAD346F0AA8E3801BFAD0@KU1P153MB0166.APCP153.PROD.OUTLOOK.COM +Signed-off-by: Dexuan Cui +Signed-off-by: Bjorn Helgaas +Reviewed-by: Rafael J. Wysocki +Cc: stable@vger.kernel.org # v4.13+ +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/pci-driver.c | 17 +++++++++++------ + 1 file changed, 11 insertions(+), 6 deletions(-) + +--- a/drivers/pci/pci-driver.c ++++ b/drivers/pci/pci-driver.c +@@ -1042,17 +1042,22 @@ static int pci_pm_thaw_noirq(struct devi + return error; + } + +- if (pci_has_legacy_pm_support(pci_dev)) +- return pci_legacy_resume_early(dev); +- + /* +- * pci_restore_state() requires the device to be in D0 (because of MSI +- * restoration among other things), so force it into D0 in case the +- * driver's "freeze" callbacks put it into a low-power state directly. ++ * Both the legacy ->resume_early() and the new pm->thaw_noirq() ++ * callbacks assume the device has been returned to D0 and its ++ * config state has been restored. ++ * ++ * In addition, pci_restore_state() restores MSI-X state in MMIO ++ * space, which requires the device to be in D0, so return it to D0 ++ * in case the driver's "freeze" callbacks put it into a low-power ++ * state. + */ + pci_set_power_state(pci_dev, PCI_D0); + pci_restore_state(pci_dev); + ++ if (pci_has_legacy_pm_support(pci_dev)) ++ return pci_legacy_resume_early(dev); ++ + if (drv && drv->pm && drv->pm->thaw_noirq) + error = drv->pm->thaw_noirq(dev); + diff --git a/queue-4.19/pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch b/queue-4.19/pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch new file mode 100644 index 00000000000..424dd5dfb03 --- /dev/null +++ b/queue-4.19/pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch @@ -0,0 +1,36 @@ +From 6acdf7e19b37cb3a9258603d0eab315079c19c5e Mon Sep 17 00:00:00 2001 +From: Logan Gunthorpe +Date: Tue, 10 Sep 2019 13:58:33 -0600 +Subject: PCI/switchtec: Read all 64 bits of part_event_bitmap + +From: Logan Gunthorpe + +commit 6acdf7e19b37cb3a9258603d0eab315079c19c5e upstream. + +The part_event_bitmap register is 64 bits wide, so read it with ioread64() +instead of the 32-bit ioread32(). + +Fixes: 52eabba5bcdb ("switchtec: Add IOCTLs to the Switchtec driver") +Link: https://lore.kernel.org/r/20190910195833.3891-1-logang@deltatee.com +Reported-by: Doug Meyer +Signed-off-by: Logan Gunthorpe +Signed-off-by: Bjorn Helgaas +Cc: stable@vger.kernel.org # v4.12+ +Cc: Kelvin Cao +Signed-off-by: Greg Kroah-Hartman + +--- + drivers/pci/switch/switchtec.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +--- a/drivers/pci/switch/switchtec.c ++++ b/drivers/pci/switch/switchtec.c +@@ -633,7 +633,7 @@ static int ioctl_event_summary(struct sw + u32 reg; + + s.global = ioread32(&stdev->mmio_sw_event->global_summary); +- s.part_bitmap = ioread32(&stdev->mmio_sw_event->part_event_bitmap); ++ s.part_bitmap = ioread64(&stdev->mmio_sw_event->part_event_bitmap); + s.local_part = ioread32(&stdev->mmio_part_cfg->part_event_summary); + + for (i = 0; i < stdev->partition_count; i++) { diff --git a/queue-4.19/series b/queue-4.19/series index e57b6fb5ab4..306c8dda946 100644 --- a/queue-4.19/series +++ b/queue-4.19/series @@ -13,3 +13,11 @@ tcp-fix-rejected-syncookies-due-to-stale-timestamps.patch tcp-tighten-acceptance-of-acks-not-matching-a-child-socket.patch tcp-protect-accesses-to-.ts_recent_stamp-with-read-write-_once.patch revert-arm64-preempt-fix-big-endian-when-checking-preempt-count-in-assembly.patch +mmc-block-make-card_busy_detect-a-bit-more-generic.patch +mmc-block-add-cmd13-polling-for-mmc-ioctls-with-r1b-response.patch +pci-switchtec-read-all-64-bits-of-part_event_bitmap.patch +pci-pm-always-return-devices-to-d0-when-thawing.patch +pci-pciehp-avoid-returning-prematurely-from-sysfs-requests.patch +pci-fix-intel-acs-quirk-updcr-register-address.patch +pci-msi-fix-incorrect-msi-x-masking-on-resume.patch +pci-apply-cavium-acs-quirk-to-thunderx2-and-thunderx3.patch -- 2.47.3