linuxppc-dev.lists.ozlabs.org archive mirror
 help / color / mirror / Atom feed
From: Anton Vorontsov <avorontsov@ru.mvista.com>
To: Grant Likely <grant.likely@secretlab.ca>,
	David Brownell <dbrownell@users.sourceforge.net>
Cc: Michal Simek <monstr@monstr.eu>,
	devicetree-discuss@lists.ozlabs.org,
	linux-kernel@vger.kernel.org, linuxppc-dev@ozlabs.org,
	microblaze-uclinux@itee.uq.edu.au,
	David Miller <davem@davemloft.net>
Subject: [PATCH 2/3] of: Introduce safe accessors for node->data
Date: Fri, 5 Feb 2010 23:50:43 +0300	[thread overview]
Message-ID: <20100205205043.GB4178@oksana.dev.rtsoft.ru> (raw)
In-Reply-To: <20100205204949.GA2575@oksana.dev.rtsoft.ru>

Platform code use node->data to store some private information
associated with a node.

Previously there was no need for any locks and accessors since we were
initializing the data mostly at boot time and never modified it later.

Though, nowadays OF GPIO infrastructure supports GPIO chips detaching,
so to handle this correctly we have to introduce locking for the
node->data field.

Signed-off-by: Anton Vorontsov <avorontsov@ru.mvista.com>
---
 drivers/of/base.c  |   45 +++++++++++++++++++++++++++++++++++++++++++++
 include/linux/of.h |    5 +++++
 2 files changed, 50 insertions(+), 0 deletions(-)

diff --git a/drivers/of/base.c b/drivers/of/base.c
index 716d439..41ed6ba 100644
--- a/drivers/of/base.c
+++ b/drivers/of/base.c
@@ -36,8 +36,53 @@ void of_node_init(struct device_node *np)
 {
 	memset(np, 0, sizeof(*np));
 	kref_init(&np->kref);
+	spin_lock_init(&np->data_lock);
 }
 
+/**
+ *	of_node_set_data - Try to set node->data
+ *	@node:	Node
+ *	@data:	Data
+ *
+ *	This function tries to safely set node->data. Returns 0 on success,
+ *	-EBUSY if node->data was already set.
+ */
+int of_node_set_data(struct device_node *np, void *data)
+{
+	int ret = 0;
+	unsigned long flags;
+
+	spin_lock_irqsave(&np->data_lock, flags);
+	if (np->data)
+		ret = -EBUSY;
+	else
+		np->data = data;
+	spin_unlock_irqrestore(&np->data_lock, flags);
+
+	if (!ret)
+		of_node_get(np);
+
+	return ret;
+}
+EXPORT_SYMBOL(of_node_set_data);
+
+/**
+ *	of_node_release_data_unlocked - Release node->data
+ *	@node:	Node
+ *
+ *	This function releases node->data, so that others could set it.
+ *
+ *	This function doesn't grab any locks, so that a caller can grab the
+ *	lock itself, atomically read the data and decide if it wants to
+ *	release it.
+ */
+void of_node_release_data_unlocked(struct device_node *np)
+{
+	np->data = NULL;
+	of_node_put(np);
+}
+EXPORT_SYMBOL(of_node_release_data_unlocked);
+
 int of_n_addr_cells(struct device_node *np)
 {
 	const int *ip;
diff --git a/include/linux/of.h b/include/linux/of.h
index 717d690..c573ee2 100644
--- a/include/linux/of.h
+++ b/include/linux/of.h
@@ -18,6 +18,7 @@
 #include <linux/types.h>
 #include <linux/bitops.h>
 #include <linux/kref.h>
+#include <linux/spinlock.h>
 #include <linux/mod_devicetable.h>
 
 typedef u32 phandle;
@@ -56,6 +57,7 @@ struct device_node {
 	struct	kref kref;
 	unsigned long _flags;
 	void	*data;
+	spinlock_t data_lock;
 #if defined(CONFIG_SPARC)
 	char	*path_component_name;
 	unsigned int unique_id;
@@ -65,6 +67,9 @@ struct device_node {
 
 extern void of_node_init(struct device_node *np);
 
+extern int of_node_set_data(struct device_node *np, void *data);
+extern void of_node_release_data_unlocked(struct device_node *np);
+
 static inline int of_node_check_flag(struct device_node *n, unsigned long flag)
 {
 	return test_bit(flag, &n->_flags);
-- 
1.6.5.7

  parent reply	other threads:[~2010-02-05 20:50 UTC|newest]

Thread overview: 16+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2010-02-05 20:49 [PATCH RFC 0/3] Implement refcounting for OF GPIO chips Anton Vorontsov
2010-02-05 20:50 ` [PATCH 1/3] of platforms: Move common static initialization to of_node_init() Anton Vorontsov
2010-02-09 17:22   ` Grant Likely
2010-02-05 20:50 ` Anton Vorontsov [this message]
2010-02-09 17:25   ` [PATCH 2/3] of: Introduce safe accessors for node->data Grant Likely
2010-02-09 19:10     ` Anton Vorontsov
2010-02-05 20:50 ` [PATCH 3/3] of/gpio: Introduce of_put_gpio(), add ref counting for OF GPIO chips Anton Vorontsov
2010-02-09  9:15   ` Michal Simek
2010-02-09  9:20     ` Michal Simek
2010-02-09 17:28   ` Grant Likely
2010-02-09 19:14     ` Anton Vorontsov
2010-02-15 19:49       ` Grant Likely
2010-02-15 20:59         ` Anton Vorontsov
2010-02-09  9:40 ` [PATCH RFC 0/3] Implement refcounting " Michal Simek
2010-02-09 17:29   ` Grant Likely
2010-02-09 19:06   ` Anton Vorontsov

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20100205205043.GB4178@oksana.dev.rtsoft.ru \
    --to=avorontsov@ru.mvista.com \
    --cc=davem@davemloft.net \
    --cc=dbrownell@users.sourceforge.net \
    --cc=devicetree-discuss@lists.ozlabs.org \
    --cc=grant.likely@secretlab.ca \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linuxppc-dev@ozlabs.org \
    --cc=microblaze-uclinux@itee.uq.edu.au \
    --cc=monstr@monstr.eu \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).