aboutsummaryrefslogtreecommitdiffstats
path: root/fs/proc/proc_devtree.c
diff options
context:
space:
mode:
authorSteven Rostedt <rostedt@goodmis.org>2006-03-26 04:36:55 -0500
committerLinus Torvalds <torvalds@g5.osdl.org>2006-03-26 11:56:53 -0500
commit64a07bd82ed526d813b64b0957543eef55bdf9c0 (patch)
tree451586526696bc4a80d8a9f4c50460ae2d4e92eb /fs/proc/proc_devtree.c
parentcd7b24bb1891a10ee25168a912ff2304a9571d23 (diff)
[PATCH] protect remove_proc_entry
It has been discovered that the remove_proc_entry has a race in the removing of entries in the proc file system that are siblings. There's no protection around the traversing and removing of elements that belong in the same subdirectory. This subdirectory list is protected in other areas by the BKL. So the BKL was at first used to protect this area too, but unfortunately, remove_proc_entry may be called with spinlocks held. The BKL may schedule, so this was not a solution. The final solution was to add a new global spin lock to protect this list, called proc_subdir_lock. This lock now protects the list in remove_proc_entry, and I also went around looking for other areas that this list is modified and added this protection there too. Care must be taken since these locations call several functions that may also schedule. Since I don't see any location that these functions that modify the subdirectory list are called by interrupts, the irqsave/restore versions of the spin lock was _not_ used. Signed-off-by: Steven Rostedt <rostedt@goodmis.org> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'fs/proc/proc_devtree.c')
-rw-r--r--fs/proc/proc_devtree.c2
1 files changed, 2 insertions, 0 deletions
diff --git a/fs/proc/proc_devtree.c b/fs/proc/proc_devtree.c
index 9bdd077d6f55..596b4b4f1cc8 100644
--- a/fs/proc/proc_devtree.c
+++ b/fs/proc/proc_devtree.c
@@ -136,9 +136,11 @@ void proc_device_tree_add_node(struct device_node *np,
136 * properties are quite unimportant for us though, thus we 136 * properties are quite unimportant for us though, thus we
137 * simply "skip" them here, but we do have to check. 137 * simply "skip" them here, but we do have to check.
138 */ 138 */
139 spin_lock(&proc_subdir_lock);
139 for (ent = de->subdir; ent != NULL; ent = ent->next) 140 for (ent = de->subdir; ent != NULL; ent = ent->next)
140 if (!strcmp(ent->name, pp->name)) 141 if (!strcmp(ent->name, pp->name))
141 break; 142 break;
143 spin_unlock(&proc_subdir_lock);
142 if (ent != NULL) { 144 if (ent != NULL) {
143 printk(KERN_WARNING "device-tree: property \"%s\" name" 145 printk(KERN_WARNING "device-tree: property \"%s\" name"
144 " conflicts with node in %s\n", pp->name, 146 " conflicts with node in %s\n", pp->name,