Commit 8f8c8b88 authored by Rusty Russell's avatar Rusty Russell

tal: store length in bytes, not count, and always store if CCAN_TAL_DEBUG.

Useful for scanning all the memory, or tallying it.
Signed-off-by: default avatarRusty Russell <rusty@rustcorp.com.au>
parent 77aa87f0
...@@ -47,7 +47,7 @@ struct name { ...@@ -47,7 +47,7 @@ struct name {
struct length { struct length {
struct prop_hdr hdr; /* LENGTH */ struct prop_hdr hdr; /* LENGTH */
size_t count; size_t len;
}; };
struct notifier { struct notifier {
...@@ -383,16 +383,43 @@ static void del_tree(struct tal_hdr *t, const tal_t *orig) ...@@ -383,16 +383,43 @@ static void del_tree(struct tal_hdr *t, const tal_t *orig)
freefn(t); freefn(t);
} }
void *tal_alloc_(const tal_t *ctx, size_t size, bool clear, const char *label) static size_t extra_for_length(size_t size)
{ {
size_t extra;
const size_t align = ALIGNOF(struct length);
/* Round up size, and add tailer. */
extra = ((size + align-1) & ~(align-1)) - size;
extra += sizeof(struct length);
return extra;
}
void *tal_alloc_(const tal_t *ctx, size_t size,
bool clear, bool add_length, const char *label)
{
size_t req_size = size;
struct tal_hdr *child, *parent = debug_tal(to_tal_hdr_or_null(ctx)); struct tal_hdr *child, *parent = debug_tal(to_tal_hdr_or_null(ctx));
#ifdef CCAN_TAL_DEBUG
/* Always record length if debugging. */
add_length = true;
#endif
if (add_length)
size += extra_for_length(size);
child = allocate(sizeof(struct tal_hdr) + size); child = allocate(sizeof(struct tal_hdr) + size);
if (!child) if (!child)
return NULL; return NULL;
if (clear) if (clear)
memset(from_tal_hdr(child), 0, size); memset(from_tal_hdr(child), 0, req_size);
child->prop = (void *)label; child->prop = (void *)label;
if (add_length) {
struct length *lprop;
lprop = (struct length *)((char *)(child+1) + size) - 1;
init_property(&lprop->hdr, child, LENGTH);
lprop->len = req_size;
}
if (!add_child(parent, child)) { if (!add_child(parent, child)) {
freefn(child); freefn(child);
return NULL; return NULL;
...@@ -422,39 +449,13 @@ overflow: ...@@ -422,39 +449,13 @@ overflow:
return false; return false;
} }
static size_t extra_for_length(size_t size)
{
size_t extra;
const size_t align = ALIGNOF(struct length);
/* Round up size, and add tailer. */
extra = ((size + align-1) & ~(align-1)) - size;
extra += sizeof(struct length);
return extra;
}
void *tal_alloc_arr_(const tal_t *ctx, size_t size, size_t count, bool clear, void *tal_alloc_arr_(const tal_t *ctx, size_t size, size_t count, bool clear,
bool add_count, const char *label) bool add_length, const char *label)
{ {
void *ret;
if (!adjust_size(&size, count)) if (!adjust_size(&size, count))
return NULL; return NULL;
if (add_count) return tal_alloc_(ctx, size, clear, add_length, label);
size += extra_for_length(size);
ret = tal_alloc_(ctx, size, clear, label);
if (unlikely(!ret))
return ret;
if (add_count) {
struct length *lprop;
lprop = (struct length *)((char *)ret + size) - 1;
init_property(&lprop->hdr, to_tal_hdr(ret), LENGTH);
lprop->count = count;
}
return ret;
} }
void *tal_free(const tal_t *ctx) void *tal_free(const tal_t *ctx)
...@@ -598,14 +599,14 @@ const char *tal_name(const tal_t *t) ...@@ -598,14 +599,14 @@ const char *tal_name(const tal_t *t)
return n->name; return n->name;
} }
size_t tal_count(const tal_t *ptr) size_t tal_len(const tal_t *ptr)
{ {
struct length *l; struct length *l;
l = find_property(debug_tal(to_tal_hdr(ptr)), LENGTH); l = find_property(debug_tal(to_tal_hdr(ptr)), LENGTH);
if (!l) if (!l)
return 0; return 0;
return l->count; return l->len;
} }
/* Start one past first child: make stopping natural in circ. list. */ /* Start one past first child: make stopping natural in circ. list. */
...@@ -661,7 +662,7 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear) ...@@ -661,7 +662,7 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear)
struct children *child; struct children *child;
struct prop_hdr **lenp; struct prop_hdr **lenp;
struct length len; struct length len;
size_t extra = 0, elemsize = size; size_t extra = 0;
old_t = debug_tal(to_tal_hdr(*ctxp)); old_t = debug_tal(to_tal_hdr(*ctxp));
...@@ -687,13 +688,14 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear) ...@@ -687,13 +688,14 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear)
struct length *new_len; struct length *new_len;
/* Clear between old end and new end. */ /* Clear between old end and new end. */
if (clear && count > len.count) { if (clear && size > len.len) {
char *old_end = (char *)(t + 1) + len.count * elemsize; char *old_end = (char *)(t + 1) + len.len;
memset(old_end, 0, elemsize * (count - len.count)); memset(old_end, 0, size - len.len);
} }
new_len = (struct length *)((char *)(t + 1) + size); new_len = (struct length *)((char *)(t + 1) + size
len.count = count; + extra - sizeof(len));
len.len = size;
*new_len = len; *new_len = len;
/* Be careful replacing next ptr; could be old hdr. */ /* Be careful replacing next ptr; could be old hdr. */
...@@ -729,26 +731,26 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear) ...@@ -729,26 +731,26 @@ bool tal_resize_(tal_t **ctxp, size_t size, size_t count, bool clear)
bool tal_expand_(tal_t **ctxp, const void *src, size_t size, size_t count) bool tal_expand_(tal_t **ctxp, const void *src, size_t size, size_t count)
{ {
struct length *l; struct length *l;
size_t old_count; size_t old_len;
bool ret = false; bool ret = false;
l = find_property(debug_tal(to_tal_hdr(*ctxp)), LENGTH); l = find_property(debug_tal(to_tal_hdr(*ctxp)), LENGTH);
old_count = l->count; old_len = l->len;
/* Check for additive overflow */ /* Check for additive overflow */
if (old_count + count < count) { if (old_len + count * size < old_len) {
call_error("dup size overflow"); call_error("dup size overflow");
goto out; goto out;
} }
/* Don't point src inside thing we're expanding! */ /* Don't point src inside thing we're expanding! */
assert(src < *ctxp assert(src < *ctxp
|| (char *)src >= (char *)(*ctxp) + (size * old_count)); || (char *)src >= (char *)(*ctxp) + old_len);
if (!tal_resize_(ctxp, size, old_count + count, false)) if (!tal_resize_(ctxp, size, old_len/size + count, false))
goto out; goto out;
memcpy((char *)*ctxp + size * old_count, src, count * size); memcpy((char *)*ctxp + old_len, src, count * size);
ret = true; ret = true;
out: out:
...@@ -758,7 +760,7 @@ out: ...@@ -758,7 +760,7 @@ out:
} }
void *tal_dup_(const tal_t *ctx, const void *p, size_t size, void *tal_dup_(const tal_t *ctx, const void *p, size_t size,
size_t n, size_t extra, bool add_count, size_t n, size_t extra, bool add_length,
const char *label) const char *label)
{ {
void *ret; void *ret;
...@@ -788,7 +790,7 @@ void *tal_dup_(const tal_t *ctx, const void *p, size_t size, ...@@ -788,7 +790,7 @@ void *tal_dup_(const tal_t *ctx, const void *p, size_t size,
return (void *)p; return (void *)p;
} }
ret = tal_alloc_arr_(ctx, size, n + extra, false, add_count, label); ret = tal_alloc_arr_(ctx, size, n + extra, false, add_length, label);
if (ret) if (ret)
memcpy(ret, p, nbytes); memcpy(ret, p, nbytes);
return ret; return ret;
...@@ -844,7 +846,7 @@ static void dump_node(unsigned int indent, const struct tal_hdr *t) ...@@ -844,7 +846,7 @@ static void dump_node(unsigned int indent, const struct tal_hdr *t)
break; break;
case LENGTH: case LENGTH:
l = (struct length *)p; l = (struct length *)p;
printf(" LENGTH(%p):count=%zu", p, l->count); printf(" LENGTH(%p):len=%zu", p, l->len);
break; break;
default: default:
printf(" **UNKNOWN(%p):%i**", p, p->type); printf(" **UNKNOWN(%p):%i**", p, p->type);
......
...@@ -32,7 +32,7 @@ typedef void tal_t; ...@@ -32,7 +32,7 @@ typedef void tal_t;
* *p = 1; * *p = 1;
*/ */
#define tal(ctx, type) \ #define tal(ctx, type) \
((type *)tal_alloc_((ctx), sizeof(type), false, TAL_LABEL(type, ""))) ((type *)tal_alloc_((ctx), sizeof(type), false, false, TAL_LABEL(type, "")))
/** /**
* talz - zeroing allocator function * talz - zeroing allocator function
...@@ -46,7 +46,7 @@ typedef void tal_t; ...@@ -46,7 +46,7 @@ typedef void tal_t;
* assert(*p == 0); * assert(*p == 0);
*/ */
#define talz(ctx, type) \ #define talz(ctx, type) \
((type *)tal_alloc_((ctx), sizeof(type), true, TAL_LABEL(type, ""))) ((type *)tal_alloc_((ctx), sizeof(type), true, false, TAL_LABEL(type, "")))
/** /**
* tal_free - free a tal-allocated pointer. * tal_free - free a tal-allocated pointer.
...@@ -259,7 +259,16 @@ const char *tal_name(const tal_t *ptr); ...@@ -259,7 +259,16 @@ const char *tal_name(const tal_t *ptr);
* Returns 0 if @ptr has no length property, but be aware that that is * Returns 0 if @ptr has no length property, but be aware that that is
* also a valid size! * also a valid size!
*/ */
size_t tal_count(const tal_t *ptr); #define tal_count(p) (tal_len(p) / sizeof(*p))
/**
* tal_len - get the count of bytes in a tal_arr.
* @ptr: The tal allocated object array.
*
* Returns 0 if @ptr has no length property, but be aware that that is
* also a valid size!
*/
size_t tal_len(const tal_t *ptr);
/** /**
* tal_first - get the first immediate tal object child. * tal_first - get the first immediate tal object child.
...@@ -423,12 +432,13 @@ bool tal_set_name_(tal_t *ctx, const char *name, bool literal); ...@@ -423,12 +432,13 @@ bool tal_set_name_(tal_t *ctx, const char *name, bool literal);
#define tal_typechk_(ptr, ptype) (ptr) #define tal_typechk_(ptr, ptype) (ptr)
#endif #endif
void *tal_alloc_(const tal_t *ctx, size_t bytes, bool clear, const char *label); void *tal_alloc_(const tal_t *ctx, size_t bytes, bool clear,
bool add_length, const char *label);
void *tal_alloc_arr_(const tal_t *ctx, size_t bytes, size_t count, bool clear, void *tal_alloc_arr_(const tal_t *ctx, size_t bytes, size_t count, bool clear,
bool add_count, const char *label); bool add_length, const char *label);
void *tal_dup_(const tal_t *ctx, const void *p, size_t size, void *tal_dup_(const tal_t *ctx, const void *p, size_t size,
size_t n, size_t extra, bool add_count, size_t n, size_t extra, bool add_length,
const char *label); const char *label);
tal_t *tal_steal_(const tal_t *new_parent, const tal_t *t); tal_t *tal_steal_(const tal_t *new_parent, const tal_t *t);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment