Received: by 2002:a05:6a10:1d13:0:0:0:0 with SMTP id pp19csp2508794pxb; Tue, 24 Aug 2021 00:21:23 -0700 (PDT) X-Google-Smtp-Source: ABdhPJwZDnKFD+EcUs5fAFDF9iSYVRvJ9FMAjiIpJXnk8Jir2SfQ8am5JWNEAMNE7b3HH+hf94U4 X-Received: by 2002:a02:7755:: with SMTP id g82mr32660605jac.45.1629789683417; Tue, 24 Aug 2021 00:21:23 -0700 (PDT) ARC-Seal: i=1; a=rsa-sha256; t=1629789683; cv=none; d=google.com; s=arc-20160816; b=m9mnXRHYoP1YrgeMc1kwwhx3l+N+8eFEMrA4CZw/FbHbRYcRrhn49NHXtaxBAKv/y5 NeXN0Imwfe36Jh4O7YxSbd07QGffqezPOHT4b2+keS4cDzTXsh/VRZYXDF+SCivVxRrn BcnBW2pBu27MgKlGEIJTbySUarlofx85ePpF6vBnhkgi+ALF2xzojcQV/u94PZclkoGK nvtIZEsSqsuO+G1TEU2JGSWudP4wz7VrD83tQ9eRNvlWckkhZ5crXcmFOxzHzolBEuJK QaBYYLVM7NJzMoBIEzrB2bOCggi//JXyjcsPDckMsjXw63M2rAH80yoIBLf7R6Vo8q4n hl7g== ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=google.com; s=arc-20160816; h=list-id:precedence:content-transfer-encoding:mime-version :message-id:date:subject:cc:to:from:dkim-signature:dkim-filter; bh=pT9MfMBwFEzM8B1XTfJ8fkYHPKmhI6ubzUcWHq4gd20=; b=vrTA7vN581oRAlscSVJUe56KGdpcgLSNQ537zNjhVGmVDt98/811V1w/it8X310muf FLMbE/w01gIJFogP90mNC96AM63FF2U5YpFjiwHic5RA5iWyzQ7e7fVzsWgugZASKcmV SWlsMlq/3sKqfTB8sJKHRZCuabkIxr0yihNsb8MAq638xX993VrtbrpKejmXMlZb4dD8 ZQscNEiN3vNiiIPXXCzobT18FgWc578Ocrqtxuwdrgmo5KMQeCILzvvm3RmSULLiiYRD IslZ8Z/aAnyDAq/5P7b7Zq4I7JtuKkUXthrznTjpkdIqQeHaQUT4WxRJZhUqtRdfPPAB Fsnw== ARC-Authentication-Results: i=1; mx.google.com; dkim=pass header.i=@linuxonhyperv.com header.s=default header.b=lLWFly0a; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxonhyperv.com Return-Path: Received: from vger.kernel.org (vger.kernel.org. [23.128.96.18]) by mx.google.com with ESMTP id u15si18574642iot.89.2021.08.24.00.21.12; Tue, 24 Aug 2021 00:21:23 -0700 (PDT) Received-SPF: pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) client-ip=23.128.96.18; Authentication-Results: mx.google.com; dkim=pass header.i=@linuxonhyperv.com header.s=default header.b=lLWFly0a; spf=pass (google.com: domain of linux-kernel-owner@vger.kernel.org designates 23.128.96.18 as permitted sender) smtp.mailfrom=linux-kernel-owner@vger.kernel.org; dmarc=pass (p=NONE sp=NONE dis=NONE) header.from=linuxonhyperv.com Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S234608AbhHXHVM (ORCPT + 99 others); Tue, 24 Aug 2021 03:21:12 -0400 Received: from linux.microsoft.com ([13.77.154.182]:54612 "EHLO linux.microsoft.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232173AbhHXHVH (ORCPT ); Tue, 24 Aug 2021 03:21:07 -0400 Received: by linux.microsoft.com (Postfix, from userid 1004) id 1BE3320B7192; Tue, 24 Aug 2021 00:20:24 -0700 (PDT) DKIM-Filter: OpenDKIM Filter v2.11.0 linux.microsoft.com 1BE3320B7192 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linuxonhyperv.com; s=default; t=1629789624; bh=pT9MfMBwFEzM8B1XTfJ8fkYHPKmhI6ubzUcWHq4gd20=; h=From:To:Cc:Subject:Date:From; b=lLWFly0aKAauojK7Rlr2GcDxHv76/4KGNj99MTYveFGZBo5d+JCmMGofQaXqrnjVA 7qxnwLDf6wZr3065KuPO1VKK4EJ/dLRzB8QpdqqDeOz5sVeDFnDiBuMmh1iEYPvaTV zWHAFTJs0q0UJr/aNG4sFBqksr+26PNektX9c1gY= From: longli@linuxonhyperv.com To: linux-pci@vger.kernel.org, linux-kernel@vger.kernel.org, linux-hyperv@vger.kernel.org Cc: Long Li , "K. Y. Srinivasan" , Haiyang Zhang , Stephen Hemminger , Wei Liu , Dexuan Cui , Lorenzo Pieralisi , Rob Herring , =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= , Bjorn Helgaas , Michael Kelley , Dan Carpenter Subject: [PATCH] PCI: hv: Fix a bug on removing child devices on the bus Date: Tue, 24 Aug 2021 00:20:20 -0700 Message-Id: <1629789620-11049-1-git-send-email-longli@linuxonhyperv.com> X-Mailer: git-send-email 1.8.3.1 MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Precedence: bulk List-ID: X-Mailing-List: linux-kernel@vger.kernel.org From: Long Li In hv_pci_bus_exit, the code is holding a spinlock while calling pci_destroy_slot(), which takes a mutex. This is not safe for spinlock. Fix this by moving the children to be deleted to a list on the stack, and removing them after spinlock is released. Fixes: 94d22763207a ("PCI: hv: Fix a race condition when removing the device") Cc: "K. Y. Srinivasan" Cc: Haiyang Zhang Cc: Stephen Hemminger Cc: Wei Liu Cc: Dexuan Cui Cc: Lorenzo Pieralisi Cc: Rob Herring Cc: "Krzysztof WilczyƄski" Cc: Bjorn Helgaas Cc: Michael Kelley Cc: Dan Carpenter Reported-by: Dan Carpenter Signed-off-by: Long Li --- drivers/pci/controller/pci-hyperv.c | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/drivers/pci/controller/pci-hyperv.c b/drivers/pci/controller/pci-hyperv.c index a53bd8728d0d..d4f3cce18957 100644 --- a/drivers/pci/controller/pci-hyperv.c +++ b/drivers/pci/controller/pci-hyperv.c @@ -3220,6 +3220,7 @@ static int hv_pci_bus_exit(struct hv_device *hdev, bool keep_devs) struct hv_pci_dev *hpdev, *tmp; unsigned long flags; int ret; + struct list_head removed; /* * After the host sends the RESCIND_CHANNEL message, it doesn't @@ -3229,9 +3230,18 @@ static int hv_pci_bus_exit(struct hv_device *hdev, bool keep_devs) return 0; if (!keep_devs) { - /* Delete any children which might still exist. */ + INIT_LIST_HEAD(&removed); + + /* Move all present children to the list on stack */ spin_lock_irqsave(&hbus->device_list_lock, flags); - list_for_each_entry_safe(hpdev, tmp, &hbus->children, list_entry) { + list_for_each_entry_safe(hpdev, tmp, &hbus->children, list_entry) + list_move_tail(&hpdev->list_entry, &removed); + spin_unlock_irqrestore(&hbus->device_list_lock, flags); + + /* Remove all children in the list */ + while (!list_empty(&removed)) { + hpdev = list_first_entry(&removed, struct hv_pci_dev, + list_entry); list_del(&hpdev->list_entry); if (hpdev->pci_slot) pci_destroy_slot(hpdev->pci_slot); @@ -3239,7 +3249,6 @@ static int hv_pci_bus_exit(struct hv_device *hdev, bool keep_devs) put_pcichild(hpdev); put_pcichild(hpdev); } - spin_unlock_irqrestore(&hbus->device_list_lock, flags); } ret = hv_send_resources_released(hdev); -- 2.25.1