$(srcdir)/iterator/iter_delegpt.h $(srcdir)/iterator/iter_utils.h $(srcdir)/iterator/iter_resptype.h \
$(srcdir)/iterator/iter_donotq.h $(srcdir)/iterator/iter_priv.h $(srcdir)/services/outside_network.h \
$(srcdir)/util/regional.h $(srcdir)/sldns/str2wire.h $(srcdir)/sldns/parseutil.h $(srcdir)/sldns/wire2str.h \
- $(srcdir)/util/timeval_func.h $(srcdir)/util/tcp_conn_limit.h $(srcdir)/util/edns.h $(srcdir)/cachedb/cachedb.h \
+ $(srcdir)/util/timeval_func.h $(srcdir)/util/tcp_conn_limit.h $(srcdir)/util/edns.h $(srcdir)/util/tsig.h $(srcdir)/cachedb/cachedb.h \
$(srcdir)/edns-subnet/subnetmod.h $(srcdir)/edns-subnet/addrtree.h $(srcdir)/edns-subnet/edns-subnet.h
stats.lo stats.o: $(srcdir)/daemon/stats.c config.h $(srcdir)/daemon/stats.h $(srcdir)/util/timehist.h \
$(srcdir)/libunbound/unbound.h $(srcdir)/daemon/worker.h $(srcdir)/libunbound/worker.h $(srcdir)/sldns/sbuffer.h \
#include "util/timeval_func.h"
#include "util/tcp_conn_limit.h"
#include "util/edns.h"
+#include "util/tsig.h"
#ifdef USE_CACHEDB
#include "cachedb/cachedb.h"
#endif
struct acl_list* acl_interface;
/** construct for tcp connection limit */
struct tcl_list* tcl;
+ /** tsig key table */
+ struct tsig_key_table* tsig_key_table;
/** construct for local zones */
struct local_zones* local_zones;
/** if there is response ip configuration in use */
acl_list_delete(ct->acl);
acl_list_delete(ct->acl_interface);
tcl_list_delete(ct->tcl);
+ tsig_key_table_delete(ct->tsig_key_table);
edns_strings_delete(ct->edns_strings);
anchors_delete(ct->anchors);
views_delete(ct->views);
mem += auth_zones_get_mem(ct->auth_zones);
mem += forwards_get_mem(ct->fwds);
mem += hints_get_mem(ct->hints);
+ mem += tsig_key_table_get_mem(ct->tsig_key_table);
mem += local_zones_get_mem(ct->local_zones);
mem += acl_list_get_mem(ct->acl);
mem += acl_list_get_mem(ct->acl_interface);
if(fr_poll_for_quit(fr))
return 1;
+ if(!(ct->tsig_key_table = tsig_key_table_create())) {
+ fr_construct_clear(ct);
+ return 0;
+ }
+ if(!tsig_key_table_apply_cfg(ct->tsig_key_table, newcfg)) {
+ fr_construct_clear(ct);
+ return 0;
+ }
+ if(fr_poll_for_quit(fr))
+ return 1;
+
if(!(ct->auth_zones = auth_zones_create())) {
fr_construct_clear(ct);
return 0;
}
if(!auth_zones_apply_cfg(ct->auth_zones, newcfg, 1, &ct->use_rpz,
fr->worker->daemon->env, &fr->worker->daemon->mods,
- fr->worker->daemon->env->tsig_key_table)) {
+ ct->tsig_key_table)) {
fr_construct_clear(ct);
return 0;
}
COPY_VAR_ptr(forwards);
COPY_VAR_ptr(auths);
COPY_VAR_ptr(views);
+ COPY_VAR_ptr(tsig_keys);
COPY_VAR_ptr(donotqueryaddrs);
#ifdef CLIENT_SUBNET
COPY_VAR_ptr(client_subnet);
lock_basic_lock(&ct->anchors->lock);
lock_basic_lock(&env->anchors->lock);
}
+ lock_rw_wrlock(&env->tsig_key_table->lock);
#if defined(ATOMIC_POINTER_LOCK_FREE) && defined(HAVE_LINK_ATOMIC_STORE)
if(fr->fr_nopause) {
acl_list_swap_tree(daemon->acl, ct->acl);
acl_list_swap_tree(daemon->acl_interface, ct->acl_interface);
tcl_list_swap_tree(daemon->tcl, ct->tcl);
+ tsig_key_table_swap_tree(daemon->env->tsig_key_table,
+ ct->tsig_key_table);
local_zones_swap_tree(daemon->local_zones, ct->local_zones);
respip_set_swap_tree(env->respip_set, ct->respip_set);
daemon->use_response_ip = ct->use_response_ip;
lock_basic_unlock(&ct->anchors->lock);
lock_basic_unlock(&env->anchors->lock);
}
+ lock_rw_unlock(&env->tsig_key_table->lock);
return 1;
}
return tsig_key_table_search(key_table, buf, len);
}
+size_t
+tsig_key_table_get_mem(struct tsig_key_table* tsig_key_table)
+{
+ size_t s;
+ struct tsig_key* p;
+ if(!tsig_key_table)
+ return 0;
+ lock_rw_rdlock(&tsig_key_table->lock);
+ s = sizeof(*tsig_key_table) + sizeof(rbtree_type);
+ RBTREE_FOR(p, struct tsig_key*, tsig_key_table->tree) {
+ s += sizeof(*p) + strlen(p->name_str)+1
+ + p->name_len + p->data_len;
+ }
+ lock_rw_unlock(&tsig_key_table->lock);
+ return s;
+}
+
+void
+tsig_key_table_swap_tree(struct tsig_key_table* tsig_key_table,
+ struct tsig_key_table* data)
+{
+ rbtree_type* oldtree = tsig_key_table->tree;
+ tsig_key_table->tree = data->tree;
+ data->tree = oldtree;
+}
+
void tsig_key_delete(struct tsig_key* key)
{
if(!key)
* They are read from config.
*/
struct tsig_key_table {
- /* Lock on the tsig key table and all keys. */
+ /* Lock on the tsig key table and all keys.
+ * This lock is after the forwards, hints and anchor locks. */
lock_rw_type lock;
/* Tree of tsig keys, by wireformat name. */
struct rbtree_type* tree;
struct tsig_key* tsig_key_table_search_fromstr(
struct tsig_key_table* key_table, char* name);
+/**
+ * Get memory usage of tsig key table.
+ * @param tsig_key_table: the tsig key table.
+ * @return memory use.
+ */
+size_t tsig_key_table_get_mem(struct tsig_key_table* tsig_key_table);
+
+/**
+ * Swap internal tree with preallocated entries. Caller should manage
+ * the locks.
+ * @param tsig_key_table: the tsig_key_table data structure.
+ * @param data: the data structure used to take elements from. This contains
+ * the old elements on return.
+ */
+void tsig_key_table_swap_tree(struct tsig_key_table* tsig_key_table,
+ struct tsig_key_table* data);
+
/**
* Delete TSIG key.
* @param key: to delete