FAILED: patch "[PATCH] PCI: hv: Fix a race condition bug in hv_pci_query_relations()" failed to apply to 4.14-stable tree
Subsystems (4)
[email protected]
maintainerThe patch below does not apply to the 4.14-stable tree.
If someone wants it applied there, or to any other stable or longterm tree, then please email the backport, including the original git commit id to <[email protected]>.
To reproduce the conflict and resubmit, you may use the following commands:
git fetch https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git/ linux-4.14.y
git checkout FETCH_HEAD
git cherry-pick -x 440b5e3663271b0ffbd4908115044a6a51fb938b
# <resolve conflicts, build, test, etc.>
git commit -s
git send-email --to '<[email protected]>' --in-reply-to '2023062321-recreate-donation-85c8@gregkh' --subject-prefix 'PATCH 4.14.y' HEAD^..
Possible dependencies:
thanks,
greg k-h
------------------ original commit in Linus's tree ------------------
From 440b5e3663271b0ffbd4908115044a6a51fb938b Mon Sep 17 00:00:00 2001
From: Dexuan Cui <[email protected]>
Date: Wed, 14 Jun 2023 21:44:47 -0700
Subject: [PATCH] PCI: hv: Fix a race condition bug in hv_pci_query_relations()
Since day 1 of the driver, there has been a race between hv_pci_query_relations() and survey_child_resources(): during fast device hotplug, hv_pci_query_relations() may error out due to device-remove and the stack variable 'comp' is no longer valid; however, pci_devices_present_work() -> survey_child_resources() -> complete() may be running on another CPU and accessing the no-longer-valid 'comp'. Fix the race by flushing the workqueue before we exit from hv_pci_query_relations().
drivers/pci/controller/pci-hyperv.c +18 -0
@@ -3401,6 +3401,24 @@ static int hv_pci_query_relations(struct hv_device *hdev)if (!ret) ret =wait_for_response (hdev, &comp); +/* +* In the case of fast device addition/removal, it's possible that +* vmbus_sendpacket() or wait_for_response() returns -ENODEV but we +* already got a PCI_BUS_RELATIONS* message from the host and the +* channel callback already scheduled a work to hbus->wq, which can be +* running pci_devices_present_work() -> survey_child_resources() -> +* complete(&hbus->survey_event), even after hv_pci_query_relations() +* exits and the stack variable 'comp' is no longer valid; as a result, +* a hang or a page fault may happen when the complete() calls +* raw_spin_lock_irqsave(). Flush hbus->wq before we exit from +* hv_pci_query_relations() to avoid the issues. Note: if 'ret' is +* -ENODEV, there can't be any more work item scheduled to hbus->wq +* after the flush_workqueue(): see vmbus_onoffer_rescind() -> +* vmbus_reset_channel_cb(), vmbus_rescind_cleanup() -> +* channel->rescind = true. +*/ +flush_workqueue (hbus->wq); +return ret; }