summary |
shortlog |
log |
commit | commitdiff |
tree
raw |
patch |
inline | side by side (from parent 1:
d1a951b)
A destructor on NULL doesn't make sense, but notifiers (eg. new children)
do. We fix up a mistake in run-notifier (comparing ctx with itself) and
loose typing in tal.c's tal_add_notifier_ too.
Signed-off-by: Rusty Russell <rusty@rustcorp.com.au>
return (void *)(hdr + 1);
}
return (void *)(hdr + 1);
}
-#ifdef TAL_DEBUG
-static void *from_tal_hdr_or_null(struct tal_hdr *hdr)
+static void *from_tal_hdr_or_null(const struct tal_hdr *hdr)
{
if (hdr == &null_parent.hdr)
return NULL;
return from_tal_hdr(hdr);
}
{
if (hdr == &null_parent.hdr)
return NULL;
return from_tal_hdr(hdr);
}
static struct tal_hdr *debug_tal(struct tal_hdr *tal)
{
tal_check(from_tal_hdr_or_null(tal), "TAL_DEBUG ");
static struct tal_hdr *debug_tal(struct tal_hdr *tal)
{
tal_check(from_tal_hdr_or_null(tal), "TAL_DEBUG ");
else
n->u.destroy(from_tal_hdr(ctx));
} else
else
n->u.destroy(from_tal_hdr(ctx));
} else
- n->u.notifyfn(from_tal_hdr(ctx), type,
+ n->u.notifyfn(from_tal_hdr_or_null(ctx), type,
bool tal_add_notifier_(const tal_t *ctx, enum tal_notify_type types,
void (*callback)(tal_t *, enum tal_notify_type, void *))
{
bool tal_add_notifier_(const tal_t *ctx, enum tal_notify_type types,
void (*callback)(tal_t *, enum tal_notify_type, void *))
{
- tal_t *t = debug_tal(to_tal_hdr(ctx));
+ struct tal_hdr *t = debug_tal(to_tal_hdr_or_null(ctx));
struct notifier *n;
assert(types);
struct notifier *n;
assert(types);
void (*callback)(tal_t *, enum tal_notify_type, void *),
bool match_extra_arg, void *extra_arg)
{
void (*callback)(tal_t *, enum tal_notify_type, void *),
bool match_extra_arg, void *extra_arg)
{
- struct tal_hdr *t = debug_tal(to_tal_hdr(ctx));
+ struct tal_hdr *t = debug_tal(to_tal_hdr_or_null(ctx));
enum tal_notify_type types;
types = del_notifier_property(t, callback, match_extra_arg, extra_arg);
enum tal_notify_type types;
types = del_notifier_property(t, callback, match_extra_arg, extra_arg);
/**
* tal_add_notifier - add a callback function when this context changes.
/**
* tal_add_notifier - add a callback function when this context changes.
- * @ptr: The tal allocated object.
+ * @ptr: The tal allocated object, or NULL.
* @types: Bitwise OR of the types the callback is interested in.
* @callback: the function to call.
*
* @types: Bitwise OR of the types the callback is interested in.
* @callback: the function to call.
*
static enum tal_notify_type expect;
static void *expect_info;
static char *ctx;
static enum tal_notify_type expect;
static void *expect_info;
static char *ctx;
-static unsigned int notified1, notified2;
+static unsigned int notified1, notified2, notified_null;
/* Make sure we always move on resize. */
static void *my_realloc(void *old, size_t size)
/* Make sure we always move on resize. */
static void *my_realloc(void *old, size_t size)
-static void notify1(char *p UNNEEDED, enum tal_notify_type notify, void *info)
+static void notify1(char *p, enum tal_notify_type notify, void *info)
ok1(notify == expect);
if (expect_info == &expect_info)
expect_info = info;
ok1(notify == expect);
if (expect_info == &expect_info)
expect_info = info;
+static void notify_null(void *p, enum tal_notify_type notify, void *info)
+{
+ ok1(p == NULL);
+ ok1(notify == expect);
+ if (expect_info == &expect_info)
+ expect_info = info;
+ else
+ ok1(info == expect_info);
+ notified_null++;
+}
+
static bool seen_move, seen_resize;
static void resize_notifier(char *p, enum tal_notify_type notify, void *info)
{
static bool seen_move, seen_resize;
static void resize_notifier(char *p, enum tal_notify_type notify, void *info)
{
ctx = tal(NULL, char);
ok1(tal_add_notifier(ctx, 511, notify1));
ctx = tal(NULL, char);
ok1(tal_add_notifier(ctx, 511, notify1));
ok1(notified1 == 7);
ok1(notified2 == 1);
ok1(notified1 == 7);
ok1(notified2 == 1);
+ /* Notifiers on NULL work, too. */
+ ok1(tal_add_notifier(NULL, TAL_NOTIFY_ADD_CHILD|TAL_NOTIFY_DEL_CHILD,
+ notify_null));
+ expect = TAL_NOTIFY_ADD_CHILD;
+ expect_info = &expect_info;
+ child = tal(NULL, char);
+ ok1(notified_null == 1);
+
+ expect = TAL_NOTIFY_DEL_CHILD;
+ expect_info = child;
+ tal_free(child);
+ ok1(notified_null == 2);
+ ok1(tal_del_notifier(NULL, notify_null));
+
tal_set_backend(NULL, my_realloc, NULL, NULL);
ctx = new_ctx = tal(NULL, char);
ok1(tal_add_notifier(new_ctx, 511, resize_notifier));
tal_set_backend(NULL, my_realloc, NULL, NULL);
ctx = new_ctx = tal(NULL, char);
ok1(tal_add_notifier(new_ctx, 511, resize_notifier));