blob: 965e0021af8bc7a734ab4b5249bb959e72505e55 [file] [log] [blame]
Subject: of-convert-devtree-lock.patch
From: Thomas Gleixner <tglx@linutronix.de>
Date: Mon, 21 Mar 2011 14:35:34 +0100
Signed-off-by: Thomas Gleixner <tglx@linutronix.de>
---
arch/sparc/kernel/prom_common.c | 4 -
drivers/of/base.c | 96 ++++++++++++++++++++++------------------
include/linux/of.h | 2
3 files changed, 57 insertions(+), 45 deletions(-)
Index: linux-stable/arch/sparc/kernel/prom_common.c
===================================================================
--- linux-stable.orig/arch/sparc/kernel/prom_common.c
+++ linux-stable/arch/sparc/kernel/prom_common.c
@@ -64,7 +64,7 @@ int of_set_property(struct device_node *
err = -ENODEV;
mutex_lock(&of_set_property_mutex);
- write_lock(&devtree_lock);
+ raw_spin_lock(&devtree_lock);
prevp = &dp->properties;
while (*prevp) {
struct property *prop = *prevp;
@@ -91,7 +91,7 @@ int of_set_property(struct device_node *
}
prevp = &(*prevp)->next;
}
- write_unlock(&devtree_lock);
+ raw_spin_unlock(&devtree_lock);
mutex_unlock(&of_set_property_mutex);
/* XXX Upate procfs if necessary... */
Index: linux-stable/drivers/of/base.c
===================================================================
--- linux-stable.orig/drivers/of/base.c
+++ linux-stable/drivers/of/base.c
@@ -54,7 +54,7 @@ static DEFINE_MUTEX(of_aliases_mutex);
/* use when traversing tree through the allnext, child, sibling,
* or parent members of struct device_node.
*/
-DEFINE_RWLOCK(devtree_lock);
+DEFINE_RAW_SPINLOCK(devtree_lock);
int of_n_addr_cells(struct device_node *np)
{
@@ -187,10 +187,11 @@ struct property *of_find_property(const
int *lenp)
{
struct property *pp;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
pp = __of_find_property(np, name, lenp);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return pp;
}
@@ -208,13 +209,13 @@ struct device_node *of_find_all_nodes(st
{
struct device_node *np;
- read_lock(&devtree_lock);
+ raw_spin_lock(&devtree_lock);
np = prev ? prev->allnext : allnodes;
for (; np != NULL; np = np->allnext)
if (of_node_get(np))
break;
of_node_put(prev);
- read_unlock(&devtree_lock);
+ raw_spin_unlock(&devtree_lock);
return np;
}
EXPORT_SYMBOL(of_find_all_nodes);
@@ -273,11 +274,12 @@ static int __of_device_is_compatible(con
int of_device_is_compatible(const struct device_node *device,
const char *compat)
{
+ unsigned long flags;
int res;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
res = __of_device_is_compatible(device, compat);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return res;
}
EXPORT_SYMBOL(of_device_is_compatible);
@@ -339,13 +341,14 @@ EXPORT_SYMBOL(of_device_is_available);
struct device_node *of_get_parent(const struct device_node *node)
{
struct device_node *np;
+ unsigned long flags;
if (!node)
return NULL;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = of_node_get(node->parent);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_get_parent);
@@ -364,14 +367,15 @@ EXPORT_SYMBOL(of_get_parent);
struct device_node *of_get_next_parent(struct device_node *node)
{
struct device_node *parent;
+ unsigned long flags;
if (!node)
return NULL;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
parent = of_node_get(node->parent);
of_node_put(node);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return parent;
}
@@ -387,14 +391,15 @@ struct device_node *of_get_next_child(co
struct device_node *prev)
{
struct device_node *next;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
next = prev ? prev->sibling : node->child;
for (; next; next = next->sibling)
if (of_node_get(next))
break;
of_node_put(prev);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return next;
}
EXPORT_SYMBOL(of_get_next_child);
@@ -412,7 +417,7 @@ struct device_node *of_get_next_availabl
{
struct device_node *next;
- read_lock(&devtree_lock);
+ raw_spin_lock(&devtree_lock);
next = prev ? prev->sibling : node->child;
for (; next; next = next->sibling) {
if (!of_device_is_available(next))
@@ -421,7 +426,7 @@ struct device_node *of_get_next_availabl
break;
}
of_node_put(prev);
- read_unlock(&devtree_lock);
+ raw_spin_unlock(&devtree_lock);
return next;
}
EXPORT_SYMBOL(of_get_next_available_child);
@@ -436,14 +441,15 @@ EXPORT_SYMBOL(of_get_next_available_chil
struct device_node *of_find_node_by_path(const char *path)
{
struct device_node *np = allnodes;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
for (; np; np = np->allnext) {
if (np->full_name && (of_node_cmp(np->full_name, path) == 0)
&& of_node_get(np))
break;
}
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_node_by_path);
@@ -463,15 +469,16 @@ struct device_node *of_find_node_by_name
const char *name)
{
struct device_node *np;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = from ? from->allnext : allnodes;
for (; np; np = np->allnext)
if (np->name && (of_node_cmp(np->name, name) == 0)
&& of_node_get(np))
break;
of_node_put(from);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_node_by_name);
@@ -492,15 +499,16 @@ struct device_node *of_find_node_by_type
const char *type)
{
struct device_node *np;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = from ? from->allnext : allnodes;
for (; np; np = np->allnext)
if (np->type && (of_node_cmp(np->type, type) == 0)
&& of_node_get(np))
break;
of_node_put(from);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_node_by_type);
@@ -523,8 +531,9 @@ struct device_node *of_find_compatible_n
const char *type, const char *compatible)
{
struct device_node *np;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = from ? from->allnext : allnodes;
for (; np; np = np->allnext) {
if (type
@@ -535,7 +544,7 @@ struct device_node *of_find_compatible_n
break;
}
of_node_put(from);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_compatible_node);
@@ -557,8 +566,9 @@ struct device_node *of_find_node_with_pr
{
struct device_node *np;
struct property *pp;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = from ? from->allnext : allnodes;
for (; np; np = np->allnext) {
for (pp = np->properties; pp; pp = pp->next) {
@@ -570,7 +580,7 @@ struct device_node *of_find_node_with_pr
}
out:
of_node_put(from);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_node_with_property);
@@ -611,10 +621,11 @@ const struct of_device_id *of_match_node
const struct device_node *node)
{
const struct of_device_id *match;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
match = __of_match_node(matches, node);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return match;
}
EXPORT_SYMBOL(of_match_node);
@@ -635,15 +646,16 @@ struct device_node *of_find_matching_nod
const struct of_device_id *matches)
{
struct device_node *np;
+ unsigned long flags;
- read_lock(&devtree_lock);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np = from ? from->allnext : allnodes;
for (; np; np = np->allnext) {
if (__of_match_node(matches, np) && of_node_get(np))
break;
}
of_node_put(from);
- read_unlock(&devtree_lock);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return np;
}
EXPORT_SYMBOL(of_find_matching_node);
@@ -686,12 +698,12 @@ struct device_node *of_find_node_by_phan
{
struct device_node *np;
- read_lock(&devtree_lock);
+ raw_spin_lock(&devtree_lock);
for (np = allnodes; np; np = np->allnext)
if (np->phandle == handle)
break;
of_node_get(np);
- read_unlock(&devtree_lock);
+ raw_spin_unlock(&devtree_lock);
return np;
}
EXPORT_SYMBOL(of_find_node_by_phandle);
@@ -1063,18 +1075,18 @@ int prom_add_property(struct device_node
unsigned long flags;
prop->next = NULL;
- write_lock_irqsave(&devtree_lock, flags);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
next = &np->properties;
while (*next) {
if (strcmp(prop->name, (*next)->name) == 0) {
/* duplicate ! don't insert it */
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
return -1;
}
next = &(*next)->next;
}
*next = prop;
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
#ifdef CONFIG_PROC_DEVICETREE
/* try to add to proc as well if it was initialized */
@@ -1099,7 +1111,7 @@ int prom_remove_property(struct device_n
unsigned long flags;
int found = 0;
- write_lock_irqsave(&devtree_lock, flags);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
next = &np->properties;
while (*next) {
if (*next == prop) {
@@ -1112,7 +1124,7 @@ int prom_remove_property(struct device_n
}
next = &(*next)->next;
}
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
if (!found)
return -ENODEV;
@@ -1149,7 +1161,7 @@ int prom_update_property(struct device_n
if (!oldprop)
return prom_add_property(np, newprop);
- write_lock_irqsave(&devtree_lock, flags);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
next = &np->properties;
while (*next) {
if (*next == oldprop) {
@@ -1163,7 +1175,7 @@ int prom_update_property(struct device_n
}
next = &(*next)->next;
}
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
if (!found)
return -ENODEV;
@@ -1193,12 +1205,12 @@ void of_attach_node(struct device_node *
{
unsigned long flags;
- write_lock_irqsave(&devtree_lock, flags);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
np->sibling = np->parent->child;
np->allnext = allnodes;
np->parent->child = np;
allnodes = np;
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
}
/**
@@ -1212,7 +1224,7 @@ void of_detach_node(struct device_node *
struct device_node *parent;
unsigned long flags;
- write_lock_irqsave(&devtree_lock, flags);
+ raw_spin_lock_irqsave(&devtree_lock, flags);
parent = np->parent;
if (!parent)
@@ -1243,7 +1255,7 @@ void of_detach_node(struct device_node *
of_node_set_flag(np, OF_DETACHED);
out_unlock:
- write_unlock_irqrestore(&devtree_lock, flags);
+ raw_spin_unlock_irqrestore(&devtree_lock, flags);
}
#endif /* defined(CONFIG_OF_DYNAMIC) */
Index: linux-stable/include/linux/of.h
===================================================================
--- linux-stable.orig/include/linux/of.h
+++ linux-stable/include/linux/of.h
@@ -91,7 +91,7 @@ static inline void of_node_put(struct de
extern struct device_node *allnodes;
extern struct device_node *of_chosen;
extern struct device_node *of_aliases;
-extern rwlock_t devtree_lock;
+extern raw_spinlock_t devtree_lock;
static inline bool of_have_populated_dt(void)
{