From patchwork Mon May 9 09:40:42 2011 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Daniel Drake X-Patchwork-Id: 768872 Received: from vger.kernel.org (vger.kernel.org [209.132.180.67]) by demeter1.kernel.org (8.14.4/8.14.3) with ESMTP id p49A59jT007700 for ; Mon, 9 May 2011 10:05:11 GMT Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S1751615Ab1EIKFG (ORCPT ); Mon, 9 May 2011 06:05:06 -0400 Received: from queueout04-winn.ispmail.ntl.com ([81.103.221.58]:33210 "EHLO queueout04-winn.ispmail.ntl.com" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S1751357Ab1EIKFF (ORCPT ); Mon, 9 May 2011 06:05:05 -0400 X-Greylist: IP, sender and recipient auto-whitelisted, not delayed by milter-greylist-4.2.6 (demeter1.kernel.org [140.211.167.41]); Mon, 09 May 2011 10:05:11 +0000 (UTC) X-Greylist: delayed 1459 seconds by postgrey-1.27 at vger.kernel.org; Mon, 09 May 2011 06:05:04 EDT Received: from aamtaout04-winn.ispmail.ntl.com ([81.103.221.35]) by mtaout03-winn.ispmail.ntl.com (InterMail vM.7.08.04.00 201-2186-134-20080326) with ESMTP id <20110509094044.NQYA3152.mtaout03-winn.ispmail.ntl.com@aamtaout04-winn.ispmail.ntl.com>; Mon, 9 May 2011 10:40:44 +0100 Received: from zog.reactivated.net ([86.14.215.141]) by aamtaout04-winn.ispmail.ntl.com (InterMail vG.3.00.04.00 201-2196-133-20080908) with ESMTP id <20110509094044.DLQN25656.aamtaout04-winn.ispmail.ntl.com@zog.reactivated.net>; Mon, 9 May 2011 10:40:44 +0100 Received: by zog.reactivated.net (Postfix, from userid 1000) id 39C2E9D401C; Mon, 9 May 2011 10:40:42 +0100 (BST) From: Daniel Drake To: linville@tuxdriver.com Cc: linux-wireless@vger.kernel.org Cc: libertas-dev@lists.infradead.org Cc: dcbw@redhat.com Cc: pgf@laptop.org Subject: [PATCH] libertas: fix cmdpendingq locking Message-Id: <20110509094042.39C2E9D401C@zog.reactivated.net> Date: Mon, 9 May 2011 10:40:42 +0100 (BST) X-Cloudmark-Analysis: v=1.1 cv=R50lirqlHffDPPkwUlkuVa99MrvKdVWo//yz83qex8g= c=1 sm=0 a=hGOPg0wuMIQA:10 a=vJ1w_8FsMGIA:10 a=Op-mwl0xAAAA:8 a=m1YFND0yjoMxsyGADHAA:9 a=pQsOLmrGnQ4Vg5U2x6MA:7 a=d4CUUju0HPYA:10 a=HpAAvcLHHh0Zw7uRqdWCyQ==:117 Sender: linux-wireless-owner@vger.kernel.org Precedence: bulk List-ID: X-Mailing-List: linux-wireless@vger.kernel.org From: Paul Fox We occasionally see list corruption using libertas. While we haven't been able to diagnose this precisely, we have spotted a possible cause: cmdpendingq is generally modified with driver_lock held. However, there are a couple of points where this is not the case. Fix up those operations to execute under the lock, it seems like the correct thing to do and will hopefully improve the situation. Signed-off-by: Paul Fox Signed-off-by: Daniel Drake Acked-by: Dan Williams --- drivers/net/wireless/libertas/cmd.c | 6 ++++-- 1 files changed, 4 insertions(+), 2 deletions(-) diff --git a/drivers/net/wireless/libertas/cmd.c b/drivers/net/wireless/libertas/cmd.c index 7e8a658..f3ac624 100644 --- a/drivers/net/wireless/libertas/cmd.c +++ b/drivers/net/wireless/libertas/cmd.c @@ -1339,8 +1339,8 @@ int lbs_execute_next_command(struct lbs_private *priv) cpu_to_le16(PS_MODE_ACTION_EXIT_PS)) { lbs_deb_host( "EXEC_NEXT_CMD: ignore ENTER_PS cmd\n"); - list_del(&cmdnode->list); spin_lock_irqsave(&priv->driver_lock, flags); + list_del(&cmdnode->list); lbs_complete_command(priv, cmdnode, 0); spin_unlock_irqrestore(&priv->driver_lock, flags); @@ -1352,8 +1352,8 @@ int lbs_execute_next_command(struct lbs_private *priv) (priv->psstate == PS_STATE_PRE_SLEEP)) { lbs_deb_host( "EXEC_NEXT_CMD: ignore EXIT_PS cmd in sleep\n"); - list_del(&cmdnode->list); spin_lock_irqsave(&priv->driver_lock, flags); + list_del(&cmdnode->list); lbs_complete_command(priv, cmdnode, 0); spin_unlock_irqrestore(&priv->driver_lock, flags); priv->needtowakeup = 1; @@ -1366,7 +1366,9 @@ int lbs_execute_next_command(struct lbs_private *priv) "EXEC_NEXT_CMD: sending EXIT_PS\n"); } } + spin_lock_irqsave(&priv->driver_lock, flags); list_del(&cmdnode->list); + spin_unlock_irqrestore(&priv->driver_lock, flags); lbs_deb_host("EXEC_NEXT_CMD: sending command 0x%04x\n", le16_to_cpu(cmd->command)); lbs_submit_command(priv, cmdnode);