From 3f86bcf30a94fe1e9f98788831d3e1291d238d4e Mon Sep 17 00:00:00 2001 From: John Crispin Date: Sun, 15 Jan 2023 13:41:44 +0100 Subject: [PATCH] ubus: also allow dumping ipv4/6 as an array Signed-off-by: John Crispin --- cache.c | 65 ++++++++++++++++++++++++++++++++++++++++++++------------- cache.h | 2 +- ubus.c | 14 ++++++------- 3 files changed, 58 insertions(+), 23 deletions(-) diff --git a/cache.c b/cache.c index 9de0fa0..046e8b9 100644 --- a/cache.c +++ b/cache.c @@ -382,20 +382,65 @@ void cache_answer(struct interface *iface, struct sockaddr *from, uint8_t *base, } void -cache_dump_records(struct blob_buf *buf, const char *name, int txt_array) +cache_dump_records(struct blob_buf *buf, const char *name, int array) { struct cache_record *r, *last, *next; const char *txt; char buffer[INET6_ADDRSTRLEN]; + void *c = NULL; last = avl_last_element(&records, last, avl); + for (r = avl_find_element(&records, name, r, avl); r; r = next) { + switch (r->type) { + case TYPE_A: + if (!c && array) + c = blobmsg_open_array(buf, "ipv4"); + if ((r->rdlength == 4) && inet_ntop(AF_INET, r->rdata, buffer, INET6_ADDRSTRLEN)) + blobmsg_add_string(buf, "ipv4", buffer); + break; + } + + if (r == last) + break; + + next = avl_next_element(r, avl); + if (strcmp(r->record, next->record) != 0) + break; + } + + if (c) { + blobmsg_close_array(buf, c); + c = NULL; + } + + for (r = avl_find_element(&records, name, r, avl); r; r = next) { + switch (r->type) { + case TYPE_AAAA: + if (!c && array) + c = blobmsg_open_array(buf, "ipv6"); + if ((r->rdlength == 16) && inet_ntop(AF_INET6, r->rdata, buffer, INET6_ADDRSTRLEN)) + blobmsg_add_string(buf, "ipv6", buffer); + break; + } + + if (r == last) + break; + + next = avl_next_element(r, avl); + if (strcmp(r->record, next->record) != 0) + break; + } + + if (c) { + blobmsg_close_array(buf, c); + c = NULL; + } + for (r = avl_find_element(&records, name, r, avl); r; r = next) { switch (r->type) { case TYPE_TXT: if (r->txt && strlen(r->txt)) { - void *c = NULL; - - if (txt_array) + if (array) c = blobmsg_open_array(buf, "txt"); txt = r->txt; @@ -403,7 +448,7 @@ cache_dump_records(struct blob_buf *buf, const char *name, int txt_array) blobmsg_add_string(buf, "txt", txt); txt = &txt[strlen(txt) + 1]; } while (*txt); - if (c) + if (array) blobmsg_close_array(buf, c); } break; @@ -412,16 +457,6 @@ cache_dump_records(struct blob_buf *buf, const char *name, int txt_array) if (r->port) blobmsg_add_u32(buf, "port", r->port); break; - - case TYPE_A: - if ((r->rdlength == 4) && inet_ntop(AF_INET, r->rdata, buffer, INET6_ADDRSTRLEN)) - blobmsg_add_string(buf, "ipv4", buffer); - break; - - case TYPE_AAAA: - if ((r->rdlength == 16) && inet_ntop(AF_INET6, r->rdata, buffer, INET6_ADDRSTRLEN)) - blobmsg_add_string(buf, "ipv6", buffer); - break; } if (r == last) diff --git a/cache.h b/cache.h index 44d407a..8affee6 100644 --- a/cache.h +++ b/cache.h @@ -58,7 +58,7 @@ void cache_answer(struct interface *iface, struct sockaddr *from, uint8_t *base, int blen, char *name, struct dns_answer *a, uint8_t *rdata, int flush); int cache_host_is_known(char *record); -void cache_dump_records(struct blob_buf *buf, const char *name, int txt_array); +void cache_dump_records(struct blob_buf *buf, const char *name, int array); void cache_dump_recursive(struct blob_buf *b, const char *name, uint16_t type, struct interface *iface); #endif diff --git a/ubus.c b/ubus.c index ff62e9a..1ff816d 100644 --- a/ubus.c +++ b/ubus.c @@ -49,13 +49,13 @@ umdns_update(struct ubus_context *ctx, struct ubus_object *obj, enum { BROWSE_SERVICE, - BROWSE_TXT_ARRAY, + BROWSE_ARRAY, BROWSE_MAX }; static const struct blobmsg_policy browse_policy[] = { [BROWSE_SERVICE] = { "service", BLOBMSG_TYPE_STRING }, - [BROWSE_TXT_ARRAY] = { "txt_array", BLOBMSG_TYPE_BOOL }, + [BROWSE_ARRAY] = { "array", BLOBMSG_TYPE_BOOL }, }; static int @@ -68,13 +68,13 @@ umdns_browse(struct ubus_context *ctx, struct ubus_object *obj, struct blob_attr *data[BROWSE_MAX]; void *c1 = NULL, *c2; char *service = NULL; - int txt_array = 0; + int array = 0; blobmsg_parse(browse_policy, BROWSE_MAX, data, blob_data(msg), blob_len(msg)); if (data[BROWSE_SERVICE]) service = blobmsg_get_string(data[BROWSE_SERVICE]); - if (data[BROWSE_TXT_ARRAY]) - txt_array = blobmsg_get_u8(data[BROWSE_TXT_ARRAY]); + if (data[BROWSE_ARRAY]) + array = blobmsg_get_u8(data[BROWSE_ARRAY]); blob_buf_init(&b, 0); avl_for_each_element(&services, s, avl) { @@ -97,8 +97,8 @@ umdns_browse(struct ubus_context *ctx, struct ubus_object *obj, *local = '\0'; c2 = blobmsg_open_table(&b, buffer); strncat(buffer, ".local", MAX_NAME_LEN); - cache_dump_records(&b, buffer, txt_array); - cache_dump_records(&b, s->entry, txt_array); + cache_dump_records(&b, buffer, array); + cache_dump_records(&b, s->entry, array); blobmsg_close_table(&b, c2); q = avl_next_element(s, avl); if (!q || avl_is_last(&services, &s->avl) || strcmp(s->avl.key, q->avl.key)) { -- 2.30.2