talloc: Introduce __talloc_with_prefix
authorVolker Lendecke <vl@samba.org>
Fri, 6 Sep 2013 19:18:26 +0000 (12:18 -0700)
committerStefan Metzmacher <metze@samba.org>
Tue, 10 Mar 2015 09:55:37 +0000 (10:55 +0100)
This will allow to exchange the extra talloc pool header with the
talloc_chunk structure

Signed-off-by: Volker Lendecke <vl@samba.org>
Signed-off-by: Jeremy Allison <jra@samba.org>
(cherry picked from commit 9887f387a10e94f71790c0c3c7dc5f8cde7e4eb2)

lib/talloc/talloc.c

index 74db284aa0d807447255cdf8a2d64394771e7047..21d675d3a2c9695273232d637e2b509c884ee6a9 100644 (file)
@@ -510,7 +510,7 @@ static void tc_invalidate_pool(union talloc_pool_chunk *pool_tc)
 */
 
 static struct talloc_chunk *talloc_alloc_pool(struct talloc_chunk *parent,
-                                             size_t size)
+                                             size_t size, size_t prefix_len)
 {
        union talloc_pool_chunk *pool_ctx = NULL;
        size_t space_left;
@@ -537,13 +537,14 @@ static struct talloc_chunk *talloc_alloc_pool(struct talloc_chunk *parent,
        /*
         * Align size to 16 bytes
         */
-       chunk_size = TC_ALIGN16(size);
+       chunk_size = TC_ALIGN16(size + prefix_len);
 
        if (space_left < chunk_size) {
                return NULL;
        }
 
-       result = (struct talloc_chunk *)pool_ctx->hdr.next;
+       result = (struct talloc_chunk *)
+               ((char *)pool_ctx->hdr.next + prefix_len);
 
 #if defined(DEVELOPER) && defined(VALGRIND_MAKE_MEM_UNDEFINED)
        VALGRIND_MAKE_MEM_UNDEFINED(result, size);
@@ -562,10 +563,12 @@ static struct talloc_chunk *talloc_alloc_pool(struct talloc_chunk *parent,
 /*
    Allocate a bit of memory as a child of an existing pointer
 */
-static inline void *__talloc(const void *context, size_t size)
+static inline void *__talloc_with_prefix(const void *context, size_t size,
+                                       size_t prefix_len)
 {
        struct talloc_chunk *tc = NULL;
        struct talloc_memlimit *limit = NULL;
+       size_t total_len = TC_HDR_SIZE + size + prefix_len;
 
        if (unlikely(context == NULL)) {
                context = null_context;
@@ -575,6 +578,10 @@ static inline void *__talloc(const void *context, size_t size)
                return NULL;
        }
 
+       if (unlikely(total_len < TC_HDR_SIZE)) {
+               return NULL;
+       }
+
        if (context != NULL) {
                struct talloc_chunk *ptc = talloc_chunk_from_ptr(context);
 
@@ -582,24 +589,24 @@ static inline void *__talloc(const void *context, size_t size)
                        limit = ptc->limit;
                }
 
-               tc = talloc_alloc_pool(ptc, TC_HDR_SIZE+size);
+               tc = talloc_alloc_pool(ptc, TC_HDR_SIZE+size, prefix_len);
        }
 
        if (tc == NULL) {
                /*
                 * Only do the memlimit check/update on actual allocation.
                 */
-               if (!talloc_memlimit_check(limit, TC_HDR_SIZE + size)) {
+               if (!talloc_memlimit_check(limit, total_len)) {
                        errno = ENOMEM;
                        return NULL;
                }
 
-               tc = (struct talloc_chunk *)malloc(TC_HDR_SIZE+size);
+               tc = (struct talloc_chunk *)malloc(total_len);
                if (unlikely(tc == NULL)) return NULL;
                tc->flags = TALLOC_MAGIC;
                tc->pool  = NULL;
 
-               talloc_memlimit_grow(limit, TC_HDR_SIZE + size);
+               talloc_memlimit_grow(limit, total_len);
        }
 
        tc->limit = limit;
@@ -629,6 +636,11 @@ static inline void *__talloc(const void *context, size_t size)
        return TC_PTR_FROM_CHUNK(tc);
 }
 
+static inline void *__talloc(const void *context, size_t size)
+{
+       return __talloc_with_prefix(context, size, 0);
+}
+
 /*
  * Create a talloc pool
  */
@@ -1558,7 +1570,7 @@ _PUBLIC_ void *_talloc_realloc(const void *context, void *ptr, size_t size, cons
 
 #if ALWAYS_REALLOC
        if (pool_tc) {
-               new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE);
+               new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE, 0);
                pool_tc->hdr.object_count--;
 
                if (new_ptr == NULL) {
@@ -1673,7 +1685,7 @@ _PUBLIC_ void *_talloc_realloc(const void *context, void *ptr, size_t size, cons
                        }
                }
 
-               new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE);
+               new_ptr = talloc_alloc_pool(tc, size + TC_HDR_SIZE, 0);
 
                if (new_ptr == NULL) {
                        new_ptr = malloc(TC_HDR_SIZE+size);