diff options
-rw-r--r-- | lib/talloc/talloc.c | 18 |
1 files changed, 3 insertions, 15 deletions
diff --git a/lib/talloc/talloc.c b/lib/talloc/talloc.c index a820ebf0ac..19e6a37f2c 100644 --- a/lib/talloc/talloc.c +++ b/lib/talloc/talloc.c @@ -838,6 +838,7 @@ static inline int _talloc_free_internal(void *ptr, const char *location) } else { if (tc->prev) tc->prev->next = tc->next; if (tc->next) tc->next->prev = tc->prev; + tc->prev = tc->next = NULL; } tc->flags |= TALLOC_FLAG_LOOP; @@ -925,6 +926,7 @@ static void *_talloc_steal_internal(const void *new_ctx, const void *ptr) } else { if (tc->prev) tc->prev->next = tc->next; if (tc->next) tc->next->prev = tc->prev; + tc->prev = tc->next = NULL; } tc->parent = new_tc; @@ -1251,23 +1253,9 @@ static inline void _talloc_free_children_internal(struct talloc_chunk *tc, struct talloc_chunk *p = talloc_parent_chunk(tc->child->refs); if (p) new_parent = TC_PTR_FROM_CHUNK(p); } - /* finding the parent here is potentially quite - expensive, but the alternative, which is to change - talloc to always have a valid tc->parent pointer, - makes realloc more expensive where there are a - large number of children. - - The reason we need the parent pointer here is that - if _talloc_free_internal() fails due to references - or a failing destructor we need to re-parent, but - the free call can invalidate the prev pointer. - */ - if (new_parent == null_context && (tc->child->refs || tc->child->destructor)) { - old_parent = talloc_parent_chunk(ptr); - } if (unlikely(_talloc_free_internal(child, location) == -1)) { if (new_parent == null_context) { - struct talloc_chunk *p = old_parent; + struct talloc_chunk *p = talloc_parent_chunk(ptr); if (p) new_parent = TC_PTR_FROM_CHUNK(p); } _talloc_steal_internal(new_parent, child); |