aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorDave Kleikamp <shaggy@austin.ibm.com>2004-11-15 04:06:16 -0800
committerLinus Torvalds <torvalds@ppc970.osdl.org>2004-11-15 04:06:16 -0800
commitd9f868c4656ae0903dcdcfd257b35d4cf7e80f05 (patch)
tree87eea0e8d845d8b29b226dcfd1890901d292c3f2 /lib
parent4062e12b2ba22fc5302d1d501a14c40ab4d89676 (diff)
downloadhistory-d9f868c4656ae0903dcdcfd257b35d4cf7e80f05.tar.gz
[PATCH] radix_tree_delete() fix
I was looking through the radix tree code and came across what I think is a bug in radix_tree_delete. for (idx = 0; idx < RADIX_TREE_TAG_LONGS; idx++) { if (pathp[0].node->tags[tag][idx]) { tags[tag] = 1; nr_cleared_tags--; break; } } The above loop should only be executed if tags[tag] is zero. Otherwise, when walking up the tree, we can decrement nr_cleared_tags twice or more for the same value of tag, thus potentially exiting the outer loop too early. Ensure that nr_cleared_tags is only decremented once for each tag. Signed-off-by: Dave Kleikamp <shaggy@austin.ibm.com> Signed-off-by: Andrew Morton <akpm@osdl.org> Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'lib')
-rw-r--r--lib/radix-tree.c6
1 files changed, 4 insertions, 2 deletions
diff --git a/lib/radix-tree.c b/lib/radix-tree.c
index a0a0902614e7c0..04d664377f2c62 100644
--- a/lib/radix-tree.c
+++ b/lib/radix-tree.c
@@ -701,8 +701,10 @@ void *radix_tree_delete(struct radix_tree_root *root, unsigned long index)
for (tag = 0; tag < RADIX_TREE_TAGS; tag++) {
int idx;
- if (!tags[tag])
- tag_clear(pathp[0].node, tag, pathp[0].offset);
+ if (tags[tag])
+ continue;
+
+ tag_clear(pathp[0].node, tag, pathp[0].offset);
for (idx = 0; idx < RADIX_TREE_TAG_LONGS; idx++) {
if (pathp[0].node->tags[tag][idx]) {