Hello,

Could you please check if the attached (untested) patch works for you.

-- 
With best wishes
Dmitry

>From 3fc7528b6b9da94cb277fb1bb6205e0a7c832758 Mon Sep 17 00:00:00 2001
From: Dmitry Eremin-Solenikov <[email protected]>
Date: Mon, 9 Aug 2010 01:13:50 +0400
Subject: [PATCH] mac802154: add a protection against adding subdevices after hw has been unregistered

Jon Smirl has found a race between hw unregistration and subdevices
registration. Fix that by adding a flag, which specifies if hw is registered
and running.

Signed-off-by: Dmitry Eremin-Solenikov <[email protected]>
---
 net/mac802154/mac802154.h |    7 +++++++
 net/mac802154/main.c      |   17 +++++++++++++++++
 2 files changed, 24 insertions(+), 0 deletions(-)

diff --git a/net/mac802154/mac802154.h b/net/mac802154/mac802154.h
index 2e809d1..f93fc40 100644
--- a/net/mac802154/mac802154.h
+++ b/net/mac802154/mac802154.h
@@ -43,6 +43,13 @@ struct mac802154_priv {
 	/* This one is used for scanning and other
 	 * jobs not to be interfered with serial driver */
 	struct workqueue_struct	*dev_workqueue;
+
+	/*
+	 * These flags are also modified under slaves_mtx and RTNL,
+	 * so you can read them using any of protection methods.
+	 */
+	/* SoftMAC device is registered and running. One can add subinterfaces. */
+	unsigned running: 1;
 };
 
 #define mac802154_to_priv(_hw)	container_of(_hw, struct mac802154_priv, hw)
diff --git a/net/mac802154/main.c b/net/mac802154/main.c
index e73f45f..bbaf58f 100644
--- a/net/mac802154/main.c
+++ b/net/mac802154/main.c
@@ -80,6 +80,13 @@ static int mac802154_netdev_register(struct wpan_phy *phy,
 
 	SET_NETDEV_DEV(dev, &ipriv->phy->dev);
 
+	mutex_lock(&ipriv->slaves_mtx);
+	if (!ipriv->running) {
+		mutex_unlock(&ipriv->slaves_mtx);
+		return -ENODEV;
+	}
+	mutex_unlock(&ipriv->slaves_mtx);
+
 	err = register_netdev(dev);
 	if (err < 0)
 		return err;
@@ -220,6 +227,12 @@ int ieee802154_register_device(struct ieee802154_dev *dev)
 	if (rc < 0)
 		goto out_wq;
 
+	rtnl_lock();
+	mutex_lock(&priv->slaves_mtx);
+	priv->running = 1;
+	mutex_unlock(&ipriv->slaves_mtx);
+	rtnl_unlock();
+
 	return 0;
 
 out_wq:
@@ -240,6 +253,10 @@ void ieee802154_unregister_device(struct ieee802154_dev *dev)
 
 	rtnl_lock();
 
+	mutex_lock(&priv->slaves_mtx);
+	priv->running = 0;
+	mutex_unlock(&ipriv->slaves_mtx);
+
 	list_for_each_entry_safe(sdata, next, &priv->slaves, list) {
 		mutex_lock(&sdata->hw->slaves_mtx);
 		list_del(&sdata->list);
-- 
1.7.1

------------------------------------------------------------------------------
This SF.net email is sponsored by 

Make an app they can't live without
Enter the BlackBerry Developer Challenge
http://p.sf.net/sfu/RIM-dev2dev 
_______________________________________________
Linux-zigbee-devel mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/linux-zigbee-devel

Reply via email to