}
static DnsCacheItem *dns_cache_get_by_key_follow_cname_dname_nsec(DnsCache *c, DnsResourceKey *k) {
- _cleanup_(dns_resource_key_unrefp) DnsResourceKey *nsec_key = NULL, *cname_key = NULL;
DnsCacheItem *i;
const char *n;
int r;
n = DNS_RESOURCE_KEY_NAME(k);
/* Check if we have an NSEC record instead for the name. */
- nsec_key = dns_resource_key_new(k->class, DNS_TYPE_NSEC, n);
- if (!nsec_key)
- return NULL;
-
- i = hashmap_get(c->by_key, nsec_key);
+ i = hashmap_get(c->by_key, &DNS_RESOURCE_KEY_CONST(k->class, DNS_TYPE_NSEC, n));
if (i)
return i;
/* Check if we have a CNAME record instead */
- cname_key = dns_resource_key_new_cname(k);
- if (!cname_key)
- return NULL;
- i = hashmap_get(c->by_key, cname_key);
+ i = hashmap_get(c->by_key, &DNS_RESOURCE_KEY_CONST(k->class, DNS_TYPE_CNAME, n));
if (i)
return i;
/* OK, let's look for cached DNAME records. */
for (;;) {
- _cleanup_(dns_resource_key_unrefp) DnsResourceKey *dname_key = NULL;
char label[DNS_LABEL_MAX];
if (isempty(n))
return NULL;
- dname_key = dns_resource_key_new(k->class, DNS_TYPE_DNAME, n);
- if (!dname_key)
- return NULL;
-
- i = hashmap_get(c->by_key, dname_key);
+ i = hashmap_get(c->by_key, &DNS_RESOURCE_KEY_CONST(k->class, DNS_TYPE_DNAME, n));
if (i)
return i;
return k;
}
-DnsResourceKey* dns_resource_key_new_cname(const DnsResourceKey *key) {
- assert(key);
-
- return dns_resource_key_new(key->class, DNS_TYPE_CNAME, DNS_RESOURCE_KEY_NAME(key));
-}
-
DnsResourceKey* dns_resource_key_new_redirect(const DnsResourceKey *key, const DnsResourceRecord *cname) {
int r;
if (!k)
return NULL;
+ /* Static/const keys created with DNS_RESOURCE_KEY_CONST will
+ * set this to -1, they should not be reffed/unreffed */
+ assert(k->n_ref != (unsigned) -1);
+
assert(k->n_ref > 0);
k->n_ref++;
if (!k)
return NULL;
+ assert(k->n_ref != (unsigned) -1);
assert(k->n_ref > 0);
if (k->n_ref == 1) {
char *_name; /* don't access directy, use DNS_RESOURCE_KEY_NAME()! */
};
+/* Creates a temporary resource key. This is only useful to quickly
+ * look up something, without allocating a full DnsResourceKey object
+ * for it. Note that it is not OK to take references to this kind of
+ * resource key object. */
+#define DNS_RESOURCE_KEY_CONST(c, t, n) \
+ ((DnsResourceKey) { \
+ .n_ref = (unsigned) -1, \
+ .class = c, \
+ .type = t, \
+ ._name = (char*) n, \
+ })
+
+
struct DnsTxtItem {
size_t length;
LIST_FIELDS(DnsTxtItem, items);
}
DnsResourceKey* dns_resource_key_new(uint16_t class, uint16_t type, const char *name);
-DnsResourceKey* dns_resource_key_new_cname(const DnsResourceKey *key);
-DnsResourceKey* dns_resource_key_new_dname(const DnsResourceKey *key);
DnsResourceKey* dns_resource_key_new_redirect(const DnsResourceKey *key, const DnsResourceRecord *cname);
int dns_resource_key_new_append_suffix(DnsResourceKey **ret, DnsResourceKey *key, char *name);
DnsResourceKey* dns_resource_key_new_consume(uint16_t class, uint16_t type, char *name);
}
static int dns_zone_item_probe_start(DnsZoneItem *i) {
- _cleanup_(dns_resource_key_unrefp) DnsResourceKey *key = NULL;
DnsTransaction *t;
int r;
if (i->probe_transaction)
return 0;
- key = dns_resource_key_new(i->rr->key->class, DNS_TYPE_ANY, DNS_RESOURCE_KEY_NAME(i->rr->key));
- if (!key)
- return -ENOMEM;
-
- t = dns_scope_find_transaction(i->scope, key, false);
+ t = dns_scope_find_transaction(i->scope, &DNS_RESOURCE_KEY_CONST(i->rr->key->class, DNS_TYPE_ANY, DNS_RESOURCE_KEY_NAME(i->rr->key)), false);
if (!t) {
+ _cleanup_(dns_resource_key_unrefp) DnsResourceKey *key = NULL;
+
+ key = dns_resource_key_new(i->rr->key->class, DNS_TYPE_ANY, DNS_RESOURCE_KEY_NAME(i->rr->key));
+ if (!key)
+ return -ENOMEM;
+
r = dns_transaction_new(&t, i->scope, key);
if (r < 0)
return r;