From patchwork Thu Mar 2 22:56:50 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Igor Druzhinin X-Patchwork-Id: 9601749 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 441DC6048B for ; Thu, 2 Mar 2017 22:59:07 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 327DD2860D for ; Thu, 2 Mar 2017 22:59:07 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 241382860F; Thu, 2 Mar 2017 22:59:07 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-4.2 required=2.0 tests=BAYES_00, RCVD_IN_DNSWL_MED autolearn=ham version=3.3.1 Received: from lists.xenproject.org (lists.xenproject.org [192.237.175.120]) (using TLSv1.2 with cipher AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 9E0B12860D for ; Thu, 2 Mar 2017 22:59:06 +0000 (UTC) Received: from localhost ([127.0.0.1] helo=lists.xenproject.org) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1cjZee-0005SG-Qg; Thu, 02 Mar 2017 22:57:00 +0000 Received: from mail6.bemta3.messagelabs.com ([195.245.230.39]) by lists.xenproject.org with esmtp (Exim 4.84_2) (envelope-from ) id 1cjZed-0005S9-Kn for xen-devel@lists.xenproject.org; Thu, 02 Mar 2017 22:56:59 +0000 Received: from [85.158.137.68] by server-16.bemta-3.messagelabs.com id 08/08-06437-A33A8B85; Thu, 02 Mar 2017 22:56:58 +0000 X-Brightmail-Tracker: H4sIAAAAAAAAA+NgFvrBLMWRWlGSWpSXmKPExsXitHRDpK7V4h0 RBrunilp83zKZyYHR4/CHKywBjFGsmXlJ+RUJrBk7l5xkLjgrXnFjpkwDY4NIFyMnh4SAv0RL 53UmEJtNwEDi1KZFLCC2iICdxKXNB9hBbGaBEom2k+tZQWxhAVeJ7e/PgdksAioSn3ongdXzC nhJLFx9gAlipoLElIfvmUFsIQE1iaNdu6BqBCVOznzCAjFTQuLgixfMExi5ZyFJzUKSWsDItI pRozi1qCy1SNfYQC+pKDM9oyQ3MTNH19DAWC83tbg4MT01JzGpWC85P3cTIzAU6hkYGHcwdp7 wO8QoycGkJMprFb0jQogvKT+lMiOxOCO+qDQntfgQowwHh5IEr+4ioJxgUWp6akVaZg4wKGHS Ehw8SiK88SBp3uKCxNzizHSI1ClGXY45s3e/YRJiycvPS5US5w0BKRIAKcoozYMbAYuQS4yyU sK8jAwMDEI8BalFuZklqPKvGMU5GJWEea1BpvBk5pXAbXoFdAQT0BEvVLaCHFGSiJCSamBs+b pi96aLsstaS3q/ynfsvfP9cVf1out/0lLXaBzQ8Bes+reu6qZd5qPr5ZGXg5ab5l6vWlj8RuF VWq3coSdM7RvkXkX4rZFP/T1zu5oGb/kZxqd5KdEVK2QV7/GGqunzW98+obf933efxzl/85id Za7tt+8oC09/ck45ka+nKvLqjJOuS5YqsRRnJBpqMRcVJwIAvTj5z4sCAAA= X-Env-Sender: prvs=227febecc=igor.druzhinin@citrix.com X-Msg-Ref: server-2.tower-31.messagelabs.com!1488495416!76645911!1 X-Originating-IP: [66.165.176.89] X-SpamReason: No, hits=0.0 required=7.0 tests=sa_preprocessor: VHJ1c3RlZCBJUDogNjYuMTY1LjE3Ni44OSA9PiAyMDMwMDc=\n, received_headers: No Received headers X-StarScan-Received: X-StarScan-Version: 9.2.3; banners=-,-,- X-VirusChecked: Checked Received: (qmail 6458 invoked from network); 2 Mar 2017 22:56:58 -0000 Received: from smtp.citrix.com (HELO SMTP.CITRIX.COM) (66.165.176.89) by server-2.tower-31.messagelabs.com with RC4-SHA encrypted SMTP; 2 Mar 2017 22:56:58 -0000 X-IronPort-AV: E=Sophos;i="5.35,233,1484006400"; d="scan'208";a="411045129" From: Igor Druzhinin To: , Date: Thu, 2 Mar 2017 22:56:50 +0000 Message-ID: <1488495410-137500-1-git-send-email-igor.druzhinin@citrix.com> X-Mailer: git-send-email 1.8.3.1 MIME-Version: 1.0 Cc: jgross@suse.com, Igor Druzhinin , paul.durrant@citrix.com, wei.liu2@citrix.com Subject: [Xen-devel] [PATCH] xen-netback: fix race condition on XenBus disconnect X-BeenThere: xen-devel@lists.xen.org X-Mailman-Version: 2.1.18 Precedence: list List-Id: Xen developer discussion List-Unsubscribe: , List-Post: List-Help: List-Subscribe: , Errors-To: xen-devel-bounces@lists.xen.org Sender: "Xen-devel" X-Virus-Scanned: ClamAV using ClamSMTP In some cases during XenBus disconnect event handling and subsequent queue resource release there may be some TX handlers active on other processors. Use RCU in order to synchronize with them. Signed-off-by: Igor Druzhinin --- drivers/net/xen-netback/interface.c | 13 ++++++++----- drivers/net/xen-netback/xenbus.c | 17 +++++++---------- 2 files changed, 15 insertions(+), 15 deletions(-) diff --git a/drivers/net/xen-netback/interface.c b/drivers/net/xen-netback/interface.c index a2d32676..32e2cc6 100644 --- a/drivers/net/xen-netback/interface.c +++ b/drivers/net/xen-netback/interface.c @@ -164,7 +164,7 @@ static int xenvif_start_xmit(struct sk_buff *skb, struct net_device *dev) { struct xenvif *vif = netdev_priv(dev); struct xenvif_queue *queue = NULL; - unsigned int num_queues = vif->num_queues; + unsigned int num_queues = rcu_dereference(vif)->num_queues; u16 index; struct xenvif_rx_cb *cb; @@ -221,18 +221,21 @@ static struct net_device_stats *xenvif_get_stats(struct net_device *dev) { struct xenvif *vif = netdev_priv(dev); struct xenvif_queue *queue = NULL; + unsigned int num_queues; u64 rx_bytes = 0; u64 rx_packets = 0; u64 tx_bytes = 0; u64 tx_packets = 0; unsigned int index; - spin_lock(&vif->lock); - if (vif->queues == NULL) + rcu_read_lock(); + + num_queues = rcu_dereference(vif)->num_queues; + if (num_queues < 1) goto out; /* Aggregate tx and rx stats from each queue */ - for (index = 0; index < vif->num_queues; ++index) { + for (index = 0; index < num_queues; ++index) { queue = &vif->queues[index]; rx_bytes += queue->stats.rx_bytes; rx_packets += queue->stats.rx_packets; @@ -241,7 +244,7 @@ static struct net_device_stats *xenvif_get_stats(struct net_device *dev) } out: - spin_unlock(&vif->lock); + rcu_read_unlock(); vif->dev->stats.rx_bytes = rx_bytes; vif->dev->stats.rx_packets = rx_packets; diff --git a/drivers/net/xen-netback/xenbus.c b/drivers/net/xen-netback/xenbus.c index d2d7cd9..76efb01 100644 --- a/drivers/net/xen-netback/xenbus.c +++ b/drivers/net/xen-netback/xenbus.c @@ -495,26 +495,23 @@ static void backend_disconnect(struct backend_info *be) struct xenvif *vif = be->vif; if (vif) { + unsigned int num_queues = vif->num_queues; unsigned int queue_index; - struct xenvif_queue *queues; xen_unregister_watchers(vif); #ifdef CONFIG_DEBUG_FS xenvif_debugfs_delif(vif); #endif /* CONFIG_DEBUG_FS */ xenvif_disconnect_data(vif); - for (queue_index = 0; - queue_index < vif->num_queues; - ++queue_index) - xenvif_deinit_queue(&vif->queues[queue_index]); - spin_lock(&vif->lock); - queues = vif->queues; vif->num_queues = 0; - vif->queues = NULL; - spin_unlock(&vif->lock); + synchronize_net(); - vfree(queues); + for (queue_index = 0; queue_index < num_queues; ++queue_index) + xenvif_deinit_queue(&vif->queues[queue_index]); + + vfree(vif->queues); + vif->queues = NULL; xenvif_disconnect_ctrl(vif); }