]> git.ipfire.org Git - thirdparty/unbound.git/commitdiff
- Response actions based on IP address from Jinmei Tatuya (Infoblox).
authorWouter Wijngaards <wouter@nlnetlabs.nl>
Tue, 7 Mar 2017 14:58:51 +0000 (14:58 +0000)
committerWouter Wijngaards <wouter@nlnetlabs.nl>
Tue, 7 Mar 2017 14:58:51 +0000 (14:58 +0000)
git-svn-id: file:///svn/unbound/trunk@4035 be551aaa-1e26-0410-a405-d3ace91eadb9

32 files changed:
Makefile.in
daemon/daemon.c
daemon/daemon.h
daemon/remote.c
daemon/worker.c
dns64/dns64.c
doc/Changelog
doc/IP-BasedActions.pdf [new file with mode: 0644]
respip/respip.c [new file with mode: 0644]
respip/respip.h [new file with mode: 0644]
services/localzone.c
services/localzone.h
services/mesh.c
services/mesh.h
services/modstack.c
services/view.c
services/view.h
smallapp/unbound-checkconf.c
testcode/unitmain.c
util/config_file.c
util/config_file.h
util/configlexer.c
util/configlexer.lex
util/configparser.c
util/configparser.h
util/configparser.y
util/data/msgencode.c
util/data/msgreply.c
util/data/msgreply.h
util/data/packed_rrset.h
util/fptr_wlist.c
util/module.h

index 480a3512533fd732ca360a3d1dc23cca1b026cf5..4eb677363d0d6d043ba07e6fa88c433ce18bf50c 100644 (file)
@@ -113,7 +113,8 @@ util/ub_event.c util/ub_event_pluggable.c util/winsock_event.c \
 validator/autotrust.c validator/val_anchor.c validator/validator.c \
 validator/val_kcache.c validator/val_kentry.c validator/val_neg.c \
 validator/val_nsec3.c validator/val_nsec.c validator/val_secalgo.c \
-validator/val_sigcrypt.c validator/val_utils.c dns64/dns64.c cachedb/cachedb.c $(CHECKLOCK_SRC) \
+validator/val_sigcrypt.c validator/val_utils.c dns64/dns64.c \
+cachedb/cachedb.c respip/respip.c $(CHECKLOCK_SRC) \
 $(DNSTAP_SRC)
 COMMON_OBJ_WITHOUT_NETCALL=dns.lo infra.lo rrset.lo dname.lo msgencode.lo \
 as112.lo msgparse.lo msgreply.lo packed_rrset.lo iterator.lo iter_delegpt.lo \
@@ -126,6 +127,7 @@ slabhash.lo timehist.lo tube.lo winsock_event.lo autotrust.lo val_anchor.lo \
 validator.lo val_kcache.lo val_kentry.lo val_neg.lo val_nsec3.lo val_nsec.lo \
 val_secalgo.lo val_sigcrypt.lo val_utils.lo dns64.lo cachedb.lo \
 $(PYTHONMOD_OBJ) $(CHECKLOCK_OBJ) $(DNSTAP_OBJ)
+COMMON_OBJ_WITHOUT_NETCALL+=respip.lo
 COMMON_OBJ_WITHOUT_UB_EVENT=$(COMMON_OBJ_WITHOUT_NETCALL) netevent.lo listen_dnsport.lo \
 outside_network.lo
 COMMON_OBJ=$(COMMON_OBJ_WITHOUT_UB_EVENT) ub_event.lo
@@ -1294,3 +1296,4 @@ sha512.lo sha512.o: $(srcdir)/compat/sha512.c config.h
 reallocarray.lo reallocarray.o: $(srcdir)/compat/reallocarray.c config.h
 isblank.lo isblank.o: $(srcdir)/compat/isblank.c config.h
 strsep.lo strsep.o: $(srcdir)/compat/strsep.c config.h
+respip.lo respip.o: $(srcdir)/respip/respip.c config.h $(srcdir)/respip/respip.h $(srcdir)/util/module.h $(srcdir)/services/outbound_list.h
index 11a887c40ee47a9da31f67b9d10b53b3c277cbb8..af65b47ac1c2eb29854e40d247be7c2ec4e32497 100644 (file)
@@ -87,6 +87,7 @@
 #include "util/tube.h"
 #include "util/net_help.h"
 #include "sldns/keyraw.h"
+#include "respip/respip.h"
 #include <signal.h>
 
 #ifdef HAVE_SYSTEMD
@@ -562,6 +563,8 @@ daemon_stop_others(struct daemon* daemon)
 void 
 daemon_fork(struct daemon* daemon)
 {
+       int have_view_respip_cfg = 0;
+
        log_assert(daemon);
        if(!(daemon->views = views_create()))
                fatal_exit("Could not create views: out of memory");
@@ -577,9 +580,27 @@ daemon_fork(struct daemon* daemon)
        if(!local_zones_apply_cfg(daemon->local_zones, daemon->cfg))
                fatal_exit("Could not set up local zones");
 
+       /* process raw response-ip configuration data */
+       if(!(daemon->respip_set = respip_set_create()))
+               fatal_exit("Could not create response IP set");
+       if(!respip_global_apply_cfg(daemon->respip_set, daemon->cfg))
+               fatal_exit("Could not set up response IP set");
+       if(!respip_views_apply_cfg(daemon->views, daemon->cfg,
+               &have_view_respip_cfg))
+               fatal_exit("Could not set up per-view response IP sets");
+       daemon->use_response_ip = !respip_set_is_empty(daemon->respip_set) ||
+               have_view_respip_cfg;
+
        /* setup modules */
        daemon_setup_modules(daemon);
 
+       /* response-ip-xxx options don't work as expected without the respip
+        * module.  To avoid run-time operational surprise we reject such
+        * configuration. */
+       if(daemon->use_response_ip &&
+               modstack_find(&daemon->mods, "respip") < 0)
+               fatal_exit("response-ip options require respip module");
+
        /* first create all the worker structures, so we can pass
         * them to the newly created threads. 
         */
@@ -645,6 +666,8 @@ daemon_cleanup(struct daemon* daemon)
        slabhash_clear(daemon->env->msg_cache);
        local_zones_delete(daemon->local_zones);
        daemon->local_zones = NULL;
+       respip_set_delete(daemon->respip_set);
+       daemon->respip_set = NULL;
        views_delete(daemon->views);
        daemon->views = NULL;
        /* key cache is cleared by module desetup during next daemon_fork() */
index dc39a9cbd81f7155707ede3ce2db975a08eb2a3d..2e70e4e5202186f561c920931f0d9ca61dcd2c2c 100644 (file)
@@ -56,6 +56,7 @@ struct local_zones;
 struct views;
 struct ub_randstate;
 struct daemon_remote;
+struct respip_set;
 struct shm_main_info;
 
 #include "dnstap/dnstap_config.h"
@@ -120,6 +121,10 @@ struct daemon {
        struct dt_env* dtenv;
 #endif
        struct shm_main_info* shm_info;
+       /** response-ip set with associated actions and tags. */
+       struct respip_set* respip_set;
+       /** some response-ip tags or actions are configured if true */
+       int use_response_ip;
 };
 
 /**
index b61dfaf1d39e5d81a3ed1536aa01a01929e722f3..3b6777a8805d86dc007be9ec19aaac8f19faeb76 100644 (file)
@@ -853,11 +853,12 @@ static int
 print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon)
 {
        int m;
-       size_t msg, rrset, val, iter;
+       size_t msg, rrset, val, iter, respip;
        msg = slabhash_get_mem(daemon->env->msg_cache);
        rrset = slabhash_get_mem(&daemon->env->rrset_cache->table);
        val=0;
        iter=0;
+       respip=0;
        m = modstack_find(&worker->env.mesh->mods, "validator");
        if(m != -1) {
                fptr_ok(fptr_whitelist_mod_get_mem(worker->env.mesh->
@@ -872,6 +873,13 @@ print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon)
                iter = (*worker->env.mesh->mods.mod[m]->get_mem)
                        (&worker->env, m);
        }
+       m = modstack_find(&worker->env.mesh->mods, "respip");
+       if(m != -1) {
+               fptr_ok(fptr_whitelist_mod_get_mem(worker->env.mesh->
+                       mods.mod[m]->get_mem));
+               respip = (*worker->env.mesh->mods.mod[m]->get_mem)
+                       (&worker->env, m);
+       }
 
        if(!print_longnum(ssl, "mem.cache.rrset"SQ, rrset))
                return 0;
@@ -881,6 +889,8 @@ print_mem(SSL* ssl, struct worker* worker, struct daemon* daemon)
                return 0;
        if(!print_longnum(ssl, "mem.mod.validator"SQ, val))
                return 0;
+       if(!print_longnum(ssl, "mem.mod.respip"SQ, respip))
+               return 0;
        return 1;
 }
 
index a6d5f1a371299119032ed5a2320a8b05cc928436..2a274a1b5be1ec8aa97f875d30eec6bf5c178cc2 100644 (file)
@@ -69,6 +69,7 @@
 #include "iterator/iter_hints.h"
 #include "validator/autotrust.h"
 #include "validator/val_anchor.h"
+#include "respip/respip.h"
 #include "libunbound/context.h"
 #include "libunbound/libworker.h"
 #include "sldns/sbuffer.h"
@@ -511,17 +512,70 @@ answer_norec_from_cache(struct worker* worker, struct query_info* qinfo,
        return 1;
 }
 
-/** answer query from the cache */
+/** Apply, if applicable, a response IP action to a cached answer.
+ * If the answer is rewritten as a result of an action, '*encode_repp' will
+ * point to the reply info containing the modified answer.  '*encode_repp' will
+ * be intact otherwise.
+ * It returns 1 on success, 0 otherwise. */
+static int
+apply_respip_action(struct worker* worker, const struct query_info* qinfo,
+       struct respip_client_info* cinfo, struct reply_info* rep,
+       struct comm_reply* repinfo, struct ub_packed_rrset_key** alias_rrset,
+       struct reply_info** encode_repp)
+{
+       struct respip_action_info actinfo = {respip_none, NULL};
+
+       if(qinfo->qtype != LDNS_RR_TYPE_A &&
+               qinfo->qtype != LDNS_RR_TYPE_AAAA &&
+               qinfo->qtype != LDNS_RR_TYPE_ANY)
+               return 1;
+
+       if(!respip_rewrite_reply(qinfo, cinfo, rep, encode_repp, &actinfo,
+               alias_rrset, 0, worker->scratchpad))
+               return 0;
+
+       /* xxx_deny actions mean dropping the reply, unless the original reply
+        * was redirected to response-ip data. */
+       if((actinfo.action == respip_deny ||
+               actinfo.action == respip_inform_deny) &&
+               *encode_repp == rep)
+               *encode_repp = NULL;
+
+       /* If address info is returned, it means the action should be an
+        * 'inform' variant and the information should be logged. */
+       if(actinfo.addrinfo) {
+               respip_inform_print(actinfo.addrinfo, qinfo->qname,
+                       qinfo->qtype, qinfo->qclass, qinfo->local_alias,
+                       repinfo);
+       }
+
+       return 1;
+}
+
+/** answer query from the cache.
+ * Normally, the answer message will be built in repinfo->c->buffer; if the
+ * answer is supposed to be suppressed or the answer is supposed to be an
+ * incomplete CNAME chain, the buffer is explicitly cleared to signal the
+ * caller as such.  In the latter case *partial_rep will point to the incomplete
+ * reply, and this function is (possibly) supposed to be called again with that
+ * *partial_rep value to complete the chain.  In addition, if the query should
+ * be completely dropped, '*need_drop' will be set to 1. */
 static int
 answer_from_cache(struct worker* worker, struct query_info* qinfo,
+       struct respip_client_info* cinfo, int* need_drop,
+       struct ub_packed_rrset_key** alias_rrset,
+       struct reply_info** partial_repp,
        struct reply_info* rep, uint16_t id, uint16_t flags, 
        struct comm_reply* repinfo, struct edns_data* edns)
 {
        time_t timenow = *worker->env.now;
        uint16_t udpsize = edns->udp_size;
+       struct reply_info* encode_rep = rep;
+       struct reply_info* partial_rep = *partial_repp;
        int secure;
        int must_validate = (!(flags&BIT_CD) || worker->env.cfg->ignore_cd)
                && worker->env.need_to_validate;
+       *partial_repp = NULL;   /* avoid accidental further pass */
        if(worker->env.cfg->serve_expired) {
                /* always lock rrsets, rep->ttl is ignored */
                if(!rrset_array_lock(rep->ref, rep->rrset_count, 0))
@@ -601,7 +655,33 @@ answer_from_cache(struct worker* worker, struct query_info* qinfo,
        if(!inplace_cb_reply_cache_call(&worker->env, qinfo, NULL, rep,
                (int)(flags&LDNS_RCODE_MASK), edns, worker->scratchpad))
                goto bail_out;
-       if(!reply_info_answer_encode(qinfo, rep, id, flags, 
+       *alias_rrset = NULL; /* avoid confusion if caller set it to non-NULL */
+       if(worker->daemon->use_response_ip && !partial_rep &&
+          !apply_respip_action(worker, qinfo, cinfo, rep, repinfo, alias_rrset,
+                       &encode_rep)) {
+               goto bail_out;
+       } else if(partial_rep &&
+               !respip_merge_cname(partial_rep, qinfo, rep, cinfo,
+               must_validate, &encode_rep, worker->scratchpad)) {
+               goto bail_out;
+       }
+       if(encode_rep != rep)
+               secure = 0; /* if rewritten, it can't be considered "secure" */
+       if(!encode_rep || *alias_rrset) {
+               sldns_buffer_clear(repinfo->c->buffer);
+               sldns_buffer_flip(repinfo->c->buffer);
+               if(!encode_rep)
+                       *need_drop = 1;
+               else {
+                       /* If a partial CNAME chain is found, we first need to
+                        * make a copy of the reply in the scratchpad so we
+                        * can release the locks and lookup the cache again. */
+                       *partial_repp = reply_info_copy(encode_rep, NULL,
+                               worker->scratchpad);
+                       if(!*partial_repp)
+                               goto bail_out;
+               }
+       } else if(!reply_info_answer_encode(qinfo, encode_rep, id, flags,
                repinfo->c->buffer, timenow, 1, worker->scratchpad,
                udpsize, edns, (int)(edns->bits & EDNS_DO), secure)) {
                if(!inplace_cb_reply_servfail_call(&worker->env, qinfo, NULL, NULL,
@@ -622,14 +702,18 @@ answer_from_cache(struct worker* worker, struct query_info* qinfo,
        return 1;
 }
 
-/** Reply to client and perform prefetch to keep cache up to date */
+/** Reply to client and perform prefetch to keep cache up to date.
+ * If the buffer for the reply is empty, it indicates that only prefetch is
+ * necessary and the reply should be suppressed (because it's dropped or
+ * being deferred). */
 static void
 reply_and_prefetch(struct worker* worker, struct query_info* qinfo, 
        uint16_t flags, struct comm_reply* repinfo, time_t leeway)
 {
        /* first send answer to client to keep its latency 
         * as small as a cachereply */
-       comm_point_send_reply(repinfo);
+       if(sldns_buffer_limit(repinfo->c->buffer) != 0)
+               comm_point_send_reply(repinfo);
        server_stats_prefetch(&worker->stats, worker);
        
        /* create the prefetch in the mesh as a normal lookup without
@@ -795,6 +879,15 @@ worker_handle_request(struct comm_point* c, void* arg, int error,
        enum acl_access acl;
        struct acl_addr* acladdr;
        int rc = 0;
+       int need_drop = 0;
+       /* We might have to chase a CNAME chain internally, in which case
+        * we'll have up to two replies and combine them to build a complete
+        * answer.  These variables control this case. */
+       struct ub_packed_rrset_key* alias_rrset = NULL;
+       struct reply_info* partial_rep = NULL;
+       struct query_info* lookup_qinfo = &qinfo;
+       struct query_info qinfo_tmp; /* placeholdoer for lookup_qinfo */
+       struct respip_client_info* cinfo = NULL, cinfo_tmp;
 
        if(error != NETEVENT_NOERROR) {
                /* some bad tcp query DNS formats give these error calls */
@@ -1037,16 +1130,43 @@ worker_handle_request(struct comm_point* c, void* arg, int error,
                qinfo.qname_len = d->rr_len[0] - 2;
        }
 
+       /* If we may apply IP-based actions to the answer, build the client
+        * information.  As this can be expensive, skip it if there is
+        * absolutely no possibility of it. */
+       if(worker->daemon->use_response_ip &&
+               (qinfo.qtype == LDNS_RR_TYPE_A ||
+               qinfo.qtype == LDNS_RR_TYPE_AAAA ||
+               qinfo.qtype == LDNS_RR_TYPE_ANY)) {
+               cinfo_tmp.taglist = acladdr->taglist;
+               cinfo_tmp.taglen = acladdr->taglen;
+               cinfo_tmp.tag_actions = acladdr->tag_actions;
+               cinfo_tmp.tag_actions_size = acladdr->tag_actions_size;
+               cinfo_tmp.tag_datas = acladdr->tag_datas;
+               cinfo_tmp.tag_datas_size = acladdr->tag_datas_size;
+               cinfo_tmp.view = acladdr->view;
+               cinfo_tmp.respip_set = worker->daemon->respip_set;
+               cinfo = &cinfo_tmp;
+       }
+
+lookup_cache:
+       /* Lookup the cache.  In case we chase an intermediate CNAME chain
+        * this is a two-pass operation, and lookup_qinfo is different for
+        * each pass.  We should still pass the original qinfo to
+        * answer_from_cache(), however, since it's used to build the reply. */
        if(!edns_bypass_cache_stage(edns.opt_list, &worker->env)) {
-               h = query_info_hash(&qinfo, sldns_buffer_read_u16_at(c->buffer, 2));
-               if((e=slabhash_lookup(worker->env.msg_cache, h, &qinfo, 0))) {
+               h = query_info_hash(lookup_qinfo, sldns_buffer_read_u16_at(c->buffer, 2));
+               if((e=slabhash_lookup(worker->env.msg_cache, h, lookup_qinfo, 0))) {
                        /* answer from cache - we have acquired a readlock on it */
                        if(answer_from_cache(worker, &qinfo, 
+                               cinfo, &need_drop, &alias_rrset, &partial_rep,
                                (struct reply_info*)e->data, 
                                *(uint16_t*)(void *)sldns_buffer_begin(c->buffer), 
                                sldns_buffer_read_u16_at(c->buffer, 2), repinfo, 
                                &edns)) {
-                               /* prefetch it if the prefetch TTL expired */
+                               /* prefetch it if the prefetch TTL expired.
+                                * Note that if there is more than one pass
+                                * its qname must be that used for cache
+                                * lookup. */
                                if((worker->env.cfg->prefetch || worker->env.cfg->serve_expired)
                                        && *worker->env.now >=
                                        ((struct reply_info*)e->data)->prefetch_ttl) {
@@ -1056,16 +1176,38 @@ worker_handle_request(struct comm_point* c, void* arg, int error,
                                                < *worker->env.now)
                                                leeway = 0;
                                        lock_rw_unlock(&e->lock);
-                                       reply_and_prefetch(worker, &qinfo, 
+                                       reply_and_prefetch(worker, lookup_qinfo,
                                                sldns_buffer_read_u16_at(c->buffer, 2),
                                                repinfo, leeway);
-                                       rc = 0;
+                                       if(!partial_rep) {
+                                               rc = 0;
+                                               regional_free_all(worker->scratchpad);
+                                               goto send_reply_rc;
+                                       }
+                               } else if(!partial_rep) {
+                                       lock_rw_unlock(&e->lock);
                                        regional_free_all(worker->scratchpad);
-                                       goto send_reply_rc;
+                                       goto send_reply;
                                }
+                               /* We've found a partial reply ending with an
+                                * alias.  Replace the lookup qinfo for the
+                                * alias target and lookup the cache again to
+                                * (possibly) complete the reply.  As we're
+                                * passing the "base" reply, there will be no
+                                * more alias chasing. */
                                lock_rw_unlock(&e->lock);
-                               regional_free_all(worker->scratchpad);
-                               goto send_reply;
+                               memset(&qinfo_tmp, 0, sizeof(qinfo_tmp));
+                               get_cname_target(alias_rrset, &qinfo_tmp.qname,
+                                       &qinfo_tmp.qname_len);
+                               if(!qinfo_tmp.qname) {
+                                       log_err("unexpected: invalid answer alias");
+                                       regional_free_all(worker->scratchpad);
+                                       return 0; /* drop query */
+                               }
+                               qinfo_tmp.qtype = qinfo.qtype;
+                               qinfo_tmp.qclass = qinfo.qclass;
+                               lookup_qinfo = &qinfo_tmp;
+                               goto lookup_cache;
                        }
                        verbose(VERB_ALGO, "answer from the cache failed");
                        lock_rw_unlock(&e->lock);
@@ -1094,7 +1236,7 @@ worker_handle_request(struct comm_point* c, void* arg, int error,
        }
 
        /* grab a work request structure for this new request */
-       mesh_new_client(worker->env.mesh, &qinfo, 
+       mesh_new_client(worker->env.mesh, &qinfo, cinfo,
                sldns_buffer_read_u16_at(c->buffer, 2),
                &edns, repinfo, *(uint16_t*)(void *)sldns_buffer_begin(c->buffer));
        regional_free_all(worker->scratchpad);
@@ -1104,6 +1246,10 @@ worker_handle_request(struct comm_point* c, void* arg, int error,
 send_reply:
        rc = 1;
 send_reply_rc:
+       if(need_drop) {
+               comm_point_drop_reply(repinfo);
+               return 0;
+       }
 #ifdef USE_DNSTAP
        if(worker->dtenv.log_client_response_messages)
                dt_msg_send_client_response(&worker->dtenv, &repinfo->addr,
index befec864d6ab976105ee11b383999ae03c002e9b..b3e3ab852bca2a735ed4fe4d6984791fdfaf0516 100644 (file)
@@ -411,31 +411,6 @@ handle_ipv6_ptr(struct module_qstate* qstate, int id)
     return module_wait_subquery;
 }
 
-/** allocate (special) rrset keys, return 0 on error */
-static int
-repinfo_alloc_rrset_keys(struct reply_info* rep, 
-       struct regional* region)
-{
-       size_t i;
-       for(i=0; i<rep->rrset_count; i++) {
-               if(region) {
-                       rep->rrsets[i] = (struct ub_packed_rrset_key*)
-                               regional_alloc(region, 
-                               sizeof(struct ub_packed_rrset_key));
-                       if(rep->rrsets[i]) {
-                               memset(rep->rrsets[i], 0, 
-                                       sizeof(struct ub_packed_rrset_key));
-                               rep->rrsets[i]->entry.key = rep->rrsets[i];
-                       }
-               }
-               else return 0;/*        rep->rrsets[i] = alloc_special_obtain(alloc);*/
-               if(!rep->rrsets[i])
-                       return 0;
-               rep->rrsets[i]->entry.data = NULL;
-       }
-       return 1;
-}
-
 static enum module_ext_state
 generate_type_A_query(struct module_qstate* qstate, int id)
 {
@@ -707,7 +682,7 @@ dns64_adjust_a(int id, struct module_qstate* super, struct module_qstate* qstate
                return;
 
        /* allocate ub_key structures special or not */
-       if(!repinfo_alloc_rrset_keys(cp, super->region)) {
+       if(!reply_info_alloc_rrset_keys(cp, NULL, super->region)) {
                return;
        }
 
index db75d0f2584d017fbc9f3e036d920418ca664407..4c1c3dffc0b400a1b2dcc78872899e70c14817f4 100644 (file)
@@ -1,6 +1,7 @@
 7 March 2017: Wouter
        - Fix #1230: swig version 2.0.0 is required for pythonmod, with
          1.3.40 it crashes when running repeatly unbound-control reload.
+       - Response actions based on IP address from Jinmei Tatuya (Infoblox).
 
 6 March 2017: Wouter
        - Fix #1229: Systemd service sandboxing in contrib/unbound.service.
diff --git a/doc/IP-BasedActions.pdf b/doc/IP-BasedActions.pdf
new file mode 100644 (file)
index 0000000..07cec0f
Binary files /dev/null and b/doc/IP-BasedActions.pdf differ
diff --git a/respip/respip.c b/respip/respip.c
new file mode 100644 (file)
index 0000000..ff7c448
--- /dev/null
@@ -0,0 +1,1176 @@
+/*
+ * respip/respip.c - filtering response IP module
+ */
+
+/**
+ * \file
+ *
+ * This file contains a module that inspects a result of recursive resolution
+ * to see if any IP address record should trigger a special action.
+ * If applicable these actions can modify the original response.
+ */
+#include "config.h"
+
+#include "services/localzone.h"
+#include "services/cache/dns.h"
+#include "sldns/str2wire.h"
+#include "util/config_file.h"
+#include "util/fptr_wlist.h"
+#include "util/module.h"
+#include "util/net_help.h"
+#include "util/regional.h"
+#include "util/data/msgreply.h"
+#include "util/storage/dnstree.h"
+#include "respip/respip.h"
+#include "services/view.h"
+#include "sldns/rrdef.h"
+
+/**
+ * Conceptual set of IP addresses for response AAAA or A records that should
+ * trigger special actions.
+ */
+struct respip_set {
+       struct regional* region;
+       struct rbtree_type ip_tree;
+       char* const* tagname;   /* shallow copy of tag names, for logging */
+       int num_tags;           /* number of tagname entries */
+};
+
+/** An address span with response control information */
+struct resp_addr {
+       /** node in address tree */
+       struct addr_tree_node node;
+       /** tag bitlist */
+       uint8_t* taglist;
+       /** length of the taglist (in bytes) */
+       size_t taglen;
+       /** action for this address span */
+       enum respip_action action;
+        /** "local data" for this node */
+       struct ub_packed_rrset_key* data;
+};
+
+/** Subset of resp_addr.node, used for inform-variant logging */
+struct respip_addr_info {
+       struct sockaddr_storage addr;
+       socklen_t addrlen;
+       int net;
+};
+
+/** Query state regarding the response-ip module. */
+enum respip_state {
+       /**
+        * The general state.  Unless CNAME chasing takes place, all processing
+        * is completed in this state without any other asynchronous event.
+        */
+       RESPIP_INIT = 0,
+
+       /**
+        * A subquery for CNAME chasing is completed.
+        */
+       RESPIP_SUBQUERY_FINISHED
+};
+
+/** Per query state for the response-ip module. */
+struct respip_qstate {
+       enum respip_state state;
+};
+
+struct respip_set*
+respip_set_create(void)
+{
+       struct respip_set* set = calloc(1, sizeof(*set));
+       if(!set)
+               return NULL;
+       set->region = regional_create();
+       if(!set->region) {
+               free(set);
+               return NULL;
+       }
+       addr_tree_init(&set->ip_tree);
+       return set;
+}
+
+void
+respip_set_delete(struct respip_set* set)
+{
+       if(!set)
+               return;
+       regional_destroy(set->region);
+       free(set);
+}
+
+struct rbtree_type*
+respip_set_get_tree(struct respip_set* set)
+{
+       if(!set)
+               return NULL;
+       return &set->ip_tree;
+}
+
+/** returns the node in the address tree for the specified netblock string;
+ * non-existent node will be created if 'create' is true */
+static struct resp_addr*
+respip_find_or_create(struct respip_set* set, const char* ipstr, int create)
+{
+       struct resp_addr* node;
+       struct sockaddr_storage addr;
+       int net;
+       socklen_t addrlen;
+
+       if(!netblockstrtoaddr(ipstr, 0, &addr, &addrlen, &net)) {
+               log_err("cannot parse netblock: '%s'", ipstr);
+               return NULL;
+       }
+       node = (struct resp_addr*)addr_tree_find(&set->ip_tree, &addr, addrlen, net);
+       if(!node && create) {
+               node = regional_alloc_zero(set->region, sizeof(*node));
+               node->action = respip_none;
+               if(!node) {
+                       log_err("out of memory");
+                       return NULL;
+               }
+               if(!addr_tree_insert(&set->ip_tree, &node->node, &addr,
+                       addrlen, net)) {
+                       /* We know we didn't find it, so this should be
+                        * impossible. */
+                       log_warn("unexpected: duplicate address: %s", ipstr);
+               }
+       }
+       return node;
+}
+
+static int
+respip_tag_cfg(struct respip_set* set, const char* ipstr,
+       const uint8_t* taglist, size_t taglen)
+{
+       struct resp_addr* node;
+
+       if(!(node=respip_find_or_create(set, ipstr, 1)))
+               return 0;
+       if(node->taglist) {
+               log_warn("duplicate response-address-tag for '%s', overridden.",
+                       ipstr);
+       }
+       node->taglist = regional_alloc_init(set->region, taglist, taglen);
+       if(!node->taglist) {
+               log_err("out of memory");
+               return 0;
+       }
+       node->taglen = taglen;
+       return 1;
+}
+
+/** set action for the node specified by the netblock string */
+static int
+respip_action_cfg(struct respip_set* set, const char* ipstr,
+       const char* actnstr)
+{
+       struct resp_addr* node;
+       enum respip_action action;
+
+       if(!(node=respip_find_or_create(set, ipstr, 1)))
+               return 0;
+       if(node->action != respip_none) {
+               log_warn("duplicate response-ip action for '%s', overridden.",
+                       ipstr);
+       }
+        if(strcmp(actnstr, "deny") == 0)
+                action = respip_deny;
+        else if(strcmp(actnstr, "redirect") == 0)
+                action = respip_redirect;
+        else if(strcmp(actnstr, "inform") == 0)
+                action = respip_inform;
+        else if(strcmp(actnstr, "inform_deny") == 0)
+                action = respip_inform_deny;
+        else if(strcmp(actnstr, "always_transparent") == 0)
+                action = respip_always_transparent;
+        else if(strcmp(actnstr, "always_refuse") == 0)
+                action = respip_always_refuse;
+        else if(strcmp(actnstr, "always_nxdomain") == 0)
+                action = respip_always_nxdomain;
+        else {
+                log_err("unknown response-ip action %s", actnstr);
+                return 0;
+        }
+       node->action = action;
+       return 1;
+}
+
+/** allocate and initialize an rrset structure; this function is based
+ * on new_local_rrset() from the localzone.c module */
+static struct ub_packed_rrset_key*
+new_rrset(struct regional* region, uint16_t rrtype, uint16_t rrclass)
+{
+       struct packed_rrset_data* pd;
+       struct ub_packed_rrset_key* rrset = regional_alloc_zero(
+               region, sizeof(*rrset));
+       if(!rrset) {
+               log_err("out of memory");
+               return NULL;
+       }
+       rrset->entry.key = rrset;
+       pd = regional_alloc_zero(region, sizeof(*pd));
+       if(!pd) {
+               log_err("out of memory");
+               return NULL;
+       }
+       pd->trust = rrset_trust_prim_noglue;
+       pd->security = sec_status_insecure;
+       rrset->entry.data = pd;
+       rrset->rk.dname = regional_alloc_zero(region, 1);
+       if(!rrset->rk.dname) {
+               log_err("out of memory");
+               return NULL;
+       }
+       rrset->rk.dname_len = 1;
+       rrset->rk.type = htons(rrtype);
+       rrset->rk.rrset_class = htons(rrclass);
+       return rrset;
+}
+
+/** enter local data as resource records into a response-ip node */
+static int
+respip_enter_rr(struct regional* region, struct resp_addr* raddr,
+               const char* rrstr, const char* netblock)
+{
+       uint8_t* nm;
+       uint16_t rrtype = 0, rrclass = 0;
+       time_t ttl = 0;
+       uint8_t rr[LDNS_RR_BUF_SIZE];
+       uint8_t* rdata = NULL;
+       size_t rdata_len = 0;
+       char buf[65536];
+       char bufshort[64];
+       struct packed_rrset_data* pd;
+       struct sockaddr* sa;
+       int ret;
+       if(raddr->action != respip_redirect) {
+               log_err("cannot parse response-ip-data %s: response-ip "
+                       "action for %s is not redirect", rrstr, netblock);
+               return 0;
+       }
+       ret = snprintf(buf, sizeof(buf), ". %s", rrstr);
+       if(ret < 0 || ret >= (int)sizeof(buf)) {
+               strlcpy(bufshort, rrstr, sizeof(bufshort));
+               log_err("bad response-ip-data: %s...", bufshort);
+               return 0;
+       }
+       if(!rrstr_get_rr_content(buf, &nm, &rrtype, &rrclass, &ttl, rr, sizeof(rr),
+               &rdata, &rdata_len)) {
+               log_err("bad response-ip-data: %s", rrstr);
+               return 0;
+       }
+       sa = (struct sockaddr*)&raddr->node.addr;
+       if (rrtype == LDNS_RR_TYPE_CNAME && raddr->data) {
+               log_err("CNAME response-ip data (%s) can not co-exist with other "
+                       "response-ip data for netblock %s", rrstr, netblock);
+               return 0;
+       } else if (raddr->data &&
+               raddr->data->rk.type == htons(LDNS_RR_TYPE_CNAME)) {
+               log_err("response-ip data (%s) can not be added; CNAME response-ip "
+                       "data already in place for netblock %s", rrstr, netblock);
+               return 0;
+       } else if((rrtype != LDNS_RR_TYPE_CNAME) &&
+               ((sa->sa_family == AF_INET && rrtype != LDNS_RR_TYPE_A) ||
+               (sa->sa_family == AF_INET6 && rrtype != LDNS_RR_TYPE_AAAA))) {
+               log_err("response-ip data %s record type does not correspond "
+                       "to netblock %s address family", rrstr, netblock);
+               return 0;
+       }
+
+       if(!raddr->data) {
+               raddr->data = new_rrset(region, rrtype, rrclass);
+               if(!raddr->data)
+                       return 0;
+       }
+       pd = raddr->data->entry.data;
+       return rrset_insert_rr(region, pd, rdata, rdata_len, ttl, rrstr);
+}
+
+static int
+respip_data_cfg(struct respip_set* set, const char* ipstr, const char* rrstr)
+{
+       struct resp_addr* node;
+
+       node=respip_find_or_create(set, ipstr, 0);
+       if(!node || node->action == respip_none) {
+               log_err("cannot parse response-ip-data %s: "
+                       "response-ip node for %s not found", rrstr, ipstr);
+               return 0;
+       }
+       return respip_enter_rr(set->region, node, rrstr, ipstr);
+}
+
+static int
+respip_set_apply_cfg(struct respip_set* set, char* const* tagname, int num_tags,
+       struct config_strbytelist* respip_tags,
+       struct config_str2list* respip_actions,
+       struct config_str2list* respip_data)
+{
+       struct config_strbytelist* p;
+       struct config_str2list* pa;
+       struct config_str2list* pd;
+
+       set->tagname = tagname;
+       set->num_tags = num_tags;
+
+       p = respip_tags;
+       while(p) {
+               struct config_strbytelist* np = p->next;
+
+               log_assert(p->str && p->str2);
+               if(!respip_tag_cfg(set, p->str, p->str2, p->str2len)) {
+                       config_del_strbytelist(p);
+                       return 0;
+               }
+               free(p->str);
+               free(p->str2);
+               free(p);
+               p = np;
+       }
+
+       pa = respip_actions;
+       while(pa) {
+               struct config_str2list* np = pa->next;
+               log_assert(pa->str && pa->str2);
+               if(!respip_action_cfg(set, pa->str, pa->str2)) {
+                       config_deldblstrlist(pa);
+                       return 0;
+               }
+               free(pa->str);
+               free(pa->str2);
+               free(pa);
+               pa = np;
+       }
+
+       pd = respip_data;
+       while(pd) {
+               struct config_str2list* np = pd->next;
+               log_assert(pd->str && pd->str2);
+               if(!respip_data_cfg(set, pd->str, pd->str2)) {
+                       config_deldblstrlist(pd);
+                       return 0;
+               }
+               free(pd->str);
+               free(pd->str2);
+               free(pd);
+               pd = np;
+       }
+
+       return 1;
+}
+
+int
+respip_global_apply_cfg(struct respip_set* set, struct config_file* cfg)
+{
+       int ret = respip_set_apply_cfg(set, cfg->tagname, cfg->num_tags,
+               cfg->respip_tags, cfg->respip_actions, cfg->respip_data);
+       cfg->respip_data = NULL;
+       cfg->respip_actions = NULL;
+       cfg->respip_tags = NULL;
+       return ret;
+}
+
+/** Iterate through raw view data and apply the view-specific respip
+ * configuration; at this point we should have already seen all the views,
+ * so if any of the views that respip data refer to does not exist, that's
+ * an error.  This additional iteration through view configuration data
+ * is expected to not have significant performance impact (or rather, its
+ * performance impact is not expected to be prohibitive in the configuration
+ * processing phase).
+ */
+int
+respip_views_apply_cfg(struct views* vs, struct config_file* cfg,
+       int* have_view_respip_cfg)
+{
+       struct config_view* cv;
+       struct view* v;
+       int ret;
+
+       for(cv = cfg->views; cv; cv = cv->next) {
+
+               /** if no respip config for this view then there's
+                 * nothing to do; note that even though respip data must go
+                 * with respip action, we're checking for both here because
+                 * we want to catch the case where the respip action is missing
+                 * while the data is present */
+               if(!cv->respip_actions && !cv->respip_data)
+                       continue;
+
+               if(!(v = views_find_view(vs, cv->name, 1))) {
+                       log_err("view '%s' unexpectedly missing", cv->name);
+                       return 0;
+               }
+               if(!v->respip_set) {
+                       v->respip_set = respip_set_create();
+                       if(!v->respip_set) {
+                               log_err("out of memory");
+                               lock_rw_unlock(&v->lock);
+                               return 0;
+                       }
+               }
+               ret = respip_set_apply_cfg(v->respip_set, NULL, 0, NULL,
+                       cv->respip_actions, cv->respip_data);
+               lock_rw_unlock(&v->lock);
+               if(!ret) {
+                       log_err("Error while applying respip configuration "
+                               "for view '%s'", cv->name);
+                       return 0;
+               }
+               *have_view_respip_cfg = (*have_view_respip_cfg ||
+                       v->respip_set->ip_tree.count);
+               cv->respip_actions = NULL;
+               cv->respip_data = NULL;
+       }
+       return 1;
+}
+
+/**
+ * make a deep copy of 'key' in 'region'.
+ * This is largely derived from packed_rrset_copy_region() and
+ * packed_rrset_ptr_fixup(), but differs in the following points:
+ *
+ * - It doesn't assume all data in 'key' are in a contiguous memory region.
+ *   Although that would be the case in most cases, 'key' can be passed from
+ *   a lower-level module and it might not build the rrset to meet the
+ *   assumption.  In fact, an rrset specified as response-ip-data or generated
+ *   in local_data_find_tag_datas() breaks the assumption.  So it would be
+ *   safer not to naively rely on the assumption.  On the other hand, this
+ *   function ensures the copied rrset data are in a contiguous region so
+ *   that it won't cause a disruption even if an upper layer module naively
+ *   assumes the memory layout.
+ * - It doesn't copy RRSIGs (if any) in 'key'.  The rrset will be used in
+ *   a reply that was already faked, so it doesn't make much sense to provide
+ *   partial sigs even if they are valid themselves.
+ * - It doesn't adjust TTLs as it basically has to be a verbatim copy of 'key'
+ *   just allocated in 'region' (the assumption is necessary TTL adjustment
+ *   has been already done in 'key').
+ *
+ * This function returns the copied rrset key on success, and NULL on memory
+ * allocation failure.
+ */
+struct ub_packed_rrset_key*
+copy_rrset(const struct ub_packed_rrset_key* key, struct regional* region)
+{
+       struct ub_packed_rrset_key* ck = regional_alloc(region,
+               sizeof(struct ub_packed_rrset_key));
+       struct packed_rrset_data* d;
+       struct packed_rrset_data* data = key->entry.data;
+       size_t dsize, i;
+       uint8_t* nextrdata;
+
+       /* derived from packed_rrset_copy_region(), but don't use
+        * packed_rrset_sizeof() and do exclude RRSIGs */
+       if(!ck)
+               return NULL;
+       ck->id = key->id;
+       memset(&ck->entry, 0, sizeof(ck->entry));
+       ck->entry.hash = key->entry.hash;
+       ck->entry.key = ck;
+       ck->rk = key->rk;
+       ck->rk.dname = regional_alloc_init(region, key->rk.dname,
+               key->rk.dname_len);
+       if(!ck->rk.dname)
+               return NULL;
+
+       dsize = sizeof(struct packed_rrset_data) + data->count *
+               (sizeof(size_t)+sizeof(uint8_t*)+sizeof(time_t));
+       for(i=0; i<data->count; i++)
+               dsize += data->rr_len[i];
+       d = regional_alloc(region, dsize);
+       if(!d)
+               return NULL;
+       *d = *data;
+       d->rrsig_count = 0;
+       ck->entry.data = d;
+
+       /* derived from packed_rrset_ptr_fixup() with copying the data */
+       d->rr_len = (size_t*)((uint8_t*)d + sizeof(struct packed_rrset_data));
+       d->rr_data = (uint8_t**)&(d->rr_len[d->count]);
+       d->rr_ttl = (time_t*)&(d->rr_data[d->count]);
+       nextrdata = (uint8_t*)&(d->rr_ttl[d->count]);
+       for(i=0; i<d->count; i++) {
+               d->rr_len[i] = data->rr_len[i];
+               d->rr_ttl[i] = data->rr_ttl[i];
+               d->rr_data[i] = nextrdata;
+               memcpy(d->rr_data[i], data->rr_data[i], data->rr_len[i]);
+               nextrdata += d->rr_len[i];
+       }
+
+       return ck;
+}
+
+int
+respip_init(struct module_env* env, int id)
+{
+       (void)env;
+       (void)id;
+       return 1;
+}
+
+void
+respip_deinit(struct module_env* env, int id)
+{
+       (void)env;
+       (void)id;
+}
+
+/** Convert a packed AAAA or A RRset to sockaddr. */
+static int
+rdata2sockaddr(const struct packed_rrset_data* rd, uint16_t rtype, size_t i,
+       struct sockaddr_storage* ss, socklen_t* addrlenp)
+{
+       /* unbound can accept and cache odd-length AAAA/A records, so we have
+        * to validate the length. */
+       if(rtype == LDNS_RR_TYPE_A && rd->rr_len[i] == 6) {
+               struct sockaddr_in* sa4 = (struct sockaddr_in*)ss;
+
+               memset(sa4, 0, sizeof(*sa4));
+               sa4->sin_family = AF_INET;
+               memcpy(&sa4->sin_addr, rd->rr_data[i] + 2,
+                       sizeof(sa4->sin_addr));
+               *addrlenp = sizeof(*sa4);
+               return 1;
+       } else if(rtype == LDNS_RR_TYPE_AAAA && rd->rr_len[i] == 18) {
+               struct sockaddr_in6* sa6 = (struct sockaddr_in6*)ss;
+
+               memset(sa6, 0, sizeof(*sa6));
+               sa6->sin6_family = AF_INET6;
+               memcpy(&sa6->sin6_addr, rd->rr_data[i] + 2,
+                       sizeof(sa6->sin6_addr));
+               *addrlenp = sizeof(*sa6);
+               return 1;
+       }
+       return 0;
+}
+
+/**
+ * Search the given 'iptree' for response address information that matches
+ * any of the IP addresses in an AAAA or A in the answer section of the
+ * response (stored in 'rep').  If found, a pointer to the matched resp_addr
+ * structure will be returned, and '*rrset_id' is set to the index in
+ * rep->rrsets for the RRset that contains the matching IP address record
+ * (the index is normally 0, but can be larger than that if this is a CNAME
+ * chain or type-ANY response).
+ */
+static const struct resp_addr*
+respip_addr_lookup(const struct reply_info *rep, struct rbtree_type* iptree,
+       size_t* rrset_id)
+{
+       size_t i;
+       struct resp_addr* ra;
+       struct sockaddr_storage ss;
+       socklen_t addrlen;
+
+       for(i=0; i<rep->an_numrrsets; i++) {
+               size_t j;
+               const struct packed_rrset_data* rd;
+               uint16_t rtype = ntohs(rep->rrsets[i]->rk.type);
+
+               if(rtype != LDNS_RR_TYPE_A && rtype != LDNS_RR_TYPE_AAAA)
+                       continue;
+               rd = rep->rrsets[i]->entry.data;
+               for(j = 0; j < rd->count; j++) {
+                       if(!rdata2sockaddr(rd, rtype, j, &ss, &addrlen))
+                               continue;
+                       ra = (struct resp_addr*)addr_tree_lookup(iptree, &ss,
+                               addrlen);
+                       if(ra) {
+                               *rrset_id = i;
+                               return ra;
+                       }
+               }
+       }
+
+       return NULL;
+}
+
+/*
+ * Create a new reply_info based on 'rep'.  The new info is based on
+ * the passed 'rep', but ignores any rrsets except for the first 'an_numrrsets'
+ * RRsets in the answer section.  These answer rrsets are copied to the
+ * new info, up to 'copy_rrsets' rrsets (which must not be larger than
+ * 'an_numrrsets').  If an_numrrsets > copy_rrsets, the remaining rrsets array
+ * entries will be kept empty so the caller can fill them later.  When rrsets
+ * are copied, they are shallow copied.  The caller must ensure that the
+ * copied rrsets are valid throughout its lifetime and must provide appropriate
+ * mutex if it can be shared by multiple threads.
+ */
+static struct reply_info *
+make_new_reply_info(const struct reply_info* rep, struct regional* region,
+       size_t an_numrrsets, size_t copy_rrsets)
+{
+       struct reply_info* new_rep;
+       size_t i;
+
+       /* create a base struct.  we specify 'insecure' security status as
+        * the modified response won't be DNSSEC-valid.  In our faked response
+        * the authority and additional sections will be empty (except possible
+        * EDNS0 OPT RR in the additional section appended on sending it out),
+        * so the total number of RRsets is an_numrrsets. */
+       new_rep = construct_reply_info_base(region, rep->flags,
+               rep->qdcount, rep->ttl, rep->prefetch_ttl, an_numrrsets,
+               0, 0, an_numrrsets, sec_status_insecure);
+       if(!new_rep)
+               return NULL;
+       if(!reply_info_alloc_rrset_keys(new_rep, NULL, region))
+               return NULL;
+       for(i=0; i<copy_rrsets; i++)
+               new_rep->rrsets[i] = rep->rrsets[i];
+
+       return new_rep;
+}
+
+/**
+ * See if response-ip or tag data should override the original answer rrset
+ * (which is rep->rrsets[rrset_id]) and if so override it.
+ * This is (mostly) equivalent to localzone.c:local_data_answer() but for
+ * response-ip actions.
+ * Note that this function distinguishes error conditions from "success but
+ * not overridden".  This is because we want to avoid accidentally applying
+ * the "no data" action in case of error.
+ * @param raddr: address span that requires an action
+ * @param action: action to apply
+ * @apram qtype: original query type
+ * @param rep: original reply message
+ * @param rrset_id: the rrset ID in 'rep' to which the action should apply
+ * @param new_repp: see respip_rewrite_reply
+ * @tag: if >= 0 the tag ID used to determine the action and data
+ * @tag_datas: data corresponding to 'tag'.
+ * @tag_datas_size: size of 'tag_datas'
+ * @tagname: array of tag names, used for logging
+ * @num_tags: size of 'tagname', used for logging
+ * @redirect_rrsetp: ptr to redirect record
+ * @param region: region for building new reply
+ * @return 1 if overridden, 0 if not overridden, -1 on error.
+ */
+static int
+respip_data_answer(const struct resp_addr* raddr, enum respip_action action,
+       uint16_t qtype, const struct reply_info* rep,
+       size_t rrset_id, struct reply_info** new_repp, int tag,
+       struct config_strlist** tag_datas, size_t tag_datas_size,
+       char* const* tagname, int num_tags,
+       struct ub_packed_rrset_key** redirect_rrsetp, struct regional* region)
+{
+       struct ub_packed_rrset_key* rp = raddr->data;
+       struct reply_info* new_rep;
+       *redirect_rrsetp = NULL;
+
+       if(action == respip_redirect && tag != -1 &&
+               (size_t)tag<tag_datas_size && tag_datas[tag]) {
+               struct query_info dataqinfo;
+               struct ub_packed_rrset_key r;
+
+               /* Extract parameters of the original answer rrset that can be
+                * rewritten below, in the form of query_info.  Note that these
+                * can be different from the info of the original query if the
+                * rrset is a CNAME target.*/
+               memset(&dataqinfo, 0, sizeof(dataqinfo));
+               dataqinfo.qname = rep->rrsets[rrset_id]->rk.dname;
+               dataqinfo.qname_len = rep->rrsets[rrset_id]->rk.dname_len;
+               dataqinfo.qtype = ntohs(rep->rrsets[rrset_id]->rk.type);
+               dataqinfo.qclass = ntohs(rep->rrsets[rrset_id]->rk.rrset_class);
+
+               memset(&r, 0, sizeof(r));
+               if(local_data_find_tag_datas(&dataqinfo, tag_datas[tag], &r,
+                       region)) {
+                       verbose(VERB_ALGO,
+                               "response-ip redirect with tag data [%d] %s",
+                               tag, (tag<num_tags?tagname[tag]:"null"));
+                       /* use copy_rrset() to 'normalize' memory layout */
+                       rp = copy_rrset(&r, region);
+                       if(!rp)
+                               return -1;
+               }
+       }
+       if(!rp)
+               return 0;
+
+       /* If we are using response-ip-data, we need to make a copy of rrset
+        * to replace the rrset's dname.  Note that, unlike local data, we
+        * rename the dname for other actions than redirect.  This is because
+        * response-ip-data isn't associated to any specific name. */
+       if(rp == raddr->data) {
+               rp = copy_rrset(rp, region);
+               if(!rp)
+                       return -1;
+               rp->rk.dname = rep->rrsets[rrset_id]->rk.dname;
+               rp->rk.dname_len = rep->rrsets[rrset_id]->rk.dname_len;
+       }
+
+       /* Build a new reply with redirect rrset.  We keep any preceding CNAMEs
+        * and replace the address rrset that triggers the action.  If it's
+        * type ANY query, however, no other answer records should be kept
+        * (note that it can't be a CNAME chain in this case due to
+        * sanitizing). */
+       if(qtype == LDNS_RR_TYPE_ANY)
+               rrset_id = 0;
+       new_rep = make_new_reply_info(rep, region, rrset_id + 1, rrset_id);
+       if(!new_rep)
+               return -1;
+       rp->rk.flags |= PACKED_RRSET_FIXEDTTL; /* avoid adjusting TTL */
+       new_rep->rrsets[rrset_id] = rp;
+
+       *redirect_rrsetp = rp;
+       *new_repp = new_rep;
+       return 1;
+}
+
+/**
+ * apply response ip action in case where no action data is provided.
+ * this is similar to localzone.c:lz_zone_answer() but simplified due to
+ * the characteristics of response ip:
+ * - 'deny' variants will be handled at the caller side
+ * - no specific processing for 'transparent' variants: unlike local zones,
+ *   there is no such a case of 'no data but name existing'.  so all variants
+ *   just mean 'transparent if no data'.
+ * @param qtype: query type
+ * @param action: found action
+ * @param rep:
+ * @param new_repp
+ * @param region: region for building new reply
+ * @return 1 on success, 0 on error.
+ */
+static int
+respip_nodata_answer(uint16_t qtype, enum respip_action action,
+       const struct reply_info *rep, size_t rrset_id,
+       struct reply_info** new_repp, struct regional* region)
+{
+       struct reply_info* new_rep;
+
+       if(action == respip_refuse || action == respip_always_refuse) {
+               new_rep = make_new_reply_info(rep, region, 0, 0);
+               if(!new_rep)
+                       return 0;
+               FLAGS_SET_RCODE(new_rep->flags, LDNS_RCODE_REFUSED);
+               *new_repp = new_rep;
+               return 1;
+       } else if(action == respip_static || action == respip_redirect ||
+               action == respip_always_nxdomain) {
+               /* Since we don't know about other types of the owner name,
+                * we generally return NOERROR/NODATA unless an NXDOMAIN action
+                * is explicitly specified. */
+               int rcode = (action == respip_always_nxdomain)?
+                       LDNS_RCODE_NXDOMAIN:LDNS_RCODE_NOERROR;
+
+               /* We should empty the answer section except for any preceding
+                * CNAMEs (in that case rrset_id > 0).  Type-ANY case is
+                * special as noted in respip_data_answer(). */
+               if(qtype == LDNS_RR_TYPE_ANY)
+                       rrset_id = 0;
+               new_rep = make_new_reply_info(rep, region, rrset_id, rrset_id);
+               if(!new_rep)
+                       return 0;
+               FLAGS_SET_RCODE(new_rep->flags, rcode);
+               *new_repp = new_rep;
+               return 1;
+       }
+
+       return 1;
+}
+
+/** Populate action info structure with the results of response-ip action
+ *  processing, iff as the result of response-ip processing we are actually
+ *  taking some action. Only action is set if action_only is true.
+ *  Returns true on success, false on failure.
+ */
+static int
+populate_action_info(struct respip_action_info* actinfo,
+       enum respip_action action, const struct resp_addr* raddr,
+       const struct ub_packed_rrset_key* ATTR_UNUSED(rrset),
+       int ATTR_UNUSED(tag), const struct respip_set* ATTR_UNUSED(ipset),
+       int ATTR_UNUSED(action_only), struct regional* region)
+{
+       if(action == respip_none || !raddr)
+               return 1;
+       actinfo->action = action;
+
+       /* for inform variants, make a copy of the matched address block for
+        * later logging.  We make a copy to proactively avoid disruption if
+        *  and when we allow a dynamic update to the respip tree. */
+       if(action == respip_inform || action == respip_inform_deny) {
+               struct respip_addr_info* a =
+                       regional_alloc_zero(region, sizeof(*a));
+               if(!a) {
+                       log_err("out of memory");
+                       return 0;
+               }
+               a->addr = raddr->node.addr;
+               a->addrlen = raddr->node.addrlen;
+               a->net = raddr->node.net;
+               actinfo->addrinfo = a;
+       }
+
+       return 1;
+}
+
+int
+respip_rewrite_reply(const struct query_info* qinfo,
+       const struct respip_client_info* cinfo, const struct reply_info* rep,
+       struct reply_info** new_repp, struct respip_action_info* actinfo,
+       struct ub_packed_rrset_key** alias_rrset, int search_only,
+       struct regional* region)
+{
+       const uint8_t* ctaglist;
+       size_t ctaglen;
+       const uint8_t* tag_actions;
+       size_t tag_actions_size;
+       struct config_strlist** tag_datas;
+       size_t tag_datas_size;
+       struct view* view = NULL;
+       struct respip_set* ipset = NULL;
+       size_t rrset_id = 0;
+       enum respip_action action = respip_none;
+       int tag = -1;
+       const struct resp_addr* raddr = NULL;
+       int ret = 1;
+       struct ub_packed_rrset_key* redirect_rrset = NULL;
+
+       if(!cinfo)
+               goto done;
+       ctaglist = cinfo->taglist;
+       ctaglen = cinfo->taglen;
+       tag_actions = cinfo->tag_actions;
+       tag_actions_size = cinfo->tag_actions_size;
+       tag_datas = cinfo->tag_datas;
+       tag_datas_size = cinfo->tag_datas_size;
+       view = cinfo->view;
+       ipset = cinfo->respip_set;
+
+       /** Try to use response-ip config from the view first; use
+         * global response-ip config if we don't have the view or we don't
+         * have the matching per-view config (and the view allows the use
+         * of global data in this case).
+         * Note that we lock the view even if we only use view members that
+         * currently don't change after creation.  This is for safety for
+         * future possible changes as the view documentation seems to expect
+         * any of its member can change in the view's lifetime.
+         * Note also that we assume 'view' is valid in this function, which
+         * should be safe (see unbound bug #1191) */
+       if(view) {
+               lock_rw_rdlock(&view->lock);
+               if(view->respip_set) {
+                       if((raddr = respip_addr_lookup(rep,
+                               &view->respip_set->ip_tree, &rrset_id))) {
+                               /** for per-view respip directives the action
+                                * can only be direct (i.e. not tag-based) */
+                               action = raddr->action;
+                       }
+               }
+               if(!raddr && !view->isfirst)
+                       goto done;
+       }
+       if(!raddr && ipset && (raddr = respip_addr_lookup(rep, &ipset->ip_tree,
+               &rrset_id))) {
+               action = local_data_find_tag_action(raddr->taglist,
+                       raddr->taglen, ctaglist, ctaglen, tag_actions,
+                       tag_actions_size, raddr->action, &tag,
+                       ipset->tagname, ipset->num_tags);
+       }
+       if(raddr && !search_only) {
+               int result = 0;
+
+               /* first, see if we have response-ip or tag action for the
+                * action except for 'always' variants. */
+               if(action != respip_always_refuse
+                       && action != respip_always_transparent
+                       && action != respip_always_nxdomain
+                       && (result = respip_data_answer(raddr, action,
+                       qinfo->qtype, rep, rrset_id, new_repp, tag, tag_datas,
+                       tag_datas_size, ipset->tagname, ipset->num_tags,
+                       &redirect_rrset, region)) < 0) {
+                       ret = 0;
+                       goto done;
+               }
+
+               /* if no action data applied, take action specific to the
+                * action without data. */
+               if(!result && !respip_nodata_answer(qinfo->qtype, action, rep,
+                       rrset_id, new_repp, region)) {
+                       ret = 0;
+                       goto done;
+               }
+       }
+  done:
+       if(view)
+               lock_rw_unlock(&view->lock);
+       if(ret) {
+               /* If we're redirecting the original answer to a
+                * CNAME, record the CNAME rrset so the caller can take
+                * the appropriate action.  Note that we don't check the
+                * action type; it should normally be 'redirect', but it
+                * can be of other type when a data-dependent tag action
+                * uses redirect response-ip data.
+                */
+               if(redirect_rrset &&
+                       redirect_rrset->rk.type == ntohs(LDNS_RR_TYPE_CNAME) &&
+                       qinfo->qtype != LDNS_RR_TYPE_ANY)
+                       *alias_rrset = redirect_rrset;
+               /* on success, populate respip result structure */
+               ret = populate_action_info(actinfo, action, raddr,
+                       redirect_rrset, tag, ipset, search_only, region);
+       }
+       return ret;
+}
+
+static int
+generate_cname_request(struct module_qstate* qstate,
+       struct ub_packed_rrset_key* alias_rrset)
+{
+       struct module_qstate* subq = NULL;
+       struct query_info subqi;
+
+       memset(&subqi, 0, sizeof(subqi));
+       get_cname_target(alias_rrset, &subqi.qname, &subqi.qname_len);
+       if(!subqi.qname)
+               return 0;    /* unexpected: not a valid CNAME RDATA */
+       subqi.qtype = qstate->qinfo.qtype;
+       subqi.qclass = qstate->qinfo.qclass;
+       fptr_ok(fptr_whitelist_modenv_attach_sub(qstate->env->attach_sub));
+       return (*qstate->env->attach_sub)(qstate, &subqi, BIT_RD, 0, 0, &subq);
+}
+
+void
+respip_operate(struct module_qstate* qstate, enum module_ev event, int id,
+       struct outbound_entry* outbound)
+{
+       struct respip_qstate* rq = (struct respip_qstate*)qstate->minfo[id];
+
+       log_query_info(VERB_QUERY, "respip operate: query", &qstate->qinfo);
+       (void)outbound;
+
+       if(event == module_event_new || event == module_event_pass) {
+               if(!rq) {
+                       rq = regional_alloc_zero(qstate->region, sizeof(*rq));
+                       if(!rq)
+                               goto servfail;
+                       rq->state = RESPIP_INIT;
+                       qstate->minfo[id] = rq;
+               }
+               if(rq->state == RESPIP_SUBQUERY_FINISHED) {
+                       qstate->ext_state[id] = module_finished;
+                       return;
+               }
+               verbose(VERB_ALGO, "respip: pass to next module");
+               qstate->ext_state[id] = module_wait_module;
+       } else if(event == module_event_moddone) {
+               /* If the reply may be subject to response-ip rewriting
+                * according to the query type, check the actions.  If a
+                * rewrite is necessary, we'll replace the reply in qstate
+                * with the new one. */
+               enum module_ext_state next_state = module_finished;
+
+               if((qstate->qinfo.qtype == LDNS_RR_TYPE_A ||
+                       qstate->qinfo.qtype == LDNS_RR_TYPE_AAAA ||
+                       qstate->qinfo.qtype == LDNS_RR_TYPE_ANY) &&
+                       qstate->return_msg && qstate->return_msg->rep) {
+                       struct respip_action_info actinfo = {respip_none, NULL};
+                       struct reply_info* new_rep = qstate->return_msg->rep;
+                       struct ub_packed_rrset_key* alias_rrset = NULL;
+
+                       if(!respip_rewrite_reply(&qstate->qinfo,
+                               qstate->client_info, qstate->return_msg->rep,
+                               &new_rep, &actinfo, &alias_rrset, 0,
+                               qstate->region)) {
+                               goto servfail;
+                       }
+                       if(actinfo.action != respip_none) {
+                               /* save action info for logging on a
+                                * per-front-end-query basis */
+                               if(!(qstate->respip_action_info =
+                                       regional_alloc_init(qstate->region,
+                                               &actinfo, sizeof(actinfo))))
+                               {
+                                       log_err("out of memory");
+                                       goto servfail;
+                               }
+                       } else {
+                               qstate->respip_action_info = NULL;
+                       }
+                       if (new_rep == qstate->return_msg->rep &&
+                               (actinfo.action == respip_deny ||
+                               actinfo.action == respip_inform_deny)) {
+                               /* for deny-variant actions (unless response-ip
+                                * data is applied), mark the query state so
+                                * the response will be dropped for all
+                                * clients. */
+                               qstate->is_drop = 1;
+                       } else if(alias_rrset) {
+                               if(!generate_cname_request(qstate, alias_rrset))
+                                       goto servfail;
+                               next_state = module_wait_subquery;
+                       }
+                       qstate->return_msg->rep = new_rep;
+               }
+               qstate->ext_state[id] = next_state;
+       } else
+               qstate->ext_state[id] = module_finished;
+
+       return;
+
+  servfail:
+       qstate->return_rcode = LDNS_RCODE_SERVFAIL;
+       qstate->return_msg = NULL;
+}
+
+int
+respip_merge_cname(struct reply_info* base_rep,
+       const struct query_info* qinfo, const struct reply_info* tgt_rep,
+       const struct respip_client_info* cinfo, int must_validate,
+       struct reply_info** new_repp, struct regional* region)
+{
+       struct reply_info* new_rep;
+       struct reply_info* tmp_rep = NULL; /* just a placeholder */
+       struct ub_packed_rrset_key* alias_rrset = NULL; /* ditto */
+       int tgt_rcode;
+       size_t i, j;
+       struct respip_action_info actinfo = {respip_none, NULL};
+
+       /* If the query for the CNAME target would result in an unusual rcode,
+        * we generally translate it as a failure for the base query
+        * (which would then be translated into SERVFAIL).  The only exception
+        * is NXDOMAIN and YXDOMAIN, which are passed to the end client(s).
+        * The YXDOMAIN case would be rare but still possible (when
+        * DNSSEC-validated DNAME has been cached but synthesizing CNAME
+        * can't be generated due to length limitation) */
+       tgt_rcode = FLAGS_GET_RCODE(tgt_rep->flags);
+       if((tgt_rcode != LDNS_RCODE_NOERROR &&
+               tgt_rcode != LDNS_RCODE_NXDOMAIN &&
+               tgt_rcode != LDNS_RCODE_YXDOMAIN) ||
+               (must_validate && tgt_rep->security <= sec_status_bogus)) {
+               return 0;
+       }
+
+       /* see if the target reply would be subject to a response-ip action. */
+       if(!respip_rewrite_reply(qinfo, cinfo, tgt_rep, &tmp_rep, &actinfo,
+               &alias_rrset, 1, region))
+               return 0;
+       if(actinfo.action != respip_none) {
+               log_info("CNAME target of redirect response-ip action would "
+                       "be subject to response-ip action, too; stripped");
+               *new_repp = base_rep;
+               return 1;
+       }
+
+       /* Append target reply to the base.  Since we cannot assume
+        * tgt_rep->rrsets is valid throughout the lifetime of new_rep
+        * or it can be safely shared by multiple threads, we need to make a
+        * deep copy. */
+       new_rep = make_new_reply_info(base_rep, region,
+               base_rep->an_numrrsets + tgt_rep->an_numrrsets,
+               base_rep->an_numrrsets);
+       if(!new_rep)
+               return 0;
+       for(i=0,j=base_rep->an_numrrsets; i<tgt_rep->an_numrrsets; i++,j++) {
+               new_rep->rrsets[j] = copy_rrset(tgt_rep->rrsets[i], region);
+               if(!new_rep->rrsets[j])
+                       return 0;
+       }
+
+       FLAGS_SET_RCODE(new_rep->flags, tgt_rcode);
+       *new_repp = new_rep;
+       return 1;
+}
+
+void
+respip_inform_super(struct module_qstate* qstate, int id,
+       struct module_qstate* super)
+{
+       struct respip_qstate* rq = (struct respip_qstate*)super->minfo[id];
+       struct reply_info* new_rep = NULL;
+
+       rq->state = RESPIP_SUBQUERY_FINISHED;
+
+       /* respip subquery should have always been created with a valid reply
+        * in super. */
+       log_assert(super->return_msg && super->return_msg->rep);
+
+       /* return_msg can be NULL when, e.g., the sub query resulted in
+        * SERVFAIL, in which case we regard it as a failure of the original
+        * query.  Other checks are probably redundant, but we check them
+        * for safety. */
+       if(!qstate->return_msg || !qstate->return_msg->rep ||
+               qstate->return_rcode != LDNS_RCODE_NOERROR)
+               goto fail;
+
+       if(!respip_merge_cname(super->return_msg->rep, &qstate->qinfo,
+               qstate->return_msg->rep, super->client_info,
+               super->env->need_to_validate, &new_rep, super->region))
+               goto fail;
+       super->return_msg->rep = new_rep;
+       return;
+
+  fail:
+       super->return_rcode = LDNS_RCODE_SERVFAIL;
+       super->return_msg = NULL;
+       return;
+}
+
+void
+respip_clear(struct module_qstate* qstate, int id)
+{
+       qstate->minfo[id] = NULL;
+}
+
+size_t
+respip_get_mem(struct module_env* env, int id)
+{
+       (void)env;
+       (void)id;
+       return 0;
+}
+
+/**
+ * The response-ip function block
+ */
+static struct module_func_block respip_block = {
+       "respip",
+       &respip_init, &respip_deinit, &respip_operate, &respip_inform_super,
+       &respip_clear, &respip_get_mem
+};
+
+struct module_func_block*
+respip_get_funcblock(void)
+{
+       return &respip_block;
+}
+
+enum respip_action
+resp_addr_get_action(const struct resp_addr* addr)
+{
+       return addr ? addr->action : respip_none;
+}
+
+struct ub_packed_rrset_key*
+resp_addr_get_rrset(struct resp_addr* addr)
+{
+       return addr ? addr->data : NULL;
+}
+
+int
+respip_set_is_empty(const struct respip_set* set)
+{
+       return set ? set->ip_tree.count == 0 : 1;
+}
+
+void
+respip_inform_print(struct respip_addr_info* respip_addr, uint8_t* qname,
+       uint16_t qtype, uint16_t qclass, struct local_rrset* local_alias,
+       struct comm_reply* repinfo)
+{
+       char srcip[128], respip[128], txt[512];
+       unsigned port;
+
+       if(local_alias)
+               qname = local_alias->rrset->rk.dname;
+       port = (repinfo->addr.ss_family == AF_INET) ?
+               ntohs(((struct sockaddr_in*)&repinfo->addr)->sin_port) :
+               ntohs(((struct sockaddr_in6*)&repinfo->addr)->sin6_port);
+       addr_to_str(&repinfo->addr, repinfo->addrlen, srcip, sizeof(srcip));
+       addr_to_str(&respip_addr->addr, respip_addr->addrlen,
+               respip, sizeof(respip));
+       snprintf(txt, sizeof(txt), "%s/%d inform %s@%u", respip,
+               respip_addr->net, srcip, port);
+       log_nametypeclass(0, txt, qname, qtype, qclass);
+}
diff --git a/respip/respip.h b/respip/respip.h
new file mode 100644 (file)
index 0000000..94e0dfa
--- /dev/null
@@ -0,0 +1,230 @@
+/*
+ * respip/respip.h - IP-based response modification module
+ */
+
+/**
+ * \file
+ *
+ * This file contains a module that selectively modifies query responses
+ * based on their AAAA/A IP addresses.
+ */
+
+#ifndef RESPIP_RESPIP_H
+#define RESPIP_RESPIP_H
+
+#include "util/module.h"
+#include "services/localzone.h"
+
+/**
+ * Set of response IP addresses with associated actions and tags. 
+ * Forward declaration only here.  Actual definition is hidden within the
+ * module.
+ */
+struct respip_set;
+
+/**
+ * Forward declaration for the structure that represents a node in the
+ * respip_set address tree
+ */
+struct resp_addr;
+
+/**
+ * Forward declaration for the structure that represents a tree of view data.
+ */
+struct views;
+
+struct respip_addr_info;
+
+/**
+ * Client-specific attributes that can affect IP-based actions.
+ * This is essentially a subset of acl_addr (except for respip_set) but
+ * defined as a separate structure to avoid dependency on the daemon-specific
+ * structure.
+ * respip_set is supposed to refer to the response-ip set for the global view.
+ */
+struct respip_client_info {
+       uint8_t* taglist;
+       size_t taglen;
+       uint8_t* tag_actions;
+       size_t tag_actions_size;
+       struct config_strlist** tag_datas;
+       size_t tag_datas_size;
+       struct view* view;
+       struct respip_set* respip_set;
+};
+
+/**
+ * Data items representing the result of response-ip processing.
+ * Note: this structure currently only define a few members, but exists
+ * as a separate struct mainly for the convenience of custom extensions.
+ */
+struct respip_action_info {
+       enum respip_action action;
+       struct respip_addr_info* addrinfo; /* set only for inform variants */
+};
+
+/**
+  * Forward declaration for the structure that represents a node in the
+  * respip_set address tree
+  */
+struct resp_addr;
+
+/**
+ * Create response IP set.
+ * @return new struct or NULL on error.
+ */
+struct respip_set* respip_set_create(void);
+
+/**
+ * Delete response IP set.
+ * @param set: to delete.
+ */
+void respip_set_delete(struct respip_set* set);
+
+/**
+ * Apply response-ip config settings to the global (default) view.
+ * It assumes exclusive access to set (no internal locks).
+ * @param set: processed global respip config data
+ * @param cfg: config data.
+ * @return 1 on success, 0 on error.
+ */
+int respip_global_apply_cfg(struct respip_set* set, struct config_file* cfg);
+
+/**
+ * Apply response-ip config settings in named views.
+ * @param vs: view structures with processed config data
+ * @param cfg: config data.
+ * @param have_view_respip_cfg: set to true if any named view has respip
+ *     configuration; otherwise set to false
+ * @return 1 on success, 0 on error.
+ */
+int respip_views_apply_cfg(struct views* vs, struct config_file* cfg,
+       int* have_view_respip_cfg);
+
+/**
+ * Merge two replies to build a complete CNAME chain.
+ * It appends the content of 'tgt_rep' to 'base_rep', assuming (but not
+ * checking) the former ends with a CNAME and the latter resolves its target.
+ * A merged new reply will be built using 'region' and *new_repp will point
+ * to the new one on success.
+ * If the target reply would also be subject to a response-ip action for
+ * 'cinfo', this function uses 'base_rep' as the merged reply, ignoring
+ * 'tgt_rep'.  This is for avoiding cases like a CNAME loop or failure of
+ * applying an action to an address.
+ * RRSIGs in 'tgt_rep' will be excluded in the merged reply, as the resulting
+ * reply is assumed to be faked due to a response-ip action and can't be
+ * considered secure in terms of DNSSEC.
+ * The caller must ensure that neither 'base_rep' nor 'tgt_rep' can be modified
+ * until this function returns. 
+ * @param base_rep: the reply info containing an incomplete CNAME.
+ * @param qinfo: query info corresponding to 'base_rep'.
+ * @param tgt_rep: the reply info that completes the CNAME chain.
+ * @param cinfo: client info corresponding to 'base_rep'.
+ * @param must_validate: whether 'tgt_rep' must be DNSSEC-validated.
+ * @param new_repp: pointer placeholder for the merged reply.  will be intact
+ *   on error.
+ * @param region: allocator to build *new_repp.
+ * @return 1 on success, 0 on error.
+ */
+int respip_merge_cname(struct reply_info* base_rep,
+       const struct query_info* qinfo, const struct reply_info* tgt_rep,
+       const struct respip_client_info* cinfo, int must_validate,
+       struct reply_info** new_repp, struct regional* region);
+
+/**
+ * See if any IP-based action should apply to any IP address of AAAA/A answer
+ * record in the reply.  If so, apply the action.  In some cases it rewrites
+ * the reply rrsets, in which case *new_repp will point to the updated reply
+ * info.  Depending on the action, some of the rrsets in 'rep' will be
+ * shallow-copied into '*new_repp'; the caller must ensure that the rrsets
+ * in 'rep' are valid throughout the lifetime of *new_repp, and it must
+ * provide appropriate mutex if the rrsets can be shared by multiple threads.
+ * @param qinfo: query info corresponding to the reply.
+ * @param cinfo: client-specific info to identify the best matching action.
+ *   can be NULL.
+ * @param rep: original reply info.  must not be NULL.
+ * @param new_repp: can be set to the rewritten reply info (intact on failure).
+ * @param actinfo: result of response-ip processing
+ * @param alias_rrset: must not be NULL.
+ * @param search_only: if true, only check if an action would apply.  actionp
+ *   will be set (or intact) accordingly but the modified reply won't be built.
+ * @param region: allocator to build *new_repp.
+ * @return 1 on success, 0 on error.
+ */
+int respip_rewrite_reply(const struct query_info* qinfo,
+       const struct respip_client_info* cinfo,
+       const struct reply_info *rep, struct reply_info** new_repp,
+       struct respip_action_info* actinfo,
+       struct ub_packed_rrset_key** alias_rrset,
+       int search_only, struct regional* region);
+
+/**
+ * Get the response-ip function block.
+ * @return: function block with function pointers to response-ip methods.
+ */
+struct module_func_block* respip_get_funcblock(void);
+
+/** response-ip init */
+int respip_init(struct module_env* env, int id);
+
+/** response-ip deinit */
+void respip_deinit(struct module_env* env, int id);
+
+/** response-ip operate on a query */
+void respip_operate(struct module_qstate* qstate, enum module_ev event, int id,
+       struct outbound_entry* outbound);
+
+/** inform response-ip super */
+void respip_inform_super(struct module_qstate* qstate, int id,
+       struct module_qstate* super);
+
+/** response-ip cleanup query state */
+void respip_clear(struct module_qstate* qstate, int id);
+
+/**
+ * returns address of the IP address tree of the specified respip set;
+ * returns NULL for NULL input; exists for test purposes only
+ */
+struct rbtree_type* respip_set_get_tree(struct respip_set* set);
+
+/**
+ * returns respip action for the specified node in the respip address
+ * returns respip_none for NULL input; exists for test purposes only
+ */
+enum respip_action resp_addr_get_action(const struct resp_addr* addr);
+
+/**
+ * returns rrset portion of the specified node in the respip address
+ * tree; returns NULL for NULL input; exists for test purposes only
+ */
+struct ub_packed_rrset_key* resp_addr_get_rrset(struct resp_addr* addr);
+
+/** response-ip alloc size routine */
+size_t respip_get_mem(struct module_env* env, int id);
+
+/**
+ * respip set emptiness test
+ * @param set respip set to test
+ * @return 0 if the specified set exists (non-NULL) and is non-empty;
+ *     otherwise returns 1
+ */
+int respip_set_is_empty(const struct respip_set* set);
+
+/**
+ * print log information for a query subject to an inform or inform-deny
+ * response-ip action.
+ * @param resp_addr response-ip information that causes the action
+ * @param qname query name in the context, will be ignored if local_alias is
+ *   non-NULL.
+ * @param qtype query type, in host byte order.
+ * @param qclass query class, in host byte order.
+ * @param local_alias set to a local alias if the query matches an alias in
+ *  a local zone.  In this case its owner name will be considered the actual
+ *  query name.
+ * @param repinfo reply info containing the client's source address and port.
+ */
+void respip_inform_print(struct respip_addr_info* respip_addr, uint8_t* qname,
+       uint16_t qtype, uint16_t qclass, struct local_rrset* local_alias,
+       struct comm_reply* repinfo);
+
+#endif /* RESPIP_RESPIP_H */
index d813ab5861723592d05cc50fefc6d12ca9bc5334..54a8660b88a5c96c9f7cdcda6dcc17c3745ec0ee 100644 (file)
@@ -229,9 +229,8 @@ lz_enter_zone(struct local_zones* zones, const char* name, const char* type,
        return z;
 }
 
-/** return name and class and rdata of rr; parses string */
-static int
-get_rr_content(const char* str, uint8_t** nm, uint16_t* type,
+int
+rrstr_get_rr_content(const char* str, uint8_t** nm, uint16_t* type,
        uint16_t* dclass, time_t* ttl, uint8_t* rr, size_t len,
        uint8_t** rdata, size_t* rdata_len)
 {
@@ -353,8 +352,8 @@ new_local_rrset(struct regional* region, struct local_data* node,
 }
 
 /** insert RR into RRset data structure; Wastes a couple of bytes */
-static int
-insert_rr(struct regional* region, struct packed_rrset_data* pd,
+int
+rrset_insert_rr(struct regional* region, struct packed_rrset_data* pd,
        uint8_t* rdata, size_t rdata_len, time_t ttl, const char* rrstr)
 {
        size_t* oldlen = pd->rr_len;
@@ -456,8 +455,8 @@ lz_enter_rr_into_zone(struct local_zone* z, const char* rrstr)
        uint8_t rr[LDNS_RR_BUF_SIZE];
        uint8_t* rdata;
        size_t rdata_len;
-       if(!get_rr_content(rrstr, &nm, &rrtype, &rrclass, &ttl, rr, sizeof(rr),
-               &rdata, &rdata_len)) {
+       if(!rrstr_get_rr_content(rrstr, &nm, &rrtype, &rrclass, &ttl, rr,
+               sizeof(rr), &rdata, &rdata_len)) {
                log_err("bad local-data: %s", rrstr);
                return 0;
        }
@@ -513,7 +512,7 @@ lz_enter_rr_into_zone(struct local_zone* z, const char* rrstr)
                verbose(VERB_ALGO, "ignoring duplicate RR: %s", rrstr);
                return 1;
        } 
-       return insert_rr(z->region, pd, rdata, rdata_len, ttl, rrstr);
+       return rrset_insert_rr(z->region, pd, rdata, rdata_len, ttl, rrstr);
 }
 
 /** enter a data RR into auth data; a zone for it must exist */
@@ -1233,9 +1232,10 @@ local_error_encode(struct query_info* qinfo, struct module_env* env,
 }
 
 /** find local data tag string match for the given type in the list */
-static int
-find_tag_datas(struct query_info* qinfo, struct config_strlist* list,
-       struct ub_packed_rrset_key* r, struct regional* temp)
+int
+local_data_find_tag_datas(const struct query_info* qinfo,
+       struct config_strlist* list, struct ub_packed_rrset_key* r,
+       struct regional* temp)
 {
        struct config_strlist* p;
        char buf[65536];
@@ -1315,10 +1315,21 @@ find_tag_datas(struct query_info* qinfo, struct config_strlist* list,
                        if(!d) return 0; /* out of memory */
                d->count++;
        }
+       if(r->rk.dname)
+               return 1;
+       return 0;
+}
+
+static int
+find_tag_datas(struct query_info* qinfo, struct config_strlist* list,
+       struct ub_packed_rrset_key* r, struct regional* temp)
+{
+       int result = local_data_find_tag_datas(qinfo, list, r, temp);
+
        /* If we've found a non-exact alias type of local data, make a shallow
         * copy of the RRset and remember it in qinfo to complete the alias
         * chain later. */
-       if(r->rk.dname && qinfo->qtype != LDNS_RR_TYPE_CNAME &&
+       if(result && qinfo->qtype != LDNS_RR_TYPE_CNAME &&
                r->rk.type == htons(LDNS_RR_TYPE_CNAME)) {
                qinfo->local_alias =
                        regional_alloc_zero(temp, sizeof(struct local_rrset));
@@ -1329,9 +1340,7 @@ find_tag_datas(struct query_info* qinfo, struct config_strlist* list,
                if(!qinfo->local_alias->rrset)
                        return 0; /* out of memory */
        }
-       if(r->rk.dname)
-               return 1;
-       return 0;
+       return result;
 }
 
 /** answer local data match */
@@ -1497,8 +1506,6 @@ lz_type(uint8_t *taglist, size_t taglen, uint8_t *taglist2, size_t taglen2,
        struct comm_reply* repinfo, struct rbtree_type* override_tree,
        int* tag, char** tagname, int num_tags)
 {
-       size_t i, j;
-       uint8_t tagmatch;
        struct local_zone_override* lzo;        
        if(repinfo && override_tree) {
                lzo = (struct local_zone_override*)addr_tree_lookup(
@@ -1511,6 +1518,19 @@ lz_type(uint8_t *taglist, size_t taglen, uint8_t *taglist2, size_t taglen2,
        }
        if(!taglist || !taglist2)
                return lzt;
+       return local_data_find_tag_action(taglist, taglen, taglist2, taglen2,
+               tagactions, tagactionssize, lzt, tag, tagname, num_tags);
+}
+
+enum localzone_type
+local_data_find_tag_action(const uint8_t* taglist, size_t taglen,
+       const uint8_t* taglist2, size_t taglen2, const uint8_t* tagactions,
+       size_t tagactionssize, enum localzone_type lzt, int* tag,
+       char* const* tagname, int num_tags)
+{
+       size_t i, j;
+       uint8_t tagmatch;
+
        for(i=0; i<taglen && i<taglen2; i++) {
                tagmatch = (taglist[i] & taglist2[i]);
                for(j=0; j<8 && tagmatch>0; j++) {
index bf9c9bf489cb04488bd011768b2929e7ea6dfb4e..658f28024ef4d16f2edd5a51b29cca5454f6f6bc 100644 (file)
@@ -46,6 +46,7 @@
 #include "util/storage/dnstree.h"
 #include "util/module.h"
 #include "services/view.h"
+struct packed_rrset_data;
 struct ub_packed_rrset_key;
 struct regional;
 struct config_file;
@@ -389,4 +390,111 @@ void local_zones_del_data(struct local_zones* zones,
  */
 int parse_dname(const char* str, uint8_t** res, size_t* len, int* labs);
 
+/**
+ * Find local data tag string match for the given type (in qinfo) in the list.
+ * If found, 'r' will be filled with corresponding rrset information.
+ * @param qinfo: contains name, type, and class for the data
+ * @param list: stores local tag data to be searched
+ * @param r: rrset key to be filled for matched data
+ * @param temp: region to allocate rrset in 'r'
+ * @return 1 if a match is found and rrset is built; otherwise 0 including
+ * errors.
+ */
+int local_data_find_tag_datas(const struct query_info* qinfo,
+       struct config_strlist* list, struct ub_packed_rrset_key* r,
+       struct regional* temp);
+
+/**
+ * See if two sets of tag lists (in the form of bitmap) have the same tag that
+ * has an action.  If so, '*tag' will be set to the found tag index, and the
+ * corresponding action will be returned in the form of local zone type.
+ * Otherwise the passed type (lzt) will be returned as the default action.
+ * Pointers except tagactions must not be NULL.
+ * @param taglist: 1st list of tags
+ * @param taglen: size of taglist in bytes
+ * @param taglist2: 2nd list of tags
+ * @param taglen2: size of taglist2 in bytes
+ * @param tagactions: local data actions for tags. May be NULL.
+ * @param tagactionssize: length of the tagactions.
+ * @param lzt: default action (local zone type) if no tag action is found.
+ * @param tag: see above.
+ * @param tagname: array of tag name strings (for debug output).
+ * @param num_tags: number of items in tagname array.
+ * @return found tag action or the default action.
+ */
+enum localzone_type local_data_find_tag_action(const uint8_t* taglist,
+       size_t taglen, const uint8_t* taglist2, size_t taglen2,
+       const uint8_t* tagactions, size_t tagactionssize,
+       enum localzone_type lzt, int* tag, char* const* tagname, int num_tags);
+
+/**
+  * Parses resource record string into wire format, also returning its field values.
+  * @param str: input resource record
+  * @param nm: domain name field
+  * @param type: record type field
+  * @param dclass: record class field
+  * @param ttl: ttl field
+  * @param rr: buffer for the parsed rr in wire format
+  * @param len: buffer length
+  * @param rdata: rdata field
+  * @param rdata_len: rdata field length
+  * @return 1 on success; 0 otherwise.
+  */
+int rrstr_get_rr_content(const char* str, uint8_t** nm, uint16_t* type,
+       uint16_t* dclass, time_t* ttl, uint8_t* rr, size_t len,
+       uint8_t** rdata, size_t* rdata_len);
+
+/**
+  * Insert specified rdata into the specified resource record.
+  * @param region: allocator
+  * @param pd: data portion of the destination resource record
+  * @param rdata: source rdata
+  * @param rdata_len: source rdata length
+  * @param ttl: time to live
+  * @param rrstr: resource record in text form (for logging)
+  * @return 1 on success; 0 otherwise.
+  */
+int rrset_insert_rr(struct regional* region, struct packed_rrset_data* pd,
+       uint8_t* rdata, size_t rdata_len, time_t ttl, const char* rrstr);
+
+/**
+  * Valid response ip actions for the IP-response-driven-action feature;
+  * defined here instead of in the respip module to enable sharing of enum
+  * values with the localzone_type enum.
+  * Note that these values except 'none' are the same as localzone types of
+  * the 'same semantics'.  It's intentional as we use these values via
+  * access-control-tags, which can be shared for both response ip actions and
+  * local zones.
+  */
+enum respip_action {
+       /** no respip action */
+       respip_none = local_zone_unset,
+       /** don't answer */
+       respip_deny = local_zone_deny,
+       /** redirect as per provided data */
+       respip_redirect = local_zone_redirect,
+        /** log query source and answer query */
+       respip_inform = local_zone_inform,
+        /** log query source and don't answer query */
+       respip_inform_deny = local_zone_inform_deny,
+        /** resolve normally, even when there is response-ip data */
+       respip_always_transparent = local_zone_always_transparent,
+        /** answer with 'refused' response */
+       respip_always_refuse = local_zone_always_refuse,
+        /** answer with 'no such domain' response */
+       respip_always_nxdomain = local_zone_always_nxdomain,
+
+       /* The rest of the values are only possible as
+        * access-control-tag-action */
+
+       /** serves response data (if any), else, drops queries. */
+       respip_refuse = local_zone_refuse,
+       /** serves response data, else, nodata answer. */
+       respip_static = local_zone_static,
+       /** gives response data (if any), else nodata answer. */
+       respip_transparent = local_zone_transparent,
+       /** gives response data (if any), else nodata answer. */
+       respip_typetransparent = local_zone_typetransparent,
+};
+
 #endif /* SERVICES_LOCALZONE_H */
index f5a193ac2d489199cb6c669b5f25cc6258535f76..540f44f35c00e804d853d70055d5f91f07ea90f9 100644 (file)
@@ -59,6 +59,7 @@
 #include "sldns/wire2str.h"
 #include "services/localzone.h"
 #include "util/data/dname.h"
+#include "respip/respip.h"
 
 /** subtract timers and the values do not overflow or become negative */
 static void
@@ -124,11 +125,64 @@ timeval_smaller(const struct timeval* x, const struct timeval* y)
 #endif
 }
 
+/*
+ * Compare two response-ip client info entries for the purpose of mesh state
+ * compare.  It returns 0 if ci_a and ci_b are considered equal; otherwise
+ * 1 or -1 (they mean 'ci_a is larger/smaller than ci_b', respectively, but
+ * in practice it should be only used to mean they are different).
+ * We cannot share the mesh state for two queries if different response-ip
+ * actions can apply in the end, even if those queries are otherwise identical.
+ * For this purpose we compare tag lists and tag action lists; they should be
+ * identical to share the same state.
+ * For tag data, we don't look into the data content, as it can be
+ * expensive; unless tag data are not defined for both or they point to the
+ * exact same data in memory (i.e., they come from the same ACL entry), we
+ * consider these data different.
+ * Likewise, if the client info is associated with views, we don't look into
+ * the views.  They are considered different unless they are exactly the same
+ * even if the views only differ in the names.
+ */
+static int
+client_info_compare(const struct respip_client_info* ci_a,
+       const struct respip_client_info* ci_b)
+{
+       int cmp;
+
+       if(!ci_a && !ci_b)
+               return 0;
+       if(ci_a && !ci_b)
+               return -1;
+       if(!ci_a && ci_b)
+               return 1;
+       if(ci_a->taglen != ci_b->taglen)
+               return (ci_a->taglen < ci_b->taglen) ? -1 : 1;
+       cmp = memcmp(ci_a->taglist, ci_b->taglist, ci_a->taglen);
+       if(cmp != 0)
+               return cmp;
+       if(ci_a->tag_actions_size != ci_b->tag_actions_size)
+               return (ci_a->tag_actions_size < ci_b->tag_actions_size) ?
+                       -1 : 1;
+       cmp = memcmp(ci_a->tag_actions, ci_b->tag_actions,
+               ci_a->tag_actions_size);
+       if(cmp != 0)
+               return cmp;
+       if(ci_a->tag_datas != ci_b->tag_datas)
+               return ci_a->tag_datas < ci_b->tag_datas ? -1 : 1;
+       if(ci_a->view != ci_b->view)
+               return ci_a->view < ci_b->view ? -1 : 1;
+       /* For the unbound daemon these should be non-NULL and identical,
+        * but we check that just in case. */
+       if(ci_a->respip_set != ci_b->respip_set)
+               return ci_a->respip_set < ci_b->respip_set ? -1 : 1;
+        return 0;
+}
+
 int
 mesh_state_compare(const void* ap, const void* bp)
 {
        struct mesh_state* a = (struct mesh_state*)ap;
        struct mesh_state* b = (struct mesh_state*)bp;
+       int cmp;
 
        if(a->unique < b->unique)
                return -1;
@@ -155,7 +209,10 @@ mesh_state_compare(const void* ap, const void* bp)
        if(!(a->s.query_flags&BIT_CD) && (b->s.query_flags&BIT_CD))
                return 1;
 
-       return query_info_compare(&a->s.qinfo, &b->s.qinfo);
+       cmp = query_info_compare(&a->s.qinfo, &b->s.qinfo);
+       if(cmp != 0)
+               return cmp;
+       return client_info_compare(a->s.client_info, b->s.client_info);
 }
 
 int
@@ -287,8 +344,8 @@ int mesh_make_new_space(struct mesh_area* mesh, sldns_buffer* qbuf)
 }
 
 void mesh_new_client(struct mesh_area* mesh, struct query_info* qinfo,
-        uint16_t qflags, struct edns_data* edns, struct comm_reply* rep,
-        uint16_t qid)
+       struct respip_client_info* cinfo, uint16_t qflags,
+       struct edns_data* edns, struct comm_reply* rep, uint16_t qid)
 {
        struct mesh_state* s = NULL;
        int unique = edns_unique_mesh_state(edns->opt_list, mesh->env);
@@ -296,7 +353,7 @@ void mesh_new_client(struct mesh_area* mesh, struct query_info* qinfo,
        int was_noreply = 0;
        int added = 0;
        if(!unique)
-               s = mesh_area_find(mesh, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+               s = mesh_area_find(mesh, cinfo, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
        /* does this create a new reply state? */
        if(!s || s->list_select == mesh_no_list) {
                if(!mesh_make_new_space(mesh, rep->c->buffer)) {
@@ -323,7 +380,8 @@ void mesh_new_client(struct mesh_area* mesh, struct query_info* qinfo,
 #ifdef UNBOUND_DEBUG
                struct rbnode_type* n;
 #endif
-               s = mesh_state_create(mesh->env, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+               s = mesh_state_create(mesh->env, qinfo, cinfo,
+                       qflags&(BIT_RD|BIT_CD), 0, 0);
                if(!s) {
                        log_err("mesh_state_create: out of memory; SERVFAIL");
                        if(!inplace_cb_reply_servfail_call(mesh->env, qinfo, NULL, NULL,
@@ -417,7 +475,8 @@ mesh_new_callback(struct mesh_area* mesh, struct query_info* qinfo,
        int was_noreply = 0;
        int added = 0;
        if(!unique)
-               s = mesh_area_find(mesh, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+               s = mesh_area_find(mesh, NULL, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+
        /* there are no limits on the number of callbacks */
 
        /* see if it already exists, if not, create one */
@@ -425,7 +484,8 @@ mesh_new_callback(struct mesh_area* mesh, struct query_info* qinfo,
 #ifdef UNBOUND_DEBUG
                struct rbnode_type* n;
 #endif
-               s = mesh_state_create(mesh->env, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+               s = mesh_state_create(mesh->env, qinfo, NULL,
+                       qflags&(BIT_RD|BIT_CD), 0, 0);
                if(!s) {
                        return 0;
                }
@@ -476,8 +536,8 @@ mesh_new_callback(struct mesh_area* mesh, struct query_info* qinfo,
 void mesh_new_prefetch(struct mesh_area* mesh, struct query_info* qinfo,
         uint16_t qflags, time_t leeway)
 {
-       struct mesh_state* s = mesh_area_find(mesh, qinfo, qflags&(BIT_RD|BIT_CD),
-               0, 0);
+       struct mesh_state* s = mesh_area_find(mesh, NULL, qinfo,
+               qflags&(BIT_RD|BIT_CD), 0, 0);
 #ifdef UNBOUND_DEBUG
        struct rbnode_type* n;
 #endif
@@ -497,7 +557,8 @@ void mesh_new_prefetch(struct mesh_area* mesh, struct query_info* qinfo,
                return;
        }
 
-       s = mesh_state_create(mesh->env, qinfo, qflags&(BIT_RD|BIT_CD), 0, 0);
+       s = mesh_state_create(mesh->env, qinfo, NULL,
+               qflags&(BIT_RD|BIT_CD), 0, 0);
        if(!s) {
                log_err("prefetch mesh_state_create: out of memory");
                return;
@@ -546,7 +607,8 @@ void mesh_report_reply(struct mesh_area* mesh, struct outbound_entry* e,
 
 struct mesh_state* 
 mesh_state_create(struct module_env* env, struct query_info* qinfo, 
-       uint16_t qflags, int prime, int valrec)
+       struct respip_client_info* cinfo, uint16_t qflags, int prime,
+       int valrec)
 {
        struct regional* region = alloc_reg_obtain(env->alloc);
        struct mesh_state* mstate;
@@ -582,6 +644,14 @@ mesh_state_create(struct module_env* env, struct query_info* qinfo,
                alloc_reg_release(env->alloc, region);
                return NULL;
        }
+       if(cinfo) {
+               mstate->s.client_info = regional_alloc_init(region, cinfo,
+                       sizeof(*cinfo));
+               if(!mstate->s.client_info) {
+                       alloc_reg_release(env->alloc, region);
+                       return NULL;
+               }
+       }
        /* remove all weird bits from qflags */
        mstate->s.query_flags = (qflags & (BIT_RD|BIT_CD));
        mstate->s.is_priming = prime;
@@ -756,7 +826,8 @@ int mesh_attach_sub(struct module_qstate* qstate, struct query_info* qinfo,
 {
        /* find it, if not, create it */
        struct mesh_area* mesh = qstate->env->mesh;
-       struct mesh_state* sub = mesh_area_find(mesh, qinfo, qflags, prime, valrec);
+       struct mesh_state* sub = mesh_area_find(mesh, NULL, qinfo, qflags,
+               prime, valrec);
        int was_detached;
        if(mesh_detect_cycle_found(qstate, sub)) {
                verbose(VERB_ALGO, "attach failed, cycle detected");
@@ -767,7 +838,8 @@ int mesh_attach_sub(struct module_qstate* qstate, struct query_info* qinfo,
                struct rbnode_type* n;
 #endif
                /* create a new one */
-               sub = mesh_state_create(qstate->env, qinfo, qflags, prime, valrec);
+               sub = mesh_state_create(qstate->env, qinfo, NULL, qflags, prime,
+                       valrec);
                if(!sub) {
                        log_err("mesh_attach_sub: out of memory");
                        return 0;
@@ -1035,8 +1107,25 @@ void mesh_query_done(struct mesh_state* mstate)
        struct reply_info* rep = (mstate->s.return_msg?
                mstate->s.return_msg->rep:NULL);
        for(r = mstate->reply_list; r; r = r->next) {
-               mesh_send_reply(mstate, mstate->s.return_rcode, rep, r, prev);
-               prev = r;
+               /* if a response-ip address block has been stored the
+                *  information should be logged for each client. */
+               if(mstate->s.respip_action_info &&
+                       mstate->s.respip_action_info->addrinfo) {
+                       respip_inform_print(mstate->s.respip_action_info->addrinfo,
+                               r->qname, mstate->s.qinfo.qtype,
+                               mstate->s.qinfo.qclass, r->local_alias,
+                               &r->query_reply);
+               }
+
+               /* if this query is determined to be dropped during the
+                * mesh processing, this is the point to take that action. */
+               if(mstate->s.is_drop)
+                       comm_point_drop_reply(&r->query_reply);
+               else {
+                       mesh_send_reply(mstate, mstate->s.return_rcode, rep,
+                               r, prev);
+                       prev = r;
+               }
        }
        mstate->replies_sent = 1;
        for(c = mstate->cb_list; c; c = c->next) {
@@ -1060,7 +1149,8 @@ void mesh_walk_supers(struct mesh_area* mesh, struct mesh_state* mstate)
 }
 
 struct mesh_state* mesh_area_find(struct mesh_area* mesh,
-       struct query_info* qinfo, uint16_t qflags, int prime, int valrec)
+       struct respip_client_info* cinfo, struct query_info* qinfo,
+       uint16_t qflags, int prime, int valrec)
 {
        struct mesh_state key;
        struct mesh_state* result;
@@ -1074,6 +1164,7 @@ struct mesh_state* mesh_area_find(struct mesh_area* mesh,
         * aggregate the state. Thus unique is set to NULL. (default when we
         * desire aggregation).*/
        key.unique = NULL;
+       key.s.client_info = cinfo;
        
        result = (struct mesh_state*)rbtree_search(&mesh->all, &key);
        return result;
@@ -1378,7 +1469,7 @@ mesh_detect_cycle(struct module_qstate* qstate, struct query_info* qinfo,
        struct mesh_area* mesh = qstate->env->mesh;
        struct mesh_state* dep_m = NULL;
        if(!mesh_state_is_unique(qstate->mesh_info))
-               dep_m = mesh_area_find(mesh, qinfo, flags, prime, valrec);
+               dep_m = mesh_area_find(mesh, NULL, qinfo, flags, prime, valrec);
        return mesh_detect_cycle_found(qstate, dep_m);
 }
 
index 435f89c689d5f311b8861c962ec9a072d96d1546..1c77945320e31f97e59aaef6190c459c314e4219 100644 (file)
@@ -59,6 +59,7 @@ struct query_info;
 struct reply_info;
 struct outbound_entry;
 struct timehist;
+struct respip_client_info;
 
 /**
  * Maximum number of mesh state activations. Any more is likely an
@@ -274,14 +275,18 @@ void mesh_delete(struct mesh_area* mesh);
  *
  * @param mesh: the mesh.
  * @param qinfo: query from client.
+ * @param cinfo: additional information associated with the query client.
+ *     'cinfo' itself is ephemeral but data pointed to by its members
+ *      can be assumed to be valid and unchanged until the query processing is
+ *      completed.
  * @param qflags: flags from client query.
  * @param edns: edns data from client query.
  * @param rep: where to reply to.
  * @param qid: query id to reply with.
  */
 void mesh_new_client(struct mesh_area* mesh, struct query_info* qinfo,
-       uint16_t qflags, struct edns_data* edns, struct comm_reply* rep, 
-       uint16_t qid);
+       struct respip_client_info* cinfo, uint16_t qflags,
+       struct edns_data* edns, struct comm_reply* rep, uint16_t qid);
 
 /**
  * New query with callback. Create new query state if needed, and
@@ -409,14 +414,16 @@ void mesh_state_delete(struct module_qstate* qstate);
  * Does not put the mesh state into rbtrees and so on.
  * @param env: module environment to set.
  * @param qinfo: query info that the mesh is for.
+ * @param cinfo: control info for the query client (can be NULL).
  * @param qflags: flags for query (RD / CD flag).
  * @param prime: if true, it is a priming query, set is_priming on mesh state.
  * @param valrec: if true, it is a validation recursion query, and sets
  *     is_valrec on the mesh state.
  * @return: new mesh state or NULL on allocation error.
  */
-struct mesh_state* mesh_state_create(struct module_env* env, 
-       struct query_info* qinfo, uint16_t qflags, int prime, int valrec);
+struct mesh_state* mesh_state_create(struct module_env* env,
+       struct query_info* qinfo, struct respip_client_info* cinfo,
+       uint16_t qflags, int prime, int valrec);
 
 /**
  * Check if the mesh state is unique.
@@ -451,14 +458,17 @@ void mesh_delete_all(struct mesh_area* mesh);
  * Find a mesh state in the mesh area. Pass relevant flags.
  *
  * @param mesh: the mesh area to look in.
+ * @param cinfo: if non-NULL client specific info that may affect IP-based
+ *     actions that apply to the query result.
  * @param qinfo: what query
  * @param qflags: if RD / CD bit is set or not.
  * @param prime: if it is a priming query.
  * @param valrec: if it is a validation-recursion query.
  * @return: mesh state or NULL if not found.
  */
-struct mesh_state* mesh_area_find(struct mesh_area* mesh, 
-       struct query_info* qinfo, uint16_t qflags, int prime, int valrec);
+struct mesh_state* mesh_area_find(struct mesh_area* mesh,
+       struct respip_client_info* cinfo, struct query_info* qinfo,
+       uint16_t qflags, int prime, int valrec);
 
 /**
  * Setup attachment super/sub relation between super and sub mesh state.
index 70e066670d5df63b4335bb3d6bfe135ed2785f52..97d67a1e18b7db9bf37582626cadf794d96ef764 100644 (file)
@@ -46,6 +46,7 @@
 #include "dns64/dns64.h"
 #include "iterator/iterator.h"
 #include "validator/validator.h"
+#include "respip/respip.h"
 
 #ifdef WITH_PYTHONMODULE
 #include "pythonmod/pythonmod.h"
@@ -127,6 +128,7 @@ module_list_avail(void)
 #ifdef USE_CACHEDB
                "cachedb",
 #endif
+               "respip",
                "validator", 
                "iterator", 
                NULL};
@@ -148,6 +150,7 @@ module_funcs_avail(void)
 #ifdef USE_CACHEDB
                &cachedb_get_funcblock,
 #endif
+               &respip_get_funcblock,
                &val_get_funcblock, 
                &iter_get_funcblock, 
                NULL};
index c9dfc3c87383ef6482a82fe3e90c25469d620ad3..5ea5ef02e583820a19095fb53dac26bac4ebb118 100644 (file)
@@ -66,6 +66,10 @@ views_create(void)
        return v;
 }
 
+/** This prototype is defined in in respip.h, but we want to avoid
+  * unnecessary dependencies */
+void respip_set_delete(struct respip_set *);
+
 void 
 view_delete(struct view* v)
 {
@@ -73,6 +77,7 @@ view_delete(struct view* v)
                return;
        lock_rw_destroy(&v->lock);
        local_zones_delete(v->local_zones);
+       respip_set_delete(v->respip_set);
        free(v->name);
        free(v);
 }
index ce4b69d6c5108a5ef0a91daebd202bd7d424d169..e0b346419e9bd691aaf2a277749ccbe88bf85614 100644 (file)
@@ -47,6 +47,7 @@
 struct regional;
 struct config_file;
 struct config_view;
+struct respip_set;
 
 
 /**
@@ -71,6 +72,8 @@ struct view {
        char* name;
        /** view specific local authority zones */
        struct local_zones* local_zones;
+       /** response-ip configuration data for this view */
+       struct respip_set* respip_set;
        /** Fallback to global local_zones when there is no match in the view
         * specific tree. 1 for yes, 0 for no */        
        int isfirst;
index eebc0e76ee8ac843eab6ed93127bf275644730ba..b112a79fa9b9070185308e0f79d523869104a895 100644 (file)
@@ -53,6 +53,8 @@
 #include "iterator/iter_hints.h"
 #include "validator/validator.h"
 #include "services/localzone.h"
+#include "services/view.h"
+#include "respip/respip.h"
 #include "sldns/sbuffer.h"
 #ifdef HAVE_GETOPT_H
 #include <getopt.h>
@@ -141,6 +143,27 @@ localzonechecks(struct config_file* cfg)
        local_zones_delete(zs);
 }
 
+/** check view and response-ip configuration */
+static void
+view_and_respipchecks(struct config_file* cfg)
+{
+       struct views* views = NULL;
+       struct respip_set* respip = NULL;
+       int ignored = 0;
+       if(!(views = views_create()))
+               fatal_exit("Could not create views: out of memory");
+       if(!(respip = respip_set_create()))
+               fatal_exit("Could not create respip set: out of memory");
+       if(!views_apply_cfg(views, cfg))
+               fatal_exit("Could not set up views");
+        if(!respip_global_apply_cfg(respip, cfg))
+               fatal_exit("Could not setup respip set");
+        if(!respip_views_apply_cfg(views, cfg, &ignored))
+               fatal_exit("Could not setup per-view respip sets");
+       views_delete(views);
+       respip_set_delete(respip);
+}
+
 /** emit warnings for IP in hosts */
 static void
 warn_hosts(const char* typ, struct config_stub* list)
@@ -406,11 +429,17 @@ morechecks(struct config_file* cfg, const char* fname)
        /* remove chroot setting so that modules are not stripping pathnames*/
        free(cfg->chrootdir);
        cfg->chrootdir = NULL;
-       
+
+       /* There should be no reason for 'respip' module not to work with
+        * dns64, but it's not explicitly confirmed,  so the combination is
+        * excluded below.   It's simply unknown yet for the combination of
+        * respip and other modules. */
        if(strcmp(cfg->module_conf, "iterator") != 0 
                && strcmp(cfg->module_conf, "validator iterator") != 0
                && strcmp(cfg->module_conf, "dns64 validator iterator") != 0
                && strcmp(cfg->module_conf, "dns64 iterator") != 0
+               && strcmp(cfg->module_conf, "respip iterator") != 0
+               && strcmp(cfg->module_conf, "respip validator iterator") != 0
 #ifdef WITH_PYTHONMODULE
                && strcmp(cfg->module_conf, "python iterator") != 0 
                && strcmp(cfg->module_conf, "python validator iterator") != 0 
@@ -464,6 +493,7 @@ morechecks(struct config_file* cfg, const char* fname)
        }
 
        localzonechecks(cfg);
+       view_and_respipchecks(cfg);
 }
 
 /** check forwards */
index e3d7a59b4c4ca81798d1481b9530748224145eab..89dbeb1d3ecc5f19b6d5dd2cdad7180fea34da65 100644 (file)
@@ -558,6 +558,267 @@ rnd_test(void)
        ub_randfree(r);
 }
 
+#include "respip/respip.h"
+#include "services/localzone.h"
+#include "util/data/packed_rrset.h"
+typedef struct addr_action {char* ip; char* sact; enum respip_action act;}
+       addr_action_t;
+
+/** Utility function that verifies that the respip set has actions as expected */
+static void
+verify_respip_set_actions(struct respip_set* set, addr_action_t actions[],
+       int actions_len)
+{
+       int i = 0;
+       struct rbtree_type* tree = respip_set_get_tree(set);
+       for (i=0; i<actions_len; i++) {
+               struct sockaddr_storage addr;
+               int net;
+               socklen_t addrlen;
+               struct resp_addr* node;
+               netblockstrtoaddr(actions[i].ip, UNBOUND_DNS_PORT, &addr,
+                       &addrlen, &net);
+               node = (struct resp_addr*)addr_tree_find(tree, &addr, addrlen, net);
+
+               /** we have the node and the node has the correct action
+                 * and has no data */
+               unit_assert(node);
+               unit_assert(actions[i].act ==
+                       resp_addr_get_action(node));
+               unit_assert(resp_addr_get_rrset(node) == NULL);
+       }
+       unit_assert(actions_len && i == actions_len);
+       unit_assert(actions_len == (int)tree->count);
+}
+
+/** Global respip actions test; apply raw config data and verify that
+  * all the nodes in the respip set, looked up by address, have expected
+  * actions */
+static void
+respip_conf_actions_test(void)
+{
+       addr_action_t config_response_ip[] = {
+               {"192.0.1.0/24", "deny", respip_deny},
+               {"192.0.2.0/24", "redirect", respip_redirect},
+               {"192.0.3.0/26", "inform", respip_inform},
+               {"192.0.4.0/27", "inform_deny", respip_inform_deny},
+               {"2001:db8:1::/48", "always_transparent", respip_always_transparent},
+               {"2001:db8:2::/49", "always_refuse", respip_always_refuse},
+               {"2001:db8:3::/50", "always_nxdomain", respip_always_nxdomain},
+       };
+       int i;
+       struct respip_set* set = respip_set_create();
+       struct config_file cfg;
+       int clen = sizeof(config_response_ip) / sizeof(addr_action_t);
+
+       unit_assert(set);
+       unit_show_feature("global respip config actions apply");
+       memset(&cfg, 0, sizeof(cfg));
+       for(i=0; i<clen; i++) {
+               char* ip = strdup(config_response_ip[i].ip);
+               char* sact = strdup(config_response_ip[i].sact);
+               unit_assert(ip && sact);
+               if(!cfg_str2list_insert(&cfg.respip_actions, ip, sact))
+                       unit_assert(0);
+       }
+       unit_assert(respip_global_apply_cfg(set, &cfg));
+       verify_respip_set_actions(set, config_response_ip, clen);
+}
+
+/** Per-view respip actions test; apply raw configuration with two views
+  * and verify that actions are as expected in respip sets of both views */
+static void
+respip_view_conf_actions_test(void)
+{
+       addr_action_t config_response_ip_view1[] = {
+               {"192.0.1.0/24", "deny", respip_deny},
+               {"192.0.2.0/24", "redirect", respip_redirect},
+               {"192.0.3.0/26", "inform", respip_inform},
+               {"192.0.4.0/27", "inform_deny", respip_inform_deny},
+       };
+       addr_action_t config_response_ip_view2[] = {
+               {"2001:db8:1::/48", "always_transparent", respip_always_transparent},
+               {"2001:db8:2::/49", "always_refuse", respip_always_refuse},
+               {"2001:db8:3::/50", "always_nxdomain", respip_always_nxdomain},
+       };
+       int i;
+       struct config_file cfg;
+       int clen1 = sizeof(config_response_ip_view1) / sizeof(addr_action_t);
+       int clen2 = sizeof(config_response_ip_view2) / sizeof(addr_action_t);
+       struct config_view* cv1;
+       struct config_view* cv2;
+       int have_respip_cfg = 0;
+       struct views* views = NULL;
+       struct view* v = NULL;
+
+       unit_show_feature("per-view respip config actions apply");
+       memset(&cfg, 0, sizeof(cfg));
+       cv1 = (struct config_view*)calloc(1, sizeof(struct config_view));
+       cv2 = (struct config_view*)calloc(1, sizeof(struct config_view));
+       unit_assert(cv1 && cv2);
+       cv1->name = strdup("view1");
+       cv2->name = strdup("view2");
+       unit_assert(cv1->name && cv2->name);
+       cv1->next = cv2;
+       cfg.views = cv1;
+
+       for(i=0; i<clen1; i++) {
+               char* ip = strdup(config_response_ip_view1[i].ip);
+               char* sact = strdup(config_response_ip_view1[i].sact);
+               unit_assert(ip && sact);
+               if(!cfg_str2list_insert(&cv1->respip_actions, ip, sact))
+                       unit_assert(0);
+       }
+       for(i=0; i<clen2; i++) {
+               char* ip = strdup(config_response_ip_view2[i].ip);
+               char* sact = strdup(config_response_ip_view2[i].sact);
+               unit_assert(ip && sact);
+               if(!cfg_str2list_insert(&cv2->respip_actions, ip, sact))
+                       unit_assert(0);
+       }
+       views = views_create();
+       unit_assert(views);
+       unit_assert(views_apply_cfg(views, &cfg));
+       unit_assert(respip_views_apply_cfg(views, &cfg, &have_respip_cfg));
+
+       /* now verify the respip sets in each view */
+       v = views_find_view(views, "view1", 0);
+       unit_assert(v);
+       verify_respip_set_actions(v->respip_set, config_response_ip_view1, clen1);
+       v = views_find_view(views, "view2", 0);
+       unit_assert(v);
+       verify_respip_set_actions(v->respip_set, config_response_ip_view2, clen2);
+}
+
+typedef struct addr_data {char* ip; char* data;} addr_data_t;
+
+/** find the respip address node in the specified tree (by address lookup)
+  * and verify type and address of the specified rdata (by index) in this
+  * node's rrset */
+static void
+verify_rrset(struct respip_set* set, const char* ipstr,
+       const char* rdatastr, size_t rdi, uint16_t type)
+{
+       struct sockaddr_storage addr;
+       int net;
+       char buf[65536];
+       socklen_t addrlen;
+       struct rbtree_type* tree;
+       struct resp_addr* node;
+       const struct ub_packed_rrset_key* rrs;
+
+       netblockstrtoaddr(ipstr, UNBOUND_DNS_PORT, &addr, &addrlen, &net);
+       tree = respip_set_get_tree(set);
+       node = (struct resp_addr*)addr_tree_find(tree, &addr, addrlen, net);
+       unit_assert(node);
+       unit_assert((rrs = resp_addr_get_rrset(node)));
+       unit_assert(ntohs(rrs->rk.type) == type);
+       packed_rr_to_string((struct ub_packed_rrset_key*)rrs,
+               rdi, 0, buf, sizeof(buf));
+       unit_assert(strstr(buf, rdatastr));
+}
+
+/** Dataset used to test redirect rrset initialization for both
+  * global and per-view respip redirect configuration */
+static addr_data_t config_response_ip_data[] = {
+       {"192.0.1.0/24", "A 1.2.3.4"},
+       {"192.0.1.0/24", "A 11.12.13.14"},
+       {"192.0.2.0/24", "CNAME www.example.com."},
+       {"2001:db8:1::/48", "AAAA 2001:db8:1::2:1"},
+};
+
+/** Populate raw respip redirect config data, used for both global and
+  * view-based respip redirect test case */
+static void
+cfg_insert_respip_data(struct config_str2list** respip_actions,
+       struct config_str2list** respip_data)
+{
+       int clen = sizeof(config_response_ip_data) / sizeof(addr_data_t);
+       int i = 0;
+
+       /* insert actions (duplicate netblocks don't matter) */
+       for(i=0; i<clen; i++) {
+               char* ip = strdup(config_response_ip_data[i].ip);
+               char* sact = strdup("redirect");
+               unit_assert(ip && sact);
+               if(!cfg_str2list_insert(respip_actions, ip, sact))
+                       unit_assert(0);
+       }
+       /* insert data */
+       for(i=0; i<clen; i++) {
+               char* ip = strdup(config_response_ip_data[i].ip);
+               char* data = strdup(config_response_ip_data[i].data);
+               unit_assert(ip && data);
+               if(!cfg_str2list_insert(respip_data, ip, data))
+                       unit_assert(0);
+       }
+}
+
+/** Test global respip redirect w/ data directives */
+static void
+respip_conf_data_test(void)
+{
+       struct respip_set* set = respip_set_create();
+       struct config_file cfg;
+
+       unit_show_feature("global respip config data apply");
+       memset(&cfg, 0, sizeof(cfg));
+
+       cfg_insert_respip_data(&cfg.respip_actions, &cfg.respip_data);
+
+       /* apply configuration and verify rrsets */
+       unit_assert(respip_global_apply_cfg(set, &cfg));
+       verify_rrset(set, "192.0.1.0/24", "1.2.3.4", 0, LDNS_RR_TYPE_A);
+       verify_rrset(set, "192.0.1.0/24", "11.12.13.14", 1, LDNS_RR_TYPE_A);
+       verify_rrset(set, "192.0.2.0/24", "www.example.com", 0, LDNS_RR_TYPE_CNAME);
+       verify_rrset(set, "2001:db8:1::/48", "2001:db8:1::2:1", 0, LDNS_RR_TYPE_AAAA);
+}
+
+/** Test per-view respip redirect w/ data directives */
+static void
+respip_view_conf_data_test(void)
+{
+       struct config_file cfg;
+       struct config_view* cv;
+       int have_respip_cfg = 0;
+       struct views* views = NULL;
+       struct view* v = NULL;
+
+       unit_show_feature("per-view respip config data apply");
+       memset(&cfg, 0, sizeof(cfg));
+       cv = (struct config_view*)calloc(1, sizeof(struct config_view));
+       unit_assert(cv);
+       cv->name = strdup("view1");
+       unit_assert(cv->name);
+       cfg.views = cv;
+       cfg_insert_respip_data(&cv->respip_actions, &cv->respip_data);
+       views = views_create();
+       unit_assert(views);
+       unit_assert(views_apply_cfg(views, &cfg));
+
+       /* apply configuration and verify rrsets */
+       unit_assert(respip_views_apply_cfg(views, &cfg, &have_respip_cfg));
+       v = views_find_view(views, "view1", 0);
+       unit_assert(v);
+       verify_rrset(v->respip_set, "192.0.1.0/24", "1.2.3.4",
+               0, LDNS_RR_TYPE_A);
+       verify_rrset(v->respip_set, "192.0.1.0/24", "11.12.13.14",
+               1, LDNS_RR_TYPE_A);
+       verify_rrset(v->respip_set, "192.0.2.0/24", "www.example.com",
+               0, LDNS_RR_TYPE_CNAME);
+       verify_rrset(v->respip_set, "2001:db8:1::/48", "2001:db8:1::2:1",
+               0, LDNS_RR_TYPE_AAAA);
+}
+
+/** respip unit tests */
+static void respip_test(void)
+{
+       respip_view_conf_data_test();
+       respip_conf_data_test();
+       respip_view_conf_actions_test();
+       respip_conf_actions_test();
+}
+
 void unit_show_func(const char* file, const char* func)
 {
        printf("test %s:%s\n", file, func);
@@ -604,6 +865,7 @@ main(int argc, char* argv[])
        checklock_start();
        neg_test();
        rnd_test();
+       respip_test();
        verify_test();
        net_test();
        config_memsize_test();
index e126668c072afc4d764ba7e6820a0fa8c2fdaadd..e51651c1b912fb4c5a62c2720ab5834c65737bc8 100644 (file)
@@ -832,6 +832,7 @@ config_get_option(struct config_file* cfg, const char* opt,
        else O_IFC(opt, "define-tag", num_tags, tagname)
        else O_LTG(opt, "local-zone-tag", local_zone_tags)
        else O_LTG(opt, "access-control-tag", acl_tags)
+       else O_LTG(opt, "response-ip-tag", respip_tags)
        else O_LS3(opt, "local-zone-override", local_zone_overrides)
        else O_LS3(opt, "access-control-tag-action", acl_tag_actions)
        else O_LS3(opt, "access-control-tag-data", acl_tag_datas)
@@ -1112,6 +1113,7 @@ config_delete(struct config_file* cfg)
        config_del_strarray(cfg->tagname, cfg->num_tags);
        config_del_strbytelist(cfg->local_zone_tags);
        config_del_strbytelist(cfg->acl_tags);
+       config_del_strbytelist(cfg->respip_tags);
        config_deltrplstrlist(cfg->acl_tag_actions);
        config_deltrplstrlist(cfg->acl_tag_datas);
        config_delstrlist(cfg->control_ifs);
index 8e21674d3afa571bfbe27b40737d6088d572b9b2..5560326a36bcfe7f949e60f0160fd13eb02fe45f 100644 (file)
@@ -321,6 +321,12 @@ struct config_file {
        struct config_str3list* acl_tag_datas;
        /** list of aclname, view*/
        struct config_str2list* acl_view;
+       /** list of IP-netblock, tagbitlist */
+       struct config_strbytelist* respip_tags;
+       /** list of response-driven access control entries, linked list */
+       struct config_str2list* respip_actions;
+       /** RRs configured for response-driven access controls */
+       struct config_str2list* respip_data;
        /** tag list, array with tagname[i] is malloced string */
        char** tagname;
        /** number of items in the taglist */
@@ -472,6 +478,10 @@ struct config_view {
        /** Fallback to global local_zones when there is no match in the view
         * view specific tree. 1 for yes, 0 for no */   
        int isfirst;
+       /** predefined actions for particular IP address responses */
+       struct config_str2list* respip_actions;
+       /** data complementing the 'redirect' response IP actions */
+       struct config_str2list* respip_data;
 };
 
 /**
index 165814a2fa66af61f8969741dab3d38507e80b22..8e91534218a4acfde347dd2882718c7c580fffe2 100644 (file)
@@ -378,8 +378,8 @@ static void yy_fatal_error (yyconst char msg[]  );
        *yy_cp = '\0'; \
        (yy_c_buf_p) = yy_cp;
 
-#define YY_NUM_RULES 205
-#define YY_END_OF_BUFFER 206
+#define YY_NUM_RULES 208
+#define YY_END_OF_BUFFER 209
 /* This struct is not used in this scanner,
    but its presence is necessary. */
 struct yy_trans_info
@@ -387,229 +387,231 @@ struct yy_trans_info
        flex_int32_t yy_verify;
        flex_int32_t yy_nxt;
        };
-static yyconst flex_int16_t yy_accept[2011] =
+static yyconst flex_int16_t yy_accept[2031] =
     {   0,
-        1,    1,  187,  187,  191,  191,  195,  195,  199,  199,
-        1,    1,  206,  203,    1,  185,  185,  204,    2,  204,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      187,  188,  188,  189,  204,  191,  192,  192,  193,  204,
-      198,  195,  196,  196,  197,  204,  199,  200,  200,  201,
-      204,  202,  186,    2,  190,  204,  202,  203,    0,    1,
-        2,    2,    2,    2,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  187,
-        0,  191,    0,  198,    0,  195,  199,    0,  202,    0,
-        2,    2,  202,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      202,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  202,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   77,  203,  203,  203,  203,
-      203,  203,    8,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,   88,  202,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  202,
-
-      203,  203,  203,  203,  203,   37,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  161,  203,   14,   15,
-      203,   18,   17,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  147,
-      203,  203,  203,  203,  203,  203,  203,  203,    3,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  202,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  194,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,   40,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,   41,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  136,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,   20,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,   96,  203,  194,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  112,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,   95,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,   75,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,   25,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-       38,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   39,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,   28,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  176,  203,  203,
-      203,  203,  203,  203,  203,  203,   32,  203,   33,  203,
-      203,  203,   78,  203,   79,  203,  203,   76,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,    7,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  154,
-
-      203,  203,  203,  203,   98,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,   29,
-      203,  203,  203,  203,  203,  203,  203,  128,  203,  127,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,   16,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,   42,  203,
-      203,  203,  203,  203,  135,  203,  203,  203,  203,   81,
-       80,  203,  203,  203,  203,  203,  203,  203,  203,  122,
-
-      203,  203,  203,  203,  203,  203,  203,  203,   89,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,   60,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,   64,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,   36,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  125,  126,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,    6,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-       26,  203,  203,  203,  203,  203,  203,  203,  203,  118,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  140,
-      203,  119,  203,  203,  152,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   27,  203,  203,  203,  203,
-       84,  203,   85,  203,   83,  203,  203,  203,  203,  203,
-      203,  203,   94,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  175,  203,  203,  120,  203,  203,
-      203,  203,  203,  123,  203,  151,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  203,   74,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   34,  203,  203,   22,  203,
-      203,  203,  203,   19,  203,  103,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-       49,   51,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  162,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   86,  203,  203,  203,  203,
-      203,  203,  203,   93,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-
-      203,  203,  203,  203,  203,   97,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  146,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      111,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  107,  203,  113,  203,  203,  203,
-      203,  203,   92,  203,  203,   70,  203,  138,  203,  203,
-      203,  203,  203,  153,  203,  203,  203,  203,  203,  203,
-      203,  167,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  110,  203,  203,  203,  203,  203,
-       52,   53,  203,  203,  203,  203,  203,   35,   59,  114,
-
-      203,  129,  203,  155,  124,  203,  203,   45,  203,  116,
-      203,  203,  203,  203,  203,    9,  203,  203,  203,   73,
-      203,  203,  203,  203,  180,  203,  137,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,   99,  166,
-      203,  203,  203,  203,  203,  203,  203,  203,  148,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  115,  203,
-      203,   44,   46,  203,  203,  203,  203,  203,  203,  203,
-
-       72,  203,  203,  203,  203,  178,  203,  203,  203,  203,
-      142,   23,   24,  203,  203,  203,  203,  203,  203,  203,
-      203,   69,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  144,  141,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,   43,  203,  203,  203,  203,
-      203,  203,  203,  203,   13,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,   12,  203,
-      203,   21,  203,  203,  203,  184,  203,   47,  203,  150,
-      143,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  106,  105,  203,  203,  203,  203,  145,
-
-      139,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,   54,  203,  203,  203,  179,  203,  203,  149,  203,
-      203,  203,  203,  203,  203,  203,  203,   48,  203,  203,
-       82,  203,  100,  102,  130,  203,  203,  203,  104,  203,
-      203,  156,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  163,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  131,  203,  203,  177,
-      203,  203,   30,  203,  203,  203,  203,    4,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  159,
-
-      203,  203,  203,  203,  203,  203,  203,  203,  165,  203,
-      203,  134,  203,  203,  203,  203,  203,  203,  203,  203,
-       57,  203,   31,  183,  160,  203,   11,  203,  203,  203,
-      203,  203,  203,  132,   61,  203,  203,  203,  109,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  164,
-       90,  203,   87,  203,  203,  203,   63,   67,   62,  203,
-       55,  203,   10,  203,  203,  203,  181,  203,  203,  108,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,   68,   66,  203,   56,  203,  121,  203,
-      203,  133,  203,  203,  203,  203,  101,   50,  203,  203,
-
-      203,  203,  203,  203,  203,   91,   65,   58,  203,  182,
-      203,  203,  203,  158,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,   71,  203,  157,  174,  203,  203,  203,
-      203,  203,  203,    5,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  117,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  170,  203,  203,  203,  203,  203,
-      203,  203,  203,  203,  203,  203,  203,  203,  168,  203,
-
-      171,  172,  203,  203,  203,  203,  203,  169,  173,    0
+        1,    1,  190,  190,  194,  194,  198,  198,  202,  202,
+        1,    1,  209,  206,    1,  188,  188,  207,    2,  207,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      190,  191,  191,  192,  207,  194,  195,  195,  196,  207,
+      201,  198,  199,  199,  200,  207,  202,  203,  203,  204,
+      207,  205,  189,    2,  193,  207,  205,  206,    0,    1,
+        2,    2,    2,    2,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  190,
+        0,  194,    0,  201,    0,  198,  202,    0,  205,    0,
+        2,    2,  205,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  205,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  205,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   77,  206,  206,
+      206,  206,  206,  206,    8,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,   88,  205,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  205,  206,  206,  206,  206,  206,   37,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      161,  206,   14,   15,  206,   18,   17,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  147,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,    3,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  205,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  197,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   40,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,   41,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  136,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+       20,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   96,  206,
+      197,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  112,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   95,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+       75,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   25,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   38,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,   39,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,   28,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  176,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,   32,  206,   33,  206,  206,  206,
+       78,  206,   79,  206,  206,   76,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,    7,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  154,  206,  206,
+      206,  206,   98,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   29,  206,  206,
+      206,  206,  206,  206,  206,  128,  206,  127,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,   16,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   42,  206,  206,
+      206,  206,  206,  135,  206,  206,  206,  206,   81,   80,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  122,  206,
+      206,  206,  206,  206,  206,  206,  206,   89,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,   60,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   64,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,   36,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  125,  126,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,    6,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  186,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,   26,  206,  206,  206,  206,  206,  206,  206,  206,
+      118,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      140,  206,  119,  206,  206,  152,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,   27,  206,  206,  206,
+      206,   84,  206,   85,  206,   83,  206,  206,  206,  206,
+      206,  206,  206,   94,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  175,  206,  206,  120,  206,
+
+      206,  206,  206,  206,  123,  206,  151,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+       74,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   34,  206,
+      206,   22,  206,  206,  206,  206,   19,  206,  103,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,   49,   51,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  162,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   86,  206,
+      206,  206,  206,  206,  206,  206,   93,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,   97,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  146,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  111,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  107,
+      206,  113,  206,  206,  206,  206,  206,   92,  206,  206,
+       70,  206,  138,  206,  206,  206,  206,  206,  153,  206,
+      206,  206,  206,  206,  206,  206,  167,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  110,
+
+      206,  206,  206,  206,  206,   52,   53,  206,  206,  206,
+      206,  206,   35,   59,  114,  206,  129,  206,  155,  124,
+      206,  206,   45,  206,  116,  206,  206,  206,  206,  206,
+        9,  206,  206,  206,   73,  206,  206,  206,  206,  180,
+      206,  137,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,   99,  166,  206,  206,  206,
+      206,  206,  206,  206,  206,  148,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  206,  115,  206,  206,   44,   46,
+      206,  206,  206,  206,  206,  206,  206,   72,  206,  206,
+      206,  206,  178,  206,  185,  206,  206,  206,  206,  142,
+       23,   24,  206,  206,  206,  206,  206,  206,  206,  206,
+       69,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  144,  141,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,   43,  206,  206,  206,  206,  206,
+      206,  206,  206,   13,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,   12,  206,  206,
+       21,  206,  206,  206,  184,  206,  187,   47,  206,  150,
+
+      143,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  106,  105,  206,  206,  206,  206,  145,
+      139,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,   54,  206,  206,  206,  179,  206,  206,  149,  206,
+      206,  206,  206,  206,  206,  206,  206,   48,  206,  206,
+       82,  206,  100,  102,  130,  206,  206,  206,  104,  206,
+      206,  156,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  163,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  131,  206,  206,  177,
+
+      206,  206,   30,  206,  206,  206,  206,    4,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  159,
+      206,  206,  206,  206,  206,  206,  206,  206,  165,  206,
+      206,  134,  206,  206,  206,  206,  206,  206,  206,  206,
+       57,  206,   31,  183,  160,  206,   11,  206,  206,  206,
+      206,  206,  206,  132,   61,  206,  206,  206,  109,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  164,
+       90,  206,   87,  206,  206,  206,   63,   67,   62,  206,
+       55,  206,   10,  206,  206,  206,  181,  206,  206,  108,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,   68,   66,  206,   56,  206,  121,  206,
+      206,  133,  206,  206,  206,  206,  101,   50,  206,  206,
+      206,  206,  206,  206,  206,   91,   65,   58,  206,  182,
+      206,  206,  206,  158,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,   71,  206,  157,  174,  206,  206,  206,
+      206,  206,  206,    5,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  117,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  206,  206,
+
+      206,  206,  206,  206,  170,  206,  206,  206,  206,  206,
+      206,  206,  206,  206,  206,  206,  206,  206,  168,  206,
+      171,  172,  206,  206,  206,  206,  206,  169,  173,    0
     } ;
 
 static yyconst YY_CHAR yy_ec[256] =
@@ -652,461 +654,465 @@ static yyconst YY_CHAR yy_meta[40] =
         1,    1,    1,    1,    1,    1,    1,    1,    1
     } ;
 
-static yyconst flex_uint16_t yy_base[2025] =
+static yyconst flex_uint16_t yy_base[2045] =
     {   0,
         0,    0,   37,   40,   44,   51,   63,   75,   56,   68,
-       87,  108, 1988, 1845,   50, 3970, 3970, 3970,  129,   94,
+       87,  108, 1880, 1760,   50, 4002, 4002, 4002,  129,   94,
        70,  104,  130,   90,  109,  106,  127,  111,   84,  122,
       146,  148,   50,  170,  136,  158,  196,  171,  138,  177,
-     1582, 3970, 3970, 3970,   70, 1472, 3970, 3970, 3970,   42,
-     1346, 1295, 3970, 3970, 3970,  208, 1213, 3970, 3970, 3970,
-      141, 1154, 3970,  214, 3970,  218,  140, 1064,  228,  167,
+     1595, 4002, 4002, 4002,   70, 1555, 4002, 4002, 4002,   42,
+     1167, 1027, 4002, 4002, 4002,  208,  899, 4002, 4002, 4002,
+      141,  857, 4002,  214, 4002,  218,  140,  633,  228,  167,
         0,  239,    0,    0,   92,  162,  164,  218,  180,  167,
       223,  224,  103,  168,  237,  226,  193,  183,  236,  241,
       244,  246,  247,  249,  258,  245,  257,  260,  256,  265,
 
       266,  271,  272,  274,  273,  275,  276,  283,  284,  288,
-      289,  190,  290,  291,  277,  296,  298,  299,  305,  301,
-      306,  303,  308,  311,  317,  318,  314,  320,  325,  890,
-      337,  587,  122,  513,  342,  346,  225,  350,  192,  354,
-      358,    0,  351,  339,  360,  322,  353,  356,  357,  359,
-      362,  368,  365,  366,  378,  376,  397,  380,  364,  377,
-      384,   49,  386,  387,  385,  388,  393,  391,  395,  402,
-      413,  404,  394,  420,  421,  428,  430,  426,  416,  432,
-      436,  443,  444,  440,  429,  445,  446,  448,  449,  450,
-      452,  455,  453,  456,  457,  459,  469,  461,  472,  463,
-
-      473,  470,  487,  474,  478,  484,  491,  494,  495,  488,
-      492,  496,  498,  505,  502,  508,  501,  499,  398,  510,
-      512,  519,  521,  524,  529,  527,  530,  520,  532,  535,
-      539,  533,  545,  534,  546,  549,  551,  557,  544,  553,
-      554,  555,  558,  560,  561,  562,  565,  569,  567,  572,
-      578,  574,  576,  580,  581,  582,  586,  592,  591,  596,
-      602,  601,  607,  606,  608,  610,  611,  612,  614,  619,
-      620,  623,  630,  626,  628,  631,  634,  627,  635,  638,
-      645,  644,  648,  650,  652,  657,  655,  659,  675,  653,
-      663,  665,  662,  666,  680,  676,  684,  681,  682,  686,
-
-      688,  692,  703,  697,  699,  700,  710,  706,  708,  718,
-      709,  712,  719,  720,  721,  726,  727,  724,  725,  732,
-      736,  733,  740,  737,  748,  747,  749,  752,  753,  750,
-      759,  757,  751,  765,  772,  769,  761,  771,  774,  763,
-      777,  778,  780,  784,  786, 3970,  788,  790,  791,  792,
-      793,  794, 3970,  796,  795,  798,  802,  800,  803,  810,
-      822,  824,  807,  820,  804,  823,  827,  828,  829,  830,
-      832,  852,  835,  837,  833,  845,  836,  841,  847,  838,
-      864,  854,  862,  857,  866,  859,  870,  867,  873,  879,
-      877, 3970,  880,  887,  886,  888,  889,  891,  896,  893,
-
-      908,  897,  901,  900,  907,  910,  911,  919,  916,  921,
-      923,  931,  925,  933,  939,  917,  935,  928,  937,  948,
-      942,  944,  936,  950,  952,  951,  955,  953,  959,  954,
-      961,  964,  962,  973,  970,  974,  978,  975,  981,  983,
-      984,  985,  987,  988,  994,  992,  993, 1002, 1001,  991,
-     1007, 1013, 1010, 1016, 1014, 1018, 1025, 1019, 1022, 1031,
-     1027, 1030, 1029, 1042, 1038, 1028, 1043, 1040, 1044, 1047,
-     1049, 1050, 1051, 1052, 1054, 1055, 1057, 1058, 1061, 1073,
-     1060, 1062, 1082, 1074, 1080, 1084, 1072, 1066, 1086, 1087,
-     1090, 1093, 1092, 1096, 1098, 1102, 1103, 1104, 1105, 1106,
-
-     1107, 1113, 1108, 1119, 1115, 3970, 1126, 1122, 1123, 1125,
-     1130, 1136, 1132, 1133, 1134, 1160, 3970, 1135, 3970, 3970,
-      995, 3970, 3970, 1138, 1139, 1149, 1143, 1146, 1183, 1152,
-     1155, 1156, 1158, 1163, 1164, 1166, 1174, 1175, 1186, 1177,
-     1188, 1168, 1192, 1178, 1194, 1196, 1198, 1199, 1203, 1205,
-     1207, 1208, 1211, 1210, 1217, 1226, 1224, 1222, 1223, 1229,
-     1230, 1233, 1232, 1234, 1236, 1240, 1242, 1246, 1243, 3970,
-     1245, 1247, 1252, 1244, 1259, 1251, 1257, 1261, 3970, 1263,
-     1268, 1269, 1270, 1271, 1273, 1274, 1277, 1276, 1278, 1280,
-     1283, 1279, 1287, 1286, 1289, 1304, 1291, 1294, 1306, 1310,
-
-     1309, 1307, 1312, 1314, 1315, 1316, 1323, 1322, 1320, 1321,
-     1333, 1327, 1330, 1331, 1340, 1335, 1337, 1342, 1343, 1344,
-     1345, 1368, 1351, 1353, 1348, 1355, 1356, 1354, 1359, 1362,
-     1372, 1366, 1375, 1378, 1382, 1374, 1381, 1385, 1391, 1400,
-     1404, 1405, 1396, 1407, 1401, 1398, 1416, 1409, 1418, 1419,
-     1420, 1422, 1423, 3970, 1430, 1429, 1428, 1435, 1441, 1437,
-     1434, 1440, 1443, 1438, 1446, 1444, 1445, 1451, 1456, 1457,
-     1458, 1459, 1465, 3970, 1461, 1464, 1466, 1469, 1473, 1479,
-     1476, 1486, 1488, 1462, 3970, 1489, 1495, 1492, 1497, 1498,
-     1491, 1499, 1501, 1503, 1502, 1504, 1508, 1510, 1507, 3970,
-
-     1516, 1509, 1518, 1527, 1528, 1517, 1529, 1530, 1531, 1533,
-     1534, 1541, 1538, 1539, 3970, 1540, 1542, 1546, 1549, 1556,
-     1559, 1552, 1555, 1563, 1564, 1565, 1566, 1572, 1569, 1571,
-     1570, 1573, 3970, 1574,  151, 1576, 1577, 1575, 1586, 1596,
-     1594, 1597, 1600, 1601, 1603, 1604, 1588, 1605, 1606, 1609,
-     1585, 1610, 1611, 1616, 1613, 1617, 1620, 1623, 1626, 1631,
-     1627, 1632, 1637, 1635, 1638, 1636, 3970, 1644, 1647, 1646,
-     1639, 1649, 1650, 1651, 1652, 1653, 1659, 1660, 1665, 1662,
-     1667, 3970, 1673, 1669, 1670, 1672, 1679, 1675, 1686, 1688,
-     1689, 1691, 1693, 1695, 1690, 1701, 1697, 1700, 1702, 1709,
-
-     1710, 1712, 1716, 1717, 1706, 1718, 1724, 1726, 1723, 1727,
-     1737, 1729, 1394, 1732, 3970, 1734, 1733, 1740, 1735, 1750,
-     1742, 1741, 1739, 1752, 1754, 1759, 1761, 1762, 1765, 1768,
-     1770, 3970, 1771, 1773, 1772, 1776, 1779, 1781, 1782, 1784,
-     1789, 1790, 1792, 1785, 1795, 1801, 1794, 1798, 1796, 1806,
-     3970, 1813, 1814, 1811, 1820, 1817, 1818, 1821, 1823, 1807,
-     1824, 1825, 1833, 1829, 1830, 1834, 1835, 1838, 1831, 1836,
-     1840, 1842, 1855, 1841, 1852, 3970, 1856, 1867, 1859, 1863,
-     1870, 1860, 1878, 1865, 1876, 1877, 1879, 1880, 1881, 1882,
-     1883, 1884, 1889, 1885, 1890, 1892, 1893, 1894, 1891, 1911,
-
-     1912, 1913, 1897, 1914, 1917, 1895, 1899, 1921, 1927, 1929,
-     1930, 1933, 3970, 1936, 1937, 1938, 1925, 1939, 1928, 1940,
-     1950, 1953, 1946, 1951, 1954, 1955, 1956, 1957, 1958, 1965,
-     1961, 1962, 1967, 1968, 1963, 1969, 1978, 1971, 1985, 1979,
-     1984, 1989, 1992, 1995, 1997, 1998, 1999, 3970, 2000, 2003,
-     2004, 2010, 2007, 2012, 2021, 2023, 3970, 2013, 3970, 2019,
-     2026, 2033, 3970, 2030, 3970, 2035, 2036, 3970, 2037, 2038,
-     2041, 2017, 2043, 2044, 2045, 2047, 2050, 2048, 2058, 2051,
-     2053, 2061, 2055, 2062, 3970, 2070, 2063, 2066, 2071, 2077,
-     2075, 2076, 2078, 2079, 2083, 2084, 2091, 2088, 2097, 3970,
-
-     2090, 2094, 2098, 2100, 3970, 2101, 2102, 2107, 2109, 2110,
-     2120, 2118, 2105, 2121, 2111, 2124, 2135, 2131, 2122, 2133,
-     2134, 2142, 2138, 2144, 2141, 2145, 2147, 2148, 2149, 2151,
-     2155, 2156, 2157, 2159, 2163, 2160, 2161, 2162, 2165, 3970,
-     2174, 2168, 2177, 2178, 2183, 2185, 2179, 3970, 2184, 3970,
-     2166, 2201, 2203, 2189, 2205, 2196, 2198, 2187, 2208, 2209,
-     2216, 2214, 2215, 2219, 2221, 2222, 2224, 2225, 3970, 2223,
-     2226, 2227, 2229, 2233, 2238, 2246, 2241, 2231, 3970, 2256,
-     2234, 2254, 2260, 2257, 3970, 2258, 2267, 2264, 2265, 3970,
-     3970, 2266, 2271, 2269, 2270, 2272, 2280, 2273, 2276, 3970,
-
-     2284, 2281, 2286, 2287, 2293, 2295, 2296, 2297, 3970, 2299,
-     2303, 2304, 2306, 2307, 2309, 2308, 2315, 2311, 2312, 2316,
-     2325, 2326, 2332, 3970, 2328, 2334, 2336, 2337, 2339, 2338,
-     2340, 2341, 2345, 2342, 2346, 2348, 2354, 2360, 2357, 2358,
-     2359, 2362, 2365, 2368, 2369, 2371, 2372, 2380, 2381, 3970,
-     2387, 2373, 2388, 2374, 2393, 2394, 2401, 2397, 2386, 2398,
-     2405, 2402, 3970, 2408, 2412, 2404, 2414, 2389, 2419, 2417,
-     2421, 2423, 2428, 3970, 3970, 2429, 2431, 2432, 2433, 2435,
-     2434, 2441, 2436, 2439, 3970, 2445, 2451, 2448, 2449, 2457,
-     2458, 2464, 2454, 2461, 2465, 2467, 2466, 2469, 2471, 2473,
-
-     2474, 2476, 2477, 2479, 2480, 2481, 2483, 2498, 2490, 2503,
-     2488, 2493, 2495, 2505, 2511, 2513, 2519, 2504, 2516, 2522,
-     3970, 2520, 2521, 2523, 2518, 2529, 2526, 2536, 2527, 3970,
-     2534, 2540, 2545, 2547, 2533, 2549, 2551, 2552, 2550, 3970,
-     2557, 3970, 2560, 2542, 3970, 2561, 2565, 2566, 2567, 2569,
-     2570, 2568, 2574, 2580, 2571, 3970, 2581, 2577, 2583, 2588,
-     3970, 2591, 3970, 2578, 3970, 2584, 2596, 2603, 2600, 2601,
-     2604, 2608, 3970, 2605, 2609, 2613, 2611, 2615, 2616, 2618,
-     2619, 2621, 2622, 2626, 3970, 2623, 2624, 3970, 2633, 2625,
-     2634, 2635, 2639, 3970, 2641, 3970, 2642, 2649, 2651, 2653,
-
-     2655, 2654, 2660, 2661, 2662, 2668, 2664, 2667, 2666, 3970,
-     2670, 2671, 2673, 2675, 2678, 2681, 2688, 2686, 2690, 2684,
-     2694, 2695, 2699, 2700, 2702, 3970, 2705, 2707, 3970, 2704,
-     2708, 2711, 2715, 3970, 2713, 3970, 2716, 2718, 2720, 2721,
-     2724, 2725, 2727, 2732, 2735, 2736, 2737, 2743, 2740, 2744,
-     3970, 3970, 2747, 2749, 2753, 2754, 2756, 2757, 2765, 2761,
-     2763, 3970, 2759, 2767, 2769, 2770, 2771, 2773, 2774, 2778,
-     2779, 2780, 2781, 2782, 2787, 3970, 2788, 2789, 2793, 2794,
-     2797, 2798, 2799, 3970, 2801, 2802, 2796, 2811, 2803, 2814,
-     2822, 2824, 2804, 2826, 2827, 2829, 2831, 2833, 2835, 2836,
-
-     2843, 2840, 2845, 2847, 2837, 3970, 2848, 2850, 2851, 2860,
-     2854, 2857, 2861, 2865, 2868, 2852, 2862, 2869, 2874, 3970,
-     2875, 2876, 2878, 2879, 2885, 2882, 2887, 2880, 2889, 2891,
-     3970, 2892, 2897, 2894, 2896, 2903, 2905, 2907, 2898, 2908,
-     2911, 2914, 2921, 2918, 3970, 2915, 3970, 2923, 2925, 2934,
-     2930, 2927, 3970, 2933, 2936, 3970, 2938, 3970, 2937, 2941,
-     2942, 2943, 2952, 3970, 2954, 2944, 2956, 2959, 2960, 2961,
-     2963, 3970, 2965, 2967, 2973, 2976, 2966, 2968, 2975, 2978,
-     2977, 2979, 2990, 2987, 3970, 2983, 2991, 3000, 2994, 3001,
-     3970, 3970, 2992, 3004, 3007, 2998, 3008, 3970, 3970, 3970,
-
-     3012, 3970, 3013, 3970, 3970, 3014, 3016, 3970, 3018, 3970,
-     3025, 3021, 3023, 3026, 3027, 3970, 3028, 3029, 3034, 3970,
-     3035, 3042, 3036, 3030, 3970, 3050, 3970, 3038, 3051, 3046,
-     3052, 3056, 3059, 3062, 3063, 3064, 3065, 3067, 3068, 3069,
-     3071, 3070, 3073, 3074, 3077, 3078, 3084, 3085, 3086, 3087,
-     3092, 3089, 3091, 3094, 3105, 3096, 3112, 3114, 3970, 3970,
-     3102, 3106, 3104, 3108, 3116, 3117, 3118, 3119, 3970, 3130,
-     3123, 3121, 3127, 3131, 3133, 3135, 3138, 3140, 3142, 3148,
-     3144, 3145, 3147, 3150, 3149, 3152, 3156, 3163, 3970, 3158,
-     3157, 3970, 3970, 3164, 3168, 3174, 3170, 3175, 3178, 3179,
-
-     3970, 3180, 3182, 3188, 3181, 3970, 3190, 3191, 3197, 3199,
-     3970, 3970, 3970, 3200, 3192, 3202, 3203, 3204, 3206, 3205,
-     3208, 3970, 3207, 3213, 3220, 3217, 3227, 3229, 3223, 3231,
-     3238, 3234, 3241, 3243, 3970, 3970, 3235, 3249, 3246, 3247,
-     3245, 3251, 3253, 3255, 3256, 3970, 3259, 3258, 3219, 3257,
-     3264, 3265, 3271, 3267, 3970, 3269, 3275, 3277, 3279, 3280,
-     3281, 3282, 3284, 3285, 3287, 3293, 3286, 3298, 3970, 3300,
-     3289, 3970, 3301, 3306, 3307, 3970, 3310, 3970, 3313, 3970,
-     3970, 3308, 3314, 3317, 3318, 3324, 3326, 3330, 3319, 3327,
-     3336, 3333, 3334, 3970, 3970, 3340, 3342, 3343, 3350, 3970,
-
-     3970, 3346, 3344, 3347, 3348, 3353, 3354, 3356, 3357, 3359,
-     3358, 3363, 3369, 3371, 3374, 3375, 3378, 3360, 3379, 3381,
-     3382, 3970, 3384, 3389, 3385, 3970, 3394, 3391, 3970, 3387,
-     3400, 3404, 3397, 3395, 3412, 3409, 3414, 3970, 3415, 3413,
-     3970, 3416, 3970, 3970, 3970, 3421, 3417, 3419, 3970, 3427,
-     3429, 3970, 3435, 3431, 3436, 3442, 3438, 3439, 3443, 3450,
-     3446, 3448, 3970, 3449, 3451, 3453, 3454, 3458, 3455, 3457,
-     3460, 3469, 3465, 3463, 3475, 3472, 3970, 3481, 3483, 3970,
-     3485, 3487, 3970, 3494, 3476, 3478, 3486, 3970, 3497, 3488,
-     3490, 3500, 3504, 3495, 3506, 3507, 3509, 3510, 3515, 3970,
-
-     3511, 3517, 3519, 3520, 3521, 3529, 3526, 3531, 3970, 3533,
-     3528, 3970, 3535, 3536, 3538, 3545, 3549, 3554, 3556, 3546,
-     3970, 3558, 3970, 3970, 3970, 3559, 3970, 3562, 3563, 3564,
-     3565, 3567, 3568, 3970, 3970, 3570, 3572, 3575, 3970, 3569,
-     3576, 3581, 3579, 3582, 3583, 3587, 3588, 3592, 3593, 3970,
-     3970, 3594, 3970, 3600, 3608, 3611, 3970, 3970, 3970, 3610,
-     3970, 3612, 3970, 3618, 3602, 3619, 3970, 3622, 3623, 3970,
-     3624, 3595, 3625, 3628, 3630, 3631, 3632, 3634, 3635, 3639,
-     3640, 3641, 3647, 3970, 3970, 3651, 3970, 3653, 3970, 3654,
-     3659, 3970, 3585, 3661, 3655, 3665, 3970, 3970, 3539, 3648,
-
-     3666, 3667, 3668, 3671, 3669, 3970, 3970, 3970, 3673, 3970,
-     3674, 3675, 3677, 3970, 3679, 3681, 3682, 3684, 3683, 3686,
-     3688, 3692, 3697, 3698, 3705, 3709, 3710, 3713, 3700, 3706,
-     3719, 3716, 3723, 3970, 3717, 3970, 3970, 3720, 3729, 3731,
-     3727, 3733, 3728, 3970, 3734, 3735, 3736, 3737, 3738, 3740,
-     3751, 3742, 3743, 3753, 3755, 3759, 3752, 3767, 3766, 3763,
-     3768, 3769, 3777, 3773, 3776, 3970, 3774, 3775, 3778, 3780,
-     3781, 3785, 3783, 3795, 3798, 3786, 3800, 3784, 3805, 3801,
-     3806, 3809, 3810, 3811, 3970, 3812, 3814, 3816, 3818, 3820,
-     3822, 3823, 3824, 3827, 3829, 3832, 3834, 3838, 3970, 3839,
-
-     3970, 3970, 3843, 3840, 3846, 3850, 3852, 3970, 3970, 3970,
-     3878, 3885, 3892, 3899, 3906,   94, 3913, 3920, 3927, 3934,
-     3941, 3948, 3955, 3962
+      289,  190,  290,  292,  291,  277,  298,  299,  308,  301,
+      314,  300,  304,  307,  317,  321,  322,  323,  324,  515,
+      339,  432,  122,  401,  353,  348,  225,  341,  192,  357,
+      361,    0,  336,  338,  359,  356,  357,  358,  360,  362,
+      363,  369,  368,  366,  379,  378,  399,  380,  383,  384,
+      385,   49,  387,  388,  386,  392,  394,  396,  405,  411,
+      417,  395,  412,  426,  424,  427,  434,  430,  431,  441,
+      438,  445,  447,  397,  444,  448,  446,  449,  450,  451,
+      456,  453,  460,  461,  462,  463,  464,  470,  471,  478,
+
+      467,  325,  474,  484,  476,  480,  493,  488,  496,  497,
+      485,  498,  500,  501,  507,  512,  518,  505,  503,  511,
+      514,  504,  523,  528,  531,  527,  533,  535,  537,  539,
+      538,  540,  542,  548,  545,  552,  549,  555,  561,  546,
+      557,  558,  563,  564,  567,  562,  568,  569,  573,  571,
+      578,  582,  581,  583,  585,  588,  586,  591,  596,  598,
+      593,  606,  599,  610,  611,  612,  614,  617,  623,  615,
+      626,  627,  618,  628,  634,  632,  635,  636,  645,  637,
+      642,  644,  654,  655,  646,  656,  657,  664,  662,  666,
+      682,  668,  670,  674,  671,  686,  675,  687,  693,  677,
+
+      689,  691,  699,  695,  708,  702,  711,  712,  718,  714,
+      715,  719,  721,  724,  727,  725,  729,  728,  733,  734,
+      735,  736,  738,  746,  744,  750,  760,  742,  756,  753,
+      761,  754,  764,  767,  768,  769,  776,  773,  775,  778,
+      779,  780,  782,  784,  789,  787,  790, 4002,  797,  793,
+      795,  800,  799,  801, 4002,  802,  804,  807,  810,  806,
+      811,  812,  817,  823,  832,  828,  829,  830,  833,  831,
+      836,  838,  837,  839,  859,  841,  844,  840,  869,  845,
+      846,  870,  847,  876,  868,  879,  873,  862,  880,  882,
+      884,  886,  889,  849, 4002,  890,  897,  895,  896,  898,
+
+      900,  910,  901,  917,  903,  916,  906,  918,  922,  920,
+      929,  927,  931,  933,  942,  935,  944,  946,  926,  945,
+      938,  948,  954,  951,  953,  956,  964,  960,  961,  966,
+      962,  967,  963,  972,  979,  971,  987,  983,  970,  986,
+      988,  989,  991,  995,  996,  997,  998, 1004, 1000, 1002,
+     1011, 1015, 1003, 1009, 1022, 1019, 1030, 1026, 1027, 1036,
+     1028, 1033, 1039, 1018, 1038, 1040, 1044, 1053, 1050, 1042,
+     1054, 1045, 1055, 1059, 1060, 1061, 1062, 1065, 1063, 1066,
+     1068, 1070, 1073, 1076, 1074, 1075, 1083, 1087, 1079, 1092,
+     1085, 1095, 1096, 1098, 1099, 1100, 1103, 1106, 1102, 1110,
+
+     1112, 1113, 1115, 1118, 1116, 1122, 1125, 1128, 1130, 4002,
+     1136, 1132, 1134, 1133, 1135, 1147, 1140, 1141, 1143, 1169,
+     4002, 1149, 4002, 4002, 1144, 4002, 4002, 1151, 1150, 1154,
+     1162, 1170, 1192, 1166, 1155, 1157, 1172, 1177, 1179, 1183,
+     1180, 1189, 1197, 1198, 1200, 1185, 1203, 1206, 1207, 1209,
+     1208, 1212, 1214, 1217, 1218, 1220, 1219, 1222, 1235, 1238,
+     1223, 1234, 1237, 1239, 1241, 1243, 1242, 1244, 1251, 1246,
+     1252, 1258, 1254, 4002, 1256, 1257, 1261, 1262, 1268, 1269,
+     1271, 1272, 1274, 4002, 1276, 1280, 1281, 1283, 1284, 1275,
+     1287, 1290, 1289, 1293, 1294, 1292, 1291, 1301, 1303, 1308,
+
+     1307, 1299, 1304, 1320, 1321, 1322, 1323, 1324, 1325, 1327,
+     1328, 1337, 1331, 1333, 1339, 1340, 1338, 1346, 1341, 1350,
+     1347, 1353, 1354, 1343, 1355, 1356, 1377, 1360, 1364, 1363,
+     1365, 1366, 1372, 1374, 1371, 1375, 1391, 1381, 1392, 1394,
+     1400, 1383, 1401, 1402, 1410, 1412, 1416, 1406, 1420, 1409,
+     1419, 1426, 1428, 1413, 1429, 1384, 1437, 1430, 4002, 1444,
+     1438, 1432, 1440, 1450, 1447, 1446, 1448, 1449, 1454, 1455,
+     1456, 1461, 1459, 1460, 1462, 1463, 1467, 1473, 4002, 1469,
+     1471, 1477, 1478, 1480, 1481, 1484, 1490, 1499, 1487, 4002,
+     1495, 1502, 1503, 1505, 1496, 1498, 1506, 1514, 1512, 1513,
+
+     1515, 1517, 1519, 1520, 1522, 4002, 1523, 1526, 1531, 1528,
+     1530, 1535, 1538, 1540, 1543, 1544, 1546, 1550, 1547, 1549,
+     4002, 1548, 1557, 1556, 1551, 1570, 1573, 1561, 1569, 1572,
+     1575, 1577, 1578, 1583, 1580, 1584, 1581, 1582, 4002, 1585,
+      151, 1587, 1588, 1586, 1597, 1610, 1608, 1609, 1602, 1611,
+     1612, 1615, 1599, 1589, 1619, 1620, 1622, 1623, 1624, 1626,
+     1627, 1628, 1631, 1633, 1635, 1638, 1643, 1644, 1645, 1646,
+     1651, 1648, 4002, 1654, 1655, 1657, 1652, 1659, 1662, 1663,
+     1660, 1666, 1668, 1670, 1673, 1677, 1680, 4002, 1683, 1681,
+     1682, 1684, 1691, 1693, 1699, 1692, 1700, 1702, 1706, 1703,
+
+     1701, 1713, 1717, 1719, 1712, 1720, 1722, 1728, 1723, 1726,
+     1730, 1733, 1739, 1740, 1736, 1738, 1752, 1745, 1749, 1737,
+     4002, 1750, 1743, 1753, 1755, 1774, 1762, 1756, 1759, 1767,
+     1763, 1779, 1780, 1757, 1781, 1784, 1785, 1790, 4002, 1791,
+     1787, 1793, 1796, 1797, 1802, 1799, 1803, 1806, 1807, 1808,
+     1810, 1809, 1815, 1811, 1819, 1821, 1820, 4002, 1831, 1835,
+     1832, 1839, 1836, 1822, 1838, 1843, 1840, 1844, 1823, 1852,
+     1848, 1850, 1851, 1853, 1854, 1856, 1857, 1859, 1861, 1873,
+     1858, 1869, 4002, 1865, 1880, 1878, 1883, 1886, 1885, 1894,
+     1892, 1890, 1893, 1895, 1897, 1898, 1900, 1902, 1904, 1905,
+
+     1906, 1907, 1910, 1911, 1913, 1914, 1927, 1909, 1929, 1917,
+     1930, 1931, 1936, 1920, 1938, 1945, 1949, 1947, 1950, 4002,
+     1953, 1954, 1955, 1956, 1957, 1959, 1960, 1966, 1968, 1969,
+     1971, 1972, 1975, 1970, 1976, 1977, 1985, 1978, 1981, 1982,
+     1984, 1988, 1986, 1993, 1998, 2006, 1992, 2011, 2012, 2014,
+     2013, 2015, 2016, 2019, 4002, 2020, 2023, 2028, 2030, 2032,
+     1987, 2022, 2046, 2034, 4002, 2031, 4002, 2043, 2044, 2052,
+     4002, 2051, 4002, 2054, 2055, 4002, 2056, 2057, 2060, 2037,
+     2063, 2061, 2064, 2068, 2065, 2070, 2072, 2074, 2076, 2078,
+     2080, 2081, 4002, 2084, 2085, 2088, 2091, 2089, 2093, 2095,
+
+     2097, 2098, 2105, 2104, 2116, 2100, 2117, 4002, 2108, 2124,
+     2110, 2119, 4002, 1685, 2126, 2121, 2114, 2132, 2136, 2137,
+     2130, 2140, 2128, 2141, 2148, 2146, 2149, 2151, 2152, 2159,
+     2155, 2161, 2157, 2158, 2165, 2166, 2168, 2162, 2169, 2173,
+     2176, 2177, 2179, 2175, 2178, 2183, 2181, 4002, 2185, 2191,
+     2194, 2192, 2193, 2196, 2201, 4002, 2203, 4002, 2204, 2210,
+     2213, 2216, 2215, 2206, 2221, 2214, 2225, 2226, 2232, 2239,
+     2224, 2228, 2231, 2236, 2240, 2242, 4002, 2243, 2245, 2246,
+     2248, 2251, 2252, 2258, 2253, 2261, 2271, 4002, 2272, 2269,
+     2275, 2281, 2277, 4002, 2274, 2289, 2278, 2290, 4002, 4002,
+
+     2282, 2288, 2285, 2286, 2292, 2300, 2297, 2302, 4002, 2306,
+     2303, 2308, 2309, 2310, 2316, 2317, 2307, 4002, 2318, 2325,
+     2322, 2327, 2319, 2328, 2329, 2337, 2335, 2338, 2339, 2342,
+     2343, 2350, 4002, 2352, 2344, 2355, 2351, 2359, 2358, 2360,
+     2361, 2365, 2362, 2366, 2368, 2374, 2380, 2369, 2377, 2378,
+     2382, 2379, 2388, 2385, 2392, 2389, 2400, 2394, 4002, 2407,
+     2401, 2408, 2404, 2410, 2411, 2418, 2414, 2405, 2415, 2421,
+     2417, 4002, 2439, 2422, 2420, 2424, 2430, 2431, 2440, 2442,
+     2443, 2446, 4002, 4002, 2448, 2450, 2447, 2451, 2452, 2453,
+     2454, 2459, 2465, 4002, 2463, 2471, 2467, 2469, 2475, 2477,
+
+     2474, 2478, 2480, 2482, 2484, 2486, 2488, 2490, 2492, 2493,
+     2495, 2496, 4002, 2501, 2497, 2505, 2507, 2506, 2522, 2514,
+     2524, 2511, 2517, 2499, 2533, 2527, 2539, 2540, 2529, 2536,
+     2542, 4002, 2541, 2543, 2544, 2545, 2551, 2549, 2557, 2550,
+     4002, 2558, 2559, 2564, 2566, 2554, 2567, 2572, 2569, 2576,
+     4002, 2578, 4002, 2579, 2568, 4002, 2581, 2587, 2584, 2588,
+     2589, 2590, 2591, 2594, 2601, 2592, 4002, 2602, 2598, 2608,
+     2610, 4002, 2612, 4002, 2605, 4002, 2600, 2613, 2623, 2620,
+     2624, 2626, 2630, 4002, 2631, 2622, 2632, 2634, 2635, 2636,
+     2639, 2640, 2641, 2644, 2647, 4002, 2645, 2649, 4002, 2650,
+
+     2658, 2646, 2657, 2654, 4002, 2663, 4002, 2668, 2671, 2673,
+     2674, 2675, 2676, 2678, 2680, 2684, 2690, 2686, 2687, 2688,
+     4002, 2689, 2692, 2694, 2701, 2695, 2697, 2712, 2709, 2703,
+     2711, 2715, 2718, 2713, 2724, 2721, 2727, 2728, 4002, 2729,
+     2730, 4002, 2731, 2732, 2733, 2737, 4002, 2739, 4002, 2741,
+     2742, 2738, 2746, 2749, 2750, 2761, 2743, 2754, 2764, 2765,
+     2771, 2767, 2756, 4002, 4002, 2773, 2768, 2780, 2781, 2774,
+     2783, 2789, 2785, 2788, 4002, 2791, 2792, 2794, 2793, 2795,
+     2796, 2799, 2803, 2805, 2798, 2806, 2804, 2807, 4002, 2810,
+     2812, 2818, 2819, 2820, 2821, 2822, 4002, 2824, 2825, 2827,
+
+     2831, 2834, 2836, 2849, 2851, 2839, 2844, 2852, 2846, 2860,
+     2862, 2864, 2856, 2866, 2867, 2869, 2871, 2872, 4002, 2873,
+     2877, 2874, 2880, 2881, 2882, 2883, 2889, 2895, 2884, 2887,
+     2892, 2897, 4002, 2898, 2900, 2901, 2904, 2907, 2909, 2913,
+     2910, 2914, 2915, 2919, 2917, 4002, 2922, 2924, 2925, 2927,
+     2931, 2932, 2933, 2936, 2935, 2939, 2942, 2954, 2943, 4002,
+     2945, 4002, 2946, 2957, 2964, 2960, 2953, 4002, 2962, 2963,
+     4002, 2966, 4002, 2967, 2971, 2968, 2974, 2980, 4002, 2982,
+     2983, 2984, 2987, 2989, 2990, 2991, 4002, 2994, 2993, 3001,
+     3002, 2995, 3004, 3005, 3006, 3008, 3011, 3017, 3014, 4002,
+
+     3013, 3018, 3026, 3022, 3025, 4002, 4002, 3031, 3032, 3034,
+     3035, 3038, 4002, 4002, 4002, 3041, 4002, 3036, 4002, 4002,
+     3042, 3044, 4002, 3049, 4002, 3051, 3052, 3050, 3055, 3057,
+     4002, 3056, 3058, 3060, 4002, 3063, 3069, 3065, 3067, 4002,
+     3074, 4002, 3078, 3081, 3071, 3084, 3085, 3087, 3089, 3091,
+     3094, 3095, 3096, 3097, 3100, 3101, 3103, 3104, 3102, 3106,
+     3108, 3110, 3111, 3116, 3118, 3119, 3120, 3123, 3125, 3124,
+     3130, 3134, 3127, 3138, 3140, 4002, 4002, 3128, 3144, 3145,
+     3149, 3147, 3150, 3153, 3151, 4002, 3155, 3157, 3158, 3161,
+     3159, 3160, 3163, 3164, 3165, 3173, 3182, 3175, 3179, 3183,
+
+     3185, 3186, 3187, 3191, 3195, 4002, 3189, 3192, 4002, 4002,
+     3188, 3200, 3205, 3199, 3201, 3210, 3212, 4002, 3213, 3217,
+     3223, 3218, 4002, 3225, 4002, 3227, 3215, 3230, 3233, 4002,
+     4002, 4002, 3235, 3220, 3237, 3238, 3239, 3240, 3241, 3243,
+     4002, 3246, 3248, 3249, 3252, 3256, 3258, 3259, 3263, 3269,
+     3265, 3272, 3274, 4002, 4002, 3262, 3281, 3278, 3279, 3277,
+     3280, 3283, 3285, 3287, 4002, 3289, 3288, 3294, 3296, 3297,
+     3298, 3300, 3302, 4002, 3303, 3304, 3308, 3314, 3310, 3316,
+     3305, 3318, 3315, 3319, 3331, 3328, 3321, 4002, 3332, 3333,
+     4002, 3335, 3337, 3338, 4002, 3342, 4002, 4002, 3345, 4002,
+
+     4002, 3340, 3347, 3350, 3352, 3357, 3359, 3362, 3354, 3363,
+     3369, 3366, 3367, 4002, 4002, 3375, 3368, 3373, 3381, 4002,
+     4002, 3378, 3380, 3382, 3384, 3385, 3386, 3389, 3390, 3393,
+     3392, 3394, 3403, 3406, 3396, 3408, 3399, 3410, 3414, 3415,
+     3417, 4002, 3421, 3422, 3416, 4002, 3427, 3424, 4002, 3428,
+     3431, 3438, 3432, 3418, 3444, 3440, 3445, 4002, 3447, 3448,
+     4002, 3449, 4002, 4002, 4002, 3450, 3451, 3457, 4002, 3458,
+     3461, 4002, 3468, 3464, 3459, 3475, 3469, 3471, 3477, 3483,
+     3472, 3481, 4002, 3482, 3484, 3486, 3487, 3488, 3489, 3491,
+     3493, 3494, 3503, 3496, 3505, 3506, 4002, 3510, 3514, 4002,
+
+     3516, 3518, 4002, 3520, 3511, 3517, 3524, 4002, 3526, 3521,
+     3528, 3530, 3533, 3534, 3536, 3537, 3539, 3541, 3545, 4002,
+     3542, 3547, 3549, 3551, 3555, 3563, 3559, 3561, 4002, 3565,
+     3562, 4002, 3569, 3566, 3570, 3573, 3580, 3583, 3586, 3587,
+     4002, 3589, 4002, 4002, 4002, 3590, 4002, 3594, 3595, 3596,
+     3597, 3599, 3600, 4002, 4002, 3602, 3604, 3607, 4002, 3601,
+     3608, 3613, 3611, 3614, 3615, 3619, 3620, 3624, 3625, 4002,
+     4002, 3626, 4002, 3632, 3640, 3643, 4002, 4002, 4002, 3642,
+     4002, 3644, 4002, 3650, 3634, 3651, 4002, 3654, 3655, 4002,
+     3656, 3627, 3657, 3660, 3662, 3663, 3664, 3666, 3667, 3671,
+
+     3672, 3673, 3679, 4002, 4002, 3683, 4002, 3685, 4002, 3686,
+     3691, 4002, 3617, 3693, 3687, 3697, 4002, 4002, 3572, 3680,
+     3698, 3699, 3700, 3703, 3701, 4002, 4002, 4002, 3705, 4002,
+     3706, 3707, 3709, 4002, 3711, 3713, 3714, 3716, 3715, 3718,
+     3720, 3724, 3729, 3730, 3737, 3741, 3742, 3745, 3732, 3738,
+     3751, 3748, 3755, 4002, 3749, 4002, 4002, 3752, 3761, 3763,
+     3759, 3765, 3760, 4002, 3766, 3767, 3768, 3769, 3770, 3772,
+     3783, 3774, 3775, 3785, 3787, 3791, 3784, 3799, 3798, 3795,
+     3800, 3801, 3809, 3805, 3808, 4002, 3806, 3807, 3810, 3812,
+     3813, 3817, 3815, 3827, 3830, 3818, 3832, 3816, 3837, 3833,
+
+     3838, 3841, 3842, 3843, 4002, 3844, 3846, 3848, 3850, 3852,
+     3854, 3855, 3856, 3859, 3861, 3864, 3866, 3870, 4002, 3871,
+     4002, 4002, 3875, 3872, 3878, 3882, 3884, 4002, 4002, 4002,
+     3910, 3917, 3924, 3931, 3938,   94, 3945, 3952, 3959, 3966,
+     3973, 3980, 3987, 3994
     } ;
 
-static yyconst flex_int16_t yy_def[2025] =
+static yyconst flex_int16_t yy_def[2045] =
     {   0,
-     2010,    1, 2011, 2011, 2012, 2012, 2013, 2013, 2014, 2014,
-     2015, 2015, 2010, 2016, 2010, 2010, 2010, 2010, 2017, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2018, 2010, 2010, 2010, 2018, 2019, 2010, 2010, 2010, 2019,
-     2020, 2010, 2010, 2010, 2010, 2020, 2021, 2010, 2010, 2010,
-     2021, 2022, 2010, 2023, 2010, 2022, 2022, 2016, 2016, 2010,
-     2024, 2017, 2024, 2017, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2018,
-     2018, 2019, 2019, 2020, 2020, 2010, 2021, 2021, 2022, 2022,
-     2023, 2023, 2022, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2022, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2022, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2022, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2022,
-
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2010, 2010,
-     2016, 2010, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2022, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2022, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2010, 2016,
-     2016, 2016, 2010, 2016, 2010, 2016, 2016, 2010, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2010,
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2010, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2010, 2016, 2010, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2010, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2010, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2010, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2010, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2010, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2010, 2016, 2010, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2010, 2010, 2016, 2016, 2016, 2016, 2016, 2010, 2010, 2010,
-
-     2016, 2010, 2016, 2010, 2010, 2016, 2016, 2010, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2010, 2016, 2010, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2010, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-
-     2010, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2010, 2010, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2010, 2016, 2016, 2016, 2010, 2016, 2010, 2016, 2010,
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2010, 2016, 2016, 2016, 2016, 2010,
-
-     2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2010, 2016, 2016, 2016, 2010, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016,
-     2010, 2016, 2010, 2010, 2010, 2016, 2016, 2016, 2010, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2010,
-     2016, 2016, 2010, 2016, 2016, 2016, 2016, 2010, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2010, 2016, 2010, 2010, 2010, 2016, 2010, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2010, 2016, 2016, 2016, 2010, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010,
-     2010, 2016, 2010, 2016, 2016, 2016, 2010, 2010, 2010, 2016,
-     2010, 2016, 2010, 2016, 2016, 2016, 2010, 2016, 2016, 2010,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2010, 2016, 2010, 2016, 2010, 2016,
-     2016, 2010, 2016, 2016, 2016, 2016, 2010, 2010, 2016, 2016,
-
-     2016, 2016, 2016, 2016, 2016, 2010, 2010, 2010, 2016, 2010,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2010, 2010, 2016, 2016, 2016,
-     2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2010, 2016, 2016, 2016, 2016, 2016,
-     2016, 2016, 2016, 2016, 2016, 2016, 2016, 2016, 2010, 2016,
-
-     2010, 2010, 2016, 2016, 2016, 2016, 2016, 2010, 2010,    0,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-     2010, 2010, 2010, 2010
+     2030,    1, 2031, 2031, 2032, 2032, 2033, 2033, 2034, 2034,
+     2035, 2035, 2030, 2036, 2030, 2030, 2030, 2030, 2037, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2038, 2030, 2030, 2030, 2038, 2039, 2030, 2030, 2030, 2039,
+     2040, 2030, 2030, 2030, 2030, 2040, 2041, 2030, 2030, 2030,
+     2041, 2042, 2030, 2043, 2030, 2042, 2042, 2036, 2036, 2030,
+     2044, 2037, 2044, 2037, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2038,
+     2038, 2039, 2039, 2040, 2040, 2030, 2041, 2041, 2042, 2042,
+     2043, 2043, 2042, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2042, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2042, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2042, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2042, 2036, 2036, 2036, 2036, 2036, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2030, 2030, 2036, 2030, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2042,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2042, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2036, 2030, 2036, 2036, 2036,
+     2030, 2036, 2030, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2030, 2030,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2030, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036,
+     2036, 2030, 2036, 2030, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2030, 2036,
+
+     2036, 2036, 2036, 2036, 2030, 2036, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2030, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2030, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+
+     2036, 2036, 2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036,
+     2036, 2036, 2030, 2030, 2030, 2036, 2030, 2036, 2030, 2030,
+     2036, 2036, 2030, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2030,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2030, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2030, 2036, 2030, 2036, 2036, 2036, 2036, 2030,
+     2030, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2030, 2036, 2036, 2036, 2030, 2036, 2030, 2030, 2036, 2030,
+
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036, 2036, 2030,
+     2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2030, 2036, 2036, 2036, 2030, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2030, 2036, 2030, 2030, 2030, 2036, 2036, 2036, 2030, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2030,
+
+     2036, 2036, 2030, 2036, 2036, 2036, 2036, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2030, 2036, 2030, 2030, 2030, 2036, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2030, 2036, 2036, 2036, 2030, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030,
+     2030, 2036, 2030, 2036, 2036, 2036, 2030, 2030, 2030, 2036,
+     2030, 2036, 2030, 2036, 2036, 2036, 2030, 2036, 2036, 2030,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2030, 2030, 2036, 2030, 2036, 2030, 2036,
+     2036, 2030, 2036, 2036, 2036, 2036, 2030, 2030, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2030, 2030, 2036, 2030,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2030, 2030, 2036, 2036, 2036,
+     2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036,
+
+     2036, 2036, 2036, 2036, 2030, 2036, 2036, 2036, 2036, 2036,
+     2036, 2036, 2036, 2036, 2036, 2036, 2036, 2036, 2030, 2036,
+     2030, 2030, 2036, 2036, 2036, 2036, 2036, 2030, 2030,    0,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030
     } ;
 
-static yyconst flex_uint16_t yy_nxt[4010] =
+static yyconst flex_uint16_t yy_nxt[4042] =
     {   0,
        14,   15,   16,   17,   18,   19,   18,   14,   14,   14,
        14,   18,   20,   21,   14,   22,   23,   24,   25,   14,
@@ -1116,7 +1122,7 @@ static yyconst flex_uint16_t yy_nxt[4010] =
        49,   70,   45,   47,   48,   71,   50,   49,   58,   59,
        60,   69,   69,   50,   52,   53,   54,   55,   61,   18,
        58,   59,   60,  130,  130,   56,   52,   53,   54,   55,
-       61,   18,   69,  106,  236,   75,   76,   56,   15,   16,
+       61,   18,   69,  106,  237,   75,   76,   56,   15,   16,
        17,   63,   64,   65,   68,   68,   69,   68,   68,   66,
 
        68,   97,   69,   77,   69,   68,   86,  144,   67,   15,
@@ -1141,417 +1147,421 @@ static yyconst flex_uint16_t yy_nxt[4010] =
       169,  170,  179,   69,   69,   69,   69,   69,   69,   69,
       180,  178,  177,  182,  174,   69,   69,  181,  183,  186,
 
-       69,   69,   69,   69,  194,  188,  185,  184,   69,  189,
-       69,   69,  198,   69,  187,   69,  193,   69,   69,  200,
-       69,  190,  192,   69,  197,  199,   69,  195,  196,   69,
-       69,  205,   69,  202,   69,  207,  203,   69,  208,  201,
-      130,  130,  210,  134,  204,  134,  134,  136,  134,  214,
-      209,   69,  206,  137,  137,  139,  212,  139,  139,   73,
-      139,   73,   73,  140,   73,   69,  211,  213,   69,   69,
-      142,   69,   69,  215,   69,  220,   69,   69,   69,  223,
-       69,  221,  222,  219,  217,  224,  225,  216,   69,   69,
-       69,  218,   69,  232,  234,  233,   69,   69,   69,   69,
-
-       69,  235,  237,   69,  238,   69,   69,   69,  226,   69,
-       69,  239,  244,  227,   69,  240,   69,  241,  228,  245,
-      242,  243,  251,  229,  301,   69,  246,  252,   69,  230,
-      231,  247,   69,   69,  253,  254,  250,  256,   69,  259,
-       69,   69,   69,  248,   69,  249,  255,  257,   69,  258,
-      261,  262,   69,  260,  264,   69,   69,   69,   69,  263,
-       69,   69,   69,  265,   69,   69,  267,   69,   69,   69,
-      269,   69,  271,   69,  274,   69,  276,  270,  266,  279,
-      272,   69,   69,  268,   69,   69,   69,  281,  273,  282,
-       69,  277,  278,  275,  283,  280,   69,  286,  287,   69,
-
-       69,  289,  285,   69,  140,  284,   69,   69,   69,  290,
-       69,   69,  296,   69,   69,  298,  293,   69,  295,  297,
-       69,  288,   69,  292,   69,  135,  291,  294,  299,  300,
-      302,   69,   69,   69,  304,  305,   69,  306,  307,   69,
-      308,   69,   69,  309,   69,   69,   69,   69,  310,  303,
-      312,   69,  315,  317,  314,  313,   69,   69,   69,  311,
-      316,   69,  318,   69,  320,   69,   69,   69,  319,   69,
-       69,  325,   69,   69,   69,  326,  321,   69,  328,   69,
-      324,   69,  330,  322,   69,  333,   69,  323,   69,  334,
-       69,  327,   69,   69,   69,  329,  332,  331,   69,  133,
-
-      335,  336,  340,   69,   69,  344,  345,  346,   69,  337,
-      338,  342,  339,   69,   69,  341,  343,  347,   69,   69,
-       69,  353,   69,   69,   69,  355,   69,  351,  354,  352,
-      348,   69,   69,  349,  350,   69,  357,  360,   69,   69,
-       69,  356,   69,   69,  358,  362,   69,   69,  363,  365,
-       69,  366,  372,  367,  364,  359,   69,   69,  361,  371,
-       69,  373,   69,  368,   69,   69,  369,   69,  370,   69,
-      379,   69,  391,  374,  140,   69,  392,   69,   69,  377,
-      389,  375,  376,  378,  390,  381,  380,   69,   69,  382,
-      383,  397,   69,   69,   69,  393,   69,  394,   69,  384,
-
-       69,  385,  386,  387,   69,  401,  388,  395,  396,   69,
-      403,   69,   69,  400,  399,   69,  398,  407,   69,  402,
-       69,   69,   69,  405,   69,  409,  406,  410,  411,  404,
-       69,   69,   69,   69,  408,  416,   69,   69,   69,   69,
-      413,  412,  417,  418,   69,   69,  415,  414,   69,   69,
-      424,  420,   69,  421,  419,  427,  425,  423,  426,   69,
-       69,   69,   69,   69,   69,   69,  422,  429,  430,   69,
-      431,   69,  433,   69,  434,   69,  435,   69,  436,  437,
-      428,   69,  432,   69,   69,  438,   69,  442,  440,   69,
-       69,  444,   69,  443,  439,  441,   69,  445,   69,  447,
-
-       69,  448,   69,   69,   69,   69,   69,   69,   69,  458,
-       69,  450,   69,  451,   69,   69,   69,  446,  453,   69,
-      460,  459,   69,  449,  457,  452,  454,  456,  455,  462,
-      461,  463,   69,  465,   69,   69,   69,  466,  467,   69,
-       69,   69,   69,  469,   69,   69,  471,   69,   69,   69,
-       69,  485,  483,   69,  464,  470,  468,   69,  472,   69,
-      487,  482,  484,  473,   69,  474,   69,  480,  481,   69,
-      475,   69,  476,  486,   69,  488,   69,  489,   69,   69,
-      477,  490,   69,  478,  492,   69,  491,  495,  496,   69,
-      479,   69,  140,  494,  501,  499,  500,  493,   69,   69,
-
-       69,   69,  131,   69,  497,   69,  498,  506,   69,   69,
-      502,  505,   69,   69,  504,  508,  510,  507,  503,   69,
-       69,  509,   69,   69,  512,  513,  516,  511,   69,   69,
-      517,   69,  519,   69,  520,   69,  522,   69,  521,  514,
-       69,  518,  515,   69,  523,   69,  524,   69,   69,   69,
-      525,   69,  526,  528,   69,  529,   69,  533,  530,  527,
-       69,  531,   69,   69,   69,   69,   69,   69,  532,  534,
-      536,   69,  540,   69,   69,  537,   69,  535,  542,  538,
-      545,  543,   69,  539,  541,   69,   69,   69,  544,  547,
-       69,  546,  550,   69,  548,   69,   69,   69,  551,   69,
-
-       69,  557,  554,   69,   69,   69,   69,   69,  559,  553,
-      558,  552,  556,   69,   69,  555,  549,  560,  561,   69,
-      564,  562,   69,  566,  637,   69,   69,  565,   69,  567,
-       69,   69,  569,  563,   69,  568,  570,   69,  573,   69,
-       69,   69,   69,   69,  571,  575,  577,  572,  574,  578,
-       69,  580,   69,  579,   69,   69,   69,  582,  584,   69,
-      576,   69,   69,   69,   69,  581,   69,   69,  589,   69,
-       69,  583,   69,   69,   69,  590,   69,  585,   69,  586,
-      595,  587,  591,  588,   69,   69,   69,  592,  594,  593,
-      599,  596,   69,  597,   69,  598,   69,  603,   69,   69,
-
-      602,  601,   69,  600,   69,   69,  605,  606,   69,  608,
-       69,  604,  607,  609,   69,   69,   69,   69,  140,   69,
-       69,  611,  616,  615,  612,   69,  614,   69,  610,  617,
-      613,   69,  619,  622,   69,   69,  621,   69,   69,  624,
-      620,  618,   69,  627,   69,   69,   69,   69,   69,  625,
-       69,   69,  628,  642,  623,   69,  641,  639,   69,  638,
-      626,   69,  636,  629,   69,  640,  140,   69,   69,  650,
-       69,  630,   69,  653,  654,   69,   69,  631,   69,  656,
-       69,  632,  662,  655,  633,  651,   69,   69,  658,   69,
-       69,  634,  660,  652,  635,   69,  643,  644,   69,  645,
-
-       69,  657,  646,  659,   69,  661,   69,  647,   69,  664,
-       69,   69,  668,  648,  649,   69,  663,   69,  667,   69,
-       69,  674,   69,   69,  675,  138,  665,  666,  673,   69,
-      669,  670,  672,  676,   69,   69,   69,  671,   69,  677,
-      678,   69,   69,  679,   69,   69,   69,  685,   69,  680,
-      682,  683,   69,  688,   69,   69,   69,   69,   69,   69,
-      681,  686,  687,   69,   69,  684,  690,  692,  691,   69,
-      693,   69,  694,   69,  689,   69,  697,  699,  695,  700,
-       69,   69,   69,   69,  698,   69,   69,  702,   69,   69,
-       69,   69,   69,  696,  708,   69,  136,  707,   69,   69,
-
-      711,   69,  701,   69,  703,  704,   69,  714,  705,  706,
-      709,  712,  713,  718,  710,  715,   69,  719,   69,   69,
-      717,   69,   69,  716,   69,  720,   69,   69,   69,  726,
-      727,  724,   69,   69,   69,   69,  722,  728,  721,   69,
-      731,  733,   69,   69,  723,   69,  730,   69,  725,   69,
-      729,  735,  140,  737,   69,   69,   69,   69,  135,  732,
-       69,  734,  736,   69,  748,   69,   69,   69,   69,  749,
-      740,   69,  752,  738,   69,  750,  754,  741,   69,  739,
-       69,  753,  757,  742,   69,  743,   69,   69,  755,  744,
-       69,  745,  751,   69,   69,  759,  746,   69,  756,  761,
-
-      762,  747,  758,   69,  941,  760,   69,  766,   69,  765,
-       69,  764,   69,   69,  763,  767,   69,   69,  768,   69,
-      773,   69,  776,  769,  774,  770,  778,  775,   69,  777,
-       69,   69,   69,  782,   69,   69,  771,  784,  779,  783,
-       69,   69,   69,  772,  785,  780,   69,   69,  788,   69,
-       69,  781,   69,   69,  789,   69,   69,   69,   69,  786,
-      787,  791,  796,   69,  792,  790,  793,  794,   69,   69,
-       69,   69,  802,   69,   69,  795,   69,   69,   69,  800,
-      801,   69,  798,  797,  133,   69,  806,  812,   69,  799,
-      807,   69,  803,  805,  804,  811,  808,  809,   69,  810,
-
-       69,   69,  814,   69,   69,  816,  815,   69,  817,   69,
-       69,   69,  818,   69,   69,   69,   69,  813,  823,   69,
-       69,   69,   69,  820,  819,  826,  821,  827,   69,   69,
-       69,  828,  825,  822,  829,  824,  831,  830,  832,   69,
-       69,   69,   69,   69,  835,   69,   69,  834,  840,  833,
-       69,   69,   69,   69,   69,  841,  842,  844,   69,  839,
-      836,   69,  837,  847,   69,  838,  848,   69,   69,  845,
-      843,   69,  850,  846,  851,   69,   69,   69,   69,  849,
-      855,   69,   69,   69,   69,   69,   69,   69,   69,   69,
-      854,  853,  857,  864,  131,  852,  876,   69,   69,  856,
-
-       69,  858,  861,  865,  862,  860,   69,  863,   69,   69,
-      859,  866,   69,   69,  867,   69,   69,   69,   69,  872,
-      870,   69,   69,   69,  873,   69,  868,  869,   69,   69,
-      881,  871,   69,  874,  879,   69,  877,  882,   69,   69,
-      875,  878,  883,   69,   69,  880,  885,   69,   69,   69,
-       69,   69,  884,  887,  888,  890,   69,  886,   69,   69,
-      892,   69,   69,   69,   69,   69,  889,  891,  893,  897,
-      895,   69,   69,  894,   69,  898,  896,   69,  902,   69,
-      906,   69,   69,  899,   69,   69,  900,   69,  905,  901,
-      908,   69,  903,  912,  904,  907,  910,  913,   69,  911,
-
-       69,   69,   69,   69,  909,   69,  917,   69,  920,   69,
-      921,  919,   69,   69,   69,  915,  916,  922,   69,  914,
-      918,   69,   69,  923,   69,  926,  924,  925,   69,   69,
-       69,  931,  929,  932,  928,   69,   69,  927,   69,   69,
-      933,   69,  940,  934,   69,   69,   69,   69,  930,   69,
-      943,   69,   69,   69,   69,  942,  946,  947,  935,  951,
-      944,  948,   69,  936,   69,  937,   69,  938,  949,  939,
-      945,   69,  950,   69,   69,  953,  957,   69,  952,  956,
-       69,  959,   69,   69,   69,   69,  960,  963,   69,  954,
-      961,   69,  965,   69,   69,  958,   69,   69,  955,  966,
-
-      968,   69,   69,  962,   69,  971,   69,   69,   69,  970,
-       69,  964,  972,   69,  973,  976,  975,  967,   69,   69,
-      978,  979,  969,   69,  974,   69,   69,  981,  980,   69,
-       69,  977,   69,   69,  985,   69,   69,   69,  982,  986,
-      989,   69,   69,   69,  984,   69,   69,   69,   69,  983,
-       69,  995,   69,   69,   69,  990,  987,   69,  993,  999,
-      988,  991,  992,  996,   69,  994, 1000,   69,   69, 1002,
-      998,   69,   69,  997, 1004,   69, 1001,   69, 1005,   69,
-     1006, 1011,   69, 1007, 1008, 1010, 1009, 1003,   69,   69,
-       69,   69,   69,   69,   69,   69,   69,   69, 1016, 1012,
-
-     1019,   69,   69,   69,   69,   69,   69,   69, 1013,   69,
-     1015,   69, 1017, 1033, 1022, 1018, 1021, 1014, 1023, 1020,
-     1024, 1025, 1026,   69,   69,   69,   69, 1030, 1027,   69,
-     1029, 1028, 1034,   69, 1036, 1031, 1037,   69, 1035,   69,
-       69,   69,   69, 1038, 1032,   69, 1039, 1040,   69,   69,
-       69,   69,   69, 1041, 1045, 1043, 1044, 1047,   69, 1042,
-     1049, 1048,   69,   69, 1050,   69,   69,   69,   69,   69,
-       69, 1046, 1058,   69,   69,   69, 1057,   69, 1051,   69,
-       69,   69, 1052,   69, 1066, 1053, 1054, 2010, 1056, 1063,
-       69,   69, 1059, 1060, 1055, 1069,   69,   69, 1061, 1062,
-
-     1067,   69, 1064, 1068,   69, 1065, 1070,   69, 1071,   69,
-       69,   69,   69, 1075, 1079,   69,   69, 1076, 1073,   69,
-     1072, 1080,   69, 1074,   69,   69, 1081, 2010, 1084,   69,
-     1077,   69, 1078,   69, 1085,   69, 1087, 1082,   69, 1088,
-     1089, 1090,   69, 1086, 1083,   69, 1091,   69,   69,   69,
-       69, 1094, 1093,   69, 1096,   69,   69,   69, 1100,   69,
-       69, 1098,   69,   69, 1092,   69, 1101,   69, 1095, 1097,
-       69, 1103, 1099,   69,   69,   69, 1105, 1106,   69, 1108,
-     1102, 1109,   69,   69, 1112, 1104, 1107,   69,   69,   69,
-       69,   69, 1111, 1110, 1113,   69,   69, 1118, 1120, 1116,
-
-       69, 1119,   69,   69, 1122, 1124,   69, 1114, 1115,   69,
-       69, 1117,   69,   69,   69, 1128, 1123,   69, 1126,   69,
-     1121,   69,   69,   69, 2010, 1131, 1136, 1134, 1132, 1125,
-       69, 1129,   69,   69,   69, 1135,   69, 1127, 1137, 1139,
-     1133, 1130, 1140,   69, 1141,   69,   69,   69, 1138, 1145,
-       69, 1147, 1142,   69,   69, 1146,   69,   69, 1150,   69,
-       69,   69, 1149,   69, 1143, 1151, 1144,   69,   69,   69,
-     1158,   69,   69,   69,   69,   69, 1148,   69,   69, 1152,
-       69, 1156, 1155, 1153, 1157, 1163,   69, 1154, 1161,   69,
-       69,   69, 1159, 1160, 1165,   69,   69,   69, 1162,   69,
-
-     1164,   69, 1167, 1173, 1176, 1166, 1168, 1170,   69, 1169,
-       69, 1171, 1174,   69, 1175,   69, 1172,   69, 1180, 1179,
-       69,   69, 1177, 1184, 1178, 1185,   69,   69,   69, 1181,
-     1183,   69, 1182,   69,   69,   69,   69,   69,   69,   69,
-     1194,   69, 2010,   69, 1187,   69,   69, 1186, 1189, 1191,
-       69, 1188, 1190,   69, 1196, 1197, 1193, 1195,   69, 1198,
-     1192, 1202, 1200, 1203, 1204, 1201,   69, 1206,   69,   69,
-       69, 1205,   69, 1199, 1209, 1207,   69,   69,   69,   69,
-     1211,   69,   69,   69,   69,   69, 1212, 1218,   69, 1210,
-     1208, 1214,   69,   69, 1215, 1221,   69, 1213,   69,   69,
-
-     1216, 1219, 1223, 1217, 1224,   69, 1220,   69,   69,   69,
-     1225,   69, 1226, 1222, 1230,   69,   69, 1227,   69,   69,
-       69,   69, 1236,   69,   69, 1232, 1229,   69,   69, 2010,
-     1231, 1233, 1228, 1234, 1239, 1237, 1240,   69,   69, 1235,
-       69, 1241, 1238, 1242,   69, 1243,   69, 1245,   69,   69,
-       69,   69,   69,   69,   69, 1244, 1247,   69,   69, 1248,
-       69, 1246, 1251, 1252, 1249, 1256,   69, 1257, 1250,   69,
-       69,   69,   69, 1261,   69, 1255, 1253,   69, 1254, 1263,
-       69,   69, 1265,   69,   69,   69,   69, 1267, 1266, 1259,
-     1258, 1260,   69,   69, 1269, 1271, 1268, 1262,   69,   69,
-
-       69,   69, 1264, 1270, 1273,   69,   69, 1274, 1275,   69,
-       69, 1272, 1282,   69,   69, 1284,   69,   69, 1280, 1285,
-       69, 1276, 1277, 1278,   69, 1288,   69, 1289, 1279,   69,
-     1281,   69, 1290,   69, 1283,   69, 1293, 1287, 1286, 1294,
-       69,   69, 1296,   69,   69,   69,   69,   69,   69, 1291,
-     1295,   69, 1298,   69, 1301, 1292, 1299,   69, 1305, 1297,
-       69,   69, 1304,   69, 1308, 1309,   69, 1303, 1307,   69,
-       69, 1311, 1300,   69, 1302, 1310,   69,   69,   69,   69,
-     1306,   69, 1312,   69, 1316,   69,   69, 1319,   69,   69,
-     1315,   69,   69,   69, 2010,   69, 1323, 1313, 1314, 1324,
-
-       69, 1317,   69, 1320, 1325,   69, 1322,   69, 1321, 1326,
-       69, 1318, 1333, 1327, 1329,   69,   69,   69, 1328, 1331,
-     1335, 1330, 1334,   69, 1336,   69, 1337, 1332,   69, 1340,
-       69,   69,   69,   69,   69,   69, 1345, 1342,   69,   69,
-     1339,   69, 1338, 1347, 1341,   69,   69, 1343,   69, 1349,
-     2010, 1348,   69, 1350,   69, 1344, 1351,   69, 1352,   69,
-     1346,   69,   69,   69,   69, 1353, 1360, 1354, 1355,   69,
-     1356, 1357,   69,   69, 1358, 1359, 1362,   69,   69,   69,
-       69,   69,   69,   69, 1367, 1361,   69, 1369, 1364,   69,
-       69, 1368,   69,   69, 1371,   69,   69, 1370, 1363, 1365,
-
-       69, 1366, 1376,   69, 1374, 1372, 1377, 1373,   69, 1375,
-     1380, 1378,   69,   69, 1382,   69,   69,   69, 1383, 1384,
-       69,   69, 1379,   69, 1385,   69, 1387,   69,   69, 1381,
-       69,   69, 1388,   69,   69,   69,   69,   69,   69, 1400,
-     1390, 1386, 1391, 1392, 1395,   69,   69,   69, 1389, 1394,
-     1399,   69, 1402,   69,   69, 1397, 1398, 1396, 1403, 1393,
-     1406,   69, 1404,   69, 1401,   69,   69,   69, 1405, 1409,
-     1408, 1410,   69,   69,   69, 1414,   69, 1411,   69,   69,
-       69, 1415,   69,   69, 1420,   69, 1417,   69, 1421, 1407,
-       69, 1412, 1416,   69, 1413, 1424,   69, 1419,   69, 2010,
-
-       69, 1418,   69, 1425, 1426, 1422,   69,   69, 1427, 1430,
-     1431,   69,   69, 1423,   69, 1428,   69,   69, 1429,   69,
-       69, 1432, 1434,   69, 1435,   69, 1433,   69,   69, 1436,
-       69, 1440,   69,   69, 1441, 1445,   69,   69, 1447,   69,
-     1437, 1438, 1444, 1439,   69, 1442, 1446,   69,   69,   69,
-     1452, 1449,   69, 1450, 1453,   69,   69, 1443, 1456,   69,
-     1454,   69, 1451, 1448, 1458,   69,   69, 1459,   69,   69,
-     1457,   69, 1462,   69, 1464,   69, 1455,   69, 1463,   69,
-     1460,   69,   69,   69, 1466,   69,   69, 1461, 1469, 1472,
-       69,   69,   69,   69,   69, 1473, 1465, 1468, 1475,   69,
-
-       69,   69, 1471, 1470, 1467,   69,   69, 1474,   69,   69,
-       69,   69, 1485,   69,   69,   69,   69, 1486, 1477, 1478,
-     1476, 1487, 1483,   69, 1479, 1481,   69, 1490, 1489, 1480,
-     1482, 1493, 1484, 1491,   69, 1492,   69, 1488,   69,   69,
-     1495,   69, 1498,   69, 1499,   69, 1500,   69,   69,   69,
-     1496, 1494,   69, 1497, 1502,   69, 1504,   69, 1505,   69,
-       69, 1508,   69,   69,   69, 1507,   69, 1501, 1506,   69,
-     1503, 1510,   69,   69,   69, 1512, 1513,   69, 1514, 1516,
-       69,   69, 1509, 1517, 1511, 1520,   69,   69,   69, 1518,
-       69,   69,   69, 1515,   69, 1524, 1525,   69, 1527,   69,
-
-     1519,   69, 1529,   69,   69, 1523,   69, 1521,   69,   69,
-       69, 1522, 1530, 1526, 1532,   69, 1531,   69, 1528,   69,
-       69, 1534, 1536,   69, 1537, 1538,   69,   69, 1542, 1539,
-       69, 1533, 1540,   69, 1543,   69, 1535,   69, 1546,   69,
-     1541, 1547,   69, 1548, 1545,   69,   69, 1544,   69,   69,
-       69, 1549, 1555,   69,   69,   69,   69, 1553, 1556, 1550,
-     1552, 1551, 1554, 1559,   69, 1560,   69, 1558,   69, 1562,
-     1561,   69,   69,   69, 1557,   69, 1566,   69,   69,   69,
-       69, 1567, 1568, 1563, 1569,   69, 1564,   69,   69,   69,
-       69,   69, 1565, 1570, 1574,   69, 1576, 1577, 1571,   69,
-
-     1572, 1573,   69,   69,   69, 1578,   69, 1581, 1580, 1575,
-       69, 1579,   69,   69, 1582, 1583,   69, 1585, 1584,   69,
-       69, 1588, 1586, 1589,   69,   69,   69, 1592,   69, 1593,
-       69, 1591, 1594,   69, 1595,   69, 1587,   69,   69,   69,
-       69,   69,   69, 1590, 1598, 1601,   69,   69,   69, 1603,
-       69, 1596, 2010, 1600,   69, 1607, 1602, 1605,   69, 1599,
-     1597, 1606,   69,   69,   69, 1608, 1604, 1611,   69, 1610,
-     1612,   69, 1609, 1613,   69,   69,   69,   69, 1616,   69,
-       69,   69,   69,   69, 1622,   69,   69, 1614, 1620,   69,
-       69, 1617, 1618, 1619, 1615, 1623,   69,   69,   69,   69,
-
-     1629,   69, 1621,   69,   69, 2010,   69, 1635,   69, 1626,
-     1625, 1633, 1628, 1630,   69, 1624,   69,   69,   69, 1631,
-       69, 1627, 1634, 1636,   69, 1632,   69, 1637,   69,   69,
-       69,   69, 1645,   69, 1638,   69, 1639, 1642, 1640,   69,
-     1641, 1646,   69,   69, 1647,   69, 1649,   69, 1644, 1643,
-       69, 1648,   69, 1655,   69, 1656,   69,   69, 1650,   69,
-       69,   69,   69, 1651,   69, 1652, 1653, 1660,   69,   69,
-       69, 1654, 1658, 1663, 1657,   69,   69, 1664, 1659, 1665,
-       69, 1661,   69, 1668, 1662, 1669,   69,   69, 1666, 1672,
-       69,   69,   69,   69,   69, 1673, 1667, 1670, 1675, 1676,
-
-       69, 1678,   69,   69,   69, 1671, 1677, 1674, 1680,   69,
-     1681,   69,   69, 1682,   69,   69,   69,   69,   69,   69,
-       69, 1686, 1679, 1687, 1685,   69, 1683, 1684, 1689,   69,
-     1691,   69,   69, 2010, 1690,   69, 1688, 1692, 1694,   69,
-     1695,   69, 1696,   69, 1693, 1698,   69,   69, 1697, 1713,
-       69, 1699, 1700,   69, 1701,   69, 1703,   69,   69,   69,
-     1702,   69, 1704,   69, 1705,   69, 1706,   69,   69,   69,
-       69,   69, 1709, 1708, 1711, 1712,   69,   69, 1707,   69,
-     1710,   69, 1714,   69, 1717, 1715, 1716,   69, 1718,   69,
-     1722,   69,   69,   69,   69, 1726,   69,   69,   69,   69,
-
-     1719,   69, 1724, 1728, 1729,   69, 1730, 1720, 1721, 1725,
-       69, 1723,   69,   69, 1733, 1731, 1727, 1734,   69,   69,
-       69, 1732,   69, 1737, 1738,   69,   69, 1740, 1741,   69,
-       69,   69, 1735, 1742, 1736, 1743,   69, 1744,   69,   69,
-     1739, 1745,   69, 1748, 1749,   69,   69, 1751,   69, 1746,
-     1750, 1752,   69, 1747,   69,   69,   69, 1755,   69,   69,
-       69, 1754,   69, 1756, 1759,   69,   69, 1763,   69,   69,
-       69,   69,   69, 1757, 1758,   69, 1767, 1753, 1760, 1765,
-     1762,   69, 1768,   69, 1769, 1761,   69,   69, 1764, 1766,
-       69,   69, 1771,   69,   69, 1777,   69,   69, 1773,   69,
-
-     1774,   69, 1770,   69, 1778, 1780,   69,   69, 1781,   69,
-     1772, 1783,   69, 1775, 1776, 1779,   69, 1782, 1785, 1787,
-     1784,   69, 1786, 1788,   69,   69,   69,   69,   69,   69,
-     1795,   69, 2010,   69, 1789, 1790, 1791, 1792, 1794,   69,
-     1796,   69, 1798,   69, 1797, 1799, 1800,   69,   69, 1803,
-       69,   69, 1801, 1793,   69,   69, 1805, 1807,   69, 1809,
-       69,   69,   69,   69, 1812,   69,   69,   69, 1802,   69,
-       69, 1804,   69, 1806, 1814,   69, 1815,   69, 1811, 1813,
-     1810,   69, 1819, 1808,   69, 1816, 1821,   69,   69, 1818,
-       69, 1817, 1823,   69, 1824,   69, 1825,   69,   69,   69,
-
-       69, 1820,   69, 1822, 1826, 1827,   69,   69, 1828,   69,
-     1831, 1834,   69, 1829, 1832, 1835,   69, 1830,   69,   69,
-     1839,   69,   69,   69, 1833, 1840, 1836,   69, 1841,   69,
-     1837,   69,   69,   69, 1844, 1842, 1847, 1845,   69, 1838,
-       69,   69, 1850,   69, 1851,   69, 1853,   69,   69, 1843,
-       69,   69, 1846, 1854, 1915, 1848, 1849,   69,   69, 1852,
-     1857,   69, 1856, 1860, 1855, 1858,   69, 1859,   69, 1861,
-       69,   69, 1862, 1863,   69,   69,   69,   69, 1867,   69,
-       69,   69,   69, 1870,   69, 1868, 1866,   69,   69, 1864,
-     1869,   69, 1871,   69,   69,   69, 1865,   69, 1874,   69,
-
-       69, 1872, 1876, 1875,   69,   69,   69,   69, 1873, 1911,
-     1882, 1884,   69, 1877,   69, 1878, 1895, 1879, 1880, 1885,
-       69, 1887,   69,   69,   69, 1881, 1883, 1886, 1888, 1889,
-       69,   69, 1890, 1892,   69,   69,   69,   69, 1896, 1897,
-       69, 1898,   69,   69,   69, 1891,   69,   69, 1899, 2010,
-     1893,   69,   69,   69, 1894, 1916, 1903, 1904, 1906,   69,
-       69, 1901, 1907,   69, 1908,   69,   69,   69, 1902, 1900,
-     1910,   69, 1905,   69, 1912, 1909, 1914,   69,   69,   69,
-       69,   69, 1913,   69, 1918,   69,   69,   69, 1922,   69,
-     1923,   69, 1917,   69,   69,   69,   69, 1921,   69, 1919,
-
-       69, 1920, 1926, 1925,   69, 2010, 1927, 1924, 1934,   69,
-       69, 1930,   69, 1928, 1929, 1932, 1936,   69,   69, 1935,
-     1937,   69,   69, 1931, 1933,   69, 1942, 1938,   69,   69,
-     1939,   69,   69, 1941, 1944,   69, 1947, 1940, 1948,   69,
-       69,   69, 1943,   69, 1945,   69,   69,   69,   69,   69,
-       69, 1946,   69, 1949,   69,   69, 1960, 1957, 1950, 1951,
-     1952, 1954, 1955,   69,   69,   69, 1953,   69, 1958, 1956,
-     1961,   69, 1962, 1959, 1965,   69, 1963, 1966,   69,   69,
-       69,   69, 1967, 1964, 1970,   69,   69,   69,   69,   69,
-       69, 1973,   69,   69, 1977,   69,   69,   69,   69, 1968,
-
-     1969, 1972, 1978, 1982, 1971, 1976, 1974,   69, 1980, 1975,
-       69, 1981,   69,   69, 1979, 1984, 1985,   69,   69, 1983,
-     1986,   69,   69,   69,   69, 1987,   69, 1989,   69, 1991,
-       69, 1992,   69, 1995,   69,   69,   69, 1998, 1999,   69,
-     1988,   69, 1990, 2001,   69, 2002,   69, 1993, 2000, 1994,
-       69,   69,   69, 1996, 1997,   69, 2004, 2003,   69, 2010,
-     2005, 2008,   69, 2009,   69, 2010, 2010, 2010, 2010, 2010,
-     2010, 2006, 2010, 2010, 2010, 2010, 2010, 2007,   41,   41,
-       41,   41,   41,   41,   41,   46,   46,   46,   46,   46,
-       46,   46,   51,   51,   51,   51,   51,   51,   51,   57,
-
-       57,   57,   57,   57,   57,   57,   62,   62,   62,   62,
-       62,   62,   62,   72,   72, 2010,   72,   72,   72,   72,
-      130,  130, 2010, 2010, 2010,  130,  130,  132,  132, 2010,
-     2010,  132, 2010,  132,  134, 2010, 2010, 2010, 2010, 2010,
-      134,  137,  137, 2010, 2010, 2010,  137,  137,  139, 2010,
-     2010, 2010, 2010, 2010,  139,  141,  141, 2010,  141,  141,
-      141,  141,   73,   73, 2010,   73,   73,   73,   73,   13,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010
+       69,   69,   69,   69,   69,  188,  185,  184,  196,  189,
+       69,   69,   69,   69,  187,  199,   69,  193,  195,   69,
+       69,  190,  192,  194,  198,  200,   69,  201,  197,   69,
+      203,  206,  204,   69,   69,   69,   69,   69,  208,  283,
+      205,  211,  130,  130,  137,  137,  209,  202,  140,  136,
+       69,  212,  207,  210,  134,  213,  134,  134,  139,  134,
+      139,  139,   73,  139,   73,   73,  214,   73,   69,   69,
+       69,   69,   69,  142,   69,   69,  221,  216,   69,  224,
+       69,   69,  222,  215,  220,  223,  225,  218,  226,  217,
+       69,   69,   69,  233,  219,   69,   69,   69,   69,   69,
+
+       69,  235,  236,  238,   69,  239,   69,   69,   69,   69,
+      227,   69,  240,  135,  234,  228,  264,   69,  242,  241,
+      229,  243,  245,   69,   69,  230,  244,  251,  246,   69,
+      247,  231,  232,  253,  255,  248,   69,  254,   69,   69,
+      252,  257,   69,   69,  133,  256,   69,  249,  260,  250,
+       69,  258,  262,   69,  263,  261,   69,   69,   69,   69,
+       69,   69,   69,   69,  259,   69,  266,  268,   69,  265,
+      272,  270,   69,   69,   69,   69,   69,  278,  267,   69,
+      276,  271,   69,   69,  269,  281,   69,  273,   69,  274,
+       69,  285,   69,  284,  275,  289,   69,   69,  277,  282,
+
+       69,  279,  280,  291,  287,   69,  288,  286,   69,   69,
+      140,  292,   69,   69,  298,   69,   69,   69,  290,   69,
+      294,  297,  295,   69,   69,  300,   69,  131,  293,  299,
+       69,  296,  301,  302,  304,   69,  309,  303,  306,   69,
+       69,  305,  307,   69,  308,   69,  310,   69,  311,   69,
+       69,   69,   69,  314,   69,  317,  315,   69,   69,  319,
+       69,   69,  320,  316,   69,  312,  313,   69,  322,   69,
+       69,  318,  321,   69,   69,   69,   69,  327,  323,   69,
+       69,   69,  328,   69,  330,   69,  332,  324,  326,  335,
+       69,  325,  329,   69,   69,   69,  336,   69,   69,  331,
+
+       69,  333,  334,   69,  348,   69,  338,  337,   69,  342,
+       69,   69,  346,  347,  339,  340,  344,  341,   69,  343,
+      345,  349,   69,   69,   69,  355,   69,   69,  350,   69,
+       69,  351,  353,  354,  356,   69,  357,  352,   69,   69,
+       69,  363,  358,  359,   69,   69,   69,   69,   69,   69,
+      361,  360,  365,  366,   69,  362,   69,   69,   69,  367,
+      368,  375,  369,  370,  364,  374,   69,   69,   69,   69,
+      371,  377,  376,  372,   69,  373,   69,  382,   69,  378,
+       69,  394,   69,  140,  380,  395,   69,   69,  379,   69,
+      381,  393,  384,  383,   69,  392,  385,  386,   69,   69,
+
+      400,   69,  398,   69,  396,   69,  387,   69,  388,  389,
+      390,   69,  401,  391,   69,  406,  404,  397,  403,  399,
+       69,  402,  405,   69,   69,  410,   69,   69,  413,  414,
+       69,   69,  412,   69,  407,  408,   69,   69,  409,   69,
+       69,   69,  411,  419,  420,   69,   69,   69,   69,  421,
+       69,  418,  416,  415,   69,  417,   69,  424,   69,  426,
+      428,  423,   69,  427,  422,   69,   69,  430,   69,  433,
+      425,  429,   69,   69,  432,  431,   69,  436,  434,   69,
+       69,   69,  439,  440,  437,   69,  435,   69,   69,  441,
+       69,   69,   69,  438,   69,  443,   69,  447,  446,   69,
+
+      444,   69,   69,  450,  445,   69,  448,   69,  442,   69,
+      451,   69,   69,   69,   69,  453,   69,  461,   69,   69,
+      449,  454,   69,   69,   69,  456,  452,  462,  463,   69,
+      466,  455,  457,  460,  458,   69,  459,  465,  464,  467,
+       69,   69,   69,   69,   69,   69,  470,  473,   69,   69,
+       69,   69,   69,   69,  469,  475,   69,   69,   69,   69,
+      489,   69,  468,  474,  471,  476,  472,  503,  486,  140,
+      477,   69,  478,  484,   69,  485,  487,  479,  490,  480,
+       69,   69,   69,  491,  492,   69,  488,  481,   69,  493,
+      482,   69,   69,  497,   69,  494,   69,  483,   69,  499,
+
+      496,   69,  140,  495,  505,  500,  504,   69,   69,   69,
+       69,  138,   69,   69,  498,   69,  502,  501,   69,  506,
+      509,  510,   69,  508,  512,  511,  507,  513,   69,   69,
+       69,  514,   69,  515,   69,  516,  520,  517,   69,   69,
+      521,   69,  523,   69,  524,   69,  526,   69,  518,  525,
+       69,  519,  522,  528,   69,  527,   69,   69,   69,  529,
+       69,  533,  530,   69,  532,   69,   69,  534,   69,  531,
+      535,  537,   69,   69,   69,   69,   69,  538,   69,   69,
+      544,  540,   69,   69,   69,  551,  541,  539,  536,  546,
+      542,   69,  543,  545,  549,   69,  547,  548,   69,   69,
+
+       69,   69,  552,   69,  550,  554,  555,   69,   69,   69,
+       69,  561,   69,  558,   69,   69,   69,  563,  562,  556,
+      557,   69,  560,   69,  553,  559,  564,   69,  136,  568,
+       69,   69,  565,  566,   69,  567,  569,  570,   69,   69,
+       69,  571,   69,  573,  572,   69,  577,  574,   69,  578,
+       69,   69,   69,  575,   69,  580,   69,   69,  576,  579,
+      583,  582,   69,  585,  584,   69,   69,   69,  587,  589,
+      581,   69,   69,   69,   69,   69,  588,   69,   69,  586,
+       69,  594,   69,  600,  595,   69,   69,   69,   69,  590,
+      591,   69,  592,  596,  593,   69,  603,   69,  597,   69,
+
+      599,  598,  605,  604,   69,  601,  602,   69,   69,  606,
+       69,   69,   69,  607,   69,   69,  611,  610,   69,  612,
+      613,  609,   69,  614,   69,   69,  608,   69,   69,  616,
+      140,  621,  615,  617,   69,  620,  619,   69,  622,  618,
+       69,  624,   69,  627,   69,   69,   69,   69,   69,  625,
+      629,  626,   69,   69,  632,   69,   69,  630,  623,   69,
+      633,   69,   69,   69,  628,  631,   69,   69,  644,   69,
+      645,  634,  643,  642,   69,  646,  641,  647,   69,  135,
+      635,   69,   69,  655,   69,  656,  636,  658,  659,   69,
+      637,   69,   69,  638,  657,   69,  661,   69,  660,  667,
+
+      639,   69,  663,  640,   69,  648,  649,  662,  650,   69,
+       69,  651,   69,  665,  664,   69,  652,  666,   69,   69,
+       69,   69,  653,  654,   69,  673,   69,  668,  672,   69,
+       69,   69,   69,  679,   69,   69,  678,  669,  682,  670,
+      671,  674,  680,  675,  677,  681,   69,   69,  676,   69,
+       69,   69,  683,   69,   69,   69,   69,  684,   69,  685,
+      687,  688,  690,   69,   69,  693,   69,  691,   69,   69,
+       69,  686,  692,   69,   69,  689,  697,  695,  696,  698,
+       69,   69,  700,   69,   69,  694,   69,   69,   69,  703,
+      705,  706,   69,   69,  699,   69,   69,  704,  701,   69,
+
+      708,   69,   69,   69,   69,   69,   69,  710,  702,  714,
+      713,   69,  717,   69,  707,   69,   69,  709,  721,   69,
+       69,  711,  712,  716,  715,  718,  720,  724,  725,  719,
+      723,  722,   69,   69,   69,   69,   69,   69,  726,   69,
+       69,  732,  730,   69,  733,   69,  734,  737,  728,   69,
+       69,   69,   69,   69,  727,   69,  729,  739,   69,   69,
+      731,  741,  140,  735,  736,   69,   69,   69,   69,  743,
+      738,  740,   69,  754,  742,   69,   69,   69,   69,  745,
+      755,  746,  758,   69,   69,  744,   69,   69,  747,   69,
+      756,  760,  748,   69,  749,   69,   69,  761,  750,  759,
+
+      751,  762,  757,   69,   69,  752,   69,  763,  764,  765,
+      753,  767,   69,   69,   69,  787,  769,  772,   69,  766,
+      771,   69,   69,  773,   69,   69,  768,  770,   69,  774,
+      779,   69,   69,  785,  775,  781,  776,  780,   69,  783,
+       69,   69,   69,  782,   69,  784,  789,  777,  788,   69,
+       69,  790,   69,  791,  778,  786,   69,  794,   69,   69,
+       69,   69,   69,  792,  795,  793,   69,   69,   69,  797,
+      798,   69,   69,   69,   69,   69,  800,  796,  802,   69,
+      808,   69,  799,   69,  806,   69,  804,  801,  807,   69,
+       69,  803,   69,   69,  805,  812,   69,  813,  814,   69,
+
+      809,  810,   69,  816,  811,  815,  817,   69,   69,  820,
+       69,   69,  818,  821,   69,   69,  822,   69,   69,  823,
+      824,  828,  825,  819,   69,   69,   69,   69,  830,   69,
+      826,   69,   69,  827,   69,   69,  833,  834,   69,  839,
+       69,  836,   69,   69,  829,  832,  835,   69,  831,  838,
+       69,  840,   69,  842,  837,   69,   69,  847,   69,   69,
+       69,   69,   69,   69,  848,  841,  849,  133,   69,   69,
+      843,  846,  851,   69,  844,  853,  845,  854,  850,  852,
+      855,   69,   69,  858,   69,   69,  857,   69,  856,   69,
+       69,  862,   69,   69,   69,   69,   69,   69,   69,   69,
+
+       69,   69,  861,  860,  871,  864,  859,  131,  880,   69,
+      863,   69,  865,  868,   69,  869,  867,  872,  870,  866,
+       69,   69,   69,   69,   69,  873,  874,   69,  875,  877,
+      879,   69,   69,  883,   69,   69,   69,  876,   69,   69,
+       69,  888,  878,   69,  886,   69,  881,   69,  889,  884,
+       69,  882,  890,  892,  885,   69,   69,   69,   69,  887,
+       69,  891,  895,   69,   69,  894,   69,   69,  897,   69,
+      899,   69,   69,  893,   69,   69,  900,  896,   69,  898,
+       69,  904,   69,  902,  901,   69,  903,  905,  909,   69,
+      913,  906,   69,   69,   69,   69,   69,   69,  908,  907,
+
+      910,  912,  915,   69,   69,   69,  919,  914,  917,  911,
+      920,   69,   69,   69,   69,   69,  916,  918,   69,  924,
+      927, 1136,  926,  921,   69,   69,  922,  923,  925,   69,
+      928,   69,   69,  930,   69,   69,  929,  931,   69,  932,
+       69,  933,   69,  935,  934,   69,  938,  939,   69,   69,
+       69,   69,   69,  940,  941,   69,  936,   69,  947,  948,
+      949,   69,   69,  937,   69,   69,  950,   69,   69,   69,
+      951,   69,   69,  942,   69,   69,  953,  957,  943,   69,
+      944,  954,  945,  952,  946,  955,   69,  959,  956,  960,
+      958,   69,   69,   69,  963,  965,   69,   69,  964,   69,
+
+      961,  967,   69,   69,  969,   69,  968,  971,   69,   69,
+      962,   69,  966,  973,   69,   69,  974,  976,   69,   69,
+       69,   69,   69,   69,  970,  978,  980,   69,  981,  972,
+      979,   69,   69,   69,   69,   69,  975,  983,  986,  977,
+      984,  982,  987,   69,   69,  985,  989,   69,   69,  988,
+       69,   69,   69,  991,  993,   69,   69,  990,  996,  997,
+       69,  992,   69,   69,   69,   69,   69, 1003,   69,   69,
+       69,   69,  994,   69,  998, 1001,  995,   69, 1007, 2030,
+      999,   69, 1000, 1002, 1008,   69, 1010, 1012, 1004, 1006,
+       69, 1013,   69, 1009, 1005,   69, 1011,   69,   69, 1014,
+
+     1016, 1018,   69, 1015,   69,   69,   69,   69, 1019,   69,
+       69, 1017,   69, 1020,   69, 1024,   69,   69,   69,   69,
+     1027,   69,   69,   69, 1021,   69,   69, 1023, 1036,   69,
+     1025, 1030,   69, 1022, 1026, 1028, 1031, 1029, 1032,   69,
+     1033,   69,   69,   69, 1035, 1034, 1037, 1038,   69, 2030,
+       69, 1039, 1044, 1042, 1041, 1043, 1045,   69, 1040,   69,
+     1046,   69,   69, 1047, 1048,   69,   69,   69,   69,   69,
+     1049,   69,   69, 1055, 1052, 1057, 1050, 1056,   69, 1058,
+       69,   69,   69,   69,   69, 1053, 1051,   69,   69,   69,
+       69, 1054, 1066,   69,   69, 1065,   69,   69,   69,   69,
+
+       69, 1059, 1060, 1061,   69,   69, 1062, 1064, 1063, 1067,
+       69, 1074, 1068, 1069, 1071, 1070, 1076, 1091,   69, 1072,
+     1073, 1075, 1077,   69,   69,   69,   69,   69,   69, 1078,
+     1079,   69,   69, 1083,   69,   69, 1081, 1084, 1080, 1088,
+       69, 1082,   69,   69,   69, 1094,   69, 1089, 1090,   69,
+     1085, 1087, 1086, 1093, 1092,   69,   69, 1097,   69, 1098,
+     1096, 1095, 1099,   69,   69, 1100,   69,   69,   69,   69,
+     1103, 1102,   69,   69, 1105,   69,   69,   69, 1107, 1109,
+       69, 1110,   69, 1101,   69, 1112,   69, 1104,   69, 1106,
+       69, 1108,   69,   69, 1115, 1118,   69,   69, 1117, 1114,
+
+       69,   69, 1111,   69, 1121,   69, 1122,   69, 1113,   69,
+       69, 1116,   69, 2030, 1120, 1119,   69,   69, 1125, 1127,
+       69, 1128,   69, 1129, 1131, 1123,   69, 1124,   69,   69,
+     1126,   69, 1130,   69, 1132, 1133,   69, 1135,   69, 1137,
+       69, 1134,   69, 1143,   69, 1138, 1139, 1140,   69,   69,
+     1141, 1145,   69,   69, 1144, 1149, 1148, 1146,   69, 1150,
+       69,   69, 1142,   69,   69, 1147, 1154,   69, 1156,   69,
+       69,   69, 1155,   69,   69, 1158, 1159,   69,   69, 1151,
+       69,   69, 1152, 1160, 1153,   69, 1167,   69,   69,   69,
+       69,   69, 1157,   69, 1162,   69, 1172,   69, 1161, 1164,
+
+     1165, 1163, 1166,   69,   69,   69,   69, 1168,   69, 1170,
+     1169, 1174, 1176,   69, 1171,   69,   69, 1177,   69, 1175,
+     1178, 1183,   69, 1173, 1184,   69,   69,   69,   69, 1179,
+     1180, 1185, 1186,   69, 1187, 1181,   69,   69,   69, 1193,
+       69, 1182, 1188,   69,   69, 1189, 1190, 1192,   69, 1191,
+     1194,   69,   69, 1196,   69,   69, 1195,   69,   69, 1203,
+       69, 1197, 1198,   69,   69,   69, 1200, 2030, 1199, 1206,
+       69, 1207, 1205,   69, 1209, 1202, 1204, 1210, 1212, 1214,
+     1201,   69, 1213,   69,   69, 1208,   69,   69, 1217,   69,
+       69, 1211, 1216,   69,   69, 1218, 1220,   69,   69, 1215,
+
+       69,   69,   69, 1221,   69, 1222, 1219, 1229, 1225,   69,
+     1226, 1223,   69, 1224,   69,   69, 1227, 1232,   69,   69,
+       69,   69,   69, 1228, 1234, 1230, 1235, 1236,   69,   69,
+       69,   69, 1231, 1237,   69, 1233, 1241,   69, 1238,   69,
+       69,   69, 1239, 1244, 1247, 1240, 1243,   69, 1242,   69,
+       69,   69, 1245, 1251,   69,   69,   69, 1250, 1252, 1248,
+     1246, 1253,   69,   69,   69, 1255, 1256,   69, 1249, 1254,
+       69,   69,   69,   69,   69, 1257, 1258,   69,   69, 1259,
+       69,   69, 1262, 1263, 1260, 1267,   69, 1268, 1261,   69,
+       69,   69,   69, 1272,   69, 1266, 1264,   69, 1265, 1274,
+
+       69,   69, 1269, 1276,   69, 1277,   69, 1278, 1270, 1279,
+     1271, 1273,   69,   69, 1280, 1282,   69,   69, 1275,   69,
+       69, 1284,   69,   69, 1285, 1286,   69,   69, 1293,   69,
+       69, 1281,   69,   69,   69, 1299,   69, 1291, 1287, 1288,
+     1289, 1283,   69,   69, 1301, 1290, 1295, 1292, 1297, 1294,
+     1296,   69,   69, 1298,   69,   69, 1304, 1305,   69,   69,
+       69, 1307,   69,   69,   69,   69,   69, 1312, 1300, 1306,
+     1309,   69, 1302, 1310, 1308,   69, 1303,   69, 1316,   69,
+     1315,   69, 1319,   69, 1320, 1321,   69,   69, 1318,   69,
+       69, 1311,   69, 1314,   69, 1322,   69, 1313,   69, 1317,
+
+       69, 1323,   69, 1327,   69,   69, 1330,   69,   69,   69,
+     1326,   69, 1332,   69, 1324, 1325, 2030,   69,   69,   69,
+     1328, 1336, 1331,   69, 1335, 1337,   69, 1338, 1333,   69,
+     1329, 1345, 1334, 1339,   69, 1342,   69, 1340, 1347,   69,
+     1346,   69, 1341, 1344, 1343,   69, 1348, 1350,   69, 1353,
+     1349,   69,   69,   69,   69,   69,   69,   69, 1358, 1355,
+     1352,   69,   69,   69, 1360, 1354,   69, 1351, 1356,   69,
+       69,   69, 1363, 1362, 1361, 1364,   69, 1365,   69,   69,
+       69,   69, 1357, 1359,   69, 1367, 1366, 1369,   69, 1368,
+       69,   69, 1373,   69, 1372, 1371,   69, 1370, 1375,   69,
+
+       69,   69,   69,   69,   69, 1374,   69, 1380, 1382, 1377,
+       69, 1381,   69,   69,   69, 1384, 1376,   69, 1383, 1378,
+       69, 1379,   69, 1389,   69,   69, 1385, 1391, 1386, 1387,
+     1393, 1388,   69, 1390,   69,   69,   69, 1395,   69, 1392,
+     1396, 1397,   69,   69,   69, 1400,   69,   69,   69, 1394,
+     1398,   69,   69,   69, 1399, 1401,   69,   69,   69,   69,
+     1403,   69,   69, 1404, 1405, 1408,   69, 1412, 1402,   69,
+       69, 1407, 1413, 1416, 1415,   69, 1414, 1410, 1409, 1406,
+       69, 1411, 1419,   69, 1417,   69,   69,   69,   69, 1422,
+       69, 1421,   69, 1423, 1418, 1424,   69, 1427,   69,   69,
+
+       69,   69,   69, 1428,   69, 1433,   69,   69, 1430,   69,
+     1425, 1420, 1429,   69, 1434,   69, 1426, 1439, 1432, 1437,
+     1431,   69, 1435,   69,   69,   69, 1438,   69, 1441, 1436,
+       69, 1442, 1446,   69, 1443, 1440,   69, 1444, 1445,   69,
+       69,   69,   69,   69,   69,   69, 1449, 1450, 1447,   69,
+       69,   69, 1448,   69,   69,   69, 1451, 1455,   69, 1456,
+     1460,   69,   69, 1453, 1452, 1454,   69, 1459,   69, 1457,
+     1464, 1461, 1462,   69, 1463, 1458,   69,   69, 1467,   69,
+       69, 1465, 1468,   69, 1471,   69,   69, 1469, 1470, 1472,
+     1466, 1473,   69,   69, 1474,   69, 1477,   69, 1475, 1479,
+
+       69,   69, 1478,   69,   69,   69,   69,   69,   69, 1481,
+       69,   69, 1484, 1476, 1487,   69,   69,   69,   69,   69,
+     1483, 1488,   69, 1490,   69, 1489, 1485, 1486, 1480, 1482,
+       69,   69,   69,   69,   69, 1500,   69,   69, 1492,   69,
+     1501, 1493, 1491,   69, 2030, 1498,   69, 1494,   69, 1505,
+     1496,   69, 1502, 1497, 1495, 1499,   69, 1503,   69, 1504,
+     1506,   69, 1507,   69,   69, 1510, 1508, 1511,   69, 1509,
+     1512, 1513,   69, 1514,   69, 1515,   69, 1517,   69,   69,
+     1519,   69, 1520,   69,   69,   69,   69, 1516, 1523,   69,
+     1522, 1525,   69,   69,   69,   69,   69, 1518, 1528,   69,
+
+     1527,   69, 1529, 1521,   69, 1524, 1531,   69, 1535,   69,
+       69, 1526,   69,   69, 1533, 1532,   69, 1530, 1540,   69,
+     1539,   69,   69, 1534, 1542,   69,   69,   69, 1538,   69,
+     1536,   69, 1546, 1544,   69, 1537,   69,   69, 1547,   69,
+     1541, 1549, 1543,   69,   69,   69, 1548,   69,   69, 1553,
+     1554,   69, 1551, 1545,   69,   69, 1556,   69,   69, 1560,
+     1557, 1559, 1550, 1555, 1552,   69,   69, 1562, 1558,   69,
+     1563, 1564,   69, 1565,   69,   69,   69, 1561,   69,   69,
+       69, 1566, 1572,   69, 1570, 1567,   69, 1568, 1573, 1569,
+     1571, 1576,   69, 1577,   69,   69,   69, 1579, 1575,   69,
+
+     1574,   69,   69,   69, 1583,   69,   69,   69, 1585, 1578,
+     1584, 1580, 1586,   69,   69, 1581,   69,   69,   69, 1587,
+       69, 1582, 1591,   69, 1594,   69,   69, 1588, 1593,   69,
+       69, 1590, 1595, 1598,   69, 1597, 1589,   69,   69, 1600,
+     1592, 1596, 1599,   69,   69, 1602,   69,   69,   69, 1603,
+       69, 1605, 1606,   69,   69, 1609,   69, 1601, 1611, 1608,
+     1610,   69,   69,   69,   69, 1612, 1607,   69,   69,   69,
+       69, 1618,   69, 1604, 1615,   69, 1620,   69, 1613,   69,
+     2030,   69, 1617,   69, 1619, 1623,   69, 1616, 1626, 1614,
+       69, 1624, 1625,   69, 1622, 1621,   69,   69, 1627,   69,
+
+     1630,   69, 1631,   69, 1629, 1632,   69,   69,   69,   69,
+     1635, 1628,   69,   69,   69,   69,   69, 1641,   69, 1633,
+       69, 1639,   69,   69, 1636, 1637, 1634, 1638,   69, 1642,
+       69,   69,   69, 1648, 1640,   69,   69,   69, 1654,   69,
+       69, 1645,   69, 1644, 1649, 1647,   69, 1652, 1643, 1655,
+       69, 1653,   69, 1656, 1646, 1650,   69,   69, 1651,   69,
+     1657,   69,   69,   69, 1664,   69, 1665,   69, 1661,   69,
+       69,   69,   69,   69, 1658,   69,   69,   69, 1666, 1659,
+     1668, 1660, 1662, 1663, 1674,   69, 1669,   69, 1667, 1675,
+     1670,   69, 1672, 1671,   69,   69, 1673,   69,   69,   69,
+
+       69,   69, 1679,   69,   69, 1676, 1677,   69, 1682, 1683,
+     1684,   69,   69,   69, 1678, 1687, 1688,   69, 1680, 1681,
+     1686, 1691,   69, 1685,   69,   69, 1689,   69, 1692,   69,
+       69, 1690,   69, 1694, 1695,   69, 1697,   69, 1698,   69,
+     1693, 1700,   69, 1696, 1701,   69, 1699,   69, 1702,   69,
+       69,   69,   69,   69, 1703,   69, 1706, 1707,   69, 1705,
+       69,   69, 1704, 1709,   69, 1711, 1712, 1714,   69, 1715,
+       69,   69, 1708, 1710,   69,   69, 1718,   69, 1716, 1713,
+     1717,   69, 1719, 1720,   69, 1721,   69, 1722, 1723,   69,
+       69,   69,   69,   69, 1724,   69, 1725,   69, 1726,   69,
+
+       69,   69, 1729, 1728, 1731, 1732,   69, 1727,   69,   69,
+       69, 1730,   69, 1737,   69,   69,   69,   69, 1735, 1736,
+       69, 1734,   69, 1738, 1733, 1742,   69,   69,   69, 1746,
+       69,   69, 1745,   69, 1739, 1748, 1740, 1744, 1751, 1741,
+       69, 1743, 1749,   69,   69,   69, 1747,   69, 1750,   69,
+       69, 1754,   69, 1752,   69, 1757, 1758,   69, 1753,   69,
+     1760, 1761,   69, 1755,   69, 1756,   69, 1762, 1763,   69,
+     1764,   69, 1759, 1765,   69,   69, 1768, 1769,   69,   69,
+       69,   69, 1771, 1770, 1766,   69, 1772,   69, 1775, 1767,
+       69, 1774,   69,   69,   69, 1776,   69,   69,   69, 1779,
+
+     1783,   69,   69, 1773,   69,   69,   69, 1787,   69, 1777,
+     1778,   69, 1782, 1785, 1780,   69, 1788, 1781,   69, 1789,
+       69, 1784,   69, 1786, 1790, 1791,   69,   69,   69,   69,
+       69, 1792, 1797,   69,   69, 1794,   69, 1798, 1800,   69,
+       69, 1801, 1803,   69,   69, 1806, 1799, 1795, 1793, 1796,
+       69, 1807,   69, 1805, 1804, 1808,   69,   69, 1802,   69,
+       69,   69,   69,   69, 1815, 1809, 1810, 1814, 1811,   69,
+       69,   69, 1812,   69, 1818, 1817,   69, 1819, 1816, 1820,
+       69,   69, 1823,   69,   69, 1821, 1813,   69, 1825,   69,
+     1827, 1822, 1829,   69,   69,   69,   69, 1832,   69,   69,
+
+       69,   69, 1824,   69, 1834,   69,   69, 1826,   69, 1828,
+     1835, 1831, 1833, 1830, 1838,   69, 1841,   69,   69, 1836,
+     1839, 1843,   69,   69, 1837, 1844,   69, 1845,   69,   69,
+       69, 1847,   69,   69, 1840, 1846,   69, 1842,   69, 1851,
+       69, 1854,   69, 1848, 1855,   69,   69, 1852,   69,   69,
+     1859,   69, 1849,   69,   69, 1850, 1860,   69, 1861,   69,
+     1857,   69, 1853,   69, 1864, 1856, 1862,   69, 1865, 1858,
+     1867,   69, 1870,   69,   69,   69, 1871,   69,   69, 1863,
+     1873,   69,   69, 1874,   69,   69, 1866, 1935, 1868, 1869,
+     1876, 1877,   69, 1872, 1878,   69, 1875, 1879,   69,   69,
+
+     1881,   69,   69, 1882, 1880, 1883,   69,   69,   69,   69,
+     1887,   69,   69,   69,   69, 1890,   69, 1888, 1886,   69,
+       69, 1884, 1889,   69, 1891,   69,   69,   69, 1885,   69,
+     1894,   69,   69, 1892, 1896, 1895,   69,   69,   69,   69,
+     1893, 1931, 1902, 1904,   69, 1897,   69, 1898, 1915, 1899,
+     1900, 1905,   69, 1907,   69,   69,   69, 1901, 1903, 1906,
+     1908, 1909,   69,   69, 1910, 1912,   69,   69,   69,   69,
+     1916, 1917,   69, 1918,   69,   69,   69, 1911,   69,   69,
+     1919, 2030, 1913,   69,   69,   69, 1914, 1936, 1923, 1924,
+     1926,   69,   69, 1921, 1927,   69, 1928,   69,   69,   69,
+
+     1922, 1920, 1930,   69, 1925,   69, 1932, 1929, 1934,   69,
+       69,   69,   69,   69, 1933,   69, 1938,   69,   69,   69,
+     1942,   69, 1943,   69, 1937,   69,   69,   69,   69, 1941,
+       69, 1939,   69, 1940, 1946, 1945,   69, 2030, 1947, 1944,
+     1954,   69,   69, 1950,   69, 1948, 1949, 1952, 1956,   69,
+       69, 1955, 1957,   69,   69, 1951, 1953,   69, 1962, 1958,
+       69,   69, 1959,   69,   69, 1961, 1964,   69, 1967, 1960,
+     1968,   69,   69,   69, 1963,   69, 1965,   69,   69,   69,
+       69,   69,   69, 1966,   69, 1969,   69,   69, 1980, 1977,
+     1970, 1971, 1972, 1974, 1975,   69,   69,   69, 1973,   69,
+
+     1978, 1976, 1981,   69, 1982, 1979, 1985,   69, 1983, 1986,
+       69,   69,   69,   69, 1987, 1984, 1990,   69,   69,   69,
+       69,   69,   69, 1993,   69,   69, 1997,   69,   69,   69,
+       69, 1988, 1989, 1992, 1998, 2002, 1991, 1996, 1994,   69,
+     2000, 1995,   69, 2001,   69,   69, 1999, 2004, 2005,   69,
+       69, 2003, 2006,   69,   69,   69,   69, 2007,   69, 2009,
+       69, 2011,   69, 2012,   69, 2015,   69,   69,   69, 2018,
+     2019,   69, 2008,   69, 2010, 2021,   69, 2022,   69, 2013,
+     2020, 2014,   69,   69,   69, 2016, 2017,   69, 2024, 2023,
+       69, 2030, 2025, 2028,   69, 2029,   69, 2030, 2030, 2030,
+
+     2030, 2030, 2030, 2026, 2030, 2030, 2030, 2030, 2030, 2027,
+       41,   41,   41,   41,   41,   41,   41,   46,   46,   46,
+       46,   46,   46,   46,   51,   51,   51,   51,   51,   51,
+       51,   57,   57,   57,   57,   57,   57,   57,   62,   62,
+       62,   62,   62,   62,   62,   72,   72, 2030,   72,   72,
+       72,   72,  130,  130, 2030, 2030, 2030,  130,  130,  132,
+      132, 2030, 2030,  132, 2030,  132,  134, 2030, 2030, 2030,
+     2030, 2030,  134,  137,  137, 2030, 2030, 2030,  137,  137,
+      139, 2030, 2030, 2030, 2030, 2030,  139,  141,  141, 2030,
+      141,  141,  141,  141,   73,   73, 2030,   73,   73,   73,
+
+       73,   13, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030
     } ;
 
-static yyconst flex_int16_t yy_chk[4010] =
+static yyconst flex_int16_t yy_chk[4042] =
     {   0,
         1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
         1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
@@ -1562,7 +1572,7 @@ static yyconst flex_int16_t yy_chk[4010] =
         9,  162,   33,    6,    7,    7,    7,    7,    9,    7,
        10,   10,   10,   45,   45,    7,    8,    8,    8,    8,
        10,    8,   21,   33,  162,   21,   21,    8,   11,   11,
-       11,   11,   11,   11, 2016,   20,   29,   20,   20,   11,
+       11,   11,   11,   11, 2036,   20,   29,   20,   20,   11,
 
        20,   29,   24,   21,   75,   20,   24,   75,   11,   12,
        12,   12,   12,   12,   12,   83,   22,   22,   26,   26,
@@ -1570,7 +1580,7 @@ static yyconst flex_int16_t yy_chk[4010] =
        19,   22,   19,   19,   30,   19,   25,   83,   28,   27,
        19,   19,   23,   27,   61,   61,   27,   23,   35,   30,
        39,   23,   67,   27,   23,   27,   23,   23,   31,   31,
-       32,   32,   35,  735,   39,   32,   67,   31,   70,   39,
+       32,   32,   35,  741,   39,   32,   67,   31,   70,   39,
        36,   36,   70,   31,   76,   36,   77,   31,   76,   80,
        84,   32,   34,   38,   38,   36,   38,   34,   36,   40,
        40,   34,   79,   80,   40,   88,   77,   34,   40,   84,
@@ -1583,417 +1593,421 @@ static yyconst flex_int16_t yy_chk[4010] =
        72,   72,   86,   90,   82,   82,   91,   96,   92,   93,
        91,   94,   85,   92,   94,   95,   89,   94,   99,   97,
        95,   90,   98,   93,   97,   98,   96,  100,  101,   98,
-       94,   94,  101,  102,  103,  105,  104,  106,  107,  115,
+       94,   94,  101,  102,  103,  105,  104,  106,  107,  116,
       102,  100,   99,  104,   97,  108,  109,  103,  105,  108,
 
-      110,  111,  113,  114,  115,  110,  107,  106,  116,  110,
-      117,  118,  119,  120,  109,  122,  114,  119,  121,  121,
-      123,  111,  113,  124,  118,  120,  127,  116,  117,  125,
-      126,  125,  128,  122,  146,  126,  123,  129,  127,  121,
-      131,  131,  129,  135,  124,  135,  135,  136,  135,  146,
-      128,  144,  125,  138,  138,  140,  144,  140,  140,  141,
-      140,  141,  141,  143,  141,  147,  143,  145,  148,  149,
-      141,  150,  145,  147,  151,  152,  159,  153,  154,  154,
-      152,  152,  153,  151,  149,  155,  156,  148,  156,  160,
-      155,  150,  158,  158,  160,  159,  161,  165,  163,  164,
-
-      166,  161,  163,  168,  164,  167,  173,  169,  156,  157,
-      219,  165,  169,  157,  170,  166,  172,  167,  157,  170,
-      167,  168,  173,  157,  219,  171,  171,  174,  179,  157,
-      157,  171,  174,  175,  175,  176,  172,  177,  178,  180,
-      176,  185,  177,  171,  180,  171,  176,  178,  181,  179,
-      182,  183,  184,  181,  185,  182,  183,  186,  187,  184,
-      188,  189,  190,  186,  191,  193,  188,  192,  194,  195,
-      190,  196,  192,  198,  195,  200,  197,  191,  187,  199,
-      193,  197,  202,  189,  199,  201,  204,  201,  194,  202,
-      205,  198,  198,  196,  203,  200,  206,  206,  207,  203,
-
-      210,  208,  205,  207,  211,  204,  208,  209,  212,  209,
-      213,  218,  214,  217,  215,  216,  211,  214,  213,  215,
-      216,  207,  220,  210,  221,  134,  209,  212,  217,  218,
-      220,  222,  228,  223,  222,  223,  224,  224,  225,  226,
-      226,  225,  227,  227,  229,  232,  234,  230,  228,  221,
-      230,  231,  233,  235,  232,  231,  239,  233,  235,  229,
-      234,  236,  236,  237,  238,  240,  241,  242,  237,  238,
-      243,  243,  244,  245,  246,  244,  239,  247,  246,  249,
-      242,  248,  248,  240,  250,  251,  252,  241,  253,  252,
-      251,  245,  254,  255,  256,  247,  250,  249,  257,  132,
-
-      253,  254,  255,  259,  258,  259,  259,  260,  260,  254,
-      254,  257,  254,  262,  261,  256,  258,  261,  264,  263,
-      265,  266,  266,  267,  268,  268,  269,  264,  267,  265,
-      262,  270,  271,  262,  263,  272,  270,  273,  274,  278,
-      275,  269,  273,  276,  271,  275,  277,  279,  276,  277,
-      280,  277,  281,  278,  276,  272,  282,  281,  274,  280,
-      283,  282,  284,  279,  285,  290,  279,  287,  279,  286,
-      287,  288,  292,  283,  293,  291,  292,  292,  294,  285,
-      290,  283,  284,  286,  291,  288,  287,  289,  296,  289,
-      289,  297,  295,  298,  299,  293,  297,  294,  300,  289,
-
-      301,  289,  289,  289,  302,  301,  289,  295,  296,  304,
-      303,  305,  306,  300,  299,  303,  298,  307,  308,  302,
-      309,  311,  307,  305,  312,  309,  306,  310,  310,  304,
-      310,  313,  314,  315,  308,  315,  318,  319,  316,  317,
-      312,  311,  316,  317,  320,  322,  314,  313,  321,  324,
-      322,  319,  323,  320,  318,  325,  323,  321,  324,  326,
-      325,  327,  330,  333,  328,  329,  320,  327,  328,  332,
-      329,  331,  331,  337,  332,  340,  333,  334,  334,  335,
-      326,  336,  330,  338,  335,  336,  339,  340,  338,  341,
-      342,  342,  343,  341,  337,  339,  344,  343,  345,  345,
-
-      347,  347,  348,  349,  350,  351,  352,  355,  354,  357,
-      356,  349,  358,  350,  357,  359,  365,  344,  352,  363,
-      359,  358,  360,  348,  356,  351,  354,  355,  354,  361,
-      360,  362,  364,  363,  361,  366,  362,  364,  365,  367,
-      368,  369,  370,  367,  371,  375,  369,  373,  377,  374,
-      380,  377,  376,  378,  362,  368,  366,  376,  370,  379,
-      379,  375,  376,  371,  372,  372,  382,  373,  374,  384,
-      372,  386,  372,  378,  383,  380,  381,  381,  385,  388,
-      372,  382,  387,  372,  384,  389,  383,  387,  388,  391,
-      372,  390,  393,  386,  394,  391,  393,  385,  395,  394,
-
-      396,  397,  130,  398,  389,  400,  390,  399,  399,  402,
-      395,  398,  404,  403,  397,  401,  403,  400,  396,  405,
-      401,  402,  406,  407,  405,  406,  408,  404,  409,  416,
-      408,  408,  410,  410,  411,  411,  413,  413,  412,  407,
-      418,  409,  407,  412,  414,  414,  415,  417,  423,  419,
-      416,  415,  417,  419,  421,  420,  422,  424,  421,  418,
-      420,  422,  424,  426,  425,  428,  430,  427,  423,  425,
-      427,  429,  429,  431,  433,  427,  432,  426,  431,  427,
-      434,  432,  435,  428,  430,  434,  436,  438,  433,  436,
-      437,  435,  438,  439,  437,  440,  441,  442,  439,  443,
-
-      444,  445,  442,  450,  446,  447,  445,  521,  447,  441,
-      446,  440,  444,  449,  448,  443,  437,  448,  449,  451,
-      452,  450,  453,  454,  521,  452,  455,  453,  454,  455,
-      456,  458,  457,  451,  459,  456,  457,  457,  460,  461,
-      466,  463,  462,  460,  458,  462,  463,  459,  461,  464,
-      465,  465,  468,  464,  464,  467,  469,  467,  469,  470,
-      462,  471,  472,  473,  474,  466,  475,  476,  474,  477,
-      478,  468,  481,  479,  482,  475,   68,  470,  488,  471,
-      480,  472,  476,  473,  487,  480,  484,  477,  479,  478,
-      484,  481,  485,  482,  483,  483,  486,  488,  489,  490,
-
-      487,  486,  491,  485,  493,  492,  490,  491,  494,  493,
-      495,  489,  492,  494,  496,  497,  498,  499,  500,  501,
-      503,  496,  501,  500,  497,  502,  499,  505,  495,  502,
-      498,  504,  504,  507,  508,  509,  505,  510,  507,  509,
-      504,  503,  511,  512,  513,  514,  515,  518,  512,  510,
-      524,  525,  513,  528,  508,  527,  527,  525,  528,  524,
-      511,  526,  518,  514,  530,  526,   62,  531,  532,  530,
-      533,  515,  516,  533,  534,  534,  535,  516,  536,  536,
-      542,  516,  542,  535,  516,  531,  537,  538,  538,  540,
-      544,  516,  540,  532,  516,  529,  529,  529,  539,  529,
-
-      541,  537,  529,  539,  543,  541,  545,  529,  546,  544,
-      547,  548,  548,  529,  529,  549,  543,  550,  547,  551,
-      552,  554,  554,  553,  555,   57,  545,  546,  553,  555,
-      549,  550,  552,  556,  558,  559,  557,  551,  556,  557,
-      558,  560,  561,  559,  563,  562,  564,  565,  565,  560,
-      562,  563,  566,  568,  567,  569,  574,  571,  568,  572,
-      561,  566,  567,  576,  573,  564,  571,  573,  572,  577,
-      574,  575,  575,  578,  569,  580,  578,  580,  576,  581,
-      581,  582,  583,  584,  578,  585,  586,  583,  588,  587,
-      589,  592,  590,  577,  589,  591,   52,  588,  594,  593,
-
-      592,  595,  582,  597,  584,  585,  598,  595,  586,  587,
-      590,  593,  594,  599,  591,  596,  596,  600,  599,  602,
-      598,  601,  600,  597,  603,  601,  604,  605,  606,  606,
-      607,  604,  609,  610,  608,  607,  603,  608,  602,  612,
-      611,  613,  613,  614,  603,  611,  610,  616,  605,  617,
-      609,  615,  615,  617,  618,  619,  620,  621,   51,  612,
-      625,  614,  616,  623,  623,  624,  628,  626,  627,  624,
-      620,  629,  627,  618,  630,  625,  629,  621,  632,  619,
-      622,  628,  632,  622,  631,  622,  636,  633,  630,  622,
-      634,  622,  626,  637,  635,  634,  622,  638,  631,  635,
-
-      636,  622,  633,  639,  813,  634,  813,  640,  643,  639,
-      646,  638,  640,  645,  637,  641,  641,  642,  642,  644,
-      643,  648,  646,  642,  644,  642,  648,  645,  647,  647,
-      649,  650,  651,  652,  652,  653,  642,  655,  649,  653,
-      657,  656,  655,  642,  656,  650,  661,  658,  659,  660,
-      664,  651,  662,  659,  660,  663,  666,  667,  665,  657,
-      658,  662,  667,  668,  663,  661,  664,  665,  669,  670,
-      671,  672,  673,  675,  684,  666,  676,  673,  677,  671,
-      672,  678,  669,  668,   46,  679,  678,  684,  681,  670,
-      679,  680,  675,  677,  676,  683,  680,  681,  682,  682,
-
-      683,  686,  687,  691,  688,  688,  687,  687,  688,  689,
-      690,  692,  689,  693,  695,  694,  696,  686,  694,  699,
-      697,  702,  698,  691,  690,  697,  692,  698,  701,  706,
-      703,  699,  696,  693,  701,  695,  703,  702,  704,  704,
-      705,  707,  708,  709,  707,  710,  711,  706,  712,  705,
-      713,  714,  716,  712,  717,  713,  714,  717,  718,  711,
-      708,  719,  709,  720,  722,  710,  721,  723,  720,  718,
-      716,  721,  723,  719,  724,  724,  725,  726,  727,  722,
-      728,  729,  731,  730,  728,  732,  734,  738,  736,  737,
-      727,  726,  730,  739,   41,  725,  751,  751,  739,  729,
-
-      747,  731,  736,  740,  737,  734,  741,  738,  740,  742,
-      732,  741,  743,  744,  742,  745,  746,  748,  749,  747,
-      745,  750,  752,  753,  748,  755,  743,  744,  754,  756,
-      756,  746,  757,  749,  754,  758,  752,  757,  759,  761,
-      750,  753,  758,  760,  762,  755,  760,  764,  766,  763,
-      765,  771,  759,  762,  763,  765,  768,  761,  770,  769,
-      768,  772,  773,  774,  775,  776,  764,  766,  769,  773,
-      771,  777,  778,  770,  780,  774,  772,  779,  778,  781,
-      783,  784,  785,  775,  786,  783,  776,  788,  781,  777,
-      785,  787,  779,  789,  780,  784,  787,  789,  789,  788,
-
-      790,  791,  795,  792,  786,  793,  793,  794,  796,  797,
-      797,  795,  798,  796,  799,  791,  792,  798,  805,  790,
-      794,  800,  801,  799,  802,  802,  800,  801,  803,  804,
-      806,  807,  805,  808,  804,  809,  807,  803,  808,  810,
-      809,  812,  812,  810,  814,  817,  816,  819,  806,  811,
-      816,  823,  818,  822,  821,  814,  819,  820,  811,  823,
-      817,  820,  820,  811,  824,  811,  825,  811,  821,  811,
-      818,  826,  822,  827,  828,  825,  829,  829,  824,  828,
-      830,  831,  831,  833,  835,  834,  833,  836,  836,  826,
-      834,  837,  838,  838,  839,  830,  840,  844,  827,  839,
-
-      841,  841,  842,  835,  843,  844,  847,  845,  849,  843,
-      848,  837,  845,  846,  846,  849,  848,  840,  850,  860,
-      852,  853,  842,  854,  847,  852,  853,  855,  854,  856,
-      857,  850,  855,  858,  859,  859,  861,  862,  856,  860,
-      863,  864,  865,  869,  858,  863,  866,  867,  870,  857,
-      868,  868,  871,  874,  872,  864,  861,   14,  866,  872,
-      862,  864,  865,  869,  875,  867,  873,  873,  877,  875,
-      871,  879,  882,  870,  878,  880,  874,  884,  878,  878,
-      879,  884,  881,  880,  881,  883,  882,  877,  885,  886,
-      883,  887,  888,  889,  890,  891,  892,  894,  889,  885,
-
-      892,  893,  895,  899,  896,  897,  898,  906,  886,  903,
-      888,  907,  890,  906,  895,  891,  894,  887,  896,  893,
-      897,  898,  899,  900,  901,  902,  904,  903,  900,  905,
-      902,  901,  907,  908,  909,  904,  910,  917,  908,  909,
-      919,  910,  911,  911,  905,  912,  912,  914,  914,  915,
-      916,  918,  920,  915,  919,  917,  918,  921,  923,  916,
-      922,  921,  921,  924,  922,  922,  925,  926,  927,  928,
-      929,  920,  930,  931,  932,  935,  929,  930,  923,  933,
-      934,  936,  924,  938,  938,  925,  926,   13,  928,  935,
-      937,  940,  931,  932,  927,  941,  941,  939,  933,  934,
-
-      939,  942,  936,  940,  943,  937,  942,  944,  943,  945,
-      946,  947,  949,  947,  950,  950,  951,  947,  945,  953,
-      944,  951,  952,  946,  954,  958,  952,    0,  955,  972,
-      947,  960,  949,  955,  956,  956,  960,  953,  961,  961,
-      962,  964,  964,  958,  954,  962,  966,  966,  967,  969,
-      970,  970,  969,  971,  972,  973,  974,  975,  976,  976,
-      978,  974,  977,  980,  967,  981,  977,  983,  971,  973,
-      979,  979,  975,  982,  984,  987,  981,  982,  988,  984,
-      978,  986,  986,  989,  989,  980,  983,  991,  992,  990,
-      993,  994,  988,  987,  990,  995,  996,  995,  997,  993,
-
-      998,  996, 1001,  997,  999, 1002, 1002,  991,  992,  999,
-     1003,  994, 1004, 1006, 1007, 1007, 1001, 1013, 1004, 1008,
-      998, 1009, 1010, 1015,    0, 1010, 1013, 1011, 1010, 1003,
-     1012, 1008, 1011, 1014, 1019, 1012, 1016, 1006, 1014, 1016,
-     1010, 1009, 1017, 1018, 1018, 1020, 1021, 1017, 1015, 1022,
-     1023, 1024, 1019, 1025, 1022, 1023, 1024, 1026, 1027, 1027,
-     1028, 1029, 1026, 1030, 1020, 1028, 1021, 1031, 1032, 1033,
-     1035, 1034, 1036, 1037, 1038, 1035, 1025, 1039, 1051, 1029,
-     1042, 1033, 1032, 1030, 1034, 1041, 1041, 1031, 1038, 1043,
-     1044, 1047, 1036, 1037, 1043, 1045, 1049, 1046, 1039, 1058,
-
-     1042, 1054, 1045, 1051, 1054, 1044, 1046, 1047, 1056, 1046,
-     1057, 1049, 1052, 1052, 1053, 1053, 1049, 1055, 1058, 1057,
-     1059, 1060, 1055, 1061, 1056, 1062, 1062, 1063, 1061, 1059,
-     1060, 1064, 1059, 1065, 1066, 1070, 1067, 1068, 1071, 1072,
-     1072, 1073,    0, 1078, 1064, 1074, 1081, 1063, 1066, 1068,
-     1075, 1065, 1067, 1077, 1074, 1075, 1071, 1073, 1076, 1076,
-     1070, 1078, 1077, 1080, 1081, 1077, 1082, 1083, 1080, 1084,
-     1086, 1082, 1083, 1076, 1087, 1084, 1088, 1089, 1092, 1087,
-     1089, 1094, 1095, 1093, 1096, 1098, 1089, 1097, 1099, 1088,
-     1086, 1093, 1097, 1102, 1094, 1101, 1101, 1092, 1103, 1104,
-
-     1095, 1098, 1103, 1096, 1104, 1105, 1099, 1106, 1107, 1108,
-     1105, 1110, 1106, 1102, 1111, 1111, 1112, 1107, 1113, 1114,
-     1116, 1115, 1117, 1118, 1119, 1113, 1110, 1117, 1120,    0,
-     1112, 1114, 1108, 1115, 1120, 1118, 1121, 1121, 1122, 1116,
-     1125, 1122, 1119, 1123, 1123, 1125, 1126, 1127, 1127, 1128,
-     1130, 1129, 1131, 1132, 1134, 1126, 1129, 1133, 1135, 1130,
-     1136, 1128, 1133, 1134, 1131, 1137, 1137, 1138, 1132, 1139,
-     1140, 1141, 1138, 1142, 1142, 1136, 1134, 1143, 1135, 1144,
-     1144, 1145, 1146, 1146, 1147, 1152, 1154, 1148, 1147, 1140,
-     1139, 1141, 1148, 1149, 1151, 1153, 1149, 1143, 1159, 1151,
-
-     1153, 1168, 1145, 1152, 1155, 1155, 1156, 1156, 1157, 1158,
-     1160, 1154, 1161, 1157, 1162, 1164, 1166, 1161, 1159, 1164,
-     1164, 1158, 1158, 1158, 1165, 1167, 1167, 1168, 1158, 1170,
-     1160, 1169, 1169, 1171, 1162, 1172, 1172, 1166, 1165, 1173,
-     1173, 1176, 1177, 1177, 1178, 1179, 1181, 1180, 1183, 1170,
-     1176, 1184, 1179, 1182, 1182, 1171, 1180, 1186, 1187, 1178,
-     1188, 1189, 1186, 1187, 1190, 1191, 1193, 1184, 1189, 1190,
-     1191, 1193, 1181, 1194, 1183, 1192, 1192, 1195, 1197, 1196,
-     1188, 1198, 1194, 1199, 1198, 1200, 1201, 1201, 1202, 1203,
-     1197, 1204, 1205, 1206,    0, 1207, 1205, 1195, 1196, 1206,
-
-     1211, 1199, 1209, 1202, 1207, 1212, 1204, 1213, 1203, 1208,
-     1208, 1200, 1214, 1209, 1210, 1210, 1218, 1214, 1209, 1212,
-     1216, 1211, 1215, 1215, 1216, 1216, 1217, 1213, 1219, 1220,
-     1225, 1217, 1222, 1223, 1220, 1224, 1226, 1223, 1227, 1229,
-     1219, 1226, 1218, 1228, 1222, 1235, 1231, 1224, 1228, 1231,
-        0, 1229, 1232, 1232, 1244, 1225, 1233, 1233, 1234, 1234,
-     1227, 1236, 1239, 1237, 1238, 1235, 1244, 1236, 1237, 1241,
-     1238, 1239, 1243, 1246, 1241, 1243, 1247, 1247, 1248, 1249,
-     1252, 1250, 1251, 1255, 1252, 1246, 1253, 1254, 1249, 1258,
-     1264, 1253, 1254, 1257, 1257, 1259, 1266, 1255, 1248, 1250,
-
-     1260, 1251, 1262, 1262, 1259, 1257, 1264, 1258, 1267, 1260,
-     1268, 1266, 1269, 1270, 1270, 1268, 1271, 1274, 1271, 1272,
-     1272, 1275, 1267, 1277, 1274, 1276, 1276, 1278, 1279, 1269,
-     1280, 1281, 1277, 1282, 1283, 1286, 1287, 1290, 1284, 1290,
-     1279, 1275, 1280, 1281, 1284, 1289, 1291, 1292, 1278, 1283,
-     1289, 1293, 1292, 1295, 1297, 1286, 1287, 1284, 1293, 1282,
-     1298, 1298, 1295, 1299, 1291, 1300, 1302, 1301, 1297, 1301,
-     1300, 1302, 1303, 1304, 1305, 1306, 1307, 1303, 1309, 1308,
-     1306, 1307, 1311, 1312, 1313, 1313, 1309, 1314, 1314, 1299,
-     1315, 1304, 1308, 1316, 1305, 1317, 1320, 1312, 1318,    0,
-
-     1317, 1311, 1319, 1318, 1319, 1315, 1321, 1322, 1320, 1322,
-     1323, 1323, 1324, 1316, 1325, 1321, 1330, 1327, 1321, 1328,
-     1331, 1324, 1327, 1332, 1328, 1335, 1325, 1333, 1337, 1330,
-     1338, 1335, 1339, 1340, 1337, 1341, 1341, 1342, 1343, 1343,
-     1331, 1332, 1340, 1333, 1344, 1338, 1342, 1345, 1346, 1347,
-     1348, 1345, 1349, 1346, 1348, 1348, 1350, 1339, 1353, 1353,
-     1349, 1354, 1347, 1344, 1355, 1355, 1356, 1356, 1357, 1358,
-     1354, 1363, 1359, 1360, 1361, 1361, 1350, 1359, 1360, 1364,
-     1357, 1365, 1366, 1367, 1364, 1368, 1369, 1358, 1367, 1370,
-     1370, 1371, 1372, 1373, 1374, 1371, 1363, 1366, 1373, 1375,
-
-     1377, 1378, 1369, 1368, 1365, 1379, 1380, 1372, 1387, 1381,
-     1382, 1383, 1385, 1385, 1386, 1389, 1393, 1386, 1375, 1377,
-     1374, 1387, 1382, 1388, 1378, 1380, 1390, 1390, 1389, 1379,
-     1381, 1393, 1383, 1391, 1391, 1392, 1392, 1388, 1394, 1395,
-     1395, 1396, 1397, 1397, 1398, 1398, 1399, 1399, 1400, 1405,
-     1396, 1394, 1402, 1396, 1401, 1401, 1403, 1403, 1404, 1404,
-     1407, 1408, 1408, 1409, 1416, 1407, 1411, 1400, 1405, 1412,
-     1402, 1410, 1410, 1413, 1417, 1412, 1413, 1414, 1414, 1415,
-     1415, 1418, 1409, 1416, 1411, 1419, 1419, 1421, 1422, 1417,
-     1423, 1424, 1428, 1414, 1426, 1424, 1425, 1425, 1427, 1427,
-
-     1418, 1429, 1429, 1430, 1432, 1423, 1434, 1421, 1435, 1433,
-     1439, 1422, 1430, 1426, 1433, 1436, 1432, 1437, 1428, 1438,
-     1440, 1435, 1437, 1441, 1438, 1439, 1442, 1446, 1443, 1440,
-     1444, 1434, 1441, 1443, 1444, 1448, 1436, 1449, 1449, 1452,
-     1442, 1450, 1451, 1451, 1448, 1454, 1450, 1446, 1455, 1459,
-     1457, 1451, 1459, 1460, 1461, 1462, 1466, 1455, 1460, 1452,
-     1454, 1452, 1457, 1463, 1463, 1465, 1465, 1462, 1467, 1467,
-     1466, 1468, 1469, 1470, 1461, 1471, 1471, 1473, 1477, 1474,
-     1478, 1473, 1474, 1468, 1475, 1475, 1469, 1479, 1476, 1481,
-     1480, 1482, 1470, 1476, 1480, 1486, 1482, 1483, 1477, 1484,
-
-     1478, 1479, 1483, 1487, 1493, 1484, 1489, 1488, 1487, 1481,
-     1496, 1486, 1488, 1490, 1489, 1490, 1494, 1494, 1493, 1495,
-     1497, 1497, 1495, 1501, 1501, 1503, 1506, 1507, 1507, 1509,
-     1509, 1506, 1511, 1512, 1512, 1513, 1496, 1511, 1514, 1515,
-     1517, 1518, 1524, 1503, 1515, 1519, 1519, 1521, 1523, 1522,
-     1528, 1513,    0, 1518, 1522, 1528, 1521, 1524, 1530, 1517,
-     1514, 1526, 1526, 1529, 1531, 1529, 1523, 1532, 1532, 1531,
-     1533, 1533, 1530, 1534, 1534, 1535, 1536, 1537, 1537, 1538,
-     1539, 1540, 1542, 1541, 1543, 1543, 1544, 1535, 1541, 1545,
-     1546, 1538, 1539, 1540, 1536, 1544, 1547, 1548, 1549, 1550,
-
-     1550, 1552, 1542, 1553, 1551,    0, 1554, 1556, 1556, 1547,
-     1546, 1554, 1549, 1551, 1561, 1545, 1563, 1555, 1562, 1552,
-     1564, 1548, 1555, 1557, 1557, 1553, 1558, 1558, 1565, 1566,
-     1567, 1568, 1568, 1572, 1561, 1571, 1562, 1565, 1563, 1573,
-     1564, 1570, 1570, 1574, 1571, 1575, 1573, 1576, 1567, 1566,
-     1577, 1572, 1578, 1579, 1579, 1580, 1581, 1582, 1574, 1583,
-     1580, 1585, 1584, 1575, 1586, 1576, 1577, 1584, 1587, 1591,
-     1590, 1578, 1582, 1587, 1581, 1588, 1594, 1588, 1583, 1590,
-     1595, 1585, 1597, 1595, 1586, 1596, 1596, 1598, 1591, 1599,
-     1599, 1600, 1602, 1605, 1603, 1600, 1594, 1597, 1603, 1604,
-
-     1604, 1607, 1607, 1608, 1615, 1598, 1605, 1602, 1609, 1609,
-     1610, 1610, 1614, 1614, 1616, 1617, 1618, 1620, 1619, 1623,
-     1621, 1618, 1608, 1619, 1617, 1624, 1615, 1616, 1621, 1626,
-     1624, 1649, 1625,    0, 1623, 1629, 1620, 1625, 1627, 1627,
-     1628, 1628, 1629, 1630, 1626, 1631, 1632, 1637, 1630, 1649,
-     1631, 1632, 1633, 1633, 1634, 1634, 1638, 1641, 1639, 1640,
-     1637, 1638, 1639, 1642, 1640, 1643, 1641, 1644, 1645, 1650,
-     1648, 1647, 1644, 1643, 1647, 1648, 1651, 1652, 1642, 1654,
-     1645, 1656, 1650, 1653, 1653, 1651, 1652, 1657, 1654, 1658,
-     1659, 1659, 1660, 1661, 1662, 1663, 1663, 1664, 1667, 1665,
-
-     1656, 1671, 1661, 1665, 1666, 1666, 1667, 1657, 1658, 1662,
-     1668, 1660, 1670, 1673, 1671, 1668, 1664, 1673, 1674, 1675,
-     1682, 1670, 1677, 1677, 1679, 1679, 1683, 1683, 1684, 1684,
-     1685, 1689, 1674, 1685, 1675, 1686, 1686, 1687, 1687, 1690,
-     1682, 1688, 1688, 1691, 1692, 1692, 1693, 1696, 1691, 1689,
-     1693, 1696, 1696, 1690, 1697, 1698, 1703, 1699, 1702, 1704,
-     1705, 1698, 1699, 1702, 1704, 1706, 1707, 1708, 1708, 1709,
-     1711, 1710, 1718, 1703, 1703, 1712, 1712, 1697, 1705, 1710,
-     1707, 1713, 1713, 1714, 1714, 1706, 1715, 1716, 1709, 1711,
-     1717, 1719, 1716, 1720, 1721, 1723, 1723, 1725, 1718, 1730,
-
-     1719, 1724, 1715, 1728, 1724, 1727, 1727, 1734, 1728, 1733,
-     1717, 1731, 1731, 1720, 1721, 1725, 1732, 1730, 1733, 1735,
-     1732, 1736, 1734, 1735, 1735, 1740, 1737, 1739, 1742, 1747,
-     1747, 1748,    0, 1746, 1736, 1737, 1739, 1740, 1746, 1750,
-     1748, 1751, 1751, 1754, 1750, 1751, 1753, 1753, 1755, 1756,
-     1757, 1758, 1754, 1742, 1756, 1759, 1758, 1760, 1761, 1762,
-     1762, 1764, 1760, 1765, 1766, 1766, 1767, 1769, 1755, 1770,
-     1768, 1757, 1771, 1759, 1768, 1774, 1769, 1773, 1765, 1767,
-     1764, 1772, 1773, 1761, 1776, 1770, 1775, 1775, 1785, 1772,
-     1786, 1771, 1778, 1778, 1779, 1779, 1781, 1781, 1787, 1782,
-
-     1790, 1774, 1791, 1776, 1782, 1784, 1784, 1794, 1785, 1789,
-     1789, 1792, 1792, 1786, 1790, 1793, 1793, 1787, 1795, 1796,
-     1797, 1797, 1798, 1801, 1791, 1798, 1794, 1799, 1799, 1802,
-     1795, 1803, 1804, 1805, 1803, 1801, 1806, 1804, 1807, 1796,
-     1811, 1806, 1808, 1808, 1810, 1810, 1813, 1813, 1814, 1802,
-     1815, 1899, 1805, 1814, 1899, 1807, 1807, 1816, 1820, 1811,
-     1817, 1817, 1816, 1820, 1815, 1818, 1818, 1819, 1819, 1822,
-     1822, 1826, 1826, 1828, 1828, 1829, 1830, 1831, 1832, 1832,
-     1833, 1840, 1836, 1837, 1837, 1833, 1831, 1838, 1841, 1829,
-     1836, 1843, 1838, 1842, 1844, 1845, 1830, 1893, 1842, 1846,
-
-     1847, 1840, 1844, 1843, 1848, 1849, 1852, 1872, 1841, 1893,
-     1849, 1854, 1854, 1845, 1865, 1846, 1872, 1847, 1847, 1855,
-     1855, 1860, 1860, 1856, 1862, 1848, 1852, 1856, 1862, 1864,
-     1864, 1866, 1865, 1868, 1868, 1869, 1871, 1873, 1873, 1874,
-     1874, 1875, 1875, 1876, 1877, 1866, 1878, 1879, 1876,    0,
-     1869, 1880, 1881, 1882, 1871, 1900, 1880, 1881, 1883, 1883,
-     1900, 1878, 1886, 1886, 1888, 1888, 1890, 1895, 1879, 1877,
-     1891, 1891, 1882, 1894, 1894, 1890, 1896, 1896, 1901, 1902,
-     1903, 1905, 1895, 1904, 1902, 1909, 1911, 1912, 1909, 1913,
-     1911, 1915, 1901, 1916, 1917, 1919, 1918, 1905, 1920, 1903,
-
-     1921, 1904, 1915, 1913, 1922,    0, 1916, 1912, 1923, 1923,
-     1924, 1919, 1929, 1917, 1918, 1921, 1925, 1925, 1930, 1924,
-     1926, 1926, 1927, 1920, 1922, 1928, 1931, 1927, 1932, 1935,
-     1928, 1931, 1938, 1930, 1933, 1933, 1939, 1929, 1940, 1941,
-     1943, 1939, 1932, 1940, 1935, 1942, 1945, 1946, 1947, 1948,
-     1949, 1938, 1950, 1941, 1952, 1953, 1953, 1950, 1942, 1943,
-     1945, 1947, 1948, 1951, 1957, 1954, 1946, 1955, 1951, 1949,
-     1954, 1956, 1955, 1952, 1958, 1960, 1956, 1959, 1959, 1958,
-     1961, 1962, 1960, 1957, 1963, 1964, 1967, 1968, 1965, 1963,
-     1969, 1967, 1970, 1971, 1971, 1973, 1978, 1972, 1976, 1961,
-
-     1962, 1965, 1972, 1976, 1964, 1970, 1968, 1974, 1974, 1969,
-     1975, 1975, 1977, 1980, 1973, 1978, 1979, 1979, 1981, 1977,
-     1980, 1982, 1983, 1984, 1986, 1981, 1987, 1983, 1988, 1986,
-     1989, 1987, 1990, 1990, 1991, 1992, 1993, 1993, 1994, 1994,
-     1982, 1995, 1984, 1996, 1996, 1997, 1997, 1988, 1995, 1989,
-     1998, 2000, 2004, 1991, 1992, 2003, 2000, 1998, 2005,    0,
-     2003, 2006, 2006, 2007, 2007,    0,    0,    0,    0,    0,
-        0, 2004,    0,    0,    0,    0,    0, 2005, 2011, 2011,
-     2011, 2011, 2011, 2011, 2011, 2012, 2012, 2012, 2012, 2012,
-     2012, 2012, 2013, 2013, 2013, 2013, 2013, 2013, 2013, 2014,
-
-     2014, 2014, 2014, 2014, 2014, 2014, 2015, 2015, 2015, 2015,
-     2015, 2015, 2015, 2017, 2017,    0, 2017, 2017, 2017, 2017,
-     2018, 2018,    0,    0,    0, 2018, 2018, 2019, 2019,    0,
-        0, 2019,    0, 2019, 2020,    0,    0,    0,    0,    0,
-     2020, 2021, 2021,    0,    0,    0, 2021, 2021, 2022,    0,
-        0,    0,    0,    0, 2022, 2023, 2023,    0, 2023, 2023,
-     2023, 2023, 2024, 2024,    0, 2024, 2024, 2024, 2024, 2010,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010,
-
-     2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010, 2010
+      110,  111,  113,  115,  114,  110,  107,  106,  116,  110,
+      117,  118,  122,  120,  109,  119,  123,  114,  115,  124,
+      119,  111,  113,  114,  118,  120,  121,  121,  117,  125,
+      122,  125,  123,  126,  127,  128,  129,  202,  126,  202,
+      124,  129,  131,  131,  138,  138,  127,  121,  143,  136,
+      144,  143,  125,  128,  135,  144,  135,  135,  140,  135,
+      140,  140,  141,  140,  141,  141,  145,  141,  146,  147,
+      148,  145,  149,  141,  150,  151,  152,  147,  154,  154,
+      153,  152,  152,  146,  151,  153,  155,  149,  156,  148,
+      156,  155,  158,  158,  150,  159,  160,  161,  165,  163,
+
+      164,  160,  161,  163,  166,  164,  167,  172,  168,  184,
+      156,  157,  165,  134,  159,  157,  184,  169,  167,  166,
+      157,  167,  169,  170,  173,  157,  168,  172,  170,  171,
+      171,  157,  157,  174,  176,  171,  175,  175,  174,  176,
+      173,  177,  178,  179,  132,  176,  177,  171,  180,  171,
+      181,  178,  182,  180,  183,  181,  185,  182,  187,  183,
+      186,  188,  189,  190,  179,  192,  186,  188,  191,  185,
+      192,  190,  193,  194,  195,  196,  197,  198,  187,  201,
+      196,  191,  198,  199,  189,  200,  203,  193,  205,  194,
+      200,  204,  206,  203,  195,  208,  204,  211,  197,  201,
+
+      208,  199,  199,  209,  206,  207,  207,  205,  209,  210,
+      212,  210,  213,  214,  215,  219,  222,  218,  208,  215,
+      211,  214,  212,  220,  216,  217,  221,  130,  210,  216,
+      217,  213,  218,  219,  221,  223,  226,  220,  223,  226,
+      224,  222,  224,  225,  225,  227,  227,  228,  228,  229,
+      231,  230,  232,  231,  233,  234,  232,  235,  240,  236,
+      234,  237,  237,  233,  236,  229,  230,  238,  239,  241,
+      242,  235,  238,  239,  246,  243,  244,  244,  240,  245,
+      247,  248,  245,  250,  247,  249,  249,  241,  243,  252,
+      251,  242,  246,  253,  252,  254,  253,  255,  257,  248,
+
+      256,  250,  251,  258,  261,  261,  255,  254,  259,  256,
+      260,  263,  260,  260,  255,  255,  258,  255,  262,  257,
+      259,  262,  264,  265,  266,  267,  267,  270,  263,  268,
+      273,  263,  265,  266,  268,  269,  269,  264,  271,  272,
+      274,  275,  270,  271,  276,   68,  275,  277,  278,  280,
+      273,  272,  277,  278,  281,  274,  282,  279,  285,  278,
+      279,  283,  279,  280,  276,  282,  283,  284,  286,  287,
+      281,  285,  284,  281,  289,  281,  288,  289,  290,  285,
+      292,  294,  293,  295,  287,  294,  294,  297,  286,  300,
+      288,  293,  290,  289,  291,  292,  291,  291,  296,  298,
+
+      299,  301,  297,  302,  295,  299,  291,  304,  291,  291,
+      291,  303,  300,  291,  306,  305,  303,  296,  302,  298,
+      305,  301,  304,  307,  308,  309,  310,  311,  312,  312,
+      309,  312,  311,  313,  306,  307,  314,  316,  308,  315,
+      318,  317,  310,  317,  318,  319,  320,  321,  322,  319,
+      323,  316,  314,  313,  328,  315,  325,  322,  324,  323,
+      325,  321,  326,  324,  320,  330,  332,  327,  329,  330,
+      322,  326,  327,  331,  329,  328,  333,  333,  331,  334,
+      335,  336,  336,  337,  334,  338,  332,  339,  337,  338,
+      340,  341,  342,  335,  343,  340,  344,  344,  343,  346,
+
+      341,  345,  347,  347,  342,  350,  345,  351,  339,  349,
+      349,  353,  352,  354,  356,  351,  357,  359,  360,  358,
+      346,  352,  359,  361,  362,  354,  350,  360,  361,  363,
+      364,  353,  356,  358,  356,  364,  357,  363,  362,  365,
+      366,  367,  368,  370,  365,  369,  367,  370,  371,  373,
+      372,  374,  378,  376,  366,  372,  377,  380,  381,  383,
+      380,  394,  365,  371,  368,  373,  369,  394,  378,   62,
+      374,  375,  375,  376,  388,  377,  379,  375,  381,  375,
+      385,  379,  382,  382,  383,  387,  379,  375,  384,  384,
+      375,  386,  389,  388,  390,  385,  391,  375,  392,  390,
+
+      387,  393,  396,  386,  397,  391,  396,  398,  399,  397,
+      400,   57,  401,  403,  389,  405,  393,  392,  407,  398,
+      401,  402,  402,  400,  404,  403,  399,  405,  406,  404,
+      408,  406,  410,  407,  409,  408,  411,  409,  419,  412,
+      411,  411,  413,  413,  414,  414,  416,  416,  410,  415,
+      421,  410,  412,  418,  415,  417,  417,  420,  418,  419,
+      422,  423,  420,  424,  422,  425,  423,  424,  426,  421,
+      425,  427,  428,  429,  431,  433,  427,  428,  430,  432,
+      432,  430,  439,  436,  434,  439,  430,  429,  426,  434,
+      430,  435,  431,  433,  437,  438,  435,  436,  440,  437,
+
+      441,  442,  440,  443,  438,  441,  442,  444,  445,  446,
+      447,  448,  449,  445,  450,  453,  448,  450,  449,  443,
+      444,  454,  447,  451,  440,  446,  451,  452,   52,  455,
+      464,  456,  452,  453,  455,  454,  456,  457,  458,  459,
+      461,  458,  457,  460,  459,  462,  463,  460,  460,  464,
+      465,  463,  466,  461,  470,  466,  467,  472,  462,  465,
+      468,  467,  469,  469,  468,  468,  471,  473,  471,  473,
+      466,  474,  475,  476,  477,  479,  472,  478,  480,  470,
+      481,  478,  482,  484,  479,  483,  485,  486,  484,  474,
+      475,  489,  476,  480,  477,  487,  487,  491,  481,  488,
+
+      483,  482,  489,  488,  490,  485,  486,  492,  493,  490,
+      494,  495,  496,  491,  499,  497,  495,  494,  498,  496,
+      497,  493,  500,  498,  501,  502,  492,  503,  505,  500,
+      504,  505,  499,  501,  506,  504,  503,  507,  506,  502,
+      508,  508,  509,  511,  512,  514,  513,  515,  511,  508,
+      513,  509,  517,  518,  516,  519,  525,  514,  507,  516,
+      517,  522,  529,  528,  512,  515,  530,  535,  529,  536,
+      530,  518,  528,  525,  531,  531,  522,  532,  534,   51,
+      519,  520,  532,  534,  537,  535,  520,  537,  538,  538,
+      520,  539,  541,  520,  536,  540,  540,  546,  539,  546,
+
+      520,  542,  542,  520,  533,  533,  533,  541,  533,  543,
+      544,  533,  545,  544,  543,  547,  533,  545,  548,  549,
+      551,  550,  533,  533,  552,  552,  553,  547,  551,  554,
+      555,  557,  556,  558,  558,  561,  557,  548,  561,  549,
+      550,  553,  559,  554,  556,  560,  562,  559,  555,  563,
+      560,  564,  562,  565,  567,  566,  568,  563,  570,  564,
+      566,  567,  569,  569,  571,  572,  573,  570,  575,  576,
+      572,  565,  571,  577,  578,  568,  577,  575,  576,  578,
+      579,  580,  580,  581,  582,  573,  583,  590,  585,  583,
+      585,  586,  586,  587,  579,  588,  589,  583,  581,  591,
+
+      588,  593,  592,  597,  596,  594,  595,  590,  582,  594,
+      593,  602,  597,  598,  587,  599,  603,  589,  601,  601,
+      600,  591,  592,  596,  595,  598,  600,  604,  605,  599,
+      603,  602,  604,  605,  606,  607,  608,  609,  606,  610,
+      611,  611,  609,  613,  612,  614,  613,  616,  608,  612,
+      617,  615,  616,  619,  607,  624,  608,  618,  618,  621,
+      610,  620,  620,  614,  615,  622,  623,  625,  626,  622,
+      617,  619,  628,  628,  621,  630,  629,  631,  632,  624,
+      629,  625,  632,  635,  633,  623,  634,  636,  626,  627,
+      630,  634,  627,  638,  627,  642,  656,  635,  627,  633,
+
+      627,  636,  631,  637,  639,  627,  640,  637,  638,  639,
+      627,  640,  641,  643,  644,  656,  642,  645,  648,  639,
+      644,  650,  645,  646,  646,  654,  641,  643,  647,  647,
+      648,  651,  649,  654,  647,  650,  647,  649,  652,  652,
+      653,  655,  658,  651,  662,  653,  658,  647,  657,  657,
+      661,  660,  663,  661,  647,  655,  660,  664,  666,  665,
+      667,  668,  664,  662,  665,  663,  669,  670,  671,  667,
+      668,  673,  674,  672,  675,  676,  670,  666,  672,  677,
+      678,  680,  669,  681,  676,  678,  674,  671,  677,  682,
+      683,  673,  684,  685,  675,  683,  686,  684,  685,  689,
+
+      680,  681,  687,  687,  682,  686,  688,  691,  695,  692,
+      696,  688,  689,  692,  692,  693,  693,  694,  697,  693,
+      694,  698,  695,  691,  699,  700,  698,  701,  700,  702,
+      696,  703,  704,  697,  705,  707,  703,  704,  708,  710,
+      710,  707,  711,  709,  699,  702,  705,  712,  701,  709,
+      713,  711,  714,  713,  708,  715,  716,  718,  717,  719,
+      722,  720,  718,  725,  719,  712,  720,   46,  724,  723,
+      714,  717,  723,  728,  715,  725,  716,  726,  722,  724,
+      727,  729,  726,  730,  730,  727,  729,  731,  728,  732,
+      733,  734,  735,  737,  738,  734,  736,  740,  744,  742,
+
+      743,  754,  733,  732,  745,  736,  731,   41,  754,  745,
+      735,  753,  737,  742,  749,  743,  740,  746,  744,  738,
+      747,  748,  746,  750,  751,  747,  748,  752,  749,  751,
+      753,  755,  756,  757,  757,  758,  759,  750,  760,  761,
+      762,  762,  752,  763,  760,  764,  755,  765,  763,  758,
+      766,  756,  764,  766,  759,  767,  768,  769,  770,  761,
+      772,  765,  769,  771,  777,  768,  774,  775,  771,  776,
+      774,  778,  781,  767,  779,  780,  775,  770,  782,  772,
+      783,  779,  784,  777,  776,  785,  778,  780,  784,  786,
+      789,  781,  787,  790,  791,  789,  792, 1014,  783,  782,
+
+      785,  787,  791,  793,  796,  794,  795,  790,  793,  786,
+      795,  795,  797,  801,  798,  800,  792,  794,  799,  799,
+      802, 1014,  801,  796,  805,  802,  797,  798,  800,  803,
+      803,  804,  806,  805,  807,  809,  804,  806,  810,  807,
+      808,  808,  811,  810,  809,  812,  813,  814,  815,  820,
+      816,  813,  814,  815,  816,  823,  811,  818,  818,  819,
+      820,  819,  822,  812,  817,  824,  822,  825,  828,  834,
+      823,  829,   14,  817,  827,  831,  825,  828,  817,  830,
+      817,  826,  817,  824,  817,  826,  826,  830,  827,  831,
+      829,  832,  833,  835,  834,  836,  836,  837,  835,  841,
+
+      832,  838,  838,  840,  841,  842,  840,  843,  843,  844,
+      833,  846,  837,  845,  845,  847,  846,  848,  848,  849,
+      850,  852,  851,  854,  842,  850,  852,  853,  853,  844,
+      851,  855,  857,  856,  864,  869,  847,  855,  859,  849,
+      856,  854,  860,  859,  861,  857,  862,  860,  863,  861,
+      865,  862,  867,  864,  866,  866,  868,  863,  869,  870,
+      871,  865,  872,  873,  870,  874,  875,  875,  876,  877,
+      881,  878,  867,  879,  871,  873,  868,  884,  879,   13,
+      871,  882,  872,  874,  880,  880,  882,  885,  876,  878,
+      886,  885,  885,  881,  877,  887,  884,  889,  888,  886,
+
+      888,  890,  892,  887,  891,  893,  890,  894,  891,  895,
+      896,  889,  897,  892,  898,  896,  899,  900,  901,  902,
+      899,  908,  903,  904,  893,  905,  906,  895,  908,  910,
+      897,  902,  914,  894,  898,  900,  903,  901,  904,  907,
+      905,  909,  911,  912,  907,  906,  909,  910,  913,    0,
+      915,  911,  916,  914,  913,  915,  917,  916,  912,  918,
+      918,  917,  919,  919,  921,  921,  922,  923,  924,  925,
+      922,  926,  927,  928,  925,  929,  923,  928,  928,  929,
+      929,  930,  934,  931,  932,  926,  924,  933,  935,  936,
+      938,  927,  937,  939,  940,  936,  941,  937,  943,  961,
+
+      942,  930,  931,  932,  947,  944,  933,  935,  934,  938,
+      945,  945,  939,  940,  942,  941,  947,  961,  946,  943,
+      944,  946,  948,  948,  949,  951,  950,  952,  953,  949,
+      950,  954,  956,  954,  962,  957,  952,  954,  951,  958,
+      958,  953,  959,  966,  960,  964,  964,  959,  960,  980,
+      954,  957,  956,  963,  962,  968,  969,  969,  963,  970,
+      968,  966,  972,  972,  970,  974,  974,  975,  977,  978,
+      978,  977,  979,  982,  980,  981,  983,  985,  982,  984,
+      984,  985,  986,  975,  987,  987,  988,  979,  989,  981,
+      990,  983,  991,  992,  990,  994,  994,  995,  992,  989,
+
+      996,  998,  986,  997,  997,  999,  998, 1000,  988, 1001,
+     1002,  991, 1006,    0,  996,  995, 1004, 1003, 1001, 1003,
+     1009, 1004, 1011, 1005, 1007,  999, 1017, 1000, 1005, 1007,
+     1002, 1012, 1006, 1016, 1009, 1010, 1010, 1012, 1015, 1015,
+     1023, 1011, 1021, 1019, 1018, 1016, 1017, 1018, 1019, 1020,
+     1018, 1021, 1022, 1024, 1020, 1025, 1024, 1022, 1026, 1026,
+     1025, 1027, 1018, 1028, 1029, 1023, 1030, 1031, 1032, 1033,
+     1034, 1030, 1031, 1032, 1038, 1034, 1035, 1035, 1036, 1027,
+     1037, 1039, 1028, 1036, 1029, 1040, 1043, 1044, 1041, 1042,
+     1045, 1043, 1033, 1047, 1038, 1046, 1049, 1049, 1037, 1040,
+
+     1041, 1039, 1042, 1050, 1052, 1053, 1051, 1044, 1054, 1046,
+     1045, 1051, 1053, 1055, 1047, 1057, 1059, 1054, 1064, 1052,
+     1054, 1060, 1060, 1050, 1061, 1061, 1066, 1063, 1062, 1055,
+     1057, 1062, 1063, 1065, 1064, 1057, 1071, 1067, 1068, 1069,
+     1072, 1059, 1065, 1073, 1069, 1066, 1067, 1068, 1074, 1067,
+     1070, 1070, 1075, 1072, 1076, 1078, 1071, 1079, 1080, 1080,
+     1081, 1073, 1074, 1082, 1083, 1085, 1076,    0, 1075, 1083,
+     1084, 1084, 1082, 1086, 1085, 1079, 1081, 1085, 1087, 1089,
+     1078, 1090, 1087, 1087, 1089, 1084, 1095, 1091, 1092, 1093,
+     1097, 1086, 1091, 1092, 1101, 1093, 1096, 1103, 1104, 1090,
+
+     1102, 1096, 1098, 1097, 1105, 1098, 1095, 1106, 1102, 1107,
+     1103, 1098, 1106, 1101, 1108, 1111, 1104, 1110, 1110, 1117,
+     1112, 1113, 1114, 1105, 1112, 1107, 1113, 1114, 1115, 1116,
+     1119, 1123, 1108, 1115, 1121, 1111, 1120, 1120, 1116, 1122,
+     1124, 1125, 1117, 1123, 1126, 1119, 1122, 1127, 1121, 1126,
+     1128, 1129, 1124, 1130, 1130, 1131, 1135, 1129, 1131, 1127,
+     1125, 1132, 1132, 1137, 1134, 1135, 1136, 1136, 1128, 1134,
+     1139, 1138, 1140, 1141, 1143, 1137, 1138, 1142, 1144, 1139,
+     1145, 1148, 1142, 1143, 1140, 1146, 1146, 1147, 1141, 1149,
+     1150, 1152, 1147, 1151, 1151, 1145, 1143, 1154, 1144, 1153,
+
+     1153, 1156, 1148, 1155, 1155, 1156, 1158, 1157, 1149, 1158,
+     1150, 1152, 1157, 1161, 1160, 1162, 1163, 1168, 1154, 1160,
+     1162, 1164, 1164, 1165, 1165, 1166, 1167, 1169, 1170, 1171,
+     1166, 1161, 1175, 1170, 1174, 1176, 1176, 1168, 1167, 1167,
+     1167, 1163, 1177, 1178, 1178, 1167, 1173, 1169, 1174, 1171,
+     1173, 1173, 1179, 1175, 1180, 1181, 1181, 1182, 1182, 1187,
+     1185, 1186, 1186, 1188, 1189, 1190, 1191, 1191, 1177, 1185,
+     1188, 1192, 1179, 1189, 1187, 1195, 1180, 1193, 1196, 1197,
+     1195, 1198, 1199, 1196, 1200, 1201, 1201, 1199, 1198, 1200,
+     1202, 1190, 1203, 1193, 1204, 1202, 1205, 1192, 1206, 1197,
+
+     1207, 1203, 1208, 1207, 1209, 1210, 1210, 1211, 1212, 1215,
+     1206, 1224, 1212, 1214, 1204, 1205,    0, 1216, 1218, 1217,
+     1208, 1216, 1211, 1222, 1215, 1217, 1220, 1218, 1212, 1223,
+     1209, 1224, 1214, 1219, 1219, 1221, 1221, 1220, 1226, 1226,
+     1225, 1229, 1220, 1223, 1222, 1225, 1227, 1228, 1230, 1231,
+     1227, 1227, 1228, 1233, 1231, 1234, 1235, 1236, 1237, 1234,
+     1230, 1238, 1240, 1237, 1239, 1233, 1246, 1229, 1235, 1239,
+     1242, 1243, 1243, 1242, 1240, 1244, 1244, 1245, 1245, 1247,
+     1255, 1249, 1236, 1238, 1248, 1247, 1246, 1249, 1250, 1248,
+     1252, 1254, 1255, 1257, 1254, 1252, 1259, 1250, 1258, 1258,
+
+     1260, 1261, 1262, 1263, 1266, 1257, 1264, 1263, 1265, 1260,
+     1269, 1264, 1277, 1265, 1268, 1268, 1259, 1275, 1266, 1261,
+     1270, 1262, 1271, 1273, 1273, 1278, 1268, 1277, 1269, 1270,
+     1279, 1271, 1280, 1275, 1286, 1279, 1281, 1281, 1282, 1278,
+     1282, 1283, 1283, 1285, 1287, 1287, 1288, 1289, 1290, 1280,
+     1285, 1291, 1292, 1293, 1286, 1288, 1294, 1297, 1302, 1295,
+     1290, 1298, 1300, 1291, 1292, 1295, 1304, 1300, 1289, 1303,
+     1301, 1294, 1301, 1304, 1303, 1306, 1302, 1297, 1295, 1293,
+     1308, 1298, 1309, 1309, 1306, 1310, 1311, 1312, 1313, 1312,
+     1314, 1311, 1315, 1313, 1308, 1314, 1316, 1317, 1318, 1319,
+
+     1320, 1322, 1317, 1318, 1323, 1324, 1324, 1326, 1320, 1327,
+     1315, 1310, 1319, 1325, 1325, 1330, 1316, 1330, 1323, 1328,
+     1322, 1329, 1326, 1331, 1328, 1334, 1329, 1332, 1332, 1327,
+     1333, 1333, 1336, 1336, 1334, 1331, 1335, 1334, 1335, 1337,
+     1338, 1340, 1341, 1343, 1344, 1345, 1340, 1341, 1337, 1346,
+     1352, 1348, 1338, 1350, 1351, 1357, 1343, 1348, 1353, 1350,
+     1354, 1354, 1355, 1345, 1344, 1346, 1358, 1353, 1363, 1351,
+     1358, 1355, 1356, 1356, 1357, 1352, 1359, 1360, 1361, 1362,
+     1367, 1359, 1361, 1361, 1366, 1366, 1370, 1362, 1363, 1367,
+     1360, 1368, 1368, 1369, 1369, 1371, 1372, 1373, 1370, 1374,
+
+     1374, 1372, 1373, 1376, 1377, 1379, 1378, 1380, 1381, 1377,
+     1385, 1382, 1380, 1371, 1383, 1383, 1387, 1384, 1386, 1388,
+     1379, 1384, 1390, 1386, 1391, 1385, 1381, 1382, 1376, 1378,
+     1392, 1393, 1394, 1395, 1396, 1398, 1398, 1399, 1388, 1400,
+     1399, 1390, 1387, 1401,    0, 1395, 1402, 1391, 1403, 1403,
+     1393, 1406, 1400, 1394, 1392, 1396, 1407, 1401, 1409, 1402,
+     1404, 1404, 1405, 1405, 1408, 1408, 1406, 1409, 1413, 1407,
+     1409, 1410, 1410, 1411, 1411, 1412, 1412, 1414, 1414, 1415,
+     1416, 1416, 1417, 1417, 1418, 1420, 1422, 1413, 1421, 1421,
+     1420, 1423, 1423, 1424, 1425, 1426, 1429, 1415, 1426, 1430,
+
+     1425, 1427, 1427, 1418, 1431, 1422, 1428, 1428, 1432, 1432,
+     1434, 1424, 1435, 1436, 1430, 1429, 1437, 1427, 1438, 1438,
+     1437, 1439, 1441, 1431, 1440, 1440, 1442, 1443, 1436, 1445,
+     1434, 1444, 1444, 1442, 1447, 1435, 1448, 1449, 1445, 1450,
+     1439, 1448, 1441, 1451, 1452, 1453, 1447, 1455, 1454, 1452,
+     1453, 1456, 1450, 1443, 1457, 1459, 1455, 1461, 1463, 1459,
+     1456, 1458, 1449, 1454, 1451, 1467, 1458, 1463, 1457, 1464,
+     1464, 1465, 1466, 1466, 1469, 1470, 1465, 1461, 1472, 1474,
+     1476, 1466, 1474, 1475, 1470, 1467, 1477, 1467, 1475, 1469,
+     1472, 1478, 1478, 1480, 1480, 1481, 1482, 1482, 1477, 1483,
+
+     1476, 1484, 1485, 1486, 1486, 1489, 1488, 1492, 1489, 1481,
+     1488, 1483, 1490, 1490, 1491, 1484, 1493, 1494, 1495, 1491,
+     1496, 1485, 1495, 1497, 1498, 1501, 1499, 1492, 1497, 1498,
+     1502, 1494, 1499, 1503, 1504, 1502, 1493, 1505, 1503, 1505,
+     1496, 1501, 1504, 1508, 1509, 1509, 1510, 1511, 1518, 1510,
+     1512, 1512, 1516, 1516, 1521, 1522, 1522, 1508, 1526, 1521,
+     1524, 1524, 1528, 1526, 1527, 1527, 1518, 1529, 1532, 1530,
+     1533, 1534, 1534, 1511, 1530, 1536, 1537, 1538, 1528, 1539,
+        0, 1537, 1533, 1545, 1536, 1541, 1541, 1532, 1545, 1529,
+     1543, 1543, 1544, 1544, 1539, 1538, 1546, 1547, 1546, 1548,
+
+     1549, 1549, 1550, 1550, 1548, 1551, 1551, 1552, 1553, 1554,
+     1554, 1547, 1555, 1556, 1559, 1557, 1558, 1560, 1560, 1552,
+     1561, 1558, 1562, 1563, 1555, 1556, 1553, 1557, 1564, 1561,
+     1565, 1566, 1567, 1567, 1559, 1568, 1570, 1569, 1573, 1573,
+     1578, 1564, 1571, 1563, 1568, 1566, 1572, 1571, 1562, 1574,
+     1574, 1572, 1575, 1575, 1565, 1569, 1579, 1580, 1570, 1582,
+     1578, 1581, 1583, 1585, 1585, 1584, 1587, 1587, 1582, 1588,
+     1589, 1591, 1592, 1590, 1579, 1593, 1594, 1595, 1588, 1580,
+     1590, 1581, 1583, 1584, 1596, 1596, 1591, 1598, 1589, 1597,
+     1592, 1599, 1594, 1593, 1597, 1600, 1595, 1601, 1602, 1603,
+
+     1611, 1607, 1601, 1604, 1608, 1598, 1599, 1605, 1604, 1605,
+     1607, 1614, 1612, 1615, 1600, 1612, 1613, 1613, 1602, 1603,
+     1611, 1616, 1616, 1608, 1617, 1619, 1614, 1627, 1617, 1620,
+     1622, 1615, 1634, 1620, 1621, 1621, 1624, 1624, 1626, 1626,
+     1619, 1628, 1628, 1622, 1629, 1629, 1627, 1633, 1633, 1635,
+     1636, 1637, 1638, 1639, 1634, 1640, 1637, 1638, 1642, 1636,
+     1643, 1644, 1635, 1640, 1645, 1643, 1644, 1646, 1646, 1647,
+     1647, 1648, 1639, 1642, 1656, 1649, 1650, 1651, 1648, 1645,
+     1649, 1650, 1651, 1652, 1652, 1653, 1653, 1656, 1657, 1660,
+     1658, 1659, 1661, 1657, 1658, 1662, 1659, 1663, 1660, 1664,
+
+     1667, 1666, 1663, 1662, 1666, 1667, 1668, 1661, 1669, 1670,
+     1671, 1664, 1672, 1672, 1673, 1675, 1676, 1681, 1670, 1671,
+     1677, 1669, 1679, 1673, 1668, 1678, 1678, 1683, 1680, 1682,
+     1682, 1684, 1681, 1687, 1675, 1684, 1676, 1680, 1687, 1677,
+     1686, 1679, 1685, 1685, 1689, 1690, 1683, 1692, 1686, 1693,
+     1694, 1692, 1702, 1689, 1696, 1696, 1699, 1699, 1690, 1703,
+     1703, 1704, 1704, 1693, 1705, 1694, 1709, 1705, 1706, 1706,
+     1707, 1707, 1702, 1708, 1708, 1710, 1711, 1712, 1712, 1713,
+     1717, 1711, 1716, 1713, 1709, 1718, 1716, 1716, 1719, 1710,
+     1722, 1718, 1723, 1719, 1724, 1722, 1725, 1726, 1727, 1724,
+
+     1728, 1728, 1729, 1717, 1731, 1730, 1732, 1732, 1735, 1723,
+     1723, 1737, 1727, 1730, 1725, 1733, 1733, 1726, 1734, 1734,
+     1736, 1729, 1738, 1731, 1735, 1736, 1739, 1740, 1745, 1741,
+     1754, 1737, 1743, 1743, 1744, 1739, 1748, 1744, 1747, 1747,
+     1750, 1748, 1751, 1751, 1753, 1754, 1745, 1740, 1738, 1741,
+     1752, 1755, 1756, 1753, 1752, 1755, 1755, 1757, 1750, 1759,
+     1760, 1762, 1766, 1767, 1767, 1756, 1757, 1766, 1759, 1768,
+     1770, 1775, 1760, 1771, 1771, 1770, 1774, 1771, 1768, 1773,
+     1773, 1777, 1776, 1778, 1781, 1774, 1762, 1776, 1778, 1779,
+     1780, 1775, 1782, 1782, 1784, 1780, 1785, 1786, 1786, 1787,
+
+     1788, 1789, 1777, 1790, 1788, 1791, 1792, 1779, 1794, 1781,
+     1789, 1785, 1787, 1784, 1792, 1793, 1795, 1795, 1796, 1790,
+     1793, 1798, 1798, 1805, 1791, 1799, 1799, 1801, 1801, 1806,
+     1802, 1804, 1804, 1810, 1794, 1802, 1807, 1796, 1809, 1809,
+     1811, 1812, 1812, 1805, 1813, 1813, 1814, 1810, 1815, 1816,
+     1817, 1817, 1806, 1818, 1821, 1807, 1818, 1819, 1819, 1822,
+     1815, 1823, 1811, 1824, 1823, 1814, 1821, 1825, 1824, 1816,
+     1826, 1827, 1828, 1828, 1831, 1826, 1830, 1830, 1834, 1822,
+     1833, 1833, 1835, 1834, 1919, 1836, 1825, 1919, 1827, 1827,
+     1836, 1837, 1837, 1831, 1838, 1838, 1835, 1839, 1839, 1840,
+
+     1842, 1842, 1846, 1846, 1840, 1848, 1848, 1849, 1850, 1851,
+     1852, 1852, 1853, 1860, 1856, 1857, 1857, 1853, 1851, 1858,
+     1861, 1849, 1856, 1863, 1858, 1862, 1864, 1865, 1850, 1913,
+     1862, 1866, 1867, 1860, 1864, 1863, 1868, 1869, 1872, 1892,
+     1861, 1913, 1869, 1874, 1874, 1865, 1885, 1866, 1892, 1867,
+     1867, 1875, 1875, 1880, 1880, 1876, 1882, 1868, 1872, 1876,
+     1882, 1884, 1884, 1886, 1885, 1888, 1888, 1889, 1891, 1893,
+     1893, 1894, 1894, 1895, 1895, 1896, 1897, 1886, 1898, 1899,
+     1896,    0, 1889, 1900, 1901, 1902, 1891, 1920, 1900, 1901,
+     1903, 1903, 1920, 1898, 1906, 1906, 1908, 1908, 1910, 1915,
+
+     1899, 1897, 1911, 1911, 1902, 1914, 1914, 1910, 1916, 1916,
+     1921, 1922, 1923, 1925, 1915, 1924, 1922, 1929, 1931, 1932,
+     1929, 1933, 1931, 1935, 1921, 1936, 1937, 1939, 1938, 1925,
+     1940, 1923, 1941, 1924, 1935, 1933, 1942,    0, 1936, 1932,
+     1943, 1943, 1944, 1939, 1949, 1937, 1938, 1941, 1945, 1945,
+     1950, 1944, 1946, 1946, 1947, 1940, 1942, 1948, 1951, 1947,
+     1952, 1955, 1948, 1951, 1958, 1950, 1953, 1953, 1959, 1949,
+     1960, 1961, 1963, 1959, 1952, 1960, 1955, 1962, 1965, 1966,
+     1967, 1968, 1969, 1958, 1970, 1961, 1972, 1973, 1973, 1970,
+     1962, 1963, 1965, 1967, 1968, 1971, 1977, 1974, 1966, 1975,
+
+     1971, 1969, 1974, 1976, 1975, 1972, 1978, 1980, 1976, 1979,
+     1979, 1978, 1981, 1982, 1980, 1977, 1983, 1984, 1987, 1988,
+     1985, 1983, 1989, 1987, 1990, 1991, 1991, 1993, 1998, 1992,
+     1996, 1981, 1982, 1985, 1992, 1996, 1984, 1990, 1988, 1994,
+     1994, 1989, 1995, 1995, 1997, 2000, 1993, 1998, 1999, 1999,
+     2001, 1997, 2000, 2002, 2003, 2004, 2006, 2001, 2007, 2003,
+     2008, 2006, 2009, 2007, 2010, 2010, 2011, 2012, 2013, 2013,
+     2014, 2014, 2002, 2015, 2004, 2016, 2016, 2017, 2017, 2008,
+     2015, 2009, 2018, 2020, 2024, 2011, 2012, 2023, 2020, 2018,
+     2025,    0, 2023, 2026, 2026, 2027, 2027,    0,    0,    0,
+
+        0,    0,    0, 2024,    0,    0,    0,    0,    0, 2025,
+     2031, 2031, 2031, 2031, 2031, 2031, 2031, 2032, 2032, 2032,
+     2032, 2032, 2032, 2032, 2033, 2033, 2033, 2033, 2033, 2033,
+     2033, 2034, 2034, 2034, 2034, 2034, 2034, 2034, 2035, 2035,
+     2035, 2035, 2035, 2035, 2035, 2037, 2037,    0, 2037, 2037,
+     2037, 2037, 2038, 2038,    0,    0,    0, 2038, 2038, 2039,
+     2039,    0,    0, 2039,    0, 2039, 2040,    0,    0,    0,
+        0,    0, 2040, 2041, 2041,    0,    0,    0, 2041, 2041,
+     2042,    0,    0,    0,    0,    0, 2042, 2043, 2043,    0,
+     2043, 2043, 2043, 2043, 2044, 2044,    0, 2044, 2044, 2044,
+
+     2044, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030, 2030,
+     2030
     } ;
 
 static yy_state_type yy_last_accepting_state;
@@ -2204,7 +2218,7 @@ static void config_end_include(void)
 #define YY_NO_INPUT 1
 #endif
 
-#line 2206 "<stdout>"
+#line 2220 "<stdout>"
 
 #define INITIAL 0
 #define quotedstring 1
@@ -2427,7 +2441,7 @@ YY_DECL
        {
 #line 207 "./util/configlexer.lex"
 
-#line 2429 "<stdout>"
+#line 2443 "<stdout>"
 
        while ( /*CONSTCOND*/1 )                /* loops until end-of-file is reached */
                {
@@ -2460,13 +2474,13 @@ yy_match:
                        while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
                                {
                                yy_current_state = (int) yy_def[yy_current_state];
-                               if ( yy_current_state >= 2011 )
+                               if ( yy_current_state >= 2031 )
                                        yy_c = yy_meta[(unsigned int) yy_c];
                                }
                        yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
                        ++yy_cp;
                        }
-               while ( yy_base[yy_current_state] != 3970 );
+               while ( yy_base[yy_current_state] != 4002 );
 
 yy_find_action:
                yy_act = yy_accept[yy_current_state];
@@ -3421,40 +3435,55 @@ YY_RULE_SETUP
 { YDVAR(1, VAR_RATELIMIT_FACTOR) }
        YY_BREAK
 case 185:
-/* rule 185 can match eol */
 YY_RULE_SETUP
 #line 402 "./util/configlexer.lex"
-{ LEXOUT(("NL\n")); cfg_parser->line++; }
+{ YDVAR(2, VAR_RESPONSE_IP_TAG) }
        YY_BREAK
-/* Quoted strings. Strip leading and ending quotes */
 case 186:
 YY_RULE_SETUP
+#line 403 "./util/configlexer.lex"
+{ YDVAR(2, VAR_RESPONSE_IP) }
+       YY_BREAK
+case 187:
+YY_RULE_SETUP
+#line 404 "./util/configlexer.lex"
+{ YDVAR(2, VAR_RESPONSE_IP_DATA) }
+       YY_BREAK
+case 188:
+/* rule 188 can match eol */
+YY_RULE_SETUP
 #line 405 "./util/configlexer.lex"
+{ LEXOUT(("NL\n")); cfg_parser->line++; }
+       YY_BREAK
+/* Quoted strings. Strip leading and ending quotes */
+case 189:
+YY_RULE_SETUP
+#line 408 "./util/configlexer.lex"
 { BEGIN(quotedstring); LEXOUT(("QS ")); }
        YY_BREAK
 case YY_STATE_EOF(quotedstring):
-#line 406 "./util/configlexer.lex"
+#line 409 "./util/configlexer.lex"
 {
         yyerror("EOF inside quoted string");
        if(--num_args == 0) { BEGIN(INITIAL); }
        else                { BEGIN(val); }
 }
        YY_BREAK
-case 187:
+case 190:
 YY_RULE_SETUP
-#line 411 "./util/configlexer.lex"
+#line 414 "./util/configlexer.lex"
 { LEXOUT(("STR(%s) ", yytext)); yymore(); }
        YY_BREAK
-case 188:
-/* rule 188 can match eol */
+case 191:
+/* rule 191 can match eol */
 YY_RULE_SETUP
-#line 412 "./util/configlexer.lex"
+#line 415 "./util/configlexer.lex"
 { yyerror("newline inside quoted string, no end \""); 
                          cfg_parser->line++; BEGIN(INITIAL); }
        YY_BREAK
-case 189:
+case 192:
 YY_RULE_SETUP
-#line 414 "./util/configlexer.lex"
+#line 417 "./util/configlexer.lex"
 {
         LEXOUT(("QE "));
        if(--num_args == 0) { BEGIN(INITIAL); }
@@ -3467,34 +3496,34 @@ YY_RULE_SETUP
 }
        YY_BREAK
 /* Single Quoted strings. Strip leading and ending quotes */
-case 190:
+case 193:
 YY_RULE_SETUP
-#line 426 "./util/configlexer.lex"
+#line 429 "./util/configlexer.lex"
 { BEGIN(singlequotedstr); LEXOUT(("SQS ")); }
        YY_BREAK
 case YY_STATE_EOF(singlequotedstr):
-#line 427 "./util/configlexer.lex"
+#line 430 "./util/configlexer.lex"
 {
         yyerror("EOF inside quoted string");
        if(--num_args == 0) { BEGIN(INITIAL); }
        else                { BEGIN(val); }
 }
        YY_BREAK
-case 191:
+case 194:
 YY_RULE_SETUP
-#line 432 "./util/configlexer.lex"
+#line 435 "./util/configlexer.lex"
 { LEXOUT(("STR(%s) ", yytext)); yymore(); }
        YY_BREAK
-case 192:
-/* rule 192 can match eol */
+case 195:
+/* rule 195 can match eol */
 YY_RULE_SETUP
-#line 433 "./util/configlexer.lex"
+#line 436 "./util/configlexer.lex"
 { yyerror("newline inside quoted string, no end '"); 
                             cfg_parser->line++; BEGIN(INITIAL); }
        YY_BREAK
-case 193:
+case 196:
 YY_RULE_SETUP
-#line 435 "./util/configlexer.lex"
+#line 438 "./util/configlexer.lex"
 {
         LEXOUT(("SQE "));
        if(--num_args == 0) { BEGIN(INITIAL); }
@@ -3507,38 +3536,38 @@ YY_RULE_SETUP
 }
        YY_BREAK
 /* include: directive */
-case 194:
+case 197:
 YY_RULE_SETUP
-#line 447 "./util/configlexer.lex"
+#line 450 "./util/configlexer.lex"
 { 
        LEXOUT(("v(%s) ", yytext)); inc_prev = YYSTATE; BEGIN(include); }
        YY_BREAK
 case YY_STATE_EOF(include):
-#line 449 "./util/configlexer.lex"
+#line 452 "./util/configlexer.lex"
 {
         yyerror("EOF inside include directive");
         BEGIN(inc_prev);
 }
        YY_BREAK
-case 195:
+case 198:
 YY_RULE_SETUP
-#line 453 "./util/configlexer.lex"
+#line 456 "./util/configlexer.lex"
 { LEXOUT(("ISP ")); /* ignore */ }
        YY_BREAK
-case 196:
-/* rule 196 can match eol */
+case 199:
+/* rule 199 can match eol */
 YY_RULE_SETUP
-#line 454 "./util/configlexer.lex"
+#line 457 "./util/configlexer.lex"
 { LEXOUT(("NL\n")); cfg_parser->line++;}
        YY_BREAK
-case 197:
+case 200:
 YY_RULE_SETUP
-#line 455 "./util/configlexer.lex"
+#line 458 "./util/configlexer.lex"
 { LEXOUT(("IQS ")); BEGIN(include_quoted); }
        YY_BREAK
-case 198:
+case 201:
 YY_RULE_SETUP
-#line 456 "./util/configlexer.lex"
+#line 459 "./util/configlexer.lex"
 {
        LEXOUT(("Iunquotedstr(%s) ", yytext));
        config_start_include_glob(yytext);
@@ -3546,27 +3575,27 @@ YY_RULE_SETUP
 }
        YY_BREAK
 case YY_STATE_EOF(include_quoted):
-#line 461 "./util/configlexer.lex"
+#line 464 "./util/configlexer.lex"
 {
         yyerror("EOF inside quoted string");
         BEGIN(inc_prev);
 }
        YY_BREAK
-case 199:
+case 202:
 YY_RULE_SETUP
-#line 465 "./util/configlexer.lex"
+#line 468 "./util/configlexer.lex"
 { LEXOUT(("ISTR(%s) ", yytext)); yymore(); }
        YY_BREAK
-case 200:
-/* rule 200 can match eol */
+case 203:
+/* rule 203 can match eol */
 YY_RULE_SETUP
-#line 466 "./util/configlexer.lex"
+#line 469 "./util/configlexer.lex"
 { yyerror("newline before \" in include name"); 
                                  cfg_parser->line++; BEGIN(inc_prev); }
        YY_BREAK
-case 201:
+case 204:
 YY_RULE_SETUP
-#line 468 "./util/configlexer.lex"
+#line 471 "./util/configlexer.lex"
 {
        LEXOUT(("IQE "));
        yytext[yyleng - 1] = '\0';
@@ -3576,7 +3605,7 @@ YY_RULE_SETUP
        YY_BREAK
 case YY_STATE_EOF(INITIAL):
 case YY_STATE_EOF(val):
-#line 474 "./util/configlexer.lex"
+#line 477 "./util/configlexer.lex"
 {
        LEXOUT(("LEXEOF "));
        yy_set_bol(1); /* Set beginning of line, so "^" rules match.  */
@@ -3588,33 +3617,33 @@ case YY_STATE_EOF(val):
        }
 }
        YY_BREAK
-case 202:
+case 205:
 YY_RULE_SETUP
-#line 485 "./util/configlexer.lex"
+#line 488 "./util/configlexer.lex"
 { LEXOUT(("unquotedstr(%s) ", yytext)); 
                        if(--num_args == 0) { BEGIN(INITIAL); }
                        yylval.str = strdup(yytext); return STRING_ARG; }
        YY_BREAK
-case 203:
+case 206:
 YY_RULE_SETUP
-#line 489 "./util/configlexer.lex"
+#line 492 "./util/configlexer.lex"
 {
        ub_c_error_msg("unknown keyword '%s'", yytext);
        }
        YY_BREAK
-case 204:
+case 207:
 YY_RULE_SETUP
-#line 493 "./util/configlexer.lex"
+#line 496 "./util/configlexer.lex"
 {
        ub_c_error_msg("stray '%s'", yytext);
        }
        YY_BREAK
-case 205:
+case 208:
 YY_RULE_SETUP
-#line 497 "./util/configlexer.lex"
+#line 500 "./util/configlexer.lex"
 ECHO;
        YY_BREAK
-#line 3616 "<stdout>"
+#line 3645 "<stdout>"
 
        case YY_END_OF_BUFFER:
                {
@@ -3905,7 +3934,7 @@ static int yy_get_next_buffer (void)
                while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
                        {
                        yy_current_state = (int) yy_def[yy_current_state];
-                       if ( yy_current_state >= 2011 )
+                       if ( yy_current_state >= 2031 )
                                yy_c = yy_meta[(unsigned int) yy_c];
                        }
                yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
@@ -3933,11 +3962,11 @@ static int yy_get_next_buffer (void)
        while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
                {
                yy_current_state = (int) yy_def[yy_current_state];
-               if ( yy_current_state >= 2011 )
+               if ( yy_current_state >= 2031 )
                        yy_c = yy_meta[(unsigned int) yy_c];
                }
        yy_current_state = yy_nxt[yy_base[yy_current_state] + (unsigned int) yy_c];
-       yy_is_jam = (yy_current_state == 2010);
+       yy_is_jam = (yy_current_state == 2030);
 
                return yy_is_jam ? 0 : yy_current_state;
 }
@@ -4576,7 +4605,7 @@ void yyfree (void * ptr )
 
 #define YYTABLES_NAME "yytables"
 
-#line 497 "./util/configlexer.lex"
+#line 500 "./util/configlexer.lex"
 
 
 
index 8bac3d818eb02f6dc0df19de68b44c3f37cfa166..c37830a3333fd8577b77ac0f93fceb12e3266102 100644 (file)
@@ -399,6 +399,9 @@ ratelimit-for-domain{COLON} { YDVAR(2, VAR_RATELIMIT_FOR_DOMAIN) }
 ratelimit-below-domain{COLON}  { YDVAR(2, VAR_RATELIMIT_BELOW_DOMAIN) }
 ip-ratelimit-factor{COLON}             { YDVAR(1, VAR_IP_RATELIMIT_FACTOR) }
 ratelimit-factor{COLON}                { YDVAR(1, VAR_RATELIMIT_FACTOR) }
+response-ip-tag{COLON}         { YDVAR(2, VAR_RESPONSE_IP_TAG) }
+response-ip{COLON}             { YDVAR(2, VAR_RESPONSE_IP) }
+response-ip-data{COLON}                { YDVAR(2, VAR_RESPONSE_IP_DATA) }
 <INITIAL,val>{NEWLINE}         { LEXOUT(("NL\n")); cfg_parser->line++; }
 
        /* Quoted strings. Strip leading and ending quotes */
index 6768bcecdd349ecc4a757e1f3b8baa90ef322e1e..e38f40e0b133013bd4c0e3672bf897346527456c 100644 (file)
@@ -79,6 +79,8 @@
 int ub_c_lex(void);
 void ub_c_error(const char *message);
 
+static void validate_respip_action(const char* action);
+
 /* these need to be global, otherwise they cannot be used inside yacc */
 extern struct config_parser_state* cfg_parser;
 
@@ -89,7 +91,7 @@ extern struct config_parser_state* cfg_parser;
 #endif
 
 
-#line 93 "util/configparser.c" /* yacc.c:339  */
+#line 95 "util/configparser.c" /* yacc.c:339  */
 
 # ifndef YY_NULLPTR
 #  if defined __cplusplus && 201103L <= __cplusplus
@@ -279,40 +281,43 @@ extern int yydebug;
     VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES = 410,
     VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES = 411,
     VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES = 412,
-    VAR_HARDEN_ALGO_DOWNGRADE = 413,
-    VAR_IP_TRANSPARENT = 414,
-    VAR_DISABLE_DNSSEC_LAME_CHECK = 415,
-    VAR_IP_RATELIMIT = 416,
-    VAR_IP_RATELIMIT_SLABS = 417,
-    VAR_IP_RATELIMIT_SIZE = 418,
-    VAR_RATELIMIT = 419,
-    VAR_RATELIMIT_SLABS = 420,
-    VAR_RATELIMIT_SIZE = 421,
-    VAR_RATELIMIT_FOR_DOMAIN = 422,
-    VAR_RATELIMIT_BELOW_DOMAIN = 423,
-    VAR_IP_RATELIMIT_FACTOR = 424,
-    VAR_RATELIMIT_FACTOR = 425,
-    VAR_CAPS_WHITELIST = 426,
-    VAR_CACHE_MAX_NEGATIVE_TTL = 427,
-    VAR_PERMIT_SMALL_HOLDDOWN = 428,
-    VAR_QNAME_MINIMISATION = 429,
-    VAR_QNAME_MINIMISATION_STRICT = 430,
-    VAR_IP_FREEBIND = 431,
-    VAR_DEFINE_TAG = 432,
-    VAR_LOCAL_ZONE_TAG = 433,
-    VAR_ACCESS_CONTROL_TAG = 434,
-    VAR_LOCAL_ZONE_OVERRIDE = 435,
-    VAR_ACCESS_CONTROL_TAG_ACTION = 436,
-    VAR_ACCESS_CONTROL_TAG_DATA = 437,
-    VAR_VIEW = 438,
-    VAR_ACCESS_CONTROL_VIEW = 439,
-    VAR_VIEW_FIRST = 440,
-    VAR_SERVE_EXPIRED = 441,
-    VAR_FAKE_DSA = 442,
-    VAR_LOG_IDENTITY = 443,
-    VAR_USE_SYSTEMD = 444,
-    VAR_SHM_ENABLE = 445,
-    VAR_SHM_KEY = 446
+    VAR_RESPONSE_IP_TAG = 413,
+    VAR_RESPONSE_IP = 414,
+    VAR_RESPONSE_IP_DATA = 415,
+    VAR_HARDEN_ALGO_DOWNGRADE = 416,
+    VAR_IP_TRANSPARENT = 417,
+    VAR_DISABLE_DNSSEC_LAME_CHECK = 418,
+    VAR_IP_RATELIMIT = 419,
+    VAR_IP_RATELIMIT_SLABS = 420,
+    VAR_IP_RATELIMIT_SIZE = 421,
+    VAR_RATELIMIT = 422,
+    VAR_RATELIMIT_SLABS = 423,
+    VAR_RATELIMIT_SIZE = 424,
+    VAR_RATELIMIT_FOR_DOMAIN = 425,
+    VAR_RATELIMIT_BELOW_DOMAIN = 426,
+    VAR_IP_RATELIMIT_FACTOR = 427,
+    VAR_RATELIMIT_FACTOR = 428,
+    VAR_CAPS_WHITELIST = 429,
+    VAR_CACHE_MAX_NEGATIVE_TTL = 430,
+    VAR_PERMIT_SMALL_HOLDDOWN = 431,
+    VAR_QNAME_MINIMISATION = 432,
+    VAR_QNAME_MINIMISATION_STRICT = 433,
+    VAR_IP_FREEBIND = 434,
+    VAR_DEFINE_TAG = 435,
+    VAR_LOCAL_ZONE_TAG = 436,
+    VAR_ACCESS_CONTROL_TAG = 437,
+    VAR_LOCAL_ZONE_OVERRIDE = 438,
+    VAR_ACCESS_CONTROL_TAG_ACTION = 439,
+    VAR_ACCESS_CONTROL_TAG_DATA = 440,
+    VAR_VIEW = 441,
+    VAR_ACCESS_CONTROL_VIEW = 442,
+    VAR_VIEW_FIRST = 443,
+    VAR_SERVE_EXPIRED = 444,
+    VAR_FAKE_DSA = 445,
+    VAR_LOG_IDENTITY = 446,
+    VAR_USE_SYSTEMD = 447,
+    VAR_SHM_ENABLE = 448,
+    VAR_SHM_KEY = 449
   };
 #endif
 /* Tokens.  */
@@ -471,51 +476,54 @@ extern int yydebug;
 #define VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES 410
 #define VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES 411
 #define VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES 412
-#define VAR_HARDEN_ALGO_DOWNGRADE 413
-#define VAR_IP_TRANSPARENT 414
-#define VAR_DISABLE_DNSSEC_LAME_CHECK 415
-#define VAR_IP_RATELIMIT 416
-#define VAR_IP_RATELIMIT_SLABS 417
-#define VAR_IP_RATELIMIT_SIZE 418
-#define VAR_RATELIMIT 419
-#define VAR_RATELIMIT_SLABS 420
-#define VAR_RATELIMIT_SIZE 421
-#define VAR_RATELIMIT_FOR_DOMAIN 422
-#define VAR_RATELIMIT_BELOW_DOMAIN 423
-#define VAR_IP_RATELIMIT_FACTOR 424
-#define VAR_RATELIMIT_FACTOR 425
-#define VAR_CAPS_WHITELIST 426
-#define VAR_CACHE_MAX_NEGATIVE_TTL 427
-#define VAR_PERMIT_SMALL_HOLDDOWN 428
-#define VAR_QNAME_MINIMISATION 429
-#define VAR_QNAME_MINIMISATION_STRICT 430
-#define VAR_IP_FREEBIND 431
-#define VAR_DEFINE_TAG 432
-#define VAR_LOCAL_ZONE_TAG 433
-#define VAR_ACCESS_CONTROL_TAG 434
-#define VAR_LOCAL_ZONE_OVERRIDE 435
-#define VAR_ACCESS_CONTROL_TAG_ACTION 436
-#define VAR_ACCESS_CONTROL_TAG_DATA 437
-#define VAR_VIEW 438
-#define VAR_ACCESS_CONTROL_VIEW 439
-#define VAR_VIEW_FIRST 440
-#define VAR_SERVE_EXPIRED 441
-#define VAR_FAKE_DSA 442
-#define VAR_LOG_IDENTITY 443
-#define VAR_USE_SYSTEMD 444
-#define VAR_SHM_ENABLE 445
-#define VAR_SHM_KEY 446
+#define VAR_RESPONSE_IP_TAG 413
+#define VAR_RESPONSE_IP 414
+#define VAR_RESPONSE_IP_DATA 415
+#define VAR_HARDEN_ALGO_DOWNGRADE 416
+#define VAR_IP_TRANSPARENT 417
+#define VAR_DISABLE_DNSSEC_LAME_CHECK 418
+#define VAR_IP_RATELIMIT 419
+#define VAR_IP_RATELIMIT_SLABS 420
+#define VAR_IP_RATELIMIT_SIZE 421
+#define VAR_RATELIMIT 422
+#define VAR_RATELIMIT_SLABS 423
+#define VAR_RATELIMIT_SIZE 424
+#define VAR_RATELIMIT_FOR_DOMAIN 425
+#define VAR_RATELIMIT_BELOW_DOMAIN 426
+#define VAR_IP_RATELIMIT_FACTOR 427
+#define VAR_RATELIMIT_FACTOR 428
+#define VAR_CAPS_WHITELIST 429
+#define VAR_CACHE_MAX_NEGATIVE_TTL 430
+#define VAR_PERMIT_SMALL_HOLDDOWN 431
+#define VAR_QNAME_MINIMISATION 432
+#define VAR_QNAME_MINIMISATION_STRICT 433
+#define VAR_IP_FREEBIND 434
+#define VAR_DEFINE_TAG 435
+#define VAR_LOCAL_ZONE_TAG 436
+#define VAR_ACCESS_CONTROL_TAG 437
+#define VAR_LOCAL_ZONE_OVERRIDE 438
+#define VAR_ACCESS_CONTROL_TAG_ACTION 439
+#define VAR_ACCESS_CONTROL_TAG_DATA 440
+#define VAR_VIEW 441
+#define VAR_ACCESS_CONTROL_VIEW 442
+#define VAR_VIEW_FIRST 443
+#define VAR_SERVE_EXPIRED 444
+#define VAR_FAKE_DSA 445
+#define VAR_LOG_IDENTITY 446
+#define VAR_USE_SYSTEMD 447
+#define VAR_SHM_ENABLE 448
+#define VAR_SHM_KEY 449
 
 /* Value type.  */
 #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
 
 union YYSTYPE
 {
-#line 64 "./util/configparser.y" /* yacc.c:355  */
+#line 66 "./util/configparser.y" /* yacc.c:355  */
 
        char*   str;
 
-#line 519 "util/configparser.c" /* yacc.c:355  */
+#line 527 "util/configparser.c" /* yacc.c:355  */
 };
 
 typedef union YYSTYPE YYSTYPE;
@@ -532,7 +540,7 @@ int yyparse (void);
 
 /* Copy the second part of user declarations.  */
 
-#line 536 "util/configparser.c" /* yacc.c:358  */
+#line 544 "util/configparser.c" /* yacc.c:358  */
 
 #ifdef short
 # undef short
@@ -774,21 +782,21 @@ union yyalloc
 /* YYFINAL -- State number of the termination state.  */
 #define YYFINAL  2
 /* YYLAST -- Last index in YYTABLE.  */
-#define YYLAST   379
+#define YYLAST   394
 
 /* YYNTOKENS -- Number of terminals.  */
-#define YYNTOKENS  192
+#define YYNTOKENS  195
 /* YYNNTS -- Number of nonterminals.  */
-#define YYNNTS  202
+#define YYNNTS  207
 /* YYNRULES -- Number of rules.  */
-#define YYNRULES  387
+#define YYNRULES  397
 /* YYNSTATES -- Number of states.  */
-#define YYNSTATES  580
+#define YYNSTATES  600
 
 /* YYTRANSLATE[YYX] -- Symbol number corresponding to YYX as returned
    by yylex, with out-of-bounds checking.  */
 #define YYUNDEFTOK  2
-#define YYMAXUTOK   446
+#define YYMAXUTOK   449
 
 #define YYTRANSLATE(YYX)                                                \
   ((unsigned int) (YYX) <= YYMAXUTOK ? yytranslate[YYX] : YYUNDEFTOK)
@@ -841,52 +849,53 @@ static const yytype_uint8 yytranslate[] =
      155,   156,   157,   158,   159,   160,   161,   162,   163,   164,
      165,   166,   167,   168,   169,   170,   171,   172,   173,   174,
      175,   176,   177,   178,   179,   180,   181,   182,   183,   184,
-     185,   186,   187,   188,   189,   190,   191
+     185,   186,   187,   188,   189,   190,   191,   192,   193,   194
 };
 
 #if YYDEBUG
   /* YYRLINE[YYN] -- Source line where rule number YYN was defined.  */
 static const yytype_uint16 yyrline[] =
 {
-       0,   141,   141,   141,   142,   142,   143,   143,   144,   144,
-     144,   149,   154,   155,   156,   156,   156,   157,   157,   158,
-     158,   159,   159,   160,   160,   161,   161,   161,   162,   162,
-     162,   163,   163,   164,   164,   165,   165,   166,   166,   167,
-     167,   168,   168,   169,   169,   170,   170,   171,   171,   171,
-     172,   172,   172,   173,   173,   173,   174,   174,   175,   175,
-     176,   176,   177,   177,   178,   178,   178,   179,   179,   180,
-     180,   181,   181,   181,   182,   182,   183,   183,   184,   184,
-     185,   185,   185,   186,   186,   187,   187,   188,   188,   189,
-     189,   190,   190,   191,   191,   191,   192,   192,   193,   193,
-     193,   194,   194,   194,   195,   195,   195,   196,   196,   196,
-     196,   197,   197,   197,   198,   198,   198,   199,   199,   200,
-     200,   201,   201,   202,   202,   203,   203,   203,   204,   204,
-     205,   205,   206,   207,   207,   208,   209,   209,   210,   210,
-     211,   211,   211,   212,   212,   213,   213,   214,   214,   215,
-     215,   216,   216,   216,   217,   217,   219,   231,   232,   233,
-     233,   233,   233,   233,   234,   236,   248,   249,   250,   250,
-     250,   250,   251,   253,   267,   268,   269,   269,   269,   269,
-     271,   280,   289,   300,   309,   318,   327,   338,   347,   360,
-     375,   384,   393,   402,   411,   420,   429,   438,   447,   456,
-     465,   474,   483,   492,   501,   510,   517,   524,   533,   542,
-     551,   565,   574,   583,   592,   599,   606,   632,   640,   647,
-     654,   661,   668,   676,   684,   692,   699,   706,   715,   724,
-     731,   738,   746,   754,   764,   774,   784,   797,   808,   816,
-     829,   838,   847,   856,   866,   876,   884,   897,   906,   914,
-     923,   931,   944,   953,   960,   970,   980,   990,  1000,  1010,
-    1020,  1030,  1040,  1047,  1054,  1061,  1070,  1079,  1088,  1095,
-    1105,  1122,  1129,  1147,  1160,  1173,  1182,  1191,  1200,  1209,
-    1219,  1229,  1238,  1247,  1260,  1269,  1276,  1285,  1294,  1303,
-    1312,  1320,  1333,  1341,  1369,  1376,  1391,  1401,  1411,  1418,
-    1425,  1434,  1448,  1467,  1486,  1498,  1510,  1522,  1533,  1543,
-    1552,  1560,  1568,  1581,  1594,  1607,  1620,  1629,  1638,  1648,
-    1658,  1668,  1675,  1682,  1691,  1701,  1711,  1721,  1728,  1735,
-    1744,  1754,  1764,  1793,  1802,  1811,  1816,  1817,  1818,  1818,
-    1818,  1819,  1819,  1819,  1820,  1820,  1822,  1832,  1841,  1848,
-    1858,  1865,  1872,  1879,  1886,  1891,  1892,  1893,  1893,  1894,
-    1894,  1895,  1895,  1896,  1897,  1898,  1899,  1900,  1901,  1903,
-    1911,  1918,  1926,  1934,  1941,  1948,  1957,  1966,  1975,  1984,
-    1993,  2002,  2007,  2008,  2009,  2011,  2017,  2027
+       0,   144,   144,   144,   145,   145,   146,   146,   147,   147,
+     147,   152,   157,   158,   159,   159,   159,   160,   160,   161,
+     161,   162,   162,   163,   163,   164,   164,   164,   165,   165,
+     165,   166,   166,   167,   167,   168,   168,   169,   169,   170,
+     170,   171,   171,   172,   172,   173,   173,   174,   174,   174,
+     175,   175,   175,   176,   176,   176,   177,   177,   178,   178,
+     179,   179,   180,   180,   181,   181,   181,   182,   182,   183,
+     183,   184,   184,   184,   185,   185,   186,   186,   187,   187,
+     188,   188,   188,   189,   189,   190,   190,   191,   191,   192,
+     192,   193,   193,   194,   194,   194,   195,   195,   196,   196,
+     196,   197,   197,   197,   198,   198,   198,   199,   199,   199,
+     199,   200,   200,   200,   201,   201,   201,   202,   202,   203,
+     203,   204,   204,   205,   205,   206,   206,   206,   207,   207,
+     208,   208,   209,   210,   210,   211,   212,   212,   213,   213,
+     214,   214,   214,   215,   215,   216,   216,   217,   217,   218,
+     218,   219,   219,   219,   220,   220,   220,   221,   221,   223,
+     235,   236,   237,   237,   237,   237,   237,   238,   240,   252,
+     253,   254,   254,   254,   254,   255,   257,   271,   272,   273,
+     273,   273,   273,   274,   274,   276,   285,   294,   305,   314,
+     323,   332,   343,   352,   365,   380,   389,   398,   407,   416,
+     425,   434,   443,   452,   461,   470,   479,   488,   497,   506,
+     515,   522,   529,   538,   547,   556,   570,   579,   588,   597,
+     604,   611,   637,   645,   652,   659,   666,   673,   681,   689,
+     697,   704,   711,   720,   729,   736,   743,   751,   759,   769,
+     779,   789,   802,   813,   821,   834,   843,   852,   861,   871,
+     881,   889,   902,   911,   919,   928,   936,   949,   958,   965,
+     975,   985,   995,  1005,  1015,  1025,  1035,  1045,  1052,  1059,
+    1066,  1075,  1084,  1093,  1100,  1110,  1127,  1134,  1152,  1165,
+    1178,  1187,  1196,  1205,  1214,  1224,  1234,  1243,  1252,  1265,
+    1274,  1281,  1290,  1299,  1308,  1317,  1325,  1338,  1346,  1374,
+    1381,  1396,  1406,  1416,  1423,  1430,  1439,  1453,  1472,  1491,
+    1503,  1515,  1527,  1538,  1557,  1567,  1576,  1584,  1592,  1605,
+    1618,  1631,  1644,  1653,  1662,  1672,  1682,  1692,  1699,  1706,
+    1715,  1725,  1735,  1745,  1752,  1759,  1768,  1778,  1788,  1817,
+    1827,  1835,  1844,  1853,  1858,  1859,  1860,  1860,  1860,  1861,
+    1861,  1861,  1862,  1862,  1864,  1874,  1883,  1890,  1900,  1907,
+    1914,  1921,  1928,  1933,  1934,  1935,  1935,  1936,  1936,  1937,
+    1937,  1938,  1939,  1940,  1941,  1942,  1943,  1945,  1953,  1960,
+    1968,  1976,  1983,  1990,  1999,  2008,  2017,  2026,  2035,  2044,
+    2049,  2050,  2051,  2053,  2059,  2069,  2076,  2085
 };
 #endif
 
@@ -948,13 +957,13 @@ static const char *const yytname[] =
   "VAR_DNSTAP_LOG_CLIENT_QUERY_MESSAGES",
   "VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES",
   "VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES",
-  "VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES",
-  "VAR_HARDEN_ALGO_DOWNGRADE", "VAR_IP_TRANSPARENT",
-  "VAR_DISABLE_DNSSEC_LAME_CHECK", "VAR_IP_RATELIMIT",
-  "VAR_IP_RATELIMIT_SLABS", "VAR_IP_RATELIMIT_SIZE", "VAR_RATELIMIT",
-  "VAR_RATELIMIT_SLABS", "VAR_RATELIMIT_SIZE", "VAR_RATELIMIT_FOR_DOMAIN",
-  "VAR_RATELIMIT_BELOW_DOMAIN", "VAR_IP_RATELIMIT_FACTOR",
-  "VAR_RATELIMIT_FACTOR", "VAR_CAPS_WHITELIST",
+  "VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES", "VAR_RESPONSE_IP_TAG",
+  "VAR_RESPONSE_IP", "VAR_RESPONSE_IP_DATA", "VAR_HARDEN_ALGO_DOWNGRADE",
+  "VAR_IP_TRANSPARENT", "VAR_DISABLE_DNSSEC_LAME_CHECK",
+  "VAR_IP_RATELIMIT", "VAR_IP_RATELIMIT_SLABS", "VAR_IP_RATELIMIT_SIZE",
+  "VAR_RATELIMIT", "VAR_RATELIMIT_SLABS", "VAR_RATELIMIT_SIZE",
+  "VAR_RATELIMIT_FOR_DOMAIN", "VAR_RATELIMIT_BELOW_DOMAIN",
+  "VAR_IP_RATELIMIT_FACTOR", "VAR_RATELIMIT_FACTOR", "VAR_CAPS_WHITELIST",
   "VAR_CACHE_MAX_NEGATIVE_TTL", "VAR_PERMIT_SMALL_HOLDDOWN",
   "VAR_QNAME_MINIMISATION", "VAR_QNAME_MINIMISATION_STRICT",
   "VAR_IP_FREEBIND", "VAR_DEFINE_TAG", "VAR_LOCAL_ZONE_TAG",
@@ -1019,16 +1028,18 @@ static const char *const yytname[] =
   "server_dns64_synthall", "server_define_tag", "server_local_zone_tag",
   "server_access_control_tag", "server_access_control_tag_action",
   "server_access_control_tag_data", "server_local_zone_override",
-  "server_access_control_view", "server_ip_ratelimit", "server_ratelimit",
-  "server_ip_ratelimit_size", "server_ratelimit_size",
-  "server_ip_ratelimit_slabs", "server_ratelimit_slabs",
-  "server_ratelimit_for_domain", "server_ratelimit_below_domain",
-  "server_ip_ratelimit_factor", "server_ratelimit_factor",
-  "server_qname_minimisation", "server_qname_minimisation_strict",
-  "stub_name", "stub_host", "stub_addr", "stub_first", "stub_ssl_upstream",
-  "stub_prime", "forward_name", "forward_host", "forward_addr",
-  "forward_first", "forward_ssl_upstream", "view_name", "view_local_zone",
-  "view_local_data", "view_first", "rcstart", "contents_rc", "content_rc",
+  "server_access_control_view", "server_response_ip_tag",
+  "server_ip_ratelimit", "server_ratelimit", "server_ip_ratelimit_size",
+  "server_ratelimit_size", "server_ip_ratelimit_slabs",
+  "server_ratelimit_slabs", "server_ratelimit_for_domain",
+  "server_ratelimit_below_domain", "server_ip_ratelimit_factor",
+  "server_ratelimit_factor", "server_qname_minimisation",
+  "server_qname_minimisation_strict", "stub_name", "stub_host",
+  "stub_addr", "stub_first", "stub_ssl_upstream", "stub_prime",
+  "forward_name", "forward_host", "forward_addr", "forward_first",
+  "forward_ssl_upstream", "view_name", "view_local_zone",
+  "view_response_ip", "view_response_ip_data", "view_local_data",
+  "view_first", "rcstart", "contents_rc", "content_rc",
   "rc_control_enable", "rc_control_port", "rc_control_interface",
   "rc_control_use_cert", "rc_server_key_file", "rc_server_cert_file",
   "rc_control_key_file", "rc_control_cert_file", "dtstart", "contents_dt",
@@ -1042,7 +1053,8 @@ static const char *const yytname[] =
   "dt_dnstap_log_forwarder_query_messages",
   "dt_dnstap_log_forwarder_response_messages", "pythonstart",
   "contents_py", "content_py", "py_script",
-  "server_disable_dnssec_lame_check", "server_log_identity", YY_NULLPTR
+  "server_disable_dnssec_lame_check", "server_log_identity",
+  "server_response_ip", "server_response_ip_data", YY_NULLPTR
 };
 #endif
 
@@ -1070,7 +1082,7 @@ static const yytype_uint16 yytoknum[] =
      415,   416,   417,   418,   419,   420,   421,   422,   423,   424,
      425,   426,   427,   428,   429,   430,   431,   432,   433,   434,
      435,   436,   437,   438,   439,   440,   441,   442,   443,   444,
-     445,   446
+     445,   446,   447,   448,   449
 };
 # endif
 
@@ -1089,22 +1101,22 @@ static const yytype_uint16 yytoknum[] =
 static const yytype_int16 yypact[] =
 {
     -132,     0,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,   134,   -39,
-     -35,   -11,   -62,  -131,  -106,    -4,    -3,    -2,    -1,     2,
-      17,    18,    28,    29,    30,    32,    33,    34,    35,    36,
-      38,    39,    40,    41,    42,    43,    44,    45,    46,    47,
-      48,    49,    50,    51,    52,    53,    57,    58,    59,    60,
-      61,    62,    63,    64,    65,    66,    67,    68,    69,    70,
-      71,    72,    73,    74,    75,    76,    77,    78,    79,    80,
-      82,    83,    85,    88,    90,    91,    92,    93,    94,    95,
-      96,    98,    99,   100,   101,   102,   103,   104,   105,   106,
-     107,   108,   109,   110,   111,   112,   113,   114,   115,   116,
-     117,   118,   119,   120,   121,   122,   123,   124,   125,   126,
-     127,   128,   129,   130,   131,   132,   133,   165,   166,   167,
-     171,   172,   215,   216,   217,   218,   219,   220,   221,   222,
-     223,   227,   231,   232,   256,   257,   258,   259,   269,   270,
-     271,   272,   273,   274,   275,   276,   277,   278,   279,   280,
-     281,   307,   309,   316,   317,   318,   319,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,   137,   -39,
+     -35,   193,   -65,  -131,  -106,    -4,    -3,    -2,    -1,     2,
+      25,    26,    27,    28,    29,    30,    32,    33,    34,    35,
+      36,    38,    39,    40,    41,    42,    43,    44,    45,    46,
+      47,    48,    49,    50,    51,    52,    53,    55,    56,    57,
+      58,    59,    60,    61,    62,    63,    64,    65,    66,    67,
+      68,    69,    70,    71,    72,    73,    74,    75,    76,    77,
+      78,    79,    80,    82,    83,    85,    88,    90,    91,    92,
+      93,    94,    95,    96,    98,    99,   100,   101,   102,   103,
+     104,   105,   106,   107,   108,   109,   110,   111,   112,   113,
+     114,   115,   116,   117,   118,   119,   120,   121,   122,   123,
+     124,   125,   126,   127,   128,   129,   130,   131,   132,   133,
+     134,   136,   138,   167,   168,   169,   170,   174,   175,   218,
+     219,   220,   221,   222,   224,   225,   226,   230,   234,   235,
+     261,   262,   272,   273,   274,   275,   276,   277,   278,   279,
+     280,   281,   282,   283,   284,   313,   315,   322,   323,   324,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
@@ -1119,33 +1131,35 @@ static const yytype_int16 yypact[] =
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-     320,   321,   322,   323,   324,   325,  -132,  -132,  -132,  -132,
-    -132,  -132,  -132,   326,   327,   328,   329,   330,  -132,  -132,
-    -132,  -132,  -132,  -132,   331,   332,   333,   334,  -132,  -132,
-    -132,  -132,  -132,   335,   336,   337,   338,   339,   340,   341,
-     342,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-     343,   344,   345,   346,   347,   348,   349,   350,   351,   352,
-     353,   354,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,  -132,  -132,  -132,   355,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,  -132,  -132,   325,   326,   327,   328,
+     329,   330,  -132,  -132,  -132,  -132,  -132,  -132,  -132,   331,
+     332,   333,   334,   335,  -132,  -132,  -132,  -132,  -132,  -132,
+     336,   337,   338,   339,   340,   341,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,   344,   345,   346,   347,   348,   349,   350,
+     351,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
+     352,   353,   354,   355,   356,   357,   358,   359,   360,   361,
+     362,   363,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,  -132,   364,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,  -132,  -132,   356,   357,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,   365,   366,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,   367,   368,
+     369,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
+     370,   372,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
+    -132,   373,   374,   375,   376,   377,   378,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,  -132,  -132,  -132,  -132,  -132,   358,   359,  -132,
-    -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,   360,   361,
-     362,   363,   364,   365,  -132,  -132,  -132,  -132,  -132,  -132,
+    -132,  -132,  -132,  -132,  -132,   379,  -132,   380,   381,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,   366,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132,   367,   368,   369,  -132,  -132,  -132,  -132,  -132
+     382,   383,   384,  -132,  -132,  -132,  -132,  -132,  -132,  -132
 };
 
   /* YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM.
@@ -1153,8 +1167,8 @@ static const yytype_int16 yypact[] =
      means the default is an error.  */
 static const yytype_uint16 yydefact[] =
 {
-       2,     0,     1,    11,   156,   165,   335,   381,   354,   173,
-       3,    13,   158,   167,   175,   337,   356,   383,     4,     5,
+       2,     0,     1,    11,   159,   168,   343,   389,   362,   176,
+       3,    13,   161,   170,   178,   345,   364,   391,     4,     5,
        6,    10,     8,     9,     7,     0,     0,     0,     0,     0,
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
@@ -1169,48 +1183,50 @@ static const yytype_uint16 yydefact[] =
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
-       0,     0,     0,     0,     0,     0,     0,    12,    14,    15,
-      74,    77,    86,   154,   155,    16,    25,    65,    17,    78,
-      79,    36,    58,    73,    18,    19,    21,    22,    20,    23,
-      24,   109,   110,   111,   112,   113,   153,    75,    64,    90,
-     107,   108,    26,    27,    28,    29,    30,    66,    80,    81,
-      96,    52,    62,    53,    91,    46,    47,    48,    49,   100,
-     104,   117,   125,   140,   101,    59,    31,    32,    33,    88,
-     118,   119,   120,    34,    35,    37,    38,    40,    41,    39,
-     123,    42,    43,    44,    50,    69,   105,    83,   124,    76,
-     136,    84,    85,   102,   103,    89,    45,    67,    70,    51,
-      54,    92,    93,    68,   137,    94,    55,    56,    57,   106,
-     150,   151,    95,    63,    97,    98,    99,   138,    60,    61,
-      82,    71,    72,    87,   114,   115,   116,   121,   122,   141,
-     142,   144,   146,   147,   145,   148,   126,   127,   130,   131,
-     128,   129,   132,   133,   135,   134,   139,   149,   143,   152,
-       0,     0,     0,     0,     0,     0,   157,   159,   160,   161,
-     163,   164,   162,     0,     0,     0,     0,     0,   166,   168,
-     169,   170,   171,   172,     0,     0,     0,     0,   174,   176,
-     177,   178,   179,     0,     0,     0,     0,     0,     0,     0,
-       0,   336,   338,   340,   339,   345,   341,   342,   343,   344,
        0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
-       0,     0,   355,   357,   358,   359,   360,   361,   362,   363,
-     364,   365,   366,   367,   368,     0,   382,   384,   181,   180,
-     187,   190,   188,   196,   197,   200,   198,   199,   201,   202,
-     214,   215,   216,   217,   218,   238,   239,   240,   245,   246,
-     193,   247,   248,   251,   249,   250,   253,   254,   255,   268,
-     227,   228,   229,   230,   256,   271,   223,   225,   272,   278,
-     279,   280,   194,   237,   290,   291,   224,   285,   210,   189,
-     219,   269,   275,   257,     0,     0,   294,   195,   182,   209,
-     261,   183,   191,   192,   220,   221,   292,   259,   263,   264,
-     184,   295,   241,   267,   211,   226,   273,   274,   277,   284,
-     222,   288,   286,   287,   231,   236,   265,   266,   232,   233,
-     258,   281,   212,   213,   203,   204,   205,   206,   207,   296,
-     297,   298,   242,   243,   244,   252,   299,   300,   260,   234,
-     386,   308,   312,   310,   309,   313,   311,     0,     0,   316,
-     317,   262,   276,   289,   318,   319,   235,   301,     0,     0,
-       0,     0,     0,     0,   282,   283,   387,   208,   185,   186,
-     320,   321,   322,   325,   324,   323,   326,   327,   328,   329,
-     330,   331,     0,   333,   334,   346,   348,   347,   350,   351,
-     352,   353,   349,   369,   370,   371,   372,   373,   374,   375,
-     376,   377,   378,   379,   380,   385,   270,   293,   314,   315,
-     302,   303,     0,     0,     0,   307,   332,   306,   304,   305
+      12,    14,    15,    74,    77,    86,   157,   158,    16,    25,
+      65,    17,    78,    79,    36,    58,    73,    18,    19,    21,
+      22,    20,    23,    24,   109,   110,   111,   112,   113,   153,
+      75,    64,    90,   107,   108,    26,    27,    28,    29,    30,
+      66,    80,    81,    96,    52,    62,    53,    91,    46,    47,
+      48,    49,   100,   104,   117,   125,   140,   101,    59,    31,
+      32,    33,    88,   118,   119,   120,    34,    35,    37,    38,
+      40,    41,    39,   123,    42,    43,    44,    50,    69,   105,
+      83,   124,    76,   136,    84,    85,   102,   103,    89,    45,
+      67,    70,    51,    54,    92,    93,    68,   137,    94,    55,
+      56,    57,   106,   150,   151,    95,    63,    97,    98,    99,
+     138,    60,    61,    82,    71,    72,    87,   114,   115,   116,
+     121,   122,   141,   142,   144,   146,   147,   145,   148,   154,
+     126,   127,   130,   131,   128,   129,   132,   133,   135,   134,
+     139,   149,   143,   152,   155,   156,     0,     0,     0,     0,
+       0,     0,   160,   162,   163,   164,   166,   167,   165,     0,
+       0,     0,     0,     0,   169,   171,   172,   173,   174,   175,
+       0,     0,     0,     0,     0,     0,   177,   179,   180,   183,
+     184,   181,   182,     0,     0,     0,     0,     0,     0,     0,
+       0,   344,   346,   348,   347,   353,   349,   350,   351,   352,
+       0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
+       0,     0,   363,   365,   366,   367,   368,   369,   370,   371,
+     372,   373,   374,   375,   376,     0,   390,   392,   186,   185,
+     192,   195,   193,   201,   202,   205,   203,   204,   206,   207,
+     219,   220,   221,   222,   223,   243,   244,   245,   250,   251,
+     198,   252,   253,   256,   254,   255,   258,   259,   260,   273,
+     232,   233,   234,   235,   261,   276,   228,   230,   277,   283,
+     284,   285,   199,   242,   295,   296,   229,   290,   215,   194,
+     224,   274,   280,   262,     0,     0,   299,   200,   187,   214,
+     266,   188,   196,   197,   225,   226,   297,   264,   268,   269,
+     189,   300,   246,   272,   216,   231,   278,   279,   282,   289,
+     227,   293,   291,   292,   236,   241,   270,   271,   237,   238,
+     263,   286,   217,   218,   208,   209,   210,   211,   212,   301,
+     302,   303,   247,   248,   249,   257,   304,   305,     0,     0,
+       0,   265,   239,   394,   314,   318,   316,   315,   319,   317,
+       0,     0,   322,   323,   267,   281,   294,   324,   325,   240,
+     306,     0,     0,     0,     0,     0,     0,   287,   288,   395,
+     213,   190,   191,   326,   327,   328,   331,   330,   329,   332,
+     333,   334,   335,   336,   337,     0,   341,     0,     0,   342,
+     354,   356,   355,   358,   359,   360,   361,   357,   377,   378,
+     379,   380,   381,   382,   383,   384,   385,   386,   387,   388,
+     393,   275,   298,   313,   396,   397,   320,   321,   307,   308,
+       0,     0,     0,   312,   338,   339,   340,   311,   309,   310
 };
 
   /* YYPGOTO[NTERM-NUM].  */
@@ -1236,33 +1252,33 @@ static const yytype_int16 yypgoto[] =
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
     -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,  -132,
-    -132,  -132
+    -132,  -132,  -132,  -132,  -132,  -132,  -132
 };
 
   /* YYDEFGOTO[NTERM-NUM].  */
 static const yytype_int16 yydefgoto[] =
 {
-      -1,     1,    10,    11,    18,   167,    12,    19,   316,    13,
-      20,   328,    14,    21,   338,   168,   169,   170,   171,   172,
-     173,   174,   175,   176,   177,   178,   179,   180,   181,   182,
-     183,   184,   185,   186,   187,   188,   189,   190,   191,   192,
-     193,   194,   195,   196,   197,   198,   199,   200,   201,   202,
-     203,   204,   205,   206,   207,   208,   209,   210,   211,   212,
-     213,   214,   215,   216,   217,   218,   219,   220,   221,   222,
-     223,   224,   225,   226,   227,   228,   229,   230,   231,   232,
-     233,   234,   235,   236,   237,   238,   239,   240,   241,   242,
-     243,   244,   245,   246,   247,   248,   249,   250,   251,   252,
-     253,   254,   255,   256,   257,   258,   259,   260,   261,   262,
-     263,   264,   265,   266,   267,   268,   269,   270,   271,   272,
-     273,   274,   275,   276,   277,   278,   279,   280,   281,   282,
-     283,   284,   285,   286,   287,   288,   289,   290,   291,   292,
-     293,   294,   295,   296,   297,   298,   299,   300,   301,   302,
-     303,   304,   305,   306,   307,   317,   318,   319,   320,   321,
-     322,   329,   330,   331,   332,   333,   339,   340,   341,   342,
-      15,    22,   351,   352,   353,   354,   355,   356,   357,   358,
-     359,    16,    23,   372,   373,   374,   375,   376,   377,   378,
-     379,   380,   381,   382,   383,   384,    17,    24,   386,   387,
-     308,   309
+      -1,     1,    10,    11,    18,   170,    12,    19,   322,    13,
+      20,   334,    14,    21,   346,   171,   172,   173,   174,   175,
+     176,   177,   178,   179,   180,   181,   182,   183,   184,   185,
+     186,   187,   188,   189,   190,   191,   192,   193,   194,   195,
+     196,   197,   198,   199,   200,   201,   202,   203,   204,   205,
+     206,   207,   208,   209,   210,   211,   212,   213,   214,   215,
+     216,   217,   218,   219,   220,   221,   222,   223,   224,   225,
+     226,   227,   228,   229,   230,   231,   232,   233,   234,   235,
+     236,   237,   238,   239,   240,   241,   242,   243,   244,   245,
+     246,   247,   248,   249,   250,   251,   252,   253,   254,   255,
+     256,   257,   258,   259,   260,   261,   262,   263,   264,   265,
+     266,   267,   268,   269,   270,   271,   272,   273,   274,   275,
+     276,   277,   278,   279,   280,   281,   282,   283,   284,   285,
+     286,   287,   288,   289,   290,   291,   292,   293,   294,   295,
+     296,   297,   298,   299,   300,   301,   302,   303,   304,   305,
+     306,   307,   308,   309,   310,   311,   323,   324,   325,   326,
+     327,   328,   335,   336,   337,   338,   339,   347,   348,   349,
+     350,   351,   352,    15,    22,   361,   362,   363,   364,   365,
+     366,   367,   368,   369,    16,    23,   382,   383,   384,   385,
+     386,   387,   388,   389,   390,   391,   392,   393,   394,    17,
+      24,   396,   397,   312,   313,   314,   315
 };
 
   /* YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM.  If
@@ -1270,55 +1286,57 @@ static const yytype_int16 yydefgoto[] =
      number is the opposite.  If YYTABLE_NINF, syntax error.  */
 static const yytype_uint16 yytable[] =
 {
-       2,   310,   385,   311,   312,   323,   388,   389,   390,   391,
-       0,     3,   392,   324,   325,   360,   361,   362,   363,   364,
-     365,   366,   367,   368,   369,   370,   371,   393,   394,   334,
-     343,   344,   345,   346,   347,   348,   349,   350,   395,   396,
-     397,     4,   398,   399,   400,   401,   402,     5,   403,   404,
-     405,   406,   407,   408,   409,   410,   411,   412,   413,   414,
-     415,   416,   417,   418,   313,   335,   336,   419,   420,   421,
-     422,   423,   424,   425,   426,   427,   428,   429,   430,   431,
-     432,   433,   434,   435,   436,   437,   438,   439,   440,   441,
-     442,     6,   443,   444,   314,   445,   315,   326,   446,   327,
-     447,   448,   449,   450,   451,   452,   453,     7,   454,   455,
-     456,   457,   458,   459,   460,   461,   462,   463,   464,   465,
-     466,   467,   468,   469,   470,   471,   472,   473,   474,   475,
-     476,   477,   478,   479,   480,   481,   482,   483,   484,   485,
-     486,   487,   488,   489,     0,     8,    25,    26,    27,    28,
-      29,    30,    31,    32,    33,    34,    35,    36,    37,    38,
-      39,    40,    41,    42,    43,    44,    45,    46,    47,    48,
-      49,    50,    51,    52,   337,   490,   491,   492,    53,    54,
-      55,   493,   494,     9,    56,    57,    58,    59,    60,    61,
-      62,    63,    64,    65,    66,    67,    68,    69,    70,    71,
-      72,    73,    74,    75,    76,    77,    78,    79,    80,    81,
-      82,    83,    84,    85,    86,    87,    88,    89,    90,    91,
-      92,    93,    94,    95,    96,   495,   496,   497,   498,   499,
-     500,   501,   502,   503,    97,    98,    99,   504,   100,   101,
-     102,   505,   506,   103,   104,   105,   106,   107,   108,   109,
-     110,   111,   112,   113,   114,   115,   116,   117,   118,   119,
-     120,   121,   122,   123,   124,   125,   507,   508,   509,   510,
-     126,   127,   128,   129,   130,   131,   132,   133,   134,   511,
-     512,   513,   514,   515,   516,   517,   518,   519,   520,   521,
-     522,   523,   135,   136,   137,   138,   139,   140,   141,   142,
-     143,   144,   145,   146,   147,   148,   149,   150,   151,   152,
-     153,   154,   155,   156,   157,   158,   159,   524,   160,   525,
-     161,   162,   163,   164,   165,   166,   526,   527,   528,   529,
-     530,   531,   532,   533,   534,   535,   536,   537,   538,   539,
-     540,   541,   542,   543,   544,   545,   546,   547,   548,   549,
-     550,   551,   552,   553,   554,   555,   556,   557,   558,   559,
-     560,   561,   562,   563,   564,   565,   566,   567,   568,   569,
-     570,   571,   572,   573,   574,   575,   576,   577,   578,   579
+       2,   316,   395,   317,   318,   329,   398,   399,   400,   401,
+       0,     3,   402,   330,   331,   370,   371,   372,   373,   374,
+     375,   376,   377,   378,   379,   380,   381,   353,   354,   355,
+     356,   357,   358,   359,   360,   403,   404,   405,   406,   407,
+     408,     4,   409,   410,   411,   412,   413,     5,   414,   415,
+     416,   417,   418,   419,   420,   421,   422,   423,   424,   425,
+     426,   427,   428,   429,   319,   430,   431,   432,   433,   434,
+     435,   436,   437,   438,   439,   440,   441,   442,   443,   444,
+     445,   446,   447,   448,   449,   450,   451,   452,   453,   454,
+     455,     6,   456,   457,   320,   458,   321,   332,   459,   333,
+     460,   461,   462,   463,   464,   465,   466,     7,   467,   468,
+     469,   470,   471,   472,   473,   474,   475,   476,   477,   478,
+     479,   480,   481,   482,   483,   484,   485,   486,   487,   488,
+     489,   490,   491,   492,   493,   494,   495,   496,   497,   498,
+     499,   500,   501,   502,   503,     8,   504,     0,   505,    25,
+      26,    27,    28,    29,    30,    31,    32,    33,    34,    35,
+      36,    37,    38,    39,    40,    41,    42,    43,    44,    45,
+      46,    47,    48,    49,    50,    51,    52,   506,   507,   508,
+     509,    53,    54,    55,   510,   511,     9,    56,    57,    58,
+      59,    60,    61,    62,    63,    64,    65,    66,    67,    68,
+      69,    70,    71,    72,    73,    74,    75,    76,    77,    78,
+      79,    80,    81,    82,    83,    84,    85,    86,    87,    88,
+      89,    90,    91,    92,    93,    94,    95,    96,   512,   513,
+     514,   515,   516,   340,   517,   518,   519,    97,    98,    99,
+     520,   100,   101,   102,   521,   522,   103,   104,   105,   106,
+     107,   108,   109,   110,   111,   112,   113,   114,   115,   116,
+     117,   118,   119,   120,   121,   122,   123,   124,   125,   341,
+     342,   523,   524,   126,   127,   128,   129,   130,   131,   132,
+     133,   134,   525,   526,   527,   528,   529,   530,   531,   532,
+     533,   534,   535,   536,   537,   135,   136,   137,   138,   139,
+     140,   141,   142,   143,   144,   145,   146,   147,   148,   149,
+     150,   151,   152,   153,   154,   155,   156,   157,   158,   159,
+     160,   161,   162,   538,   163,   539,   164,   165,   166,   167,
+     168,   169,   540,   541,   542,   543,   544,   545,   546,   547,
+     548,   549,   550,   551,   552,   553,   554,   555,   556,   557,
+     558,   559,   343,   344,   560,   561,   562,   563,   564,   565,
+     566,   567,   568,   569,   570,   571,   572,   573,   574,   575,
+     576,   577,   578,   579,   580,   581,   582,   583,   584,   585,
+     586,   345,   587,   588,   589,   590,   591,   592,   593,   594,
+     595,   596,   597,   598,   599
 };
 
 static const yytype_int16 yycheck[] =
 {
        0,    40,   108,    42,    43,    40,    10,    10,    10,    10,
       -1,    11,    10,    48,    49,   146,   147,   148,   149,   150,
-     151,   152,   153,   154,   155,   156,   157,    10,    10,    40,
-      92,    93,    94,    95,    96,    97,    98,    99,    10,    10,
+     151,   152,   153,   154,   155,   156,   157,    92,    93,    94,
+      95,    96,    97,    98,    99,    10,    10,    10,    10,    10,
       10,    41,    10,    10,    10,    10,    10,    47,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
-      10,    10,    10,    10,   103,    76,    77,    10,    10,    10,
+      10,    10,    10,    10,   103,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    91,    10,    10,   133,    10,   135,   132,    10,   134,
@@ -1326,39 +1344,41 @@ static const yytype_int16 yycheck[] =
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
-      10,    10,    10,    10,    -1,   145,    12,    13,    14,    15,
-      16,    17,    18,    19,    20,    21,    22,    23,    24,    25,
-      26,    27,    28,    29,    30,    31,    32,    33,    34,    35,
-      36,    37,    38,    39,   185,    10,    10,    10,    44,    45,
-      46,    10,    10,   183,    50,    51,    52,    53,    54,    55,
-      56,    57,    58,    59,    60,    61,    62,    63,    64,    65,
-      66,    67,    68,    69,    70,    71,    72,    73,    74,    75,
-      76,    77,    78,    79,    80,    81,    82,    83,    84,    85,
-      86,    87,    88,    89,    90,    10,    10,    10,    10,    10,
-      10,    10,    10,    10,   100,   101,   102,    10,   104,   105,
-     106,    10,    10,   109,   110,   111,   112,   113,   114,   115,
-     116,   117,   118,   119,   120,   121,   122,   123,   124,   125,
-     126,   127,   128,   129,   130,   131,    10,    10,    10,    10,
-     136,   137,   138,   139,   140,   141,   142,   143,   144,    10,
-      10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
-      10,    10,   158,   159,   160,   161,   162,   163,   164,   165,
-     166,   167,   168,   169,   170,   171,   172,   173,   174,   175,
-     176,   177,   178,   179,   180,   181,   182,    10,   184,    10,
-     186,   187,   188,   189,   190,   191,    10,    10,    10,    10,
-      10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
+      10,    10,    10,    10,    10,   145,    10,    -1,    10,    12,
+      13,    14,    15,    16,    17,    18,    19,    20,    21,    22,
+      23,    24,    25,    26,    27,    28,    29,    30,    31,    32,
+      33,    34,    35,    36,    37,    38,    39,    10,    10,    10,
+      10,    44,    45,    46,    10,    10,   186,    50,    51,    52,
+      53,    54,    55,    56,    57,    58,    59,    60,    61,    62,
+      63,    64,    65,    66,    67,    68,    69,    70,    71,    72,
+      73,    74,    75,    76,    77,    78,    79,    80,    81,    82,
+      83,    84,    85,    86,    87,    88,    89,    90,    10,    10,
+      10,    10,    10,    40,    10,    10,    10,   100,   101,   102,
+      10,   104,   105,   106,    10,    10,   109,   110,   111,   112,
+     113,   114,   115,   116,   117,   118,   119,   120,   121,   122,
+     123,   124,   125,   126,   127,   128,   129,   130,   131,    76,
+      77,    10,    10,   136,   137,   138,   139,   140,   141,   142,
+     143,   144,    10,    10,    10,    10,    10,    10,    10,    10,
+      10,    10,    10,    10,    10,   158,   159,   160,   161,   162,
+     163,   164,   165,   166,   167,   168,   169,   170,   171,   172,
+     173,   174,   175,   176,   177,   178,   179,   180,   181,   182,
+     183,   184,   185,    10,   187,    10,   189,   190,   191,   192,
+     193,   194,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
+      10,    10,   159,   160,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
-      10,    10,    10,    10,    10,    10,    10,    10,    10,    10
+      10,   188,    10,    10,    10,    10,    10,    10,    10,    10,
+      10,    10,    10,    10,    10
 };
 
   /* YYSTOS[STATE-NUM] -- The (internal number of the) accessing
      symbol of state STATE-NUM.  */
 static const yytype_uint16 yystos[] =
 {
-       0,   193,     0,    11,    41,    47,    91,   107,   145,   183,
-     194,   195,   198,   201,   204,   362,   373,   388,   196,   199,
-     202,   205,   363,   374,   389,    12,    13,    14,    15,    16,
+       0,   196,     0,    11,    41,    47,    91,   107,   145,   186,
+     197,   198,   201,   204,   207,   368,   379,   394,   199,   202,
+     205,   208,   369,   380,   395,    12,    13,    14,    15,    16,
       17,    18,    19,    20,    21,    22,    23,    24,    25,    26,
       27,    28,    29,    30,    31,    32,    33,    34,    35,    36,
       37,    38,    39,    44,    45,    46,    50,    51,    52,    53,
@@ -1372,8 +1392,8 @@ static const yytype_uint16 yystos[] =
      140,   141,   142,   143,   144,   158,   159,   160,   161,   162,
      163,   164,   165,   166,   167,   168,   169,   170,   171,   172,
      173,   174,   175,   176,   177,   178,   179,   180,   181,   182,
-     184,   186,   187,   188,   189,   190,   191,   197,   207,   208,
-     209,   210,   211,   212,   213,   214,   215,   216,   217,   218,
+     183,   184,   185,   187,   189,   190,   191,   192,   193,   194,
+     200,   210,   211,   212,   213,   214,   215,   216,   217,   218,
      219,   220,   221,   222,   223,   224,   225,   226,   227,   228,
      229,   230,   231,   232,   233,   234,   235,   236,   237,   238,
      239,   240,   241,   242,   243,   244,   245,   246,   247,   248,
@@ -1386,15 +1406,17 @@ static const yytype_uint16 yystos[] =
      309,   310,   311,   312,   313,   314,   315,   316,   317,   318,
      319,   320,   321,   322,   323,   324,   325,   326,   327,   328,
      329,   330,   331,   332,   333,   334,   335,   336,   337,   338,
-     339,   340,   341,   342,   343,   344,   345,   346,   392,   393,
-      40,    42,    43,   103,   133,   135,   200,   347,   348,   349,
-     350,   351,   352,    40,    48,    49,   132,   134,   203,   353,
-     354,   355,   356,   357,    40,    76,    77,   185,   206,   358,
-     359,   360,   361,    92,    93,    94,    95,    96,    97,    98,
-      99,   364,   365,   366,   367,   368,   369,   370,   371,   372,
+     339,   340,   341,   342,   343,   344,   345,   346,   347,   348,
+     349,   350,   398,   399,   400,   401,    40,    42,    43,   103,
+     133,   135,   203,   351,   352,   353,   354,   355,   356,    40,
+      48,    49,   132,   134,   206,   357,   358,   359,   360,   361,
+      40,    76,    77,   159,   160,   188,   209,   362,   363,   364,
+     365,   366,   367,    92,    93,    94,    95,    96,    97,    98,
+      99,   370,   371,   372,   373,   374,   375,   376,   377,   378,
      146,   147,   148,   149,   150,   151,   152,   153,   154,   155,
-     156,   157,   375,   376,   377,   378,   379,   380,   381,   382,
-     383,   384,   385,   386,   387,   108,   390,   391,    10,    10,
+     156,   157,   381,   382,   383,   384,   385,   386,   387,   388,
+     389,   390,   391,   392,   393,   108,   396,   397,    10,    10,
+      10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
       10,    10,    10,    10,    10,    10,    10,    10,    10,    10,
@@ -1419,45 +1441,46 @@ static const yytype_uint16 yystos[] =
   /* YYR1[YYN] -- Symbol number of symbol that rule YYN derives.  */
 static const yytype_uint16 yyr1[] =
 {
-       0,   192,   193,   193,   194,   194,   194,   194,   194,   194,
-     194,   195,   196,   196,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   197,   197,   197,   197,
-     197,   197,   197,   197,   197,   197,   198,   199,   199,   200,
-     200,   200,   200,   200,   200,   201,   202,   202,   203,   203,
-     203,   203,   203,   204,   205,   205,   206,   206,   206,   206,
-     207,   208,   209,   210,   211,   212,   213,   214,   215,   216,
-     217,   218,   219,   220,   221,   222,   223,   224,   225,   226,
-     227,   228,   229,   230,   231,   232,   233,   234,   235,   236,
-     237,   238,   239,   240,   241,   242,   243,   244,   245,   246,
-     247,   248,   249,   250,   251,   252,   253,   254,   255,   256,
-     257,   258,   259,   260,   261,   262,   263,   264,   265,   266,
-     267,   268,   269,   270,   271,   272,   273,   274,   275,   276,
-     277,   278,   279,   280,   281,   282,   283,   284,   285,   286,
-     287,   288,   289,   290,   291,   292,   293,   294,   295,   296,
-     297,   298,   299,   300,   301,   302,   303,   304,   305,   306,
-     307,   308,   309,   310,   311,   312,   313,   314,   315,   316,
-     317,   318,   319,   320,   321,   322,   323,   324,   325,   326,
-     327,   328,   329,   330,   331,   332,   333,   334,   335,   336,
-     337,   338,   339,   340,   341,   342,   343,   344,   345,   346,
-     347,   348,   349,   350,   351,   352,   353,   354,   355,   356,
-     357,   358,   359,   360,   361,   362,   363,   363,   364,   364,
-     364,   364,   364,   364,   364,   364,   365,   366,   367,   368,
-     369,   370,   371,   372,   373,   374,   374,   375,   375,   375,
-     375,   375,   375,   375,   375,   375,   375,   375,   375,   376,
-     377,   378,   379,   380,   381,   382,   383,   384,   385,   386,
-     387,   388,   389,   389,   390,   391,   392,   393
+       0,   195,   196,   196,   197,   197,   197,   197,   197,   197,
+     197,   198,   199,   199,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   200,
+     200,   200,   200,   200,   200,   200,   200,   200,   200,   201,
+     202,   202,   203,   203,   203,   203,   203,   203,   204,   205,
+     205,   206,   206,   206,   206,   206,   207,   208,   208,   209,
+     209,   209,   209,   209,   209,   210,   211,   212,   213,   214,
+     215,   216,   217,   218,   219,   220,   221,   222,   223,   224,
+     225,   226,   227,   228,   229,   230,   231,   232,   233,   234,
+     235,   236,   237,   238,   239,   240,   241,   242,   243,   244,
+     245,   246,   247,   248,   249,   250,   251,   252,   253,   254,
+     255,   256,   257,   258,   259,   260,   261,   262,   263,   264,
+     265,   266,   267,   268,   269,   270,   271,   272,   273,   274,
+     275,   276,   277,   278,   279,   280,   281,   282,   283,   284,
+     285,   286,   287,   288,   289,   290,   291,   292,   293,   294,
+     295,   296,   297,   298,   299,   300,   301,   302,   303,   304,
+     305,   306,   307,   308,   309,   310,   311,   312,   313,   314,
+     315,   316,   317,   318,   319,   320,   321,   322,   323,   324,
+     325,   326,   327,   328,   329,   330,   331,   332,   333,   334,
+     335,   336,   337,   338,   339,   340,   341,   342,   343,   344,
+     345,   346,   347,   348,   349,   350,   351,   352,   353,   354,
+     355,   356,   357,   358,   359,   360,   361,   362,   363,   364,
+     365,   366,   367,   368,   369,   369,   370,   370,   370,   370,
+     370,   370,   370,   370,   371,   372,   373,   374,   375,   376,
+     377,   378,   379,   380,   380,   381,   381,   381,   381,   381,
+     381,   381,   381,   381,   381,   381,   381,   382,   383,   384,
+     385,   386,   387,   388,   389,   390,   391,   392,   393,   394,
+     395,   395,   396,   397,   398,   399,   400,   401
 };
 
   /* YYR2[YYN] -- Number of symbols on the right hand side of rule YYN.  */
@@ -1478,30 +1501,31 @@ static const yytype_uint8 yyr2[] =
        1,     1,     1,     1,     1,     1,     1,     1,     1,     1,
        1,     1,     1,     1,     1,     1,     1,     1,     1,     1,
        1,     1,     1,     1,     1,     1,     1,     1,     1,     1,
-       1,     1,     1,     1,     1,     1,     1,     2,     0,     1,
-       1,     1,     1,     1,     1,     1,     2,     0,     1,     1,
-       1,     1,     1,     1,     2,     0,     1,     1,     1,     1,
-       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
+       1,     1,     1,     1,     1,     1,     1,     1,     1,     1,
+       2,     0,     1,     1,     1,     1,     1,     1,     1,     2,
+       0,     1,     1,     1,     1,     1,     1,     2,     0,     1,
+       1,     1,     1,     1,     1,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       3,     2,     2,     2,     2,     2,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       2,     2,     2,     3,     2,     2,     2,     2,     2,     2,
-       2,     2,     3,     3,     4,     4,     4,     3,     2,     2,
-       2,     2,     2,     2,     3,     3,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       2,     2,     3,     2,     2,     1,     2,     0,     1,     1,
-       1,     1,     1,     1,     1,     1,     2,     2,     2,     2,
-       2,     2,     2,     2,     1,     2,     0,     1,     1,     1,
-       1,     1,     1,     1,     1,     1,     1,     1,     1,     2,
+       2,     2,     2,     2,     2,     3,     2,     2,     2,     2,
        2,     2,     2,     2,     2,     2,     2,     2,     2,     2,
-       2,     1,     2,     0,     1,     2,     2,     2
+       2,     2,     2,     2,     2,     2,     2,     2,     3,     2,
+       2,     2,     2,     2,     2,     2,     2,     3,     3,     4,
+       4,     4,     3,     3,     2,     2,     2,     2,     2,     2,
+       3,     3,     2,     2,     2,     2,     2,     2,     2,     2,
+       2,     2,     2,     2,     2,     2,     2,     2,     3,     3,
+       3,     2,     2,     1,     2,     0,     1,     1,     1,     1,
+       1,     1,     1,     1,     2,     2,     2,     2,     2,     2,
+       2,     2,     1,     2,     0,     1,     1,     1,     1,     1,
+       1,     1,     1,     1,     1,     1,     1,     2,     2,     2,
+       2,     2,     2,     2,     2,     2,     2,     2,     2,     1,
+       2,     0,     1,     2,     2,     2,     3,     3
 };
 
 
@@ -2178,15 +2202,15 @@ yyreduce:
   switch (yyn)
     {
         case 11:
-#line 150 "./util/configparser.y" /* yacc.c:1646  */
+#line 153 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("\nP(server:)\n")); 
        }
-#line 2186 "util/configparser.c" /* yacc.c:1646  */
+#line 2210 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 156:
-#line 220 "./util/configparser.y" /* yacc.c:1646  */
+  case 159:
+#line 224 "./util/configparser.y" /* yacc.c:1646  */
     {
                struct config_stub* s;
                OUTYY(("\nP(stub_zone:)\n")); 
@@ -2197,11 +2221,11 @@ yyreduce:
                } else 
                        yyerror("out of memory");
        }
-#line 2201 "util/configparser.c" /* yacc.c:1646  */
+#line 2225 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 165:
-#line 237 "./util/configparser.y" /* yacc.c:1646  */
+  case 168:
+#line 241 "./util/configparser.y" /* yacc.c:1646  */
     {
                struct config_stub* s;
                OUTYY(("\nP(forward_zone:)\n")); 
@@ -2212,11 +2236,11 @@ yyreduce:
                } else 
                        yyerror("out of memory");
        }
-#line 2216 "util/configparser.c" /* yacc.c:1646  */
+#line 2240 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 173:
-#line 254 "./util/configparser.y" /* yacc.c:1646  */
+  case 176:
+#line 258 "./util/configparser.y" /* yacc.c:1646  */
     {
                struct config_view* s;
                OUTYY(("\nP(view:)\n")); 
@@ -2229,11 +2253,11 @@ yyreduce:
                } else 
                        yyerror("out of memory");
        }
-#line 2233 "util/configparser.c" /* yacc.c:1646  */
+#line 2257 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 180:
-#line 272 "./util/configparser.y" /* yacc.c:1646  */
+  case 185:
+#line 277 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_num_threads:%s)\n", (yyvsp[0].str))); 
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2241,11 +2265,11 @@ yyreduce:
                else cfg_parser->cfg->num_threads = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2245 "util/configparser.c" /* yacc.c:1646  */
+#line 2269 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 181:
-#line 281 "./util/configparser.y" /* yacc.c:1646  */
+  case 186:
+#line 286 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_verbosity:%s)\n", (yyvsp[0].str))); 
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2253,11 +2277,11 @@ yyreduce:
                else cfg_parser->cfg->verbosity = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2257 "util/configparser.c" /* yacc.c:1646  */
+#line 2281 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 182:
-#line 290 "./util/configparser.y" /* yacc.c:1646  */
+  case 187:
+#line 295 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_statistics_interval:%s)\n", (yyvsp[0].str))); 
                if(strcmp((yyvsp[0].str), "") == 0 || strcmp((yyvsp[0].str), "0") == 0)
@@ -2267,11 +2291,11 @@ yyreduce:
                else cfg_parser->cfg->stat_interval = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2271 "util/configparser.c" /* yacc.c:1646  */
+#line 2295 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 183:
-#line 301 "./util/configparser.y" /* yacc.c:1646  */
+  case 188:
+#line 306 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_statistics_cumulative:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2279,11 +2303,11 @@ yyreduce:
                else cfg_parser->cfg->stat_cumulative = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2283 "util/configparser.c" /* yacc.c:1646  */
+#line 2307 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 184:
-#line 310 "./util/configparser.y" /* yacc.c:1646  */
+  case 189:
+#line 315 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_extended_statistics:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2291,11 +2315,11 @@ yyreduce:
                else cfg_parser->cfg->stat_extended = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2295 "util/configparser.c" /* yacc.c:1646  */
+#line 2319 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 185:
-#line 319 "./util/configparser.y" /* yacc.c:1646  */
+  case 190:
+#line 324 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_shm_enable:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2303,11 +2327,11 @@ yyreduce:
                else cfg_parser->cfg->shm_enable = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2307 "util/configparser.c" /* yacc.c:1646  */
+#line 2331 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 186:
-#line 328 "./util/configparser.y" /* yacc.c:1646  */
+  case 191:
+#line 333 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_shm_key:%s)\n", (yyvsp[0].str))); 
                if(strcmp((yyvsp[0].str), "") == 0 || strcmp((yyvsp[0].str), "0") == 0)
@@ -2317,11 +2341,11 @@ yyreduce:
                else cfg_parser->cfg->shm_key = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2321 "util/configparser.c" /* yacc.c:1646  */
+#line 2345 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 187:
-#line 339 "./util/configparser.y" /* yacc.c:1646  */
+  case 192:
+#line 344 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_port:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2329,11 +2353,11 @@ yyreduce:
                else cfg_parser->cfg->port = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2333 "util/configparser.c" /* yacc.c:1646  */
+#line 2357 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 188:
-#line 348 "./util/configparser.y" /* yacc.c:1646  */
+  case 193:
+#line 353 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_interface:%s)\n", (yyvsp[0].str)));
                if(cfg_parser->cfg->num_ifs == 0)
@@ -2345,11 +2369,11 @@ yyreduce:
                else
                        cfg_parser->cfg->ifs[cfg_parser->cfg->num_ifs++] = (yyvsp[0].str);
        }
-#line 2349 "util/configparser.c" /* yacc.c:1646  */
+#line 2373 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 189:
-#line 361 "./util/configparser.y" /* yacc.c:1646  */
+  case 194:
+#line 366 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_interface:%s)\n", (yyvsp[0].str)));
                if(cfg_parser->cfg->num_out_ifs == 0)
@@ -2363,11 +2387,11 @@ yyreduce:
                        cfg_parser->cfg->out_ifs[
                                cfg_parser->cfg->num_out_ifs++] = (yyvsp[0].str);
        }
-#line 2367 "util/configparser.c" /* yacc.c:1646  */
+#line 2391 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 190:
-#line 376 "./util/configparser.y" /* yacc.c:1646  */
+  case 195:
+#line 381 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_range:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2375,11 +2399,11 @@ yyreduce:
                else cfg_parser->cfg->outgoing_num_ports = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2379 "util/configparser.c" /* yacc.c:1646  */
+#line 2403 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 191:
-#line 385 "./util/configparser.y" /* yacc.c:1646  */
+  case 196:
+#line 390 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_port_permit:%s)\n", (yyvsp[0].str)));
                if(!cfg_mark_ports((yyvsp[0].str), 1, 
@@ -2387,11 +2411,11 @@ yyreduce:
                        yyerror("port number or range (\"low-high\") expected");
                free((yyvsp[0].str));
        }
-#line 2391 "util/configparser.c" /* yacc.c:1646  */
+#line 2415 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 192:
-#line 394 "./util/configparser.y" /* yacc.c:1646  */
+  case 197:
+#line 399 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_port_avoid:%s)\n", (yyvsp[0].str)));
                if(!cfg_mark_ports((yyvsp[0].str), 0, 
@@ -2399,11 +2423,11 @@ yyreduce:
                        yyerror("port number or range (\"low-high\") expected");
                free((yyvsp[0].str));
        }
-#line 2403 "util/configparser.c" /* yacc.c:1646  */
+#line 2427 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 193:
-#line 403 "./util/configparser.y" /* yacc.c:1646  */
+  case 198:
+#line 408 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_num_tcp:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2411,11 +2435,11 @@ yyreduce:
                else cfg_parser->cfg->outgoing_num_tcp = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2415 "util/configparser.c" /* yacc.c:1646  */
+#line 2439 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 194:
-#line 412 "./util/configparser.y" /* yacc.c:1646  */
+  case 199:
+#line 417 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_incoming_num_tcp:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2423,11 +2447,11 @@ yyreduce:
                else cfg_parser->cfg->incoming_num_tcp = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2427 "util/configparser.c" /* yacc.c:1646  */
+#line 2451 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 195:
-#line 421 "./util/configparser.y" /* yacc.c:1646  */
+  case 200:
+#line 426 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_interface_automatic:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2435,11 +2459,11 @@ yyreduce:
                else cfg_parser->cfg->if_automatic = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2439 "util/configparser.c" /* yacc.c:1646  */
+#line 2463 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 196:
-#line 430 "./util/configparser.y" /* yacc.c:1646  */
+  case 201:
+#line 435 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_ip4:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2447,11 +2471,11 @@ yyreduce:
                else cfg_parser->cfg->do_ip4 = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2451 "util/configparser.c" /* yacc.c:1646  */
+#line 2475 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 197:
-#line 439 "./util/configparser.y" /* yacc.c:1646  */
+  case 202:
+#line 444 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_ip6:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2459,11 +2483,11 @@ yyreduce:
                else cfg_parser->cfg->do_ip6 = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2463 "util/configparser.c" /* yacc.c:1646  */
+#line 2487 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 198:
-#line 448 "./util/configparser.y" /* yacc.c:1646  */
+  case 203:
+#line 453 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_udp:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2471,11 +2495,11 @@ yyreduce:
                else cfg_parser->cfg->do_udp = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2475 "util/configparser.c" /* yacc.c:1646  */
+#line 2499 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 199:
-#line 457 "./util/configparser.y" /* yacc.c:1646  */
+  case 204:
+#line 462 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_tcp:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2483,11 +2507,11 @@ yyreduce:
                else cfg_parser->cfg->do_tcp = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2487 "util/configparser.c" /* yacc.c:1646  */
+#line 2511 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 200:
-#line 466 "./util/configparser.y" /* yacc.c:1646  */
+  case 205:
+#line 471 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_prefer_ip6:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2495,11 +2519,11 @@ yyreduce:
                else cfg_parser->cfg->prefer_ip6 = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2499 "util/configparser.c" /* yacc.c:1646  */
+#line 2523 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 201:
-#line 475 "./util/configparser.y" /* yacc.c:1646  */
+  case 206:
+#line 480 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_tcp_mss:%s)\n", (yyvsp[0].str)));
                 if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2507,11 +2531,11 @@ yyreduce:
                 else cfg_parser->cfg->tcp_mss = atoi((yyvsp[0].str));
                 free((yyvsp[0].str));
        }
-#line 2511 "util/configparser.c" /* yacc.c:1646  */
+#line 2535 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 202:
-#line 484 "./util/configparser.y" /* yacc.c:1646  */
+  case 207:
+#line 489 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_outgoing_tcp_mss:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2519,11 +2543,11 @@ yyreduce:
                else cfg_parser->cfg->outgoing_tcp_mss = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2523 "util/configparser.c" /* yacc.c:1646  */
+#line 2547 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 203:
-#line 493 "./util/configparser.y" /* yacc.c:1646  */
+  case 208:
+#line 498 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_tcp_upstream:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2531,11 +2555,11 @@ yyreduce:
                else cfg_parser->cfg->tcp_upstream = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2535 "util/configparser.c" /* yacc.c:1646  */
+#line 2559 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 204:
-#line 502 "./util/configparser.y" /* yacc.c:1646  */
+  case 209:
+#line 507 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ssl_upstream:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2543,31 +2567,31 @@ yyreduce:
                else cfg_parser->cfg->ssl_upstream = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2547 "util/configparser.c" /* yacc.c:1646  */
+#line 2571 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 205:
-#line 511 "./util/configparser.y" /* yacc.c:1646  */
+  case 210:
+#line 516 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ssl_service_key:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->ssl_service_key);
                cfg_parser->cfg->ssl_service_key = (yyvsp[0].str);
        }
-#line 2557 "util/configparser.c" /* yacc.c:1646  */
+#line 2581 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 206:
-#line 518 "./util/configparser.y" /* yacc.c:1646  */
+  case 211:
+#line 523 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ssl_service_pem:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->ssl_service_pem);
                cfg_parser->cfg->ssl_service_pem = (yyvsp[0].str);
        }
-#line 2567 "util/configparser.c" /* yacc.c:1646  */
+#line 2591 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 207:
-#line 525 "./util/configparser.y" /* yacc.c:1646  */
+  case 212:
+#line 530 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ssl_port:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2575,11 +2599,11 @@ yyreduce:
                else cfg_parser->cfg->ssl_port = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2579 "util/configparser.c" /* yacc.c:1646  */
+#line 2603 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 208:
-#line 534 "./util/configparser.y" /* yacc.c:1646  */
+  case 213:
+#line 539 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_use_systemd:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2587,11 +2611,11 @@ yyreduce:
                else cfg_parser->cfg->use_systemd = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2591 "util/configparser.c" /* yacc.c:1646  */
+#line 2615 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 209:
-#line 543 "./util/configparser.y" /* yacc.c:1646  */
+  case 214:
+#line 548 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_daemonize:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2599,11 +2623,11 @@ yyreduce:
                else cfg_parser->cfg->do_daemonize = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2603 "util/configparser.c" /* yacc.c:1646  */
+#line 2627 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 210:
-#line 552 "./util/configparser.y" /* yacc.c:1646  */
+  case 215:
+#line 557 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_use_syslog:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2616,11 +2640,11 @@ yyreduce:
 #endif
                free((yyvsp[0].str));
        }
-#line 2620 "util/configparser.c" /* yacc.c:1646  */
+#line 2644 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 211:
-#line 566 "./util/configparser.y" /* yacc.c:1646  */
+  case 216:
+#line 571 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_log_time_ascii:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2628,11 +2652,11 @@ yyreduce:
                else cfg_parser->cfg->log_time_ascii = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2632 "util/configparser.c" /* yacc.c:1646  */
+#line 2656 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 212:
-#line 575 "./util/configparser.y" /* yacc.c:1646  */
+  case 217:
+#line 580 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_log_queries:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2640,11 +2664,11 @@ yyreduce:
                else cfg_parser->cfg->log_queries = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2644 "util/configparser.c" /* yacc.c:1646  */
+#line 2668 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 213:
-#line 584 "./util/configparser.y" /* yacc.c:1646  */
+  case 218:
+#line 589 "./util/configparser.y" /* yacc.c:1646  */
     {
        OUTYY(("P(server_log_replies:%s)\n", (yyvsp[0].str)));
        if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2652,31 +2676,31 @@ yyreduce:
        else cfg_parser->cfg->log_replies = (strcmp((yyvsp[0].str), "yes")==0);
        free((yyvsp[0].str));
   }
-#line 2656 "util/configparser.c" /* yacc.c:1646  */
+#line 2680 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 214:
-#line 593 "./util/configparser.y" /* yacc.c:1646  */
+  case 219:
+#line 598 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_chroot:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->chrootdir);
                cfg_parser->cfg->chrootdir = (yyvsp[0].str);
        }
-#line 2666 "util/configparser.c" /* yacc.c:1646  */
+#line 2690 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 215:
-#line 600 "./util/configparser.y" /* yacc.c:1646  */
+  case 220:
+#line 605 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_username:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->username);
                cfg_parser->cfg->username = (yyvsp[0].str);
        }
-#line 2676 "util/configparser.c" /* yacc.c:1646  */
+#line 2700 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 216:
-#line 607 "./util/configparser.y" /* yacc.c:1646  */
+  case 221:
+#line 612 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_directory:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->directory);
@@ -2701,115 +2725,115 @@ yyreduce:
                        }
                }
        }
-#line 2705 "util/configparser.c" /* yacc.c:1646  */
+#line 2729 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 217:
-#line 633 "./util/configparser.y" /* yacc.c:1646  */
+  case 222:
+#line 638 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_logfile:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->logfile);
                cfg_parser->cfg->logfile = (yyvsp[0].str);
                cfg_parser->cfg->use_syslog = 0;
        }
-#line 2716 "util/configparser.c" /* yacc.c:1646  */
+#line 2740 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 218:
-#line 641 "./util/configparser.y" /* yacc.c:1646  */
+  case 223:
+#line 646 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_pidfile:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->pidfile);
                cfg_parser->cfg->pidfile = (yyvsp[0].str);
        }
-#line 2726 "util/configparser.c" /* yacc.c:1646  */
+#line 2750 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 219:
-#line 648 "./util/configparser.y" /* yacc.c:1646  */
+  case 224:
+#line 653 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_root_hints:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->root_hints, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2736 "util/configparser.c" /* yacc.c:1646  */
+#line 2760 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 220:
-#line 655 "./util/configparser.y" /* yacc.c:1646  */
+  case 225:
+#line 660 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_dlv_anchor_file:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->dlv_anchor_file);
                cfg_parser->cfg->dlv_anchor_file = (yyvsp[0].str);
        }
-#line 2746 "util/configparser.c" /* yacc.c:1646  */
+#line 2770 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 221:
-#line 662 "./util/configparser.y" /* yacc.c:1646  */
+  case 226:
+#line 667 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_dlv_anchor:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->dlv_anchor_list, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2756 "util/configparser.c" /* yacc.c:1646  */
+#line 2780 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 222:
-#line 669 "./util/configparser.y" /* yacc.c:1646  */
+  case 227:
+#line 674 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_auto_trust_anchor_file:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->
                        auto_trust_anchor_file_list, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2767 "util/configparser.c" /* yacc.c:1646  */
+#line 2791 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 223:
-#line 677 "./util/configparser.y" /* yacc.c:1646  */
+  case 228:
+#line 682 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_trust_anchor_file:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->
                        trust_anchor_file_list, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2778 "util/configparser.c" /* yacc.c:1646  */
+#line 2802 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 224:
-#line 685 "./util/configparser.y" /* yacc.c:1646  */
+  case 229:
+#line 690 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_trusted_keys_file:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->
                        trusted_keys_file_list, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2789 "util/configparser.c" /* yacc.c:1646  */
+#line 2813 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 225:
-#line 693 "./util/configparser.y" /* yacc.c:1646  */
+  case 230:
+#line 698 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_trust_anchor:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->trust_anchor_list, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2799 "util/configparser.c" /* yacc.c:1646  */
+#line 2823 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 226:
-#line 700 "./util/configparser.y" /* yacc.c:1646  */
+  case 231:
+#line 705 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_domain_insecure:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->domain_insecure, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 2809 "util/configparser.c" /* yacc.c:1646  */
+#line 2833 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 227:
-#line 707 "./util/configparser.y" /* yacc.c:1646  */
+  case 232:
+#line 712 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_hide_identity:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2817,11 +2841,11 @@ yyreduce:
                else cfg_parser->cfg->hide_identity = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2821 "util/configparser.c" /* yacc.c:1646  */
+#line 2845 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 228:
-#line 716 "./util/configparser.y" /* yacc.c:1646  */
+  case 233:
+#line 721 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_hide_version:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2829,53 +2853,53 @@ yyreduce:
                else cfg_parser->cfg->hide_version = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 2833 "util/configparser.c" /* yacc.c:1646  */
+#line 2857 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 229:
-#line 725 "./util/configparser.y" /* yacc.c:1646  */
+  case 234:
+#line 730 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_identity:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->identity);
                cfg_parser->cfg->identity = (yyvsp[0].str);
        }
-#line 2843 "util/configparser.c" /* yacc.c:1646  */
+#line 2867 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 230:
-#line 732 "./util/configparser.y" /* yacc.c:1646  */
+  case 235:
+#line 737 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_version:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->version);
                cfg_parser->cfg->version = (yyvsp[0].str);
        }
-#line 2853 "util/configparser.c" /* yacc.c:1646  */
+#line 2877 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 231:
-#line 739 "./util/configparser.y" /* yacc.c:1646  */
+  case 236:
+#line 744 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_so_rcvbuf:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->so_rcvbuf))
                        yyerror("buffer size expected");
                free((yyvsp[0].str));
        }
-#line 2864 "util/configparser.c" /* yacc.c:1646  */
+#line 2888 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 232:
-#line 747 "./util/configparser.y" /* yacc.c:1646  */
+  case 237:
+#line 752 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_so_sndbuf:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->so_sndbuf))
                        yyerror("buffer size expected");
                free((yyvsp[0].str));
        }
-#line 2875 "util/configparser.c" /* yacc.c:1646  */
+#line 2899 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 233:
-#line 755 "./util/configparser.y" /* yacc.c:1646  */
+  case 238:
+#line 760 "./util/configparser.y" /* yacc.c:1646  */
     {
         OUTYY(("P(server_so_reuseport:%s)\n", (yyvsp[0].str)));
         if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2884,11 +2908,11 @@ yyreduce:
             (strcmp((yyvsp[0].str), "yes")==0);
         free((yyvsp[0].str));
     }
-#line 2888 "util/configparser.c" /* yacc.c:1646  */
+#line 2912 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 234:
-#line 765 "./util/configparser.y" /* yacc.c:1646  */
+  case 239:
+#line 770 "./util/configparser.y" /* yacc.c:1646  */
     {
         OUTYY(("P(server_ip_transparent:%s)\n", (yyvsp[0].str)));
         if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2897,11 +2921,11 @@ yyreduce:
             (strcmp((yyvsp[0].str), "yes")==0);
         free((yyvsp[0].str));
     }
-#line 2901 "util/configparser.c" /* yacc.c:1646  */
+#line 2925 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 235:
-#line 775 "./util/configparser.y" /* yacc.c:1646  */
+  case 240:
+#line 780 "./util/configparser.y" /* yacc.c:1646  */
     {
         OUTYY(("P(server_ip_freebind:%s)\n", (yyvsp[0].str)));
         if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -2910,11 +2934,11 @@ yyreduce:
             (strcmp((yyvsp[0].str), "yes")==0);
         free((yyvsp[0].str));
     }
-#line 2914 "util/configparser.c" /* yacc.c:1646  */
+#line 2938 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 236:
-#line 785 "./util/configparser.y" /* yacc.c:1646  */
+  case 241:
+#line 790 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_edns_buffer_size:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2926,11 +2950,11 @@ yyreduce:
                else cfg_parser->cfg->edns_buffer_size = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2930 "util/configparser.c" /* yacc.c:1646  */
+#line 2954 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 237:
-#line 798 "./util/configparser.y" /* yacc.c:1646  */
+  case 242:
+#line 803 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_msg_buffer_size:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2940,22 +2964,22 @@ yyreduce:
                else cfg_parser->cfg->msg_buffer_size = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2944 "util/configparser.c" /* yacc.c:1646  */
+#line 2968 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 238:
-#line 809 "./util/configparser.y" /* yacc.c:1646  */
+  case 243:
+#line 814 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_msg_cache_size:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->msg_cache_size))
                        yyerror("memory size expected");
                free((yyvsp[0].str));
        }
-#line 2955 "util/configparser.c" /* yacc.c:1646  */
+#line 2979 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 239:
-#line 817 "./util/configparser.y" /* yacc.c:1646  */
+  case 244:
+#line 822 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_msg_cache_slabs:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2967,11 +2991,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 2971 "util/configparser.c" /* yacc.c:1646  */
+#line 2995 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 240:
-#line 830 "./util/configparser.y" /* yacc.c:1646  */
+  case 245:
+#line 835 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_num_queries_per_thread:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -2979,11 +3003,11 @@ yyreduce:
                else cfg_parser->cfg->num_queries_per_thread = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2983 "util/configparser.c" /* yacc.c:1646  */
+#line 3007 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 241:
-#line 839 "./util/configparser.y" /* yacc.c:1646  */
+  case 246:
+#line 844 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_jostle_timeout:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -2991,11 +3015,11 @@ yyreduce:
                else cfg_parser->cfg->jostle_time = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 2995 "util/configparser.c" /* yacc.c:1646  */
+#line 3019 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 242:
-#line 848 "./util/configparser.y" /* yacc.c:1646  */
+  case 247:
+#line 853 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_delay_close:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3003,11 +3027,11 @@ yyreduce:
                else cfg_parser->cfg->delay_close = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3007 "util/configparser.c" /* yacc.c:1646  */
+#line 3031 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 243:
-#line 857 "./util/configparser.y" /* yacc.c:1646  */
+  case 248:
+#line 862 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_unblock_lan_zones:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3016,11 +3040,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3020 "util/configparser.c" /* yacc.c:1646  */
+#line 3044 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 244:
-#line 867 "./util/configparser.y" /* yacc.c:1646  */
+  case 249:
+#line 872 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_insecure_lan_zones:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3029,22 +3053,22 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3033 "util/configparser.c" /* yacc.c:1646  */
+#line 3057 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 245:
-#line 877 "./util/configparser.y" /* yacc.c:1646  */
+  case 250:
+#line 882 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_rrset_cache_size:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->rrset_cache_size))
                        yyerror("memory size expected");
                free((yyvsp[0].str));
        }
-#line 3044 "util/configparser.c" /* yacc.c:1646  */
+#line 3068 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 246:
-#line 885 "./util/configparser.y" /* yacc.c:1646  */
+  case 251:
+#line 890 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_rrset_cache_slabs:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -3056,11 +3080,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3060 "util/configparser.c" /* yacc.c:1646  */
+#line 3084 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 247:
-#line 898 "./util/configparser.y" /* yacc.c:1646  */
+  case 252:
+#line 903 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_host_ttl:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3068,22 +3092,22 @@ yyreduce:
                else cfg_parser->cfg->host_ttl = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3072 "util/configparser.c" /* yacc.c:1646  */
+#line 3096 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 248:
-#line 907 "./util/configparser.y" /* yacc.c:1646  */
+  case 253:
+#line 912 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_lame_ttl:%s)\n", (yyvsp[0].str)));
                verbose(VERB_DETAIL, "ignored infra-lame-ttl: %s (option "
                        "removed, use infra-host-ttl)", (yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3083 "util/configparser.c" /* yacc.c:1646  */
+#line 3107 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 249:
-#line 915 "./util/configparser.y" /* yacc.c:1646  */
+  case 254:
+#line 920 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_cache_numhosts:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -3091,22 +3115,22 @@ yyreduce:
                else cfg_parser->cfg->infra_cache_numhosts = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3095 "util/configparser.c" /* yacc.c:1646  */
+#line 3119 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 250:
-#line 924 "./util/configparser.y" /* yacc.c:1646  */
+  case 255:
+#line 929 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_cache_lame_size:%s)\n", (yyvsp[0].str)));
                verbose(VERB_DETAIL, "ignored infra-cache-lame-size: %s "
                        "(option removed, use infra-cache-numhosts)", (yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3106 "util/configparser.c" /* yacc.c:1646  */
+#line 3130 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 251:
-#line 932 "./util/configparser.y" /* yacc.c:1646  */
+  case 256:
+#line 937 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_cache_slabs:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -3118,11 +3142,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3122 "util/configparser.c" /* yacc.c:1646  */
+#line 3146 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 252:
-#line 945 "./util/configparser.y" /* yacc.c:1646  */
+  case 257:
+#line 950 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_infra_cache_min_rtt:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3130,21 +3154,21 @@ yyreduce:
                else cfg_parser->cfg->infra_cache_min_rtt = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3134 "util/configparser.c" /* yacc.c:1646  */
+#line 3158 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 253:
-#line 954 "./util/configparser.y" /* yacc.c:1646  */
+  case 258:
+#line 959 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_target_fetch_policy:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->target_fetch_policy);
                cfg_parser->cfg->target_fetch_policy = (yyvsp[0].str);
        }
-#line 3144 "util/configparser.c" /* yacc.c:1646  */
+#line 3168 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 254:
-#line 961 "./util/configparser.y" /* yacc.c:1646  */
+  case 259:
+#line 966 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_short_bufsize:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3153,11 +3177,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3157 "util/configparser.c" /* yacc.c:1646  */
+#line 3181 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 255:
-#line 971 "./util/configparser.y" /* yacc.c:1646  */
+  case 260:
+#line 976 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_large_queries:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3166,11 +3190,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3170 "util/configparser.c" /* yacc.c:1646  */
+#line 3194 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 256:
-#line 981 "./util/configparser.y" /* yacc.c:1646  */
+  case 261:
+#line 986 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_glue:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3179,11 +3203,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3183 "util/configparser.c" /* yacc.c:1646  */
+#line 3207 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 257:
-#line 991 "./util/configparser.y" /* yacc.c:1646  */
+  case 262:
+#line 996 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_dnssec_stripped:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3192,11 +3216,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3196 "util/configparser.c" /* yacc.c:1646  */
+#line 3220 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 258:
-#line 1001 "./util/configparser.y" /* yacc.c:1646  */
+  case 263:
+#line 1006 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_below_nxdomain:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3205,11 +3229,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3209 "util/configparser.c" /* yacc.c:1646  */
+#line 3233 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 259:
-#line 1011 "./util/configparser.y" /* yacc.c:1646  */
+  case 264:
+#line 1016 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_referral_path:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3218,11 +3242,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3222 "util/configparser.c" /* yacc.c:1646  */
+#line 3246 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 260:
-#line 1021 "./util/configparser.y" /* yacc.c:1646  */
+  case 265:
+#line 1026 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_harden_algo_downgrade:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3231,11 +3255,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3235 "util/configparser.c" /* yacc.c:1646  */
+#line 3259 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 261:
-#line 1031 "./util/configparser.y" /* yacc.c:1646  */
+  case 266:
+#line 1036 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_use_caps_for_id:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3244,41 +3268,41 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3248 "util/configparser.c" /* yacc.c:1646  */
+#line 3272 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 262:
-#line 1041 "./util/configparser.y" /* yacc.c:1646  */
+  case 267:
+#line 1046 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_caps_whitelist:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->caps_whitelist, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 3258 "util/configparser.c" /* yacc.c:1646  */
+#line 3282 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 263:
-#line 1048 "./util/configparser.y" /* yacc.c:1646  */
+  case 268:
+#line 1053 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_private_address:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->private_address, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 3268 "util/configparser.c" /* yacc.c:1646  */
+#line 3292 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 264:
-#line 1055 "./util/configparser.y" /* yacc.c:1646  */
+  case 269:
+#line 1060 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_private_domain:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->private_domain, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 3278 "util/configparser.c" /* yacc.c:1646  */
+#line 3302 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 265:
-#line 1062 "./util/configparser.y" /* yacc.c:1646  */
+  case 270:
+#line 1067 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_prefetch:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3286,11 +3310,11 @@ yyreduce:
                else cfg_parser->cfg->prefetch = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3290 "util/configparser.c" /* yacc.c:1646  */
+#line 3314 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 266:
-#line 1071 "./util/configparser.y" /* yacc.c:1646  */
+  case 271:
+#line 1076 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_prefetch_key:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3298,11 +3322,11 @@ yyreduce:
                else cfg_parser->cfg->prefetch_key = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3302 "util/configparser.c" /* yacc.c:1646  */
+#line 3326 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 267:
-#line 1080 "./util/configparser.y" /* yacc.c:1646  */
+  case 272:
+#line 1085 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_unwanted_reply_threshold:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3310,21 +3334,21 @@ yyreduce:
                else cfg_parser->cfg->unwanted_threshold = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3314 "util/configparser.c" /* yacc.c:1646  */
+#line 3338 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 268:
-#line 1089 "./util/configparser.y" /* yacc.c:1646  */
+  case 273:
+#line 1094 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_not_query_address:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->donotqueryaddrs, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 3324 "util/configparser.c" /* yacc.c:1646  */
+#line 3348 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 269:
-#line 1096 "./util/configparser.y" /* yacc.c:1646  */
+  case 274:
+#line 1101 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_do_not_query_localhost:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3333,11 +3357,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3337 "util/configparser.c" /* yacc.c:1646  */
+#line 3361 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 270:
-#line 1106 "./util/configparser.y" /* yacc.c:1646  */
+  case 275:
+#line 1111 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_access_control:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "deny")!=0 && strcmp((yyvsp[0].str), "refuse")!=0 &&
@@ -3353,21 +3377,21 @@ yyreduce:
                                fatal_exit("out of memory adding acl");
                }
        }
-#line 3357 "util/configparser.c" /* yacc.c:1646  */
+#line 3381 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 271:
-#line 1123 "./util/configparser.y" /* yacc.c:1646  */
+  case 276:
+#line 1128 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_module_conf:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->module_conf);
                cfg_parser->cfg->module_conf = (yyvsp[0].str);
        }
-#line 3367 "util/configparser.c" /* yacc.c:1646  */
+#line 3391 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 272:
-#line 1130 "./util/configparser.y" /* yacc.c:1646  */
+  case 277:
+#line 1135 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_override_date:%s)\n", (yyvsp[0].str)));
                if(*(yyvsp[0].str) == '\0' || strcmp((yyvsp[0].str), "0") == 0) {
@@ -3384,11 +3408,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3388 "util/configparser.c" /* yacc.c:1646  */
+#line 3412 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 273:
-#line 1148 "./util/configparser.y" /* yacc.c:1646  */
+  case 278:
+#line 1153 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_sig_skew_min:%s)\n", (yyvsp[0].str)));
                if(*(yyvsp[0].str) == '\0' || strcmp((yyvsp[0].str), "0") == 0) {
@@ -3400,11 +3424,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3404 "util/configparser.c" /* yacc.c:1646  */
+#line 3428 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 274:
-#line 1161 "./util/configparser.y" /* yacc.c:1646  */
+  case 279:
+#line 1166 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_sig_skew_max:%s)\n", (yyvsp[0].str)));
                if(*(yyvsp[0].str) == '\0' || strcmp((yyvsp[0].str), "0") == 0) {
@@ -3416,11 +3440,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3420 "util/configparser.c" /* yacc.c:1646  */
+#line 3444 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 275:
-#line 1174 "./util/configparser.y" /* yacc.c:1646  */
+  case 280:
+#line 1179 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_cache_max_ttl:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3428,11 +3452,11 @@ yyreduce:
                else cfg_parser->cfg->max_ttl = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3432 "util/configparser.c" /* yacc.c:1646  */
+#line 3456 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 276:
-#line 1183 "./util/configparser.y" /* yacc.c:1646  */
+  case 281:
+#line 1188 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_cache_max_negative_ttl:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3440,11 +3464,11 @@ yyreduce:
                else cfg_parser->cfg->max_negative_ttl = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3444 "util/configparser.c" /* yacc.c:1646  */
+#line 3468 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 277:
-#line 1192 "./util/configparser.y" /* yacc.c:1646  */
+  case 282:
+#line 1197 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_cache_min_ttl:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3452,11 +3476,11 @@ yyreduce:
                else cfg_parser->cfg->min_ttl = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3456 "util/configparser.c" /* yacc.c:1646  */
+#line 3480 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 278:
-#line 1201 "./util/configparser.y" /* yacc.c:1646  */
+  case 283:
+#line 1206 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_bogus_ttl:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3464,11 +3488,11 @@ yyreduce:
                else cfg_parser->cfg->bogus_ttl = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3468 "util/configparser.c" /* yacc.c:1646  */
+#line 3492 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 279:
-#line 1210 "./util/configparser.y" /* yacc.c:1646  */
+  case 284:
+#line 1215 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_clean_additional:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3477,11 +3501,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3481 "util/configparser.c" /* yacc.c:1646  */
+#line 3505 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 280:
-#line 1220 "./util/configparser.y" /* yacc.c:1646  */
+  case 285:
+#line 1225 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_permissive_mode:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3490,11 +3514,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3494 "util/configparser.c" /* yacc.c:1646  */
+#line 3518 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 281:
-#line 1230 "./util/configparser.y" /* yacc.c:1646  */
+  case 286:
+#line 1235 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ignore_cd_flag:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3502,11 +3526,11 @@ yyreduce:
                else cfg_parser->cfg->ignore_cd = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3506 "util/configparser.c" /* yacc.c:1646  */
+#line 3530 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 282:
-#line 1239 "./util/configparser.y" /* yacc.c:1646  */
+  case 287:
+#line 1244 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_serve_expired:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3514,11 +3538,11 @@ yyreduce:
                else cfg_parser->cfg->serve_expired = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3518 "util/configparser.c" /* yacc.c:1646  */
+#line 3542 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 283:
-#line 1248 "./util/configparser.y" /* yacc.c:1646  */
+  case 288:
+#line 1253 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_fake_dsa:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3530,11 +3554,11 @@ yyreduce:
 #endif
                free((yyvsp[0].str));
        }
-#line 3534 "util/configparser.c" /* yacc.c:1646  */
+#line 3558 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 284:
-#line 1261 "./util/configparser.y" /* yacc.c:1646  */
+  case 289:
+#line 1266 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_log_level:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3542,21 +3566,21 @@ yyreduce:
                else cfg_parser->cfg->val_log_level = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3546 "util/configparser.c" /* yacc.c:1646  */
+#line 3570 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 285:
-#line 1270 "./util/configparser.y" /* yacc.c:1646  */
+  case 290:
+#line 1275 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_val_nsec3_keysize_iterations:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->val_nsec3_key_iterations);
                cfg_parser->cfg->val_nsec3_key_iterations = (yyvsp[0].str);
        }
-#line 3556 "util/configparser.c" /* yacc.c:1646  */
+#line 3580 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 286:
-#line 1277 "./util/configparser.y" /* yacc.c:1646  */
+  case 291:
+#line 1282 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_add_holddown:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3564,11 +3588,11 @@ yyreduce:
                else cfg_parser->cfg->add_holddown = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3568 "util/configparser.c" /* yacc.c:1646  */
+#line 3592 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 287:
-#line 1286 "./util/configparser.y" /* yacc.c:1646  */
+  case 292:
+#line 1291 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_del_holddown:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3576,11 +3600,11 @@ yyreduce:
                else cfg_parser->cfg->del_holddown = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3580 "util/configparser.c" /* yacc.c:1646  */
+#line 3604 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 288:
-#line 1295 "./util/configparser.y" /* yacc.c:1646  */
+  case 293:
+#line 1300 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_keep_missing:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3588,11 +3612,11 @@ yyreduce:
                else cfg_parser->cfg->keep_missing = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3592 "util/configparser.c" /* yacc.c:1646  */
+#line 3616 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 289:
-#line 1304 "./util/configparser.y" /* yacc.c:1646  */
+  case 294:
+#line 1309 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_permit_small_holddown:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3601,22 +3625,22 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3605 "util/configparser.c" /* yacc.c:1646  */
+#line 3629 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 290:
-#line 1313 "./util/configparser.y" /* yacc.c:1646  */
+  case 295:
+#line 1318 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_key_cache_size:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->key_cache_size))
                        yyerror("memory size expected");
                free((yyvsp[0].str));
        }
-#line 3616 "util/configparser.c" /* yacc.c:1646  */
+#line 3640 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 291:
-#line 1321 "./util/configparser.y" /* yacc.c:1646  */
+  case 296:
+#line 1326 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_key_cache_slabs:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -3628,22 +3652,22 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3632 "util/configparser.c" /* yacc.c:1646  */
+#line 3656 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 292:
-#line 1334 "./util/configparser.y" /* yacc.c:1646  */
+  case 297:
+#line 1339 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_neg_cache_size:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->neg_cache_size))
                        yyerror("memory size expected");
                free((yyvsp[0].str));
        }
-#line 3643 "util/configparser.c" /* yacc.c:1646  */
+#line 3667 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 293:
-#line 1342 "./util/configparser.y" /* yacc.c:1646  */
+  case 298:
+#line 1347 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_local_zone:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "static")!=0 && strcmp((yyvsp[0].str), "deny")!=0 &&
@@ -3670,21 +3694,21 @@ yyreduce:
                                fatal_exit("out of memory adding local-zone");
                }
        }
-#line 3674 "util/configparser.c" /* yacc.c:1646  */
+#line 3698 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 294:
-#line 1370 "./util/configparser.y" /* yacc.c:1646  */
+  case 299:
+#line 1375 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_local_data:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->local_data, (yyvsp[0].str)))
                        fatal_exit("out of memory adding local-data");
        }
-#line 3684 "util/configparser.c" /* yacc.c:1646  */
+#line 3708 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 295:
-#line 1377 "./util/configparser.y" /* yacc.c:1646  */
+  case 300:
+#line 1382 "./util/configparser.y" /* yacc.c:1646  */
     {
                char* ptr;
                OUTYY(("P(server_local_data_ptr:%s)\n", (yyvsp[0].str)));
@@ -3698,11 +3722,11 @@ yyreduce:
                        yyerror("local-data-ptr could not be reversed");
                }
        }
-#line 3702 "util/configparser.c" /* yacc.c:1646  */
+#line 3726 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 296:
-#line 1392 "./util/configparser.y" /* yacc.c:1646  */
+  case 301:
+#line 1397 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_minimal_responses:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3711,11 +3735,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3715 "util/configparser.c" /* yacc.c:1646  */
+#line 3739 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 297:
-#line 1402 "./util/configparser.y" /* yacc.c:1646  */
+  case 302:
+#line 1407 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_rrset_roundrobin:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3724,31 +3748,31 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3728 "util/configparser.c" /* yacc.c:1646  */
+#line 3752 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 298:
-#line 1412 "./util/configparser.y" /* yacc.c:1646  */
+  case 303:
+#line 1417 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_max_udp_size:%s)\n", (yyvsp[0].str)));
                cfg_parser->cfg->max_udp_size = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3738 "util/configparser.c" /* yacc.c:1646  */
+#line 3762 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 299:
-#line 1419 "./util/configparser.y" /* yacc.c:1646  */
+  case 304:
+#line 1424 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dns64_prefix:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->dns64_prefix);
                cfg_parser->cfg->dns64_prefix = (yyvsp[0].str);
        }
-#line 3748 "util/configparser.c" /* yacc.c:1646  */
+#line 3772 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 300:
-#line 1426 "./util/configparser.y" /* yacc.c:1646  */
+  case 305:
+#line 1431 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_dns64_synthall:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -3756,11 +3780,11 @@ yyreduce:
                else cfg_parser->cfg->dns64_synthall = (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 3760 "util/configparser.c" /* yacc.c:1646  */
+#line 3784 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 301:
-#line 1435 "./util/configparser.y" /* yacc.c:1646  */
+  case 306:
+#line 1440 "./util/configparser.y" /* yacc.c:1646  */
     {
                char* p, *s = (yyvsp[0].str);
                OUTYY(("P(server_define_tag:%s)\n", (yyvsp[0].str)));
@@ -3773,11 +3797,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3777 "util/configparser.c" /* yacc.c:1646  */
+#line 3801 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 302:
-#line 1449 "./util/configparser.y" /* yacc.c:1646  */
+  case 307:
+#line 1454 "./util/configparser.y" /* yacc.c:1646  */
     {
                size_t len = 0;
                uint8_t* bitlist = config_parse_taglist(cfg_parser->cfg, (yyvsp[0].str),
@@ -3795,11 +3819,11 @@ yyreduce:
                        }
                }
        }
-#line 3799 "util/configparser.c" /* yacc.c:1646  */
+#line 3823 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 303:
-#line 1468 "./util/configparser.y" /* yacc.c:1646  */
+  case 308:
+#line 1473 "./util/configparser.y" /* yacc.c:1646  */
     {
                size_t len = 0;
                uint8_t* bitlist = config_parse_taglist(cfg_parser->cfg, (yyvsp[0].str),
@@ -3817,11 +3841,11 @@ yyreduce:
                        }
                }
        }
-#line 3821 "util/configparser.c" /* yacc.c:1646  */
+#line 3845 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 304:
-#line 1487 "./util/configparser.y" /* yacc.c:1646  */
+  case 309:
+#line 1492 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_access_control_tag_action:%s %s %s)\n", (yyvsp[-2].str), (yyvsp[-1].str), (yyvsp[0].str)));
                if(!cfg_str3list_insert(&cfg_parser->cfg->acl_tag_actions,
@@ -3832,11 +3856,11 @@ yyreduce:
                        free((yyvsp[0].str));
                }
        }
-#line 3836 "util/configparser.c" /* yacc.c:1646  */
+#line 3860 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 305:
-#line 1499 "./util/configparser.y" /* yacc.c:1646  */
+  case 310:
+#line 1504 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_access_control_tag_data:%s %s %s)\n", (yyvsp[-2].str), (yyvsp[-1].str), (yyvsp[0].str)));
                if(!cfg_str3list_insert(&cfg_parser->cfg->acl_tag_datas,
@@ -3847,11 +3871,11 @@ yyreduce:
                        free((yyvsp[0].str));
                }
        }
-#line 3851 "util/configparser.c" /* yacc.c:1646  */
+#line 3875 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 306:
-#line 1511 "./util/configparser.y" /* yacc.c:1646  */
+  case 311:
+#line 1516 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_local_zone_override:%s %s %s)\n", (yyvsp[-2].str), (yyvsp[-1].str), (yyvsp[0].str)));
                if(!cfg_str3list_insert(&cfg_parser->cfg->local_zone_overrides,
@@ -3862,11 +3886,11 @@ yyreduce:
                        free((yyvsp[0].str));
                }
        }
-#line 3866 "util/configparser.c" /* yacc.c:1646  */
+#line 3890 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 307:
-#line 1523 "./util/configparser.y" /* yacc.c:1646  */
+  case 312:
+#line 1528 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_access_control_view:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(!cfg_str2list_insert(&cfg_parser->cfg->acl_view,
@@ -3876,11 +3900,33 @@ yyreduce:
                        free((yyvsp[0].str));
                }
        }
-#line 3880 "util/configparser.c" /* yacc.c:1646  */
+#line 3904 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 308:
-#line 1534 "./util/configparser.y" /* yacc.c:1646  */
+  case 313:
+#line 1539 "./util/configparser.y" /* yacc.c:1646  */
+    {
+               size_t len = 0;
+               uint8_t* bitlist = config_parse_taglist(cfg_parser->cfg, (yyvsp[0].str),
+                       &len);
+               free((yyvsp[0].str));
+               OUTYY(("P(response_ip_tag:%s)\n", (yyvsp[-1].str)));
+               if(!bitlist)
+                       yyerror("could not parse tags, (define-tag them first)");
+               if(bitlist) {
+                       if(!cfg_strbytelist_insert(
+                               &cfg_parser->cfg->respip_tags,
+                               (yyvsp[-1].str), bitlist, len)) {
+                               yyerror("out of memory");
+                               free((yyvsp[-1].str));
+                       }
+               }
+       }
+#line 3926 "util/configparser.c" /* yacc.c:1646  */
+    break;
+
+  case 314:
+#line 1558 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_ip_ratelimit:%s)\n", (yyvsp[0].str))); 
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3888,11 +3934,11 @@ yyreduce:
                else cfg_parser->cfg->ip_ratelimit = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3892 "util/configparser.c" /* yacc.c:1646  */
+#line 3938 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 309:
-#line 1544 "./util/configparser.y" /* yacc.c:1646  */
+  case 315:
+#line 1568 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_ratelimit:%s)\n", (yyvsp[0].str))); 
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3900,33 +3946,33 @@ yyreduce:
                else cfg_parser->cfg->ratelimit = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 3904 "util/configparser.c" /* yacc.c:1646  */
+#line 3950 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 310:
-#line 1553 "./util/configparser.y" /* yacc.c:1646  */
+  case 316:
+#line 1577 "./util/configparser.y" /* yacc.c:1646  */
     {
        OUTYY(("P(server_ip_ratelimit_size:%s)\n", (yyvsp[0].str)));
        if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->ip_ratelimit_size))
                yyerror("memory size expected");
        free((yyvsp[0].str));
   }
-#line 3915 "util/configparser.c" /* yacc.c:1646  */
+#line 3961 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 311:
-#line 1561 "./util/configparser.y" /* yacc.c:1646  */
+  case 317:
+#line 1585 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ratelimit_size:%s)\n", (yyvsp[0].str)));
                if(!cfg_parse_memsize((yyvsp[0].str), &cfg_parser->cfg->ratelimit_size))
                        yyerror("memory size expected");
                free((yyvsp[0].str));
        }
-#line 3926 "util/configparser.c" /* yacc.c:1646  */
+#line 3972 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 312:
-#line 1569 "./util/configparser.y" /* yacc.c:1646  */
+  case 318:
+#line 1593 "./util/configparser.y" /* yacc.c:1646  */
     {
        OUTYY(("P(server_ip_ratelimit_slabs:%s)\n", (yyvsp[0].str)));
        if(atoi((yyvsp[0].str)) == 0)
@@ -3938,11 +3984,11 @@ yyreduce:
        }
        free((yyvsp[0].str));
   }
-#line 3942 "util/configparser.c" /* yacc.c:1646  */
+#line 3988 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 313:
-#line 1582 "./util/configparser.y" /* yacc.c:1646  */
+  case 319:
+#line 1606 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ratelimit_slabs:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -3954,11 +4000,11 @@ yyreduce:
                }
                free((yyvsp[0].str));
        }
-#line 3958 "util/configparser.c" /* yacc.c:1646  */
+#line 4004 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 314:
-#line 1595 "./util/configparser.y" /* yacc.c:1646  */
+  case 320:
+#line 1619 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ratelimit_for_domain:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0) {
@@ -3970,11 +4016,11 @@ yyreduce:
                                        "ratelimit-for-domain");
                }
        }
-#line 3974 "util/configparser.c" /* yacc.c:1646  */
+#line 4020 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 315:
-#line 1608 "./util/configparser.y" /* yacc.c:1646  */
+  case 321:
+#line 1632 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_ratelimit_below_domain:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0) {
@@ -3986,11 +4032,11 @@ yyreduce:
                                        "ratelimit-below-domain");
                }
        }
-#line 3990 "util/configparser.c" /* yacc.c:1646  */
+#line 4036 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 316:
-#line 1621 "./util/configparser.y" /* yacc.c:1646  */
+  case 322:
+#line 1645 "./util/configparser.y" /* yacc.c:1646  */
     { 
        OUTYY(("P(server_ip_ratelimit_factor:%s)\n", (yyvsp[0].str))); 
        if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -3998,11 +4044,11 @@ yyreduce:
        else cfg_parser->cfg->ip_ratelimit_factor = atoi((yyvsp[0].str));
        free((yyvsp[0].str));
        }
-#line 4002 "util/configparser.c" /* yacc.c:1646  */
+#line 4048 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 317:
-#line 1630 "./util/configparser.y" /* yacc.c:1646  */
+  case 323:
+#line 1654 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("P(server_ratelimit_factor:%s)\n", (yyvsp[0].str))); 
                if(atoi((yyvsp[0].str)) == 0 && strcmp((yyvsp[0].str), "0") != 0)
@@ -4010,11 +4056,11 @@ yyreduce:
                else cfg_parser->cfg->ratelimit_factor = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 4014 "util/configparser.c" /* yacc.c:1646  */
+#line 4060 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 318:
-#line 1639 "./util/configparser.y" /* yacc.c:1646  */
+  case 324:
+#line 1663 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_qname_minimisation:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4023,11 +4069,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4027 "util/configparser.c" /* yacc.c:1646  */
+#line 4073 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 319:
-#line 1649 "./util/configparser.y" /* yacc.c:1646  */
+  case 325:
+#line 1673 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_qname_minimisation_strict:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4036,11 +4082,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4040 "util/configparser.c" /* yacc.c:1646  */
+#line 4086 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 320:
-#line 1659 "./util/configparser.y" /* yacc.c:1646  */
+  case 326:
+#line 1683 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(name:%s)\n", (yyvsp[0].str)));
                if(cfg_parser->cfg->stubs->name)
@@ -4049,31 +4095,31 @@ yyreduce:
                free(cfg_parser->cfg->stubs->name);
                cfg_parser->cfg->stubs->name = (yyvsp[0].str);
        }
-#line 4053 "util/configparser.c" /* yacc.c:1646  */
+#line 4099 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 321:
-#line 1669 "./util/configparser.y" /* yacc.c:1646  */
+  case 327:
+#line 1693 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(stub-host:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->stubs->hosts, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 4063 "util/configparser.c" /* yacc.c:1646  */
+#line 4109 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 322:
-#line 1676 "./util/configparser.y" /* yacc.c:1646  */
+  case 328:
+#line 1700 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(stub-addr:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->stubs->addrs, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 4073 "util/configparser.c" /* yacc.c:1646  */
+#line 4119 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 323:
-#line 1683 "./util/configparser.y" /* yacc.c:1646  */
+  case 329:
+#line 1707 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(stub-first:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4081,11 +4127,11 @@ yyreduce:
                else cfg_parser->cfg->stubs->isfirst=(strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4085 "util/configparser.c" /* yacc.c:1646  */
+#line 4131 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 324:
-#line 1692 "./util/configparser.y" /* yacc.c:1646  */
+  case 330:
+#line 1716 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(stub-ssl-upstream:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4094,11 +4140,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4098 "util/configparser.c" /* yacc.c:1646  */
+#line 4144 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 325:
-#line 1702 "./util/configparser.y" /* yacc.c:1646  */
+  case 331:
+#line 1726 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(stub-prime:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4107,11 +4153,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4111 "util/configparser.c" /* yacc.c:1646  */
+#line 4157 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 326:
-#line 1712 "./util/configparser.y" /* yacc.c:1646  */
+  case 332:
+#line 1736 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(name:%s)\n", (yyvsp[0].str)));
                if(cfg_parser->cfg->forwards->name)
@@ -4120,31 +4166,31 @@ yyreduce:
                free(cfg_parser->cfg->forwards->name);
                cfg_parser->cfg->forwards->name = (yyvsp[0].str);
        }
-#line 4124 "util/configparser.c" /* yacc.c:1646  */
+#line 4170 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 327:
-#line 1722 "./util/configparser.y" /* yacc.c:1646  */
+  case 333:
+#line 1746 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(forward-host:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->forwards->hosts, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 4134 "util/configparser.c" /* yacc.c:1646  */
+#line 4180 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 328:
-#line 1729 "./util/configparser.y" /* yacc.c:1646  */
+  case 334:
+#line 1753 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(forward-addr:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->forwards->addrs, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 4144 "util/configparser.c" /* yacc.c:1646  */
+#line 4190 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 329:
-#line 1736 "./util/configparser.y" /* yacc.c:1646  */
+  case 335:
+#line 1760 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(forward-first:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4152,11 +4198,11 @@ yyreduce:
                else cfg_parser->cfg->forwards->isfirst=(strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4156 "util/configparser.c" /* yacc.c:1646  */
+#line 4202 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 330:
-#line 1745 "./util/configparser.y" /* yacc.c:1646  */
+  case 336:
+#line 1769 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(forward-ssl-upstream:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4165,11 +4211,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4169 "util/configparser.c" /* yacc.c:1646  */
+#line 4215 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 331:
-#line 1755 "./util/configparser.y" /* yacc.c:1646  */
+  case 337:
+#line 1779 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(name:%s)\n", (yyvsp[0].str)));
                if(cfg_parser->cfg->views->name)
@@ -4178,11 +4224,11 @@ yyreduce:
                free(cfg_parser->cfg->views->name);
                cfg_parser->cfg->views->name = (yyvsp[0].str);
        }
-#line 4182 "util/configparser.c" /* yacc.c:1646  */
+#line 4228 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 332:
-#line 1765 "./util/configparser.y" /* yacc.c:1646  */
+  case 338:
+#line 1789 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(view_local_zone:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "static")!=0 && strcmp((yyvsp[0].str), "deny")!=0 &&
@@ -4210,11 +4256,35 @@ yyreduce:
                                fatal_exit("out of memory adding local-zone");
                }
        }
-#line 4214 "util/configparser.c" /* yacc.c:1646  */
+#line 4260 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 333:
-#line 1794 "./util/configparser.y" /* yacc.c:1646  */
+  case 339:
+#line 1818 "./util/configparser.y" /* yacc.c:1646  */
+    {
+               OUTYY(("P(view_response_ip:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
+               validate_respip_action((yyvsp[0].str));
+               if(!cfg_str2list_insert(
+                       &cfg_parser->cfg->views->respip_actions, (yyvsp[-1].str), (yyvsp[0].str)))
+                       fatal_exit("out of memory adding per-view "
+                               "response-ip action");
+       }
+#line 4273 "util/configparser.c" /* yacc.c:1646  */
+    break;
+
+  case 340:
+#line 1828 "./util/configparser.y" /* yacc.c:1646  */
+    {
+               OUTYY(("P(view_response_ip_data:%s)\n", (yyvsp[-1].str)));
+               if(!cfg_str2list_insert(
+                       &cfg_parser->cfg->views->respip_data, (yyvsp[-1].str), (yyvsp[0].str)))
+                       fatal_exit("out of memory adding response-ip-data");
+       }
+#line 4284 "util/configparser.c" /* yacc.c:1646  */
+    break;
+
+  case 341:
+#line 1836 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(view_local_data:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->views->local_data, (yyvsp[0].str))) {
@@ -4222,11 +4292,11 @@ yyreduce:
                        free((yyvsp[0].str));
                }
        }
-#line 4226 "util/configparser.c" /* yacc.c:1646  */
+#line 4296 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 334:
-#line 1803 "./util/configparser.y" /* yacc.c:1646  */
+  case 342:
+#line 1845 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(view-first:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4234,19 +4304,19 @@ yyreduce:
                else cfg_parser->cfg->views->isfirst=(strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4238 "util/configparser.c" /* yacc.c:1646  */
+#line 4308 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 335:
-#line 1812 "./util/configparser.y" /* yacc.c:1646  */
+  case 343:
+#line 1854 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("\nP(remote-control:)\n")); 
        }
-#line 4246 "util/configparser.c" /* yacc.c:1646  */
+#line 4316 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 346:
-#line 1823 "./util/configparser.y" /* yacc.c:1646  */
+  case 354:
+#line 1865 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(control_enable:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4255,11 +4325,11 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4259 "util/configparser.c" /* yacc.c:1646  */
+#line 4329 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 347:
-#line 1833 "./util/configparser.y" /* yacc.c:1646  */
+  case 355:
+#line 1875 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(control_port:%s)\n", (yyvsp[0].str)));
                if(atoi((yyvsp[0].str)) == 0)
@@ -4267,21 +4337,21 @@ yyreduce:
                else cfg_parser->cfg->control_port = atoi((yyvsp[0].str));
                free((yyvsp[0].str));
        }
-#line 4271 "util/configparser.c" /* yacc.c:1646  */
+#line 4341 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 348:
-#line 1842 "./util/configparser.y" /* yacc.c:1646  */
+  case 356:
+#line 1884 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(control_interface:%s)\n", (yyvsp[0].str)));
                if(!cfg_strlist_insert(&cfg_parser->cfg->control_ifs, (yyvsp[0].str)))
                        yyerror("out of memory");
        }
-#line 4281 "util/configparser.c" /* yacc.c:1646  */
+#line 4351 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 349:
-#line 1849 "./util/configparser.y" /* yacc.c:1646  */
+  case 357:
+#line 1891 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(control_use_cert:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4290,122 +4360,122 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4294 "util/configparser.c" /* yacc.c:1646  */
+#line 4364 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 350:
-#line 1859 "./util/configparser.y" /* yacc.c:1646  */
+  case 358:
+#line 1901 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(rc_server_key_file:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->server_key_file);
                cfg_parser->cfg->server_key_file = (yyvsp[0].str);
        }
-#line 4304 "util/configparser.c" /* yacc.c:1646  */
+#line 4374 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 351:
-#line 1866 "./util/configparser.y" /* yacc.c:1646  */
+  case 359:
+#line 1908 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(rc_server_cert_file:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->server_cert_file);
                cfg_parser->cfg->server_cert_file = (yyvsp[0].str);
        }
-#line 4314 "util/configparser.c" /* yacc.c:1646  */
+#line 4384 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 352:
-#line 1873 "./util/configparser.y" /* yacc.c:1646  */
+  case 360:
+#line 1915 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(rc_control_key_file:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->control_key_file);
                cfg_parser->cfg->control_key_file = (yyvsp[0].str);
        }
-#line 4324 "util/configparser.c" /* yacc.c:1646  */
+#line 4394 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 353:
-#line 1880 "./util/configparser.y" /* yacc.c:1646  */
+  case 361:
+#line 1922 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(rc_control_cert_file:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->control_cert_file);
                cfg_parser->cfg->control_cert_file = (yyvsp[0].str);
        }
-#line 4334 "util/configparser.c" /* yacc.c:1646  */
+#line 4404 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 354:
-#line 1887 "./util/configparser.y" /* yacc.c:1646  */
+  case 362:
+#line 1929 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("\nP(dnstap:)\n"));
        }
-#line 4342 "util/configparser.c" /* yacc.c:1646  */
+#line 4412 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 369:
-#line 1904 "./util/configparser.y" /* yacc.c:1646  */
+  case 377:
+#line 1946 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_enable:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
                        yyerror("expected yes or no.");
                else cfg_parser->cfg->dnstap = (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4353 "util/configparser.c" /* yacc.c:1646  */
+#line 4423 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 370:
-#line 1912 "./util/configparser.y" /* yacc.c:1646  */
+  case 378:
+#line 1954 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_socket_path:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->dnstap_socket_path);
                cfg_parser->cfg->dnstap_socket_path = (yyvsp[0].str);
        }
-#line 4363 "util/configparser.c" /* yacc.c:1646  */
+#line 4433 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 371:
-#line 1919 "./util/configparser.y" /* yacc.c:1646  */
+  case 379:
+#line 1961 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_send_identity:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
                        yyerror("expected yes or no.");
                else cfg_parser->cfg->dnstap_send_identity = (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4374 "util/configparser.c" /* yacc.c:1646  */
+#line 4444 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 372:
-#line 1927 "./util/configparser.y" /* yacc.c:1646  */
+  case 380:
+#line 1969 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_send_version:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
                        yyerror("expected yes or no.");
                else cfg_parser->cfg->dnstap_send_version = (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4385 "util/configparser.c" /* yacc.c:1646  */
+#line 4455 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 373:
-#line 1935 "./util/configparser.y" /* yacc.c:1646  */
+  case 381:
+#line 1977 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_identity:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->dnstap_identity);
                cfg_parser->cfg->dnstap_identity = (yyvsp[0].str);
        }
-#line 4395 "util/configparser.c" /* yacc.c:1646  */
+#line 4465 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 374:
-#line 1942 "./util/configparser.y" /* yacc.c:1646  */
+  case 382:
+#line 1984 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_version:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->dnstap_version);
                cfg_parser->cfg->dnstap_version = (yyvsp[0].str);
        }
-#line 4405 "util/configparser.c" /* yacc.c:1646  */
+#line 4475 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 375:
-#line 1949 "./util/configparser.y" /* yacc.c:1646  */
+  case 383:
+#line 1991 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_resolver_query_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4413,11 +4483,11 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_resolver_query_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4417 "util/configparser.c" /* yacc.c:1646  */
+#line 4487 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 376:
-#line 1958 "./util/configparser.y" /* yacc.c:1646  */
+  case 384:
+#line 2000 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_resolver_response_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4425,11 +4495,11 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_resolver_response_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4429 "util/configparser.c" /* yacc.c:1646  */
+#line 4499 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 377:
-#line 1967 "./util/configparser.y" /* yacc.c:1646  */
+  case 385:
+#line 2009 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_client_query_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4437,11 +4507,11 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_client_query_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4441 "util/configparser.c" /* yacc.c:1646  */
+#line 4511 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 378:
-#line 1976 "./util/configparser.y" /* yacc.c:1646  */
+  case 386:
+#line 2018 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_client_response_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4449,11 +4519,11 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_client_response_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4453 "util/configparser.c" /* yacc.c:1646  */
+#line 4523 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 379:
-#line 1985 "./util/configparser.y" /* yacc.c:1646  */
+  case 387:
+#line 2027 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_forwarder_query_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4461,11 +4531,11 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_forwarder_query_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4465 "util/configparser.c" /* yacc.c:1646  */
+#line 4535 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 380:
-#line 1994 "./util/configparser.y" /* yacc.c:1646  */
+  case 388:
+#line 2036 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(dt_dnstap_log_forwarder_response_messages:%s)\n", (yyvsp[0].str)));
                if(strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4473,29 +4543,29 @@ yyreduce:
                else cfg_parser->cfg->dnstap_log_forwarder_response_messages =
                        (strcmp((yyvsp[0].str), "yes")==0);
        }
-#line 4477 "util/configparser.c" /* yacc.c:1646  */
+#line 4547 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 381:
-#line 2003 "./util/configparser.y" /* yacc.c:1646  */
+  case 389:
+#line 2045 "./util/configparser.y" /* yacc.c:1646  */
     { 
                OUTYY(("\nP(python:)\n")); 
        }
-#line 4485 "util/configparser.c" /* yacc.c:1646  */
+#line 4555 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 385:
-#line 2012 "./util/configparser.y" /* yacc.c:1646  */
+  case 393:
+#line 2054 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(python-script:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->python_script);
                cfg_parser->cfg->python_script = (yyvsp[0].str);
        }
-#line 4495 "util/configparser.c" /* yacc.c:1646  */
+#line 4565 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 386:
-#line 2018 "./util/configparser.y" /* yacc.c:1646  */
+  case 394:
+#line 2060 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(disable_dnssec_lame_check:%s)\n", (yyvsp[0].str)));
                if (strcmp((yyvsp[0].str), "yes") != 0 && strcmp((yyvsp[0].str), "no") != 0)
@@ -4504,21 +4574,44 @@ yyreduce:
                        (strcmp((yyvsp[0].str), "yes")==0);
                free((yyvsp[0].str));
        }
-#line 4508 "util/configparser.c" /* yacc.c:1646  */
+#line 4578 "util/configparser.c" /* yacc.c:1646  */
     break;
 
-  case 387:
-#line 2028 "./util/configparser.y" /* yacc.c:1646  */
+  case 395:
+#line 2070 "./util/configparser.y" /* yacc.c:1646  */
     {
                OUTYY(("P(server_log_identity:%s)\n", (yyvsp[0].str)));
                free(cfg_parser->cfg->log_identity);
                cfg_parser->cfg->log_identity = (yyvsp[0].str);
        }
-#line 4518 "util/configparser.c" /* yacc.c:1646  */
+#line 4588 "util/configparser.c" /* yacc.c:1646  */
+    break;
+
+  case 396:
+#line 2077 "./util/configparser.y" /* yacc.c:1646  */
+    {
+               OUTYY(("P(server_response_ip:%s %s)\n", (yyvsp[-1].str), (yyvsp[0].str)));
+               validate_respip_action((yyvsp[0].str));
+               if(!cfg_str2list_insert(&cfg_parser->cfg->respip_actions,
+                       (yyvsp[-1].str), (yyvsp[0].str)))
+                       fatal_exit("out of memory adding response-ip");
+       }
+#line 4600 "util/configparser.c" /* yacc.c:1646  */
+    break;
+
+  case 397:
+#line 2086 "./util/configparser.y" /* yacc.c:1646  */
+    {
+               OUTYY(("P(server_response_ip_data:%s)\n", (yyvsp[-1].str)));
+                       if(!cfg_str2list_insert(&cfg_parser->cfg->respip_data,
+                               (yyvsp[-1].str), (yyvsp[0].str)))
+                               fatal_exit("out of memory adding response-ip-data");
+       }
+#line 4611 "util/configparser.c" /* yacc.c:1646  */
     break;
 
 
-#line 4522 "util/configparser.c" /* yacc.c:1646  */
+#line 4615 "util/configparser.c" /* yacc.c:1646  */
       default: break;
     }
   /* User semantic actions sometimes alter yychar, and that requires
@@ -4746,7 +4839,23 @@ yyreturn:
 #endif
   return yyresult;
 }
-#line 2034 "./util/configparser.y" /* yacc.c:1906  */
+#line 2093 "./util/configparser.y" /* yacc.c:1906  */
 
 
 /* parse helper routines could be here */
+static void
+validate_respip_action(const char* action)
+{
+       if(strcmp(action, "deny")!=0 &&
+               strcmp(action, "redirect")!=0 &&
+               strcmp(action, "inform")!=0 &&
+               strcmp(action, "inform_deny")!=0 &&
+               strcmp(action, "always_transparent")!=0 &&
+               strcmp(action, "always_refuse")!=0 &&
+               strcmp(action, "always_nxdomain")!=0)
+       {
+               yyerror("response-ip action: expected deny, redirect, "
+                       "inform, inform_deny, always_transparent, "
+                       "always_refuse or always_nxdomain");
+       }
+}
index 80360c651e0176471ba279b714dd54e2ef2b67f0..08542392b06c93d7fa04fbb91554b052682fec28 100644 (file)
@@ -200,40 +200,43 @@ extern int yydebug;
     VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES = 410,
     VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES = 411,
     VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES = 412,
-    VAR_HARDEN_ALGO_DOWNGRADE = 413,
-    VAR_IP_TRANSPARENT = 414,
-    VAR_DISABLE_DNSSEC_LAME_CHECK = 415,
-    VAR_IP_RATELIMIT = 416,
-    VAR_IP_RATELIMIT_SLABS = 417,
-    VAR_IP_RATELIMIT_SIZE = 418,
-    VAR_RATELIMIT = 419,
-    VAR_RATELIMIT_SLABS = 420,
-    VAR_RATELIMIT_SIZE = 421,
-    VAR_RATELIMIT_FOR_DOMAIN = 422,
-    VAR_RATELIMIT_BELOW_DOMAIN = 423,
-    VAR_IP_RATELIMIT_FACTOR = 424,
-    VAR_RATELIMIT_FACTOR = 425,
-    VAR_CAPS_WHITELIST = 426,
-    VAR_CACHE_MAX_NEGATIVE_TTL = 427,
-    VAR_PERMIT_SMALL_HOLDDOWN = 428,
-    VAR_QNAME_MINIMISATION = 429,
-    VAR_QNAME_MINIMISATION_STRICT = 430,
-    VAR_IP_FREEBIND = 431,
-    VAR_DEFINE_TAG = 432,
-    VAR_LOCAL_ZONE_TAG = 433,
-    VAR_ACCESS_CONTROL_TAG = 434,
-    VAR_LOCAL_ZONE_OVERRIDE = 435,
-    VAR_ACCESS_CONTROL_TAG_ACTION = 436,
-    VAR_ACCESS_CONTROL_TAG_DATA = 437,
-    VAR_VIEW = 438,
-    VAR_ACCESS_CONTROL_VIEW = 439,
-    VAR_VIEW_FIRST = 440,
-    VAR_SERVE_EXPIRED = 441,
-    VAR_FAKE_DSA = 442,
-    VAR_LOG_IDENTITY = 443,
-    VAR_USE_SYSTEMD = 444,
-    VAR_SHM_ENABLE = 445,
-    VAR_SHM_KEY = 446
+    VAR_RESPONSE_IP_TAG = 413,
+    VAR_RESPONSE_IP = 414,
+    VAR_RESPONSE_IP_DATA = 415,
+    VAR_HARDEN_ALGO_DOWNGRADE = 416,
+    VAR_IP_TRANSPARENT = 417,
+    VAR_DISABLE_DNSSEC_LAME_CHECK = 418,
+    VAR_IP_RATELIMIT = 419,
+    VAR_IP_RATELIMIT_SLABS = 420,
+    VAR_IP_RATELIMIT_SIZE = 421,
+    VAR_RATELIMIT = 422,
+    VAR_RATELIMIT_SLABS = 423,
+    VAR_RATELIMIT_SIZE = 424,
+    VAR_RATELIMIT_FOR_DOMAIN = 425,
+    VAR_RATELIMIT_BELOW_DOMAIN = 426,
+    VAR_IP_RATELIMIT_FACTOR = 427,
+    VAR_RATELIMIT_FACTOR = 428,
+    VAR_CAPS_WHITELIST = 429,
+    VAR_CACHE_MAX_NEGATIVE_TTL = 430,
+    VAR_PERMIT_SMALL_HOLDDOWN = 431,
+    VAR_QNAME_MINIMISATION = 432,
+    VAR_QNAME_MINIMISATION_STRICT = 433,
+    VAR_IP_FREEBIND = 434,
+    VAR_DEFINE_TAG = 435,
+    VAR_LOCAL_ZONE_TAG = 436,
+    VAR_ACCESS_CONTROL_TAG = 437,
+    VAR_LOCAL_ZONE_OVERRIDE = 438,
+    VAR_ACCESS_CONTROL_TAG_ACTION = 439,
+    VAR_ACCESS_CONTROL_TAG_DATA = 440,
+    VAR_VIEW = 441,
+    VAR_ACCESS_CONTROL_VIEW = 442,
+    VAR_VIEW_FIRST = 443,
+    VAR_SERVE_EXPIRED = 444,
+    VAR_FAKE_DSA = 445,
+    VAR_LOG_IDENTITY = 446,
+    VAR_USE_SYSTEMD = 447,
+    VAR_SHM_ENABLE = 448,
+    VAR_SHM_KEY = 449
   };
 #endif
 /* Tokens.  */
@@ -392,51 +395,54 @@ extern int yydebug;
 #define VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES 410
 #define VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES 411
 #define VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES 412
-#define VAR_HARDEN_ALGO_DOWNGRADE 413
-#define VAR_IP_TRANSPARENT 414
-#define VAR_DISABLE_DNSSEC_LAME_CHECK 415
-#define VAR_IP_RATELIMIT 416
-#define VAR_IP_RATELIMIT_SLABS 417
-#define VAR_IP_RATELIMIT_SIZE 418
-#define VAR_RATELIMIT 419
-#define VAR_RATELIMIT_SLABS 420
-#define VAR_RATELIMIT_SIZE 421
-#define VAR_RATELIMIT_FOR_DOMAIN 422
-#define VAR_RATELIMIT_BELOW_DOMAIN 423
-#define VAR_IP_RATELIMIT_FACTOR 424
-#define VAR_RATELIMIT_FACTOR 425
-#define VAR_CAPS_WHITELIST 426
-#define VAR_CACHE_MAX_NEGATIVE_TTL 427
-#define VAR_PERMIT_SMALL_HOLDDOWN 428
-#define VAR_QNAME_MINIMISATION 429
-#define VAR_QNAME_MINIMISATION_STRICT 430
-#define VAR_IP_FREEBIND 431
-#define VAR_DEFINE_TAG 432
-#define VAR_LOCAL_ZONE_TAG 433
-#define VAR_ACCESS_CONTROL_TAG 434
-#define VAR_LOCAL_ZONE_OVERRIDE 435
-#define VAR_ACCESS_CONTROL_TAG_ACTION 436
-#define VAR_ACCESS_CONTROL_TAG_DATA 437
-#define VAR_VIEW 438
-#define VAR_ACCESS_CONTROL_VIEW 439
-#define VAR_VIEW_FIRST 440
-#define VAR_SERVE_EXPIRED 441
-#define VAR_FAKE_DSA 442
-#define VAR_LOG_IDENTITY 443
-#define VAR_USE_SYSTEMD 444
-#define VAR_SHM_ENABLE 445
-#define VAR_SHM_KEY 446
+#define VAR_RESPONSE_IP_TAG 413
+#define VAR_RESPONSE_IP 414
+#define VAR_RESPONSE_IP_DATA 415
+#define VAR_HARDEN_ALGO_DOWNGRADE 416
+#define VAR_IP_TRANSPARENT 417
+#define VAR_DISABLE_DNSSEC_LAME_CHECK 418
+#define VAR_IP_RATELIMIT 419
+#define VAR_IP_RATELIMIT_SLABS 420
+#define VAR_IP_RATELIMIT_SIZE 421
+#define VAR_RATELIMIT 422
+#define VAR_RATELIMIT_SLABS 423
+#define VAR_RATELIMIT_SIZE 424
+#define VAR_RATELIMIT_FOR_DOMAIN 425
+#define VAR_RATELIMIT_BELOW_DOMAIN 426
+#define VAR_IP_RATELIMIT_FACTOR 427
+#define VAR_RATELIMIT_FACTOR 428
+#define VAR_CAPS_WHITELIST 429
+#define VAR_CACHE_MAX_NEGATIVE_TTL 430
+#define VAR_PERMIT_SMALL_HOLDDOWN 431
+#define VAR_QNAME_MINIMISATION 432
+#define VAR_QNAME_MINIMISATION_STRICT 433
+#define VAR_IP_FREEBIND 434
+#define VAR_DEFINE_TAG 435
+#define VAR_LOCAL_ZONE_TAG 436
+#define VAR_ACCESS_CONTROL_TAG 437
+#define VAR_LOCAL_ZONE_OVERRIDE 438
+#define VAR_ACCESS_CONTROL_TAG_ACTION 439
+#define VAR_ACCESS_CONTROL_TAG_DATA 440
+#define VAR_VIEW 441
+#define VAR_ACCESS_CONTROL_VIEW 442
+#define VAR_VIEW_FIRST 443
+#define VAR_SERVE_EXPIRED 444
+#define VAR_FAKE_DSA 445
+#define VAR_LOG_IDENTITY 446
+#define VAR_USE_SYSTEMD 447
+#define VAR_SHM_ENABLE 448
+#define VAR_SHM_KEY 449
 
 /* Value type.  */
 #if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
 
 union YYSTYPE
 {
-#line 64 "./util/configparser.y" /* yacc.c:1909  */
+#line 66 "./util/configparser.y" /* yacc.c:1909  */
 
        char*   str;
 
-#line 440 "util/configparser.h" /* yacc.c:1909  */
+#line 446 "util/configparser.h" /* yacc.c:1909  */
 };
 
 typedef union YYSTYPE YYSTYPE;
index 1fb12e7f8b6cbf4b5a8ddc4863aea3e179031a9a..16c97004f629db3bfee237aa6f2692c60047f01f 100644 (file)
@@ -51,6 +51,8 @@
 int ub_c_lex(void);
 void ub_c_error(const char *message);
 
+static void validate_respip_action(const char* action);
+
 /* these need to be global, otherwise they cannot be used inside yacc */
 extern struct config_parser_state* cfg_parser;
 
@@ -122,6 +124,7 @@ extern struct config_parser_state* cfg_parser;
 %token VAR_DNSTAP_LOG_CLIENT_RESPONSE_MESSAGES
 %token VAR_DNSTAP_LOG_FORWARDER_QUERY_MESSAGES
 %token VAR_DNSTAP_LOG_FORWARDER_RESPONSE_MESSAGES
+%token VAR_RESPONSE_IP_TAG VAR_RESPONSE_IP VAR_RESPONSE_IP_DATA
 %token VAR_HARDEN_ALGO_DOWNGRADE VAR_IP_TRANSPARENT
 %token VAR_DISABLE_DNSSEC_LAME_CHECK
 %token VAR_IP_RATELIMIT VAR_IP_RATELIMIT_SLABS VAR_IP_RATELIMIT_SIZE
@@ -214,6 +217,7 @@ content_server: server_num_threads | server_verbosity | server_port |
        server_access_control_tag_data | server_access_control_view |
        server_qname_minimisation_strict | server_serve_expired |
        server_fake_dsa | server_log_identity | server_use_systemd |
+       server_response_ip_tag | server_response_ip | server_response_ip_data |
        server_shm_enable | server_shm_key
        ;
 stubstart: VAR_STUB_ZONE
@@ -266,7 +270,8 @@ viewstart: VAR_VIEW
        ;
 contents_view: contents_view content_view 
        | ;
-content_view: view_name | view_local_zone | view_local_data | view_first
+content_view: view_name | view_local_zone | view_local_data | view_first |
+               view_response_ip | view_response_ip_data
        ;
 server_num_threads: VAR_NUM_THREADS STRING_ARG 
        { 
@@ -1530,6 +1535,25 @@ server_access_control_view: VAR_ACCESS_CONTROL_VIEW STRING_ARG STRING_ARG
                }
        }
        ;
+server_response_ip_tag: VAR_RESPONSE_IP_TAG STRING_ARG STRING_ARG
+       {
+               size_t len = 0;
+               uint8_t* bitlist = config_parse_taglist(cfg_parser->cfg, $3,
+                       &len);
+               free($3);
+               OUTYY(("P(response_ip_tag:%s)\n", $2));
+               if(!bitlist)
+                       yyerror("could not parse tags, (define-tag them first)");
+               if(bitlist) {
+                       if(!cfg_strbytelist_insert(
+                               &cfg_parser->cfg->respip_tags,
+                               $2, bitlist, len)) {
+                               yyerror("out of memory");
+                               free($2);
+                       }
+               }
+       }
+       ;
 server_ip_ratelimit: VAR_IP_RATELIMIT STRING_ARG 
        { 
                OUTYY(("P(server_ip_ratelimit:%s)\n", $2)); 
@@ -1790,6 +1814,24 @@ view_local_zone: VAR_LOCAL_ZONE STRING_ARG STRING_ARG
                }
        }
        ;
+view_response_ip: VAR_RESPONSE_IP STRING_ARG STRING_ARG
+       {
+               OUTYY(("P(view_response_ip:%s %s)\n", $2, $3));
+               validate_respip_action($3);
+               if(!cfg_str2list_insert(
+                       &cfg_parser->cfg->views->respip_actions, $2, $3))
+                       fatal_exit("out of memory adding per-view "
+                               "response-ip action");
+       }
+       ;
+view_response_ip_data: VAR_RESPONSE_IP_DATA STRING_ARG STRING_ARG
+       {
+               OUTYY(("P(view_response_ip_data:%s)\n", $2));
+               if(!cfg_str2list_insert(
+                       &cfg_parser->cfg->views->respip_data, $2, $3))
+                       fatal_exit("out of memory adding response-ip-data");
+       }
+       ;
 view_local_data: VAR_LOCAL_DATA STRING_ARG
        {
                OUTYY(("P(view_local_data:%s)\n", $2));
@@ -2031,6 +2073,39 @@ server_log_identity: VAR_LOG_IDENTITY STRING_ARG
                cfg_parser->cfg->log_identity = $2;
        }
        ;
+server_response_ip: VAR_RESPONSE_IP STRING_ARG STRING_ARG
+       {
+               OUTYY(("P(server_response_ip:%s %s)\n", $2, $3));
+               validate_respip_action($3);
+               if(!cfg_str2list_insert(&cfg_parser->cfg->respip_actions,
+                       $2, $3))
+                       fatal_exit("out of memory adding response-ip");
+       }
+       ;
+server_response_ip_data: VAR_RESPONSE_IP_DATA STRING_ARG STRING_ARG
+       {
+               OUTYY(("P(server_response_ip_data:%s)\n", $2));
+                       if(!cfg_str2list_insert(&cfg_parser->cfg->respip_data,
+                               $2, $3))
+                               fatal_exit("out of memory adding response-ip-data");
+       }
+       ;
 %%
 
 /* parse helper routines could be here */
+static void
+validate_respip_action(const char* action)
+{
+       if(strcmp(action, "deny")!=0 &&
+               strcmp(action, "redirect")!=0 &&
+               strcmp(action, "inform")!=0 &&
+               strcmp(action, "inform_deny")!=0 &&
+               strcmp(action, "always_transparent")!=0 &&
+               strcmp(action, "always_refuse")!=0 &&
+               strcmp(action, "always_nxdomain")!=0)
+       {
+               yyerror("response-ip action: expected deny, redirect, "
+                       "inform, inform_deny, always_transparent, "
+                       "always_refuse or always_nxdomain");
+       }
+}
index 5d3a2476217800ef78d72972f2e21293386b8e4e..1f72a03b8c64d92dcd4dbab313497f0662714eba 100644 (file)
@@ -459,6 +459,10 @@ packed_rrset_encode(struct ub_packed_rrset_key* key, sldns_buffer* pkt,
        owner_labs = dname_count_labels(key->rk.dname);
        owner_pos = sldns_buffer_position(pkt);
 
+       /* For an rrset with a fixed TTL, use the rrset's TTL as given */
+       if((key->rk.flags & PACKED_RRSET_FIXEDTTL) != 0)
+               timenow = 0;
+
        if(do_data) {
                const sldns_rr_descriptor* c = type_rdata_compressable(key);
                for(i=0; i<data->count; i++) {
index 8869716b679393c8b1e2eab863ec9993732123bb..d1b7a43885f6f8194aa6ca0c2bfcdd4768ba6fb7 100644 (file)
@@ -133,9 +133,8 @@ parse_create_repinfo(struct msg_parse* msg, struct reply_info** rep,
        return 1;
 }
 
-/** allocate (special) rrset keys, return 0 on error */
-static int
-repinfo_alloc_rrset_keys(struct reply_info* rep, struct alloc_cache* alloc, 
+int
+reply_info_alloc_rrset_keys(struct reply_info* rep, struct alloc_cache* alloc,
        struct regional* region)
 {
        size_t i;
@@ -438,7 +437,7 @@ parse_create_msg(sldns_buffer* pkt, struct msg_parse* msg,
                return 0;
        if(!parse_create_repinfo(msg, rep, region))
                return 0;
-       if(!repinfo_alloc_rrset_keys(*rep, alloc, region))
+       if(!reply_info_alloc_rrset_keys(*rep, alloc, region))
                return 0;
        if(!parse_copy_decompress(pkt, msg, *rep, region))
                return 0;
@@ -688,7 +687,7 @@ reply_info_copy(struct reply_info* rep, struct alloc_cache* alloc,
        if(!cp)
                return NULL;
        /* allocate ub_key structures special or not */
-       if(!repinfo_alloc_rrset_keys(cp, alloc, region)) {
+       if(!reply_info_alloc_rrset_keys(cp, alloc, region)) {
                if(!region)
                        reply_info_parsedelete(cp, alloc);
                return NULL;
index 485d49afa87da01e66b8615cd5bc3a0ab64cecb5..037bbaa79863a5576da026b6aa295b04803db3e7 100644 (file)
@@ -356,6 +356,21 @@ struct msgreply_entry* query_info_entrysetup(struct query_info* q,
 struct reply_info* reply_info_copy(struct reply_info* rep, 
        struct alloc_cache* alloc, struct regional* region);
 
+/**
+ * Allocate (special) rrset keys.
+ * @param rep: reply info in which the rrset keys to be allocated, rrset[]
+ *     array should have bee allocated with NULL pointers.
+ * @param alloc: how to allocate rrset keys.
+ *     Not used if region!=NULL, it can be NULL in that case.
+ * @region: if this parameter is NULL then the alloc is used.
+ *     otherwise, rrset keys are allocated in this region.
+ *     In a region, no special rrset key structures are needed (not shared).
+ *     and no rrset_ref array in the reply needs to be built up.
+ * @return 1 on success, 0 on error
+ */
+int reply_info_alloc_rrset_keys(struct reply_info* rep,
+       struct alloc_cache* alloc, struct regional* region);
+
 /**
  * Copy a parsed rrset into given key, decompressing and allocating rdata.
  * @param pkt: packet for decompression
index a2f116afba430268702406ab65c8bdad602b755c..28f603d6f98f1d071c3a697c79846f8562d948f2 100644 (file)
@@ -57,6 +57,10 @@ typedef uint64_t rrset_id_type;
  * this is set on SOA rrsets in the authority section, to keep its TTL separate
  * from the SOA in the answer section from a direct SOA query or ANY query. */
 #define PACKED_RRSET_SOA_NEG 0x4
+/** This rrset is considered to have a fixed TTL; its TTL doesn't have to be
+ * updated on encoding in a reply.  This flag is not expected to be set in
+ * cached data. */
+#define PACKED_RRSET_FIXEDTTL 0x80000000
 
 /** number of rrs and rrsets for integer overflow protection.  More than
  * this is not really possible (64K packet has much less RRs and RRsets) in
@@ -83,6 +87,7 @@ struct packed_rrset_key {
         *      o PACKED_RRSET_NSEC_AT_APEX
         *      o PACKED_RRSET_PARENT_SIDE
         *      o PACKED_RRSET_SOA_NEG
+        *      o PACKED_RRSET_FIXEDTTL (not supposed to be cached)
         */
        uint32_t flags;
        /** the rrset type in network format */
index 8bd7b973c2f749e1a065148450040b1b18875528..bf7b943ff640345344a7c92886801654453139e8 100644 (file)
@@ -75,6 +75,7 @@
 #ifdef UB_ON_WINDOWS
 #include "winrc/win_svc.h"
 #endif
+#include "respip/respip.h"
 
 #ifdef WITH_PYTHONMODULE
 #include "pythonmod/pythonmod.h"
@@ -318,6 +319,7 @@ fptr_whitelist_mod_init(int (*fptr)(struct module_env* env, int id))
        if(fptr == &iter_init) return 1;
        else if(fptr == &val_init) return 1;
        else if(fptr == &dns64_init) return 1;
+       else if(fptr == &respip_init) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_init) return 1;
 #endif
@@ -333,6 +335,7 @@ fptr_whitelist_mod_deinit(void (*fptr)(struct module_env* env, int id))
        if(fptr == &iter_deinit) return 1;
        else if(fptr == &val_deinit) return 1;
        else if(fptr == &dns64_deinit) return 1;
+       else if(fptr == &respip_deinit) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_deinit) return 1;
 #endif
@@ -349,6 +352,7 @@ fptr_whitelist_mod_operate(void (*fptr)(struct module_qstate* qstate,
        if(fptr == &iter_operate) return 1;
        else if(fptr == &val_operate) return 1;
        else if(fptr == &dns64_operate) return 1;
+       else if(fptr == &respip_operate) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_operate) return 1;
 #endif
@@ -365,6 +369,7 @@ fptr_whitelist_mod_inform_super(void (*fptr)(
        if(fptr == &iter_inform_super) return 1;
        else if(fptr == &val_inform_super) return 1;
        else if(fptr == &dns64_inform_super) return 1;
+       else if(fptr == &respip_inform_super) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_inform_super) return 1;
 #endif
@@ -381,6 +386,7 @@ fptr_whitelist_mod_clear(void (*fptr)(struct module_qstate* qstate,
        if(fptr == &iter_clear) return 1;
        else if(fptr == &val_clear) return 1;
        else if(fptr == &dns64_clear) return 1;
+       else if(fptr == &respip_clear) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_clear) return 1;
 #endif
@@ -396,6 +402,7 @@ fptr_whitelist_mod_get_mem(size_t (*fptr)(struct module_env* env, int id))
        if(fptr == &iter_get_mem) return 1;
        else if(fptr == &val_get_mem) return 1;
        else if(fptr == &dns64_get_mem) return 1;
+       else if(fptr == &respip_get_mem) return 1;
 #ifdef WITH_PYTHONMODULE
        else if(fptr == &pythonmod_get_mem) return 1;
 #endif
index d3db3eaec151ca6f41c3ee154a762de23bfba58e..5803353e0c6b88a27737b6601cb7fa4331130647 100644 (file)
@@ -174,6 +174,9 @@ struct val_anchors;
 struct val_neg_cache;
 struct iter_forwards;
 struct iter_hints;
+struct respip_set;
+struct respip_client_info;
+struct respip_addr_info;
 
 /** Maximum number of modules in operation */
 #define MAX_MODULE 16
@@ -508,6 +511,8 @@ struct sock_list {
        struct sockaddr_storage addr;
 };
 
+struct respip_action_info;
+
 /**
  * Module state, per query.
  */
@@ -562,6 +567,19 @@ struct module_qstate {
        int no_cache_lookup;
        /** whether modules should store answer in the cache */
        int no_cache_store;
+
+       /**
+        * Attributes of clients that share the qstate that may affect IP-based
+        * actions.
+        */
+       struct respip_client_info* client_info;
+
+       /** Extended result of response-ip action processing, mainly
+        *  for logging purposes. */
+       struct respip_action_info* respip_action_info;
+
+       /** whether the reply should be dropped */
+       int is_drop;
 };
 
 /**