Commit 58def8bb authored by Vladimír Čunát's avatar Vladimír Čunát

zonecut, treewide: remove incorrect arrays of knot_rdata_t

To simplify this, some of the zonecut API was generalized
(API+ABI break).  Detected by -Wpedantic.
parent 60760b44
......@@ -12,6 +12,7 @@ Module API changes
- kr_request keeps ::qsource.packet beyond the begin layer
- kr_request::qsource.tcp renamed to ::qsource.flags.tcp
- kr_request::has_tls renamed to ::qsource.flags.tls
- kr_zonecut_add() and kr_zonecut_del() changed parameters slightly
Bugfixes
--------
......
......@@ -377,9 +377,7 @@ static void roothints_add(zs_scanner_t *zs)
return;
}
if (zs->r_type == KNOT_RRTYPE_A || zs->r_type == KNOT_RRTYPE_AAAA) {
knot_rdata_t rdata[RDATA_ARR_MAX];
knot_rdata_init(rdata, zs->r_data_length, zs->r_data);
kr_zonecut_add(hints, zs->r_owner, rdata);
kr_zonecut_add(hints, zs->r_owner, zs->r_data, zs->r_data_length);
}
}
const char* engine_hint_root_file(struct kr_context *ctx, const char *file)
......
......@@ -311,7 +311,7 @@ struct sockaddr *kr_straddr_socket(const char *, int);
int kr_ranked_rrarray_add(ranked_rr_array_t *, const knot_rrset_t *, uint8_t, _Bool, uint32_t, knot_mm_t *);
void kr_qflags_set(struct kr_qflags *, struct kr_qflags);
void kr_qflags_clear(struct kr_qflags *, struct kr_qflags);
int kr_zonecut_add(struct kr_zonecut *, const knot_dname_t *, const knot_rdata_t *);
int kr_zonecut_add(struct kr_zonecut *, const knot_dname_t *, const void *, int);
_Bool kr_zonecut_is_empty(struct kr_zonecut *);
void kr_zonecut_set(struct kr_zonecut *, const knot_dname_t *);
uint64_t kr_now();
......
......@@ -180,7 +180,7 @@ static int update_nsaddr(const knot_rrset_t *rr, struct kr_query *query, int *gl
"'%s': '%s'\n", name_str, addr_str);
return KR_STATE_CONSUME; /* Ignore invalid addresses */
}
int ret = kr_zonecut_add(&query->zone_cut, rr->owner, rdata);
int ret = kr_zonecut_add(&query->zone_cut, rr->owner, rdata->data, rdata->len);
if (ret != 0) {
return KR_STATE_FAIL;
}
......@@ -309,7 +309,7 @@ static int update_cut(knot_pkt_t *pkt, const knot_rrset_t *rr,
}
continue;
}
int ret = kr_zonecut_add(cut, ns_name, NULL);
int ret = kr_zonecut_add(cut, ns_name, NULL, 0);
assert(!ret); (void)ret;
/* Choose when to use glue records. */
......
......@@ -161,11 +161,8 @@ static int invalidate_ns(struct kr_rplan *rplan, struct kr_query *qry)
{
if (qry->ns.addr[0].ip.sa_family != AF_UNSPEC) {
const char *addr = kr_inaddr(&qry->ns.addr[0].ip);
size_t addr_len = kr_inaddr_len(&qry->ns.addr[0].ip);
/* @warning _NOT_ thread-safe */
static knot_rdata_t rdata_arr[RDATA_ARR_MAX];
knot_rdata_init(rdata_arr, addr_len, (const uint8_t *)addr);
return kr_zonecut_del(&qry->zone_cut, qry->ns.name, rdata_arr);
int addr_len = kr_inaddr_len(&qry->ns.addr[0].ip);
return kr_zonecut_del(&qry->zone_cut, qry->ns.name, addr, addr_len);
} else {
return kr_zonecut_del_all(&qry->zone_cut, qry->ns.name);
}
......
......@@ -327,12 +327,10 @@ int kr_pkt_put(knot_pkt_t *pkt, const knot_dname_t *name, uint32_t ttl,
/* Create empty RR */
knot_rrset_t rr;
knot_rrset_init(&rr, knot_dname_copy(name, &pkt->mm), rtype, rclass, ttl);
/* Create RDATA
* @warning _NOT_ thread safe.
*/
static knot_rdata_t rdata_arr[RDATA_ARR_MAX];
knot_rdata_init(rdata_arr, rdlen, rdata);
knot_rdataset_add(&rr.rrs, rdata_arr, &pkt->mm);
/* Create RDATA */
knot_rdata_t *rdata_tmp = mm_malloc(&pkt->mm, offsetof(knot_rdata_t, data) + rdlen);
knot_rdata_init(rdata_tmp, rdlen, rdata);
knot_rdataset_add(&rr.rrs, rdata_tmp, &pkt->mm);
/* Append RR */
return knot_pkt_put(pkt, 0, &rr, KNOT_PF_FREE);
}
......
......@@ -168,9 +168,6 @@ typedef struct ranked_rr_array_entry ranked_rr_array_entry_t;
typedef array_t(ranked_rr_array_entry_t *) ranked_rr_array_t;
/* @endcond */
/** @internal RDATA array maximum size. */
#define RDATA_ARR_MAX (UINT16_MAX + sizeof(uint64_t))
/** Concatenate N strings. */
KR_EXPORT
char* kr_strcatdup(unsigned n, ...);
......
......@@ -174,15 +174,15 @@ int kr_zonecut_copy_trust(struct kr_zonecut *dst, const struct kr_zonecut *src)
return kr_ok();
}
int kr_zonecut_add(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rdata_t *rdata)
int kr_zonecut_add(struct kr_zonecut *cut, const knot_dname_t *ns, const void *data, int len)
{
if (!cut || !ns || !cut->nsset) {
if (!cut || !ns || !cut->nsset || (data && len <= 0)) {
assert(!EINVAL);
return kr_error(EINVAL);
}
/* Disabled; add_reverse_pair() misuses this for domain name in rdata. */
if (false && rdata && rdata->len != sizeof(struct in_addr)
&& rdata->len != sizeof(struct in6_addr)) {
if (false && data && len != sizeof(struct in_addr)
&& len != sizeof(struct in6_addr)) {
assert(!EINVAL);
return kr_error(EINVAL);
}
......@@ -196,24 +196,24 @@ int kr_zonecut_add(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rd
pack_init(**pack);
}
/* Insert data (if has any) */
if (rdata == NULL) {
if (data == NULL) {
return kr_ok();
}
/* Check for duplicates */
if (pack_obj_find(*pack, rdata->data, rdata->len)) {
if (pack_obj_find(*pack, data, len)) {
return kr_ok();
}
/* Push new address */
int ret = pack_reserve_mm(**pack, 1, rdata->len, kr_memreserve, cut->pool);
int ret = pack_reserve_mm(**pack, 1, len, kr_memreserve, cut->pool);
if (ret != 0) {
return kr_error(ENOMEM);
}
return pack_obj_push(*pack, rdata->data, rdata->len);
return pack_obj_push(*pack, data, len);
}
int kr_zonecut_del(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rdata_t *rdata)
int kr_zonecut_del(struct kr_zonecut *cut, const knot_dname_t *ns, const void *data, int len)
{
if (!cut || !ns) {
if (!cut || !ns || (data && len <= 0)) {
return kr_error(EINVAL);
}
......@@ -224,8 +224,8 @@ int kr_zonecut_del(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rd
return kr_error(ENOENT);
}
/* Remove address from the pack. */
if (rdata) {
ret = pack_obj_del(pack, rdata->data, rdata->len);
if (data) {
ret = pack_obj_del(pack, data, len);
}
/* No servers left, remove NS from the set. */
if (pack->len == 0) {
......
......@@ -98,21 +98,23 @@ int kr_zonecut_copy_trust(struct kr_zonecut *dst, const struct kr_zonecut *src);
*
* @param cut zone cut to be populated
* @param ns nameserver name
* @param rdata nameserver address (as rdata)
* @param data typically knot_rdata_t::data
* @param len typically knot_rdata_t::len
* @return 0 or error code
*/
KR_EXPORT
int kr_zonecut_add(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rdata_t *rdata);
int kr_zonecut_add(struct kr_zonecut *cut, const knot_dname_t *ns, const void *data, int len);
/**
* Delete nameserver/address pair from the zone cut.
* @param cut
* @param ns name server name
* @param rdata name server address
* @param data typically knot_rdata_t::data
* @param len typically knot_rdata_t::len
* @return 0 or error code
*/
KR_EXPORT
int kr_zonecut_del(struct kr_zonecut *cut, const knot_dname_t *ns, const knot_rdata_t *rdata);
int kr_zonecut_del(struct kr_zonecut *cut, const knot_dname_t *ns, const void *data, int len);
/**
* Delete all addresses associated with the given name.
......
......@@ -167,34 +167,18 @@ static int query(kr_layer_t *ctx, knot_pkt_t *pkt)
return KR_STATE_DONE;
}
static int parse_addr_str(struct sockaddr_storage *sa, const char *addr)
static int parse_addr_str(union inaddr *sa, const char *addr)
{
int family = strchr(addr, ':') ? AF_INET6 : AF_INET;
memset(sa, 0, sizeof(struct sockaddr_storage));
sa->ss_family = family;
char *addr_bytes = (char *)kr_inaddr((struct sockaddr *)sa);
memset(sa, 0, sizeof(*sa));
sa->ip.sa_family = family;
char *addr_bytes = (/*const*/char *)kr_inaddr(&sa->ip);
if (inet_pton(family, addr, addr_bytes) < 1) {
return kr_error(EILSEQ);
}
return 0;
}
/** @warning _NOT_ thread-safe; returns a pointer to static data! */
static const knot_rdata_t * addr2rdata(const char *addr) {
/* Parse address string */
struct sockaddr_storage ss;
if (parse_addr_str(&ss, addr) != 0) {
return NULL;
}
/* Build RDATA */
static knot_rdata_t rdata_arr[RDATA_ARR_MAX];
size_t addr_len = kr_inaddr_len((struct sockaddr *)&ss);
const uint8_t *raw_addr = (const uint8_t *)kr_inaddr((struct sockaddr *)&ss);
knot_rdata_init(rdata_arr, addr_len, raw_addr);
return rdata_arr;
}
/** @warning _NOT_ thread-safe; returns a pointer to static data! */
static const knot_dname_t * raw_addr2reverse(const uint8_t *raw_addr, int family)
{
......@@ -233,18 +217,15 @@ static const knot_dname_t * raw_addr2reverse(const uint8_t *raw_addr, int family
return dname;
}
/** @warning _NOT_ thread-safe; returns a pointer to static data! */
static const knot_dname_t * addr2reverse(const char *addr)
{
/* Parse address string */
struct sockaddr_storage ss;
if (parse_addr_str(&ss, addr) != 0) {
union inaddr ia;
if (parse_addr_str(&ia, addr) != 0) {
return NULL;
}
const struct sockaddr *sa = (const struct sockaddr *)&ss;
const uint8_t *raw_addr = (const uint8_t *)kr_inaddr(sa);
int family = kr_inaddr_family(sa);
return raw_addr2reverse(raw_addr, family);
return raw_addr2reverse((const /*sign*/uint8_t *)kr_inaddr(&ia.ip),
kr_inaddr_family(&ia.ip));
}
static int add_pair(struct kr_zonecut *hints, const char *name, const char *addr)
......@@ -255,12 +236,13 @@ static int add_pair(struct kr_zonecut *hints, const char *name, const char *addr
return kr_error(EINVAL);
}
knot_dname_to_lower(key);
const knot_rdata_t *rdata = addr2rdata(addr);
if (!rdata) {
union inaddr ia;
if (parse_addr_str(&ia, addr) != 0) {
return kr_error(EINVAL);
}
return kr_zonecut_add(hints, key, rdata);
return kr_zonecut_add(hints, key, kr_inaddr(&ia.ip), kr_inaddr_len(&ia.ip));
}
static int add_reverse_pair(struct kr_zonecut *hints, const char *name, const char *addr)
......@@ -276,11 +258,7 @@ static int add_reverse_pair(struct kr_zonecut *hints, const char *name, const ch
return kr_error(EINVAL);
}
/* Build RDATA */
knot_rdata_t rdata[RDATA_ARR_MAX];
knot_rdata_init(rdata, knot_dname_size(ptr_name), ptr_name);
return kr_zonecut_add(hints, key, rdata);
return kr_zonecut_add(hints, key, ptr_name, knot_dname_size(ptr_name));
}
/** For a given name, remove either one address or all of them (if == NULL).
......@@ -294,18 +272,19 @@ static int del_pair(struct hints_data *data, const char *name, const char *addr)
if (!knot_dname_from_str(key, name, sizeof(key))) {
return kr_error(EINVAL);
}
knot_rdata_t ptr_rdata[RDATA_ARR_MAX];
knot_rdata_init(ptr_rdata, knot_dname_size(key), key);
int key_len = knot_dname_size(key);
if (addr) {
/* Remove the pair. */
const knot_rdata_t *rdata = addr2rdata(addr);
if (!rdata) {
union inaddr ia;
if (parse_addr_str(&ia, addr) != 0) {
return kr_error(EINVAL);
}
const knot_dname_t *reverse_key = addr2reverse(addr);
kr_zonecut_del(&data->reverse_hints, reverse_key, ptr_rdata);
return kr_zonecut_del(&data->hints, key, rdata);
kr_zonecut_del(&data->reverse_hints, reverse_key, key, key_len);
return kr_zonecut_del(&data->hints, key,
kr_inaddr(&ia.ip), kr_inaddr_len(&ia.ip));
} else {
/* Find a matching name */
pack_t *addr_set = kr_zonecut_find(&data->hints, key);
......@@ -321,7 +300,7 @@ static int del_pair(struct hints_data *data, const char *name, const char *addr)
? AF_INET : AF_INET6;
const knot_dname_t *reverse_key = raw_addr2reverse(addr_val, family);
if (reverse_key != NULL) {
kr_zonecut_del(&data->reverse_hints, reverse_key, ptr_rdata);
kr_zonecut_del(&data->reverse_hints, reverse_key, key, key_len);
}
addr = pack_obj_next(addr);
}
......
......@@ -21,7 +21,8 @@ local function publish_hints(nsset)
ffi.C.kr_zonecut_set(roothints, kres.str2dname("."))
for dname, addrsets in pairs(nsset) do
for i = 0, addrsets:rdcount() - 1 do
ffi.C.kr_zonecut_add(roothints, dname, addrsets:rdata_pt(i))
local rdpt = addrsets:rdata_pt(i)
ffi.C.kr_zonecut_add(roothints, dname, rdpt.data, rdpt.len)
end
end
end
......
......@@ -29,7 +29,7 @@ static void test_zonecut_params(void **state)
kr_zonecut_set(NULL, NULL);
kr_zonecut_set(&cut, NULL);
/* TODO triggerring inner assert:
assert_int_not_equal(kr_zonecut_add(NULL, NULL, NULL), 0);
assert_int_not_equal(kr_zonecut_add(NULL, NULL, NULL, 0), 0);
*/
assert_null((void *)kr_zonecut_find(NULL, NULL));
assert_null((void *)kr_zonecut_find(&cut, NULL));
......@@ -47,8 +47,8 @@ static void test_zonecut_copy(void **state)
const knot_dname_t
*n_1 = (const uint8_t *)"\4dead",
*n_2 = (const uint8_t *)"\3bee\1f";
assert_int_equal(kr_zonecut_add(&cut1, n_1, NULL), 0);
assert_int_equal(kr_zonecut_add(&cut1, n_2, NULL), 0);
assert_int_equal(kr_zonecut_add(&cut1, n_1, NULL, 0), 0);
assert_int_equal(kr_zonecut_add(&cut1, n_2, NULL, 0), 0);
/* Copy */
assert_int_equal(kr_zonecut_copy(&cut2, &cut1), 0);
/* Check if exist */
......
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