2 Samba Unix SMB/CIFS implementation.
4 Samba trivial allocation library - new interface
6 NOTE: Please read talloc_guide.txt for full documentation
8 Copyright (C) Andrew Tridgell 2004
9 Copyright (C) Stefan Metzmacher 2006
11 ** NOTE! The following LGPL license applies to the talloc
12 ** library. This does NOT imply that all of Samba is released
15 This library is free software; you can redistribute it and/or
16 modify it under the terms of the GNU Lesser General Public
17 License as published by the Free Software Foundation; either
18 version 3 of the License, or (at your option) any later version.
20 This library is distributed in the hope that it will be useful,
21 but WITHOUT ANY WARRANTY; without even the implied warranty of
22 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
23 Lesser General Public License for more details.
25 You should have received a copy of the GNU Lesser General Public
26 License along with this library; if not, see <http://www.gnu.org/licenses/>.
30 inspired by http://swapped.cc/halloc/
36 #define TALLOC_MIN(a,b) ((a)<(b)?(a):(b))
38 /* Visual C++ 2008 compatibility */
39 #if defined(_MSC_VER) && !defined(_cplusplus)
40 typedef size_t ssize_t
;
41 #define inline __inline
44 /* Xcode/gcc4.0 compatibility */
45 #if defined(__APPLE__) || defined(__MINGW32__)
46 static size_t strnlen (const char* s
, size_t n
)
49 for (i
= 0; i
< n
; ++i
)
58 /* Visual C++ 2008 & Xcode/gcc4.0 compatibility */
59 #if !defined(_cplusplus) && (defined(WIN32) || defined(__APPLE__))
66 #ifdef TALLOC_BUILD_VERSION_MAJOR
67 #if (TALLOC_VERSION_MAJOR != TALLOC_BUILD_VERSION_MAJOR)
68 #error "TALLOC_VERSION_MAJOR != TALLOC_BUILD_VERSION_MAJOR"
72 #ifdef TALLOC_BUILD_VERSION_MINOR
73 #if (TALLOC_VERSION_MINOR != TALLOC_BUILD_VERSION_MINOR)
74 #error "TALLOC_VERSION_MINOR != TALLOC_BUILD_VERSION_MINOR"
78 /* use this to force every realloc to change the pointer, to stress test
79 code that might not cope */
80 #define ALWAYS_REALLOC 0
83 #define MAX_TALLOC_SIZE 0x10000000
84 #define TALLOC_MAGIC_BASE 0xe814ec70
85 #define TALLOC_MAGIC ( \
87 (TALLOC_VERSION_MAJOR << 12) + \
88 (TALLOC_VERSION_MINOR << 4) \
91 #define TALLOC_FLAG_FREE 0x01
92 #define TALLOC_FLAG_LOOP 0x02
93 #define TALLOC_FLAG_POOL 0x04 /* This is a talloc pool */
94 #define TALLOC_FLAG_POOLMEM 0x08 /* This is allocated in a pool */
95 #define TALLOC_MAGIC_REFERENCE ((const char *)1)
97 /* by default we abort when given a bad pointer (such as when talloc_free() is called
98 on a pointer that came from malloc() */
100 #define TALLOC_ABORT(reason) abort()
103 #ifndef discard_const_p
104 #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
105 # define discard_const_p(type, ptr) ((type *)((intptr_t)(ptr)))
107 # define discard_const_p(type, ptr) ((type *)(ptr))
111 /* these macros gain us a few percent of speed on gcc */
113 /* the strange !! is to ensure that __builtin_expect() takes either 0 or 1
114 as its first argument */
116 #define likely(x) __builtin_expect(!!(x), 1)
119 #define unlikely(x) __builtin_expect(!!(x), 0)
123 #define likely(x) (x)
126 #define unlikely(x) (x)
130 /* this null_context is only used if talloc_enable_leak_report() or
131 talloc_enable_leak_report_full() is called, otherwise it remains
134 static void *null_context
;
135 static void *autofree_context
;
137 struct talloc_reference_handle
{
138 struct talloc_reference_handle
*next
, *prev
;
140 const char *location
;
143 typedef int (*talloc_destructor_t
)(void *);
145 struct talloc_chunk
{
146 struct talloc_chunk
*next
, *prev
;
147 struct talloc_chunk
*parent
, *child
;
148 struct talloc_reference_handle
*refs
;
149 talloc_destructor_t destructor
;
155 * "pool" has dual use:
157 * For the talloc pool itself (i.e. TALLOC_FLAG_POOL is set), "pool"
158 * marks the end of the currently allocated area.
160 * For members of the pool (i.e. TALLOC_FLAG_POOLMEM is set), "pool"
161 * is a pointer to the struct talloc_chunk of the pool that it was
162 * allocated from. This way children can quickly find the pool to chew
168 /* 16 byte alignment seems to keep everyone happy */
169 #define TC_HDR_SIZE ((sizeof(struct talloc_chunk)+15)&~15)
170 #define TC_PTR_FROM_CHUNK(tc) ((void *)(TC_HDR_SIZE + (char*)tc))
172 int talloc_version_major(void)
174 return TALLOC_VERSION_MAJOR
;
177 int talloc_version_minor(void)
179 return TALLOC_VERSION_MINOR
;
182 static void (*talloc_log_fn
)(const char *message
);
184 void talloc_set_log_fn(void (*log_fn
)(const char *message
))
186 talloc_log_fn
= log_fn
;
189 static void talloc_log(const char *fmt
, ...) PRINTF_ATTRIBUTE(1,2);
190 static void talloc_log(const char *fmt
, ...)
195 if (!talloc_log_fn
) {
200 message
= talloc_vasprintf(NULL
, fmt
, ap
);
203 talloc_log_fn(message
);
204 talloc_free(message
);
207 static void talloc_log_stderr(const char *message
)
209 fprintf(stderr
, "%s", message
);
212 void talloc_set_log_stderr(void)
214 talloc_set_log_fn(talloc_log_stderr
);
217 static void (*talloc_abort_fn
)(const char *reason
);
219 void talloc_set_abort_fn(void (*abort_fn
)(const char *reason
))
221 talloc_abort_fn
= abort_fn
;
224 static void talloc_abort(const char *reason
)
226 talloc_log("%s\n", reason
);
228 if (!talloc_abort_fn
) {
229 TALLOC_ABORT(reason
);
232 talloc_abort_fn(reason
);
235 static void talloc_abort_magic(unsigned magic
)
237 unsigned striped
= magic
- TALLOC_MAGIC_BASE
;
238 unsigned major
= (striped
& 0xFFFFF000) >> 12;
239 unsigned minor
= (striped
& 0x00000FF0) >> 4;
240 talloc_log("Bad talloc magic[0x%08X/%u/%u] expected[0x%08X/%u/%u]\n",
242 TALLOC_MAGIC
, TALLOC_VERSION_MAJOR
, TALLOC_VERSION_MINOR
);
243 talloc_abort("Bad talloc magic value - wrong talloc version used/mixed");
246 static void talloc_abort_double_free(void)
248 talloc_abort("Bad talloc magic value - double free");
251 static void talloc_abort_unknown_value(void)
253 talloc_abort("Bad talloc magic value - unknown value");
256 /* panic if we get a bad magic value */
257 static inline struct talloc_chunk
*talloc_chunk_from_ptr(const void *ptr
)
259 const char *pp
= (const char *)ptr
;
260 struct talloc_chunk
*tc
= discard_const_p(struct talloc_chunk
, pp
- TC_HDR_SIZE
);
261 if (unlikely((tc
->flags
& (TALLOC_FLAG_FREE
| ~0xF)) != TALLOC_MAGIC
)) {
262 if ((tc
->flags
& (~0xFFF)) == TALLOC_MAGIC_BASE
) {
263 talloc_abort_magic(tc
->flags
& (~0xF));
267 if (tc
->flags
& TALLOC_FLAG_FREE
) {
268 talloc_log("talloc: double free error - first free may be at %s\n", tc
->name
);
269 talloc_abort_double_free();
272 talloc_abort_unknown_value();
279 /* hook into the front of the list */
280 #define _TLIST_ADD(list, p) \
284 (p)->next = (p)->prev = NULL; \
286 (list)->prev = (p); \
287 (p)->next = (list); \
293 /* remove an element from a list - element doesn't have to be in list. */
294 #define _TLIST_REMOVE(list, p) \
296 if ((p) == (list)) { \
297 (list) = (p)->next; \
298 if (list) (list)->prev = NULL; \
300 if ((p)->prev) (p)->prev->next = (p)->next; \
301 if ((p)->next) (p)->next->prev = (p)->prev; \
303 if ((p) && ((p) != (list))) (p)->next = (p)->prev = NULL; \
308 return the parent chunk of a pointer
310 static inline struct talloc_chunk
*talloc_parent_chunk(const void *ptr
)
312 struct talloc_chunk
*tc
;
314 if (unlikely(ptr
== NULL
)) {
318 tc
= talloc_chunk_from_ptr(ptr
);
319 while (tc
->prev
) tc
=tc
->prev
;
324 void *talloc_parent(const void *ptr
)
326 struct talloc_chunk
*tc
= talloc_parent_chunk(ptr
);
327 return tc
? TC_PTR_FROM_CHUNK(tc
) : NULL
;
333 const char *talloc_parent_name(const void *ptr
)
335 struct talloc_chunk
*tc
= talloc_parent_chunk(ptr
);
336 return tc
? tc
->name
: NULL
;
340 A pool carries an in-pool object count count in the first 16 bytes.
341 bytes. This is done to support talloc_steal() to a parent outside of the
342 pool. The count includes the pool itself, so a talloc_free() on a pool will
343 only destroy the pool if the count has dropped to zero. A talloc_free() of a
344 pool member will reduce the count, and eventually also call free(3) on the
347 The object count is not put into "struct talloc_chunk" because it is only
348 relevant for talloc pools and the alignment to 16 bytes would increase the
349 memory footprint of each talloc chunk by those 16 bytes.
352 #define TALLOC_POOL_HDR_SIZE 16
354 static unsigned int *talloc_pool_objectcount(struct talloc_chunk
*tc
)
356 return (unsigned int *)((char *)tc
+ sizeof(struct talloc_chunk
));
363 static struct talloc_chunk
*talloc_alloc_pool(struct talloc_chunk
*parent
,
366 struct talloc_chunk
*pool_ctx
= NULL
;
368 struct talloc_chunk
*result
;
371 if (parent
== NULL
) {
375 if (parent
->flags
& TALLOC_FLAG_POOL
) {
378 else if (parent
->flags
& TALLOC_FLAG_POOLMEM
) {
379 pool_ctx
= (struct talloc_chunk
*)parent
->pool
;
382 if (pool_ctx
== NULL
) {
386 space_left
= ((char *)pool_ctx
+ TC_HDR_SIZE
+ pool_ctx
->size
)
387 - ((char *)pool_ctx
->pool
);
390 * Align size to 16 bytes
392 chunk_size
= ((size
+ 15) & ~15);
394 if (space_left
< chunk_size
) {
398 result
= (struct talloc_chunk
*)pool_ctx
->pool
;
400 #if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
401 VALGRIND_MAKE_MEM_UNDEFINED(result
, size
);
404 pool_ctx
->pool
= (void *)((char *)result
+ chunk_size
);
406 result
->flags
= TALLOC_MAGIC
| TALLOC_FLAG_POOLMEM
;
407 result
->pool
= pool_ctx
;
409 *talloc_pool_objectcount(pool_ctx
) += 1;
415 Allocate a bit of memory as a child of an existing pointer
417 static inline void *__talloc(const void *context
, size_t size
)
419 struct talloc_chunk
*tc
= NULL
;
421 if (unlikely(context
== NULL
)) {
422 context
= null_context
;
425 if (unlikely(size
>= MAX_TALLOC_SIZE
)) {
429 if (context
!= NULL
) {
430 tc
= talloc_alloc_pool(talloc_chunk_from_ptr(context
),
435 tc
= (struct talloc_chunk
*)malloc(TC_HDR_SIZE
+size
);
436 if (unlikely(tc
== NULL
)) return NULL
;
437 tc
->flags
= TALLOC_MAGIC
;
442 tc
->destructor
= NULL
;
447 if (likely(context
)) {
448 struct talloc_chunk
*parent
= talloc_chunk_from_ptr(context
);
451 parent
->child
->parent
= NULL
;
452 tc
->next
= parent
->child
;
461 tc
->next
= tc
->prev
= tc
->parent
= NULL
;
464 return TC_PTR_FROM_CHUNK(tc
);
468 * Create a talloc pool
471 void *talloc_pool(const void *context
, size_t size
)
473 void *result
= __talloc(context
, size
+ TALLOC_POOL_HDR_SIZE
);
474 struct talloc_chunk
*tc
;
476 if (unlikely(result
== NULL
)) {
480 tc
= talloc_chunk_from_ptr(result
);
482 tc
->flags
|= TALLOC_FLAG_POOL
;
483 tc
->pool
= (char *)result
+ TALLOC_POOL_HDR_SIZE
;
485 *talloc_pool_objectcount(tc
) = 1;
487 #if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_NOACCESS)
488 VALGRIND_MAKE_MEM_NOACCESS(tc
->pool
, size
);
495 setup a destructor to be called on free of a pointer
496 the destructor should return 0 on success, or -1 on failure.
497 if the destructor fails then the free is failed, and the memory can
498 be continued to be used
500 void _talloc_set_destructor(const void *ptr
, int (*destructor
)(void *))
502 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
503 tc
->destructor
= destructor
;
507 increase the reference count on a piece of memory.
509 int talloc_increase_ref_count(const void *ptr
)
511 if (unlikely(!talloc_reference(null_context
, ptr
))) {
518 helper for talloc_reference()
520 this is referenced by a function pointer and should not be inline
522 static int talloc_reference_destructor(struct talloc_reference_handle
*handle
)
524 struct talloc_chunk
*ptr_tc
= talloc_chunk_from_ptr(handle
->ptr
);
525 _TLIST_REMOVE(ptr_tc
->refs
, handle
);
530 more efficient way to add a name to a pointer - the name must point to a
533 static inline void _talloc_set_name_const(const void *ptr
, const char *name
)
535 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
540 internal talloc_named_const()
542 static inline void *_talloc_named_const(const void *context
, size_t size
, const char *name
)
546 ptr
= __talloc(context
, size
);
547 if (unlikely(ptr
== NULL
)) {
551 _talloc_set_name_const(ptr
, name
);
557 make a secondary reference to a pointer, hanging off the given context.
558 the pointer remains valid until both the original caller and this given
561 the major use for this is when two different structures need to reference the
562 same underlying data, and you want to be able to free the two instances separately,
565 void *_talloc_reference_loc(const void *context
, const void *ptr
, const char *location
)
567 struct talloc_chunk
*tc
;
568 struct talloc_reference_handle
*handle
;
569 if (unlikely(ptr
== NULL
)) return NULL
;
571 tc
= talloc_chunk_from_ptr(ptr
);
572 handle
= (struct talloc_reference_handle
*)_talloc_named_const(context
,
573 sizeof(struct talloc_reference_handle
),
574 TALLOC_MAGIC_REFERENCE
);
575 if (unlikely(handle
== NULL
)) return NULL
;
577 /* note that we hang the destructor off the handle, not the
578 main context as that allows the caller to still setup their
579 own destructor on the context if they want to */
580 talloc_set_destructor(handle
, talloc_reference_destructor
);
581 handle
->ptr
= discard_const_p(void, ptr
);
582 handle
->location
= location
;
583 _TLIST_ADD(tc
->refs
, handle
);
587 static void *_talloc_steal_internal(const void *new_ctx
, const void *ptr
);
590 internal talloc_free call
592 static inline int _talloc_free_internal(void *ptr
, const char *location
)
594 struct talloc_chunk
*tc
;
596 if (unlikely(ptr
== NULL
)) {
600 tc
= talloc_chunk_from_ptr(ptr
);
602 if (unlikely(tc
->refs
)) {
604 /* check this is a reference from a child or grantchild
605 * back to it's parent or grantparent
607 * in that case we need to remove the reference and
608 * call another instance of talloc_free() on the current
611 is_child
= talloc_is_parent(tc
->refs
, ptr
);
612 _talloc_free_internal(tc
->refs
, location
);
614 return _talloc_free_internal(ptr
, location
);
619 if (unlikely(tc
->flags
& TALLOC_FLAG_LOOP
)) {
620 /* we have a free loop - stop looping */
624 if (unlikely(tc
->destructor
)) {
625 talloc_destructor_t d
= tc
->destructor
;
626 if (d
== (talloc_destructor_t
)-1) {
629 tc
->destructor
= (talloc_destructor_t
)-1;
634 tc
->destructor
= NULL
;
638 _TLIST_REMOVE(tc
->parent
->child
, tc
);
639 if (tc
->parent
->child
) {
640 tc
->parent
->child
->parent
= tc
->parent
;
643 if (tc
->prev
) tc
->prev
->next
= tc
->next
;
644 if (tc
->next
) tc
->next
->prev
= tc
->prev
;
647 tc
->flags
|= TALLOC_FLAG_LOOP
;
650 /* we need to work out who will own an abandoned child
651 if it cannot be freed. In priority order, the first
652 choice is owner of any remaining reference to this
653 pointer, the second choice is our parent, and the
654 final choice is the null context. */
655 void *child
= TC_PTR_FROM_CHUNK(tc
->child
);
656 const void *new_parent
= null_context
;
657 if (unlikely(tc
->child
->refs
)) {
658 struct talloc_chunk
*p
= talloc_parent_chunk(tc
->child
->refs
);
659 if (p
) new_parent
= TC_PTR_FROM_CHUNK(p
);
661 if (unlikely(_talloc_free_internal(child
, location
) == -1)) {
662 if (new_parent
== null_context
) {
663 struct talloc_chunk
*p
= talloc_parent_chunk(ptr
);
664 if (p
) new_parent
= TC_PTR_FROM_CHUNK(p
);
666 _talloc_steal_internal(new_parent
, child
);
670 tc
->flags
|= TALLOC_FLAG_FREE
;
672 /* we mark the freed memory with where we called the free
673 * from. This means on a double free error we can report where
674 * the first free came from
678 if (tc
->flags
& (TALLOC_FLAG_POOL
|TALLOC_FLAG_POOLMEM
)) {
679 struct talloc_chunk
*pool
;
680 unsigned int *pool_object_count
;
682 pool
= (tc
->flags
& TALLOC_FLAG_POOL
)
683 ? tc
: (struct talloc_chunk
*)tc
->pool
;
685 pool_object_count
= talloc_pool_objectcount(pool
);
687 if (*pool_object_count
== 0) {
688 talloc_abort("Pool object count zero!");
692 *pool_object_count
-= 1;
694 if (*pool_object_count
== 0) {
705 move a lump of memory from one talloc context to another return the
706 ptr on success, or NULL if it could not be transferred.
707 passing NULL as ptr will always return NULL with no side effects.
709 static void *_talloc_steal_internal(const void *new_ctx
, const void *ptr
)
711 struct talloc_chunk
*tc
, *new_tc
;
713 if (unlikely(!ptr
)) {
717 if (unlikely(new_ctx
== NULL
)) {
718 new_ctx
= null_context
;
721 tc
= talloc_chunk_from_ptr(ptr
);
723 if (unlikely(new_ctx
== NULL
)) {
725 _TLIST_REMOVE(tc
->parent
->child
, tc
);
726 if (tc
->parent
->child
) {
727 tc
->parent
->child
->parent
= tc
->parent
;
730 if (tc
->prev
) tc
->prev
->next
= tc
->next
;
731 if (tc
->next
) tc
->next
->prev
= tc
->prev
;
734 tc
->parent
= tc
->next
= tc
->prev
= NULL
;
735 return discard_const_p(void, ptr
);
738 new_tc
= talloc_chunk_from_ptr(new_ctx
);
740 if (unlikely(tc
== new_tc
|| tc
->parent
== new_tc
)) {
741 return discard_const_p(void, ptr
);
745 _TLIST_REMOVE(tc
->parent
->child
, tc
);
746 if (tc
->parent
->child
) {
747 tc
->parent
->child
->parent
= tc
->parent
;
750 if (tc
->prev
) tc
->prev
->next
= tc
->next
;
751 if (tc
->next
) tc
->next
->prev
= tc
->prev
;
755 if (new_tc
->child
) new_tc
->child
->parent
= NULL
;
756 _TLIST_ADD(new_tc
->child
, tc
);
758 return discard_const_p(void, ptr
);
762 move a lump of memory from one talloc context to another return the
763 ptr on success, or NULL if it could not be transferred.
764 passing NULL as ptr will always return NULL with no side effects.
766 void *_talloc_steal_loc(const void *new_ctx
, const void *ptr
, const char *location
)
768 struct talloc_chunk
*tc
;
770 if (unlikely(ptr
== NULL
)) {
774 tc
= talloc_chunk_from_ptr(ptr
);
776 if (unlikely(tc
->refs
!= NULL
) && talloc_parent(ptr
) != new_ctx
) {
777 struct talloc_reference_handle
*h
;
779 talloc_log("WARNING: talloc_steal with references at %s\n",
782 for (h
=tc
->refs
; h
; h
=h
->next
) {
783 talloc_log("\treference at %s\n",
788 return _talloc_steal_internal(new_ctx
, ptr
);
792 this is like a talloc_steal(), but you must supply the old
793 parent. This resolves the ambiguity in a talloc_steal() which is
794 called on a context that has more than one parent (via references)
796 The old parent can be either a reference or a parent
798 void *talloc_reparent(const void *old_parent
, const void *new_parent
, const void *ptr
)
800 struct talloc_chunk
*tc
;
801 struct talloc_reference_handle
*h
;
803 if (unlikely(ptr
== NULL
)) {
807 if (old_parent
== talloc_parent(ptr
)) {
808 return _talloc_steal_internal(new_parent
, ptr
);
811 tc
= talloc_chunk_from_ptr(ptr
);
812 for (h
=tc
->refs
;h
;h
=h
->next
) {
813 if (talloc_parent(h
) == old_parent
) {
814 if (_talloc_steal_internal(new_parent
, h
) != h
) {
817 return discard_const_p(void, ptr
);
821 /* it wasn't a parent */
826 remove a secondary reference to a pointer. This undo's what
827 talloc_reference() has done. The context and pointer arguments
828 must match those given to a talloc_reference()
830 static inline int talloc_unreference(const void *context
, const void *ptr
)
832 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
833 struct talloc_reference_handle
*h
;
835 if (unlikely(context
== NULL
)) {
836 context
= null_context
;
839 for (h
=tc
->refs
;h
;h
=h
->next
) {
840 struct talloc_chunk
*p
= talloc_parent_chunk(h
);
842 if (context
== NULL
) break;
843 } else if (TC_PTR_FROM_CHUNK(p
) == context
) {
851 return _talloc_free_internal(h
, __location__
);
855 remove a specific parent context from a pointer. This is a more
856 controlled varient of talloc_free()
858 int talloc_unlink(const void *context
, void *ptr
)
860 struct talloc_chunk
*tc_p
, *new_p
;
867 if (context
== NULL
) {
868 context
= null_context
;
871 if (talloc_unreference(context
, ptr
) == 0) {
875 if (context
== NULL
) {
876 if (talloc_parent_chunk(ptr
) != NULL
) {
880 if (talloc_chunk_from_ptr(context
) != talloc_parent_chunk(ptr
)) {
885 tc_p
= talloc_chunk_from_ptr(ptr
);
887 if (tc_p
->refs
== NULL
) {
888 return _talloc_free_internal(ptr
, __location__
);
891 new_p
= talloc_parent_chunk(tc_p
->refs
);
893 new_parent
= TC_PTR_FROM_CHUNK(new_p
);
898 if (talloc_unreference(new_parent
, ptr
) != 0) {
902 _talloc_steal_internal(new_parent
, ptr
);
908 add a name to an existing pointer - va_list version
910 static inline const char *talloc_set_name_v(const void *ptr
, const char *fmt
, va_list ap
) PRINTF_ATTRIBUTE(2,0);
912 static inline const char *talloc_set_name_v(const void *ptr
, const char *fmt
, va_list ap
)
914 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
915 tc
->name
= talloc_vasprintf(ptr
, fmt
, ap
);
916 if (likely(tc
->name
)) {
917 _talloc_set_name_const(tc
->name
, ".name");
923 add a name to an existing pointer
925 const char *talloc_set_name(const void *ptr
, const char *fmt
, ...)
930 name
= talloc_set_name_v(ptr
, fmt
, ap
);
937 create a named talloc pointer. Any talloc pointer can be named, and
938 talloc_named() operates just like talloc() except that it allows you
941 void *talloc_named(const void *context
, size_t size
, const char *fmt
, ...)
947 ptr
= __talloc(context
, size
);
948 if (unlikely(ptr
== NULL
)) return NULL
;
951 name
= talloc_set_name_v(ptr
, fmt
, ap
);
954 if (unlikely(name
== NULL
)) {
955 _talloc_free_internal(ptr
, __location__
);
963 return the name of a talloc ptr, or "UNNAMED"
965 const char *talloc_get_name(const void *ptr
)
967 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
968 if (unlikely(tc
->name
== TALLOC_MAGIC_REFERENCE
)) {
971 if (likely(tc
->name
)) {
979 check if a pointer has the given name. If it does, return the pointer,
980 otherwise return NULL
982 void *talloc_check_name(const void *ptr
, const char *name
)
985 if (unlikely(ptr
== NULL
)) return NULL
;
986 pname
= talloc_get_name(ptr
);
987 if (likely(pname
== name
|| strcmp(pname
, name
) == 0)) {
988 return discard_const_p(void, ptr
);
993 static void talloc_abort_type_missmatch(const char *location
,
995 const char *expected
)
999 reason
= talloc_asprintf(NULL
,
1000 "%s: Type mismatch: name[%s] expected[%s]",
1005 reason
= "Type mismatch";
1008 talloc_abort(reason
);
1011 void *_talloc_get_type_abort(const void *ptr
, const char *name
, const char *location
)
1015 if (unlikely(ptr
== NULL
)) {
1016 talloc_abort_type_missmatch(location
, NULL
, name
);
1020 pname
= talloc_get_name(ptr
);
1021 if (likely(pname
== name
|| strcmp(pname
, name
) == 0)) {
1022 return discard_const_p(void, ptr
);
1025 talloc_abort_type_missmatch(location
, pname
, name
);
1030 this is for compatibility with older versions of talloc
1032 void *talloc_init(const char *fmt
, ...)
1039 * samba3 expects talloc_report_depth_cb(NULL, ...)
1040 * reports all talloc'ed memory, so we need to enable
1043 talloc_enable_null_tracking();
1045 ptr
= __talloc(NULL
, 0);
1046 if (unlikely(ptr
== NULL
)) return NULL
;
1049 name
= talloc_set_name_v(ptr
, fmt
, ap
);
1052 if (unlikely(name
== NULL
)) {
1053 _talloc_free_internal(ptr
, __location__
);
1061 this is a replacement for the Samba3 talloc_destroy_pool functionality. It
1062 should probably not be used in new code. It's in here to keep the talloc
1063 code consistent across Samba 3 and 4.
1065 void talloc_free_children(void *ptr
)
1067 struct talloc_chunk
*tc
;
1069 if (unlikely(ptr
== NULL
)) {
1073 tc
= talloc_chunk_from_ptr(ptr
);
1076 /* we need to work out who will own an abandoned child
1077 if it cannot be freed. In priority order, the first
1078 choice is owner of any remaining reference to this
1079 pointer, the second choice is our parent, and the
1080 final choice is the null context. */
1081 void *child
= TC_PTR_FROM_CHUNK(tc
->child
);
1082 const void *new_parent
= null_context
;
1083 if (unlikely(tc
->child
->refs
)) {
1084 struct talloc_chunk
*p
= talloc_parent_chunk(tc
->child
->refs
);
1085 if (p
) new_parent
= TC_PTR_FROM_CHUNK(p
);
1087 if (unlikely(talloc_free(child
) == -1)) {
1088 if (new_parent
== null_context
) {
1089 struct talloc_chunk
*p
= talloc_parent_chunk(ptr
);
1090 if (p
) new_parent
= TC_PTR_FROM_CHUNK(p
);
1092 _talloc_steal_internal(new_parent
, child
);
1096 if ((tc
->flags
& TALLOC_FLAG_POOL
)
1097 && (*talloc_pool_objectcount(tc
) == 1)) {
1098 tc
->pool
= ((char *)tc
+ TC_HDR_SIZE
+ TALLOC_POOL_HDR_SIZE
);
1099 #if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_NOACCESS)
1100 VALGRIND_MAKE_MEM_NOACCESS(
1101 tc
->pool
, tc
->size
- TALLOC_POOL_HDR_SIZE
);
1107 Allocate a bit of memory as a child of an existing pointer
1109 void *_talloc(const void *context
, size_t size
)
1111 return __talloc(context
, size
);
1115 externally callable talloc_set_name_const()
1117 void talloc_set_name_const(const void *ptr
, const char *name
)
1119 _talloc_set_name_const(ptr
, name
);
1123 create a named talloc pointer. Any talloc pointer can be named, and
1124 talloc_named() operates just like talloc() except that it allows you
1125 to name the pointer.
1127 void *talloc_named_const(const void *context
, size_t size
, const char *name
)
1129 return _talloc_named_const(context
, size
, name
);
1133 free a talloc pointer. This also frees all child pointers of this
1136 return 0 if the memory is actually freed, otherwise -1. The memory
1137 will not be freed if the ref_count is > 1 or the destructor (if
1138 any) returns non-zero
1140 int _talloc_free(void *ptr
, const char *location
)
1142 struct talloc_chunk
*tc
;
1144 if (unlikely(ptr
== NULL
)) {
1148 tc
= talloc_chunk_from_ptr(ptr
);
1150 if (unlikely(tc
->refs
!= NULL
)) {
1151 struct talloc_reference_handle
*h
;
1153 talloc_log("ERROR: talloc_free with references at %s\n",
1156 for (h
=tc
->refs
; h
; h
=h
->next
) {
1157 talloc_log("\treference at %s\n",
1163 return _talloc_free_internal(ptr
, location
);
1169 A talloc version of realloc. The context argument is only used if
1172 void *_talloc_realloc(const void *context
, void *ptr
, size_t size
, const char *name
)
1174 struct talloc_chunk
*tc
;
1176 bool malloced
= false;
1178 /* size zero is equivalent to free() */
1179 if (unlikely(size
== 0)) {
1180 talloc_unlink(context
, ptr
);
1184 if (unlikely(size
>= MAX_TALLOC_SIZE
)) {
1188 /* realloc(NULL) is equivalent to malloc() */
1190 return _talloc_named_const(context
, size
, name
);
1193 tc
= talloc_chunk_from_ptr(ptr
);
1195 /* don't allow realloc on referenced pointers */
1196 if (unlikely(tc
->refs
)) {
1200 /* don't let anybody try to realloc a talloc_pool */
1201 if (unlikely(tc
->flags
& TALLOC_FLAG_POOL
)) {
1205 /* don't shrink if we have less than 1k to gain */
1206 if ((size
< tc
->size
) && ((tc
->size
- size
) < 1024)) {
1211 /* by resetting magic we catch users of the old memory */
1212 tc
->flags
|= TALLOC_FLAG_FREE
;
1215 new_ptr
= malloc(size
+ TC_HDR_SIZE
);
1217 memcpy(new_ptr
, tc
, tc
->size
+ TC_HDR_SIZE
);
1221 if (tc
->flags
& TALLOC_FLAG_POOLMEM
) {
1223 new_ptr
= talloc_alloc_pool(tc
, size
+ TC_HDR_SIZE
);
1224 *talloc_pool_objectcount((struct talloc_chunk
*)
1227 if (new_ptr
== NULL
) {
1228 new_ptr
= malloc(TC_HDR_SIZE
+size
);
1233 memcpy(new_ptr
, tc
, TALLOC_MIN(tc
->size
,size
) + TC_HDR_SIZE
);
1237 new_ptr
= realloc(tc
, size
+ TC_HDR_SIZE
);
1240 if (unlikely(!new_ptr
)) {
1241 tc
->flags
&= ~TALLOC_FLAG_FREE
;
1245 tc
= (struct talloc_chunk
*)new_ptr
;
1246 tc
->flags
&= ~TALLOC_FLAG_FREE
;
1248 tc
->flags
&= ~TALLOC_FLAG_POOLMEM
;
1251 tc
->parent
->child
= tc
;
1254 tc
->child
->parent
= tc
;
1258 tc
->prev
->next
= tc
;
1261 tc
->next
->prev
= tc
;
1265 _talloc_set_name_const(TC_PTR_FROM_CHUNK(tc
), name
);
1267 return TC_PTR_FROM_CHUNK(tc
);
1271 a wrapper around talloc_steal() for situations where you are moving a pointer
1272 between two structures, and want the old pointer to be set to NULL
1274 void *_talloc_move(const void *new_ctx
, const void *_pptr
)
1276 const void **pptr
= discard_const_p(const void *,_pptr
);
1277 void *ret
= talloc_steal(new_ctx
, discard_const_p(void, *pptr
));
1283 return the total size of a talloc pool (subtree)
1285 size_t talloc_total_size(const void *ptr
)
1288 struct talloc_chunk
*c
, *tc
;
1297 tc
= talloc_chunk_from_ptr(ptr
);
1299 if (tc
->flags
& TALLOC_FLAG_LOOP
) {
1303 tc
->flags
|= TALLOC_FLAG_LOOP
;
1305 if (likely(tc
->name
!= TALLOC_MAGIC_REFERENCE
)) {
1308 for (c
=tc
->child
;c
;c
=c
->next
) {
1309 total
+= talloc_total_size(TC_PTR_FROM_CHUNK(c
));
1312 tc
->flags
&= ~TALLOC_FLAG_LOOP
;
1318 return the total number of blocks in a talloc pool (subtree)
1320 size_t talloc_total_blocks(const void *ptr
)
1323 struct talloc_chunk
*c
, *tc
;
1332 tc
= talloc_chunk_from_ptr(ptr
);
1334 if (tc
->flags
& TALLOC_FLAG_LOOP
) {
1338 tc
->flags
|= TALLOC_FLAG_LOOP
;
1341 for (c
=tc
->child
;c
;c
=c
->next
) {
1342 total
+= talloc_total_blocks(TC_PTR_FROM_CHUNK(c
));
1345 tc
->flags
&= ~TALLOC_FLAG_LOOP
;
1351 return the number of external references to a pointer
1353 size_t talloc_reference_count(const void *ptr
)
1355 struct talloc_chunk
*tc
= talloc_chunk_from_ptr(ptr
);
1356 struct talloc_reference_handle
*h
;
1359 for (h
=tc
->refs
;h
;h
=h
->next
) {
1366 report on memory usage by all children of a pointer, giving a full tree view
1368 void talloc_report_depth_cb(const void *ptr
, int depth
, int max_depth
,
1369 void (*callback
)(const void *ptr
,
1370 int depth
, int max_depth
,
1372 void *private_data
),
1375 struct talloc_chunk
*c
, *tc
;
1380 if (ptr
== NULL
) return;
1382 tc
= talloc_chunk_from_ptr(ptr
);
1384 if (tc
->flags
& TALLOC_FLAG_LOOP
) {
1388 callback(ptr
, depth
, max_depth
, 0, private_data
);
1390 if (max_depth
>= 0 && depth
>= max_depth
) {
1394 tc
->flags
|= TALLOC_FLAG_LOOP
;
1395 for (c
=tc
->child
;c
;c
=c
->next
) {
1396 if (c
->name
== TALLOC_MAGIC_REFERENCE
) {
1397 struct talloc_reference_handle
*h
= (struct talloc_reference_handle
*)TC_PTR_FROM_CHUNK(c
);
1398 callback(h
->ptr
, depth
+ 1, max_depth
, 1, private_data
);
1400 talloc_report_depth_cb(TC_PTR_FROM_CHUNK(c
), depth
+ 1, max_depth
, callback
, private_data
);
1403 tc
->flags
&= ~TALLOC_FLAG_LOOP
;
1406 static void talloc_report_depth_FILE_helper(const void *ptr
, int depth
, int max_depth
, int is_ref
, void *_f
)
1408 const char *name
= talloc_get_name(ptr
);
1409 FILE *f
= (FILE *)_f
;
1412 fprintf(f
, "%*sreference to: %s\n", depth
*4, "", name
);
1417 fprintf(f
,"%stalloc report on '%s' (total %6lu bytes in %3lu blocks)\n",
1418 (max_depth
< 0 ? "full " :""), name
,
1419 (unsigned long)talloc_total_size(ptr
),
1420 (unsigned long)talloc_total_blocks(ptr
));
1424 fprintf(f
, "%*s%-30s contains %6lu bytes in %3lu blocks (ref %d) %p\n",
1427 (unsigned long)talloc_total_size(ptr
),
1428 (unsigned long)talloc_total_blocks(ptr
),
1429 (int)talloc_reference_count(ptr
), ptr
);
1432 fprintf(f
, "content: ");
1433 if (talloc_total_size(ptr
)) {
1434 int tot
= talloc_total_size(ptr
);
1437 for (i
= 0; i
< tot
; i
++) {
1438 if ((((char *)ptr
)[i
] > 31) && (((char *)ptr
)[i
] < 126)) {
1439 fprintf(f
, "%c", ((char *)ptr
)[i
]);
1441 fprintf(f
, "~%02x", ((char *)ptr
)[i
]);
1450 report on memory usage by all children of a pointer, giving a full tree view
1452 void talloc_report_depth_file(const void *ptr
, int depth
, int max_depth
, FILE *f
)
1455 talloc_report_depth_cb(ptr
, depth
, max_depth
, talloc_report_depth_FILE_helper
, f
);
1461 report on memory usage by all children of a pointer, giving a full tree view
1463 void talloc_report_full(const void *ptr
, FILE *f
)
1465 talloc_report_depth_file(ptr
, 0, -1, f
);
1469 report on memory usage by all children of a pointer
1471 void talloc_report(const void *ptr
, FILE *f
)
1473 talloc_report_depth_file(ptr
, 0, 1, f
);
1477 report on any memory hanging off the null context
1479 static void talloc_report_null(void)
1481 if (talloc_total_size(null_context
) != 0) {
1482 talloc_report(null_context
, stderr
);
1487 report on any memory hanging off the null context
1489 static void talloc_report_null_full(void)
1491 if (talloc_total_size(null_context
) != 0) {
1492 talloc_report_full(null_context
, stderr
);
1497 enable tracking of the NULL context
1499 void talloc_enable_null_tracking(void)
1501 if (null_context
== NULL
) {
1502 null_context
= _talloc_named_const(NULL
, 0, "null_context");
1503 if (autofree_context
!= NULL
) {
1504 talloc_reparent(NULL
, null_context
, autofree_context
);
1510 enable tracking of the NULL context, not moving the autofree context
1511 into the NULL context. This is needed for the talloc testsuite
1513 void talloc_enable_null_tracking_no_autofree(void)
1515 if (null_context
== NULL
) {
1516 null_context
= _talloc_named_const(NULL
, 0, "null_context");
1521 disable tracking of the NULL context
1523 void talloc_disable_null_tracking(void)
1525 if (null_context
!= NULL
) {
1526 /* we have to move any children onto the real NULL
1528 struct talloc_chunk
*tc
, *tc2
;
1529 tc
= talloc_chunk_from_ptr(null_context
);
1530 for (tc2
= tc
->child
; tc2
; tc2
=tc2
->next
) {
1531 if (tc2
->parent
== tc
) tc2
->parent
= NULL
;
1532 if (tc2
->prev
== tc
) tc2
->prev
= NULL
;
1534 for (tc2
= tc
->next
; tc2
; tc2
=tc2
->next
) {
1535 if (tc2
->parent
== tc
) tc2
->parent
= NULL
;
1536 if (tc2
->prev
== tc
) tc2
->prev
= NULL
;
1541 talloc_free(null_context
);
1542 null_context
= NULL
;
1546 enable leak reporting on exit
1548 void talloc_enable_leak_report(void)
1550 talloc_enable_null_tracking();
1551 atexit(talloc_report_null
);
1555 enable full leak reporting on exit
1557 void talloc_enable_leak_report_full(void)
1559 talloc_enable_null_tracking();
1560 atexit(talloc_report_null_full
);
1564 talloc and zero memory.
1566 void *_talloc_zero(const void *ctx
, size_t size
, const char *name
)
1568 void *p
= _talloc_named_const(ctx
, size
, name
);
1571 memset(p
, '\0', size
);
1578 memdup with a talloc.
1580 void *_talloc_memdup(const void *t
, const void *p
, size_t size
, const char *name
)
1582 void *newp
= _talloc_named_const(t
, size
, name
);
1585 memcpy(newp
, p
, size
);
1591 static inline char *__talloc_strlendup(const void *t
, const char *p
, size_t len
)
1595 ret
= (char *)__talloc(t
, len
+ 1);
1596 if (unlikely(!ret
)) return NULL
;
1598 memcpy(ret
, p
, len
);
1601 _talloc_set_name_const(ret
, ret
);
1606 strdup with a talloc
1608 char *talloc_strdup(const void *t
, const char *p
)
1610 if (unlikely(!p
)) return NULL
;
1611 return __talloc_strlendup(t
, p
, strlen(p
));
1615 strndup with a talloc
1617 char *talloc_strndup(const void *t
, const char *p
, size_t n
)
1619 if (unlikely(!p
)) return NULL
;
1620 return __talloc_strlendup(t
, p
, strnlen(p
, n
));
1623 static inline char *__talloc_strlendup_append(char *s
, size_t slen
,
1624 const char *a
, size_t alen
)
1628 ret
= talloc_realloc(NULL
, s
, char, slen
+ alen
+ 1);
1629 if (unlikely(!ret
)) return NULL
;
1631 /* append the string and the trailing \0 */
1632 memcpy(&ret
[slen
], a
, alen
);
1635 _talloc_set_name_const(ret
, ret
);
1640 * Appends at the end of the string.
1642 char *talloc_strdup_append(char *s
, const char *a
)
1645 return talloc_strdup(NULL
, a
);
1652 return __talloc_strlendup_append(s
, strlen(s
), a
, strlen(a
));
1656 * Appends at the end of the talloc'ed buffer,
1657 * not the end of the string.
1659 char *talloc_strdup_append_buffer(char *s
, const char *a
)
1664 return talloc_strdup(NULL
, a
);
1671 slen
= talloc_get_size(s
);
1672 if (likely(slen
> 0)) {
1676 return __talloc_strlendup_append(s
, slen
, a
, strlen(a
));
1680 * Appends at the end of the string.
1682 char *talloc_strndup_append(char *s
, const char *a
, size_t n
)
1685 return talloc_strdup(NULL
, a
);
1692 return __talloc_strlendup_append(s
, strlen(s
), a
, strnlen(a
, n
));
1696 * Appends at the end of the talloc'ed buffer,
1697 * not the end of the string.
1699 char *talloc_strndup_append_buffer(char *s
, const char *a
, size_t n
)
1704 return talloc_strdup(NULL
, a
);
1711 slen
= talloc_get_size(s
);
1712 if (likely(slen
> 0)) {
1716 return __talloc_strlendup_append(s
, slen
, a
, strnlen(a
, n
));
1720 #ifdef HAVE___VA_COPY
1721 #define va_copy(dest, src) __va_copy(dest, src)
1723 #define va_copy(dest, src) (dest) = (src)
1727 char *talloc_vasprintf(const void *t
, const char *fmt
, va_list ap
)
1734 /* this call looks strange, but it makes it work on older solaris boxes */
1737 /* MSVC runtime needs to use _vcsprintf to return buffer size; vsnprintf would return -1 */
1738 len
= _vscprintf(fmt
, ap2
);
1740 len
= vsnprintf(&c
, 1, fmt
, ap2
);
1743 if (unlikely(len
< 0)) {
1747 ret
= (char *)__talloc(t
, len
+1);
1748 if (unlikely(!ret
)) return NULL
;
1751 vsnprintf(ret
, len
+1, fmt
, ap2
);
1754 _talloc_set_name_const(ret
, ret
);
1760 Perform string formatting, and return a pointer to newly allocated
1761 memory holding the result, inside a memory pool.
1763 char *talloc_asprintf(const void *t
, const char *fmt
, ...)
1769 ret
= talloc_vasprintf(t
, fmt
, ap
);
1774 static inline char *__talloc_vaslenprintf_append(char *s
, size_t slen
,
1775 const char *fmt
, va_list ap
)
1776 PRINTF_ATTRIBUTE(3,0);
1778 static inline char *__talloc_vaslenprintf_append(char *s
, size_t slen
,
1779 const char *fmt
, va_list ap
)
1787 /* MSVC runtime needs to use _vcsprintf to return buffer size; vsnprintf would return -1 */
1788 alen
= _vscprintf(fmt
, ap2
);
1790 alen
= vsnprintf(&c
, 1, fmt
, ap2
);
1795 /* Either the vsnprintf failed or the format resulted in
1796 * no characters being formatted. In the former case, we
1797 * ought to return NULL, in the latter we ought to return
1798 * the original string. Most current callers of this
1799 * function expect it to never return NULL.
1804 s
= talloc_realloc(NULL
, s
, char, slen
+ alen
+ 1);
1805 if (!s
) return NULL
;
1808 vsnprintf(s
+ slen
, alen
+ 1, fmt
, ap2
);
1811 _talloc_set_name_const(s
, s
);
1816 * Realloc @p s to append the formatted result of @p fmt and @p ap,
1817 * and return @p s, which may have moved. Good for gradually
1818 * accumulating output into a string buffer. Appends at the end
1821 char *talloc_vasprintf_append(char *s
, const char *fmt
, va_list ap
)
1824 return talloc_vasprintf(NULL
, fmt
, ap
);
1827 return __talloc_vaslenprintf_append(s
, strlen(s
), fmt
, ap
);
1831 * Realloc @p s to append the formatted result of @p fmt and @p ap,
1832 * and return @p s, which may have moved. Always appends at the
1833 * end of the talloc'ed buffer, not the end of the string.
1835 char *talloc_vasprintf_append_buffer(char *s
, const char *fmt
, va_list ap
)
1840 return talloc_vasprintf(NULL
, fmt
, ap
);
1843 slen
= talloc_get_size(s
);
1844 if (likely(slen
> 0)) {
1848 return __talloc_vaslenprintf_append(s
, slen
, fmt
, ap
);
1852 Realloc @p s to append the formatted result of @p fmt and return @p
1853 s, which may have moved. Good for gradually accumulating output
1854 into a string buffer.
1856 char *talloc_asprintf_append(char *s
, const char *fmt
, ...)
1861 s
= talloc_vasprintf_append(s
, fmt
, ap
);
1867 Realloc @p s to append the formatted result of @p fmt and return @p
1868 s, which may have moved. Good for gradually accumulating output
1871 char *talloc_asprintf_append_buffer(char *s
, const char *fmt
, ...)
1876 s
= talloc_vasprintf_append_buffer(s
, fmt
, ap
);
1882 alloc an array, checking for integer overflow in the array size
1884 void *_talloc_array(const void *ctx
, size_t el_size
, unsigned count
, const char *name
)
1886 if (count
>= MAX_TALLOC_SIZE
/el_size
) {
1889 return _talloc_named_const(ctx
, el_size
* count
, name
);
1893 alloc an zero array, checking for integer overflow in the array size
1895 void *_talloc_zero_array(const void *ctx
, size_t el_size
, unsigned count
, const char *name
)
1897 if (count
>= MAX_TALLOC_SIZE
/el_size
) {
1900 return _talloc_zero(ctx
, el_size
* count
, name
);
1904 realloc an array, checking for integer overflow in the array size
1906 void *_talloc_realloc_array(const void *ctx
, void *ptr
, size_t el_size
, unsigned count
, const char *name
)
1908 if (count
>= MAX_TALLOC_SIZE
/el_size
) {
1911 return _talloc_realloc(ctx
, ptr
, el_size
* count
, name
);
1915 a function version of talloc_realloc(), so it can be passed as a function pointer
1916 to libraries that want a realloc function (a realloc function encapsulates
1917 all the basic capabilities of an allocation library, which is why this is useful)
1919 void *talloc_realloc_fn(const void *context
, void *ptr
, size_t size
)
1921 return _talloc_realloc(context
, ptr
, size
, NULL
);
1925 static int talloc_autofree_destructor(void *ptr
)
1927 autofree_context
= NULL
;
1931 static void talloc_autofree(void)
1933 talloc_free(autofree_context
);
1937 return a context which will be auto-freed on exit
1938 this is useful for reducing the noise in leak reports
1940 void *talloc_autofree_context(void)
1942 if (autofree_context
== NULL
) {
1943 autofree_context
= _talloc_named_const(NULL
, 0, "autofree_context");
1944 talloc_set_destructor(autofree_context
, talloc_autofree_destructor
);
1945 atexit(talloc_autofree
);
1947 return autofree_context
;
1950 size_t talloc_get_size(const void *context
)
1952 struct talloc_chunk
*tc
;
1954 if (context
== NULL
) {
1955 context
= null_context
;
1957 if (context
== NULL
) {
1961 tc
= talloc_chunk_from_ptr(context
);
1967 find a parent of this context that has the given name, if any
1969 void *talloc_find_parent_byname(const void *context
, const char *name
)
1971 struct talloc_chunk
*tc
;
1973 if (context
== NULL
) {
1977 tc
= talloc_chunk_from_ptr(context
);
1979 if (tc
->name
&& strcmp(tc
->name
, name
) == 0) {
1980 return TC_PTR_FROM_CHUNK(tc
);
1982 while (tc
&& tc
->prev
) tc
= tc
->prev
;
1991 show the parentage of a context
1993 void talloc_show_parents(const void *context
, FILE *file
)
1995 struct talloc_chunk
*tc
;
1997 if (context
== NULL
) {
1998 fprintf(file
, "talloc no parents for NULL\n");
2002 tc
= talloc_chunk_from_ptr(context
);
2003 fprintf(file
, "talloc parents of '%s'\n", talloc_get_name(context
));
2005 fprintf(file
, "\t'%s'\n", talloc_get_name(TC_PTR_FROM_CHUNK(tc
)));
2006 while (tc
&& tc
->prev
) tc
= tc
->prev
;
2015 return 1 if ptr is a parent of context
2017 int talloc_is_parent(const void *context
, const void *ptr
)
2019 struct talloc_chunk
*tc
;
2021 if (context
== NULL
) {
2025 tc
= talloc_chunk_from_ptr(context
);
2027 if (TC_PTR_FROM_CHUNK(tc
) == ptr
) return 1;
2028 while (tc
&& tc
->prev
) tc
= tc
->prev
;