Example #1
0
/** filter out unsuitable targets
 * @param iter_env: iterator environment with ipv6-support flag.
 * @param env: module environment with infra cache.
 * @param name: zone name
 * @param namelen: length of name
 * @param qtype: query type (host order).
 * @param now: current time
 * @param a: address in delegation point we are examining.
 * @return an integer that signals the target suitability.
 *	as follows:
 *	-1: The address should be omitted from the list.
 *	    Because:
 *		o The address is bogus (DNSSEC validation failure).
 *		o Listed as donotquery
 *		o is ipv6 but no ipv6 support (in operating system).
 *		o is ipv4 but no ipv4 support (in operating system).
 *		o is lame
 *	Otherwise, an rtt in milliseconds.
 *	0 .. USEFUL_SERVER_TOP_TIMEOUT-1
 *		The roundtrip time timeout estimate. less than 2 minutes.
 *		Note that util/rtt.c has a MIN_TIMEOUT of 50 msec, thus
 *		values 0 .. 49 are not used, unless that is changed.
 *	USEFUL_SERVER_TOP_TIMEOUT
 *		This value exactly is given for unresponsive blacklisted.
 *	USEFUL_SERVER_TOP_TIMEOUT+1
 *		For non-blacklisted servers: huge timeout, but has traffic.
 *	USEFUL_SERVER_TOP_TIMEOUT*1 ..
 *		parent-side lame servers get this penalty. A dispreferential
 *		server. (lame in delegpt).
 *	USEFUL_SERVER_TOP_TIMEOUT*2 ..
 *		dnsseclame servers get penalty
 *	USEFUL_SERVER_TOP_TIMEOUT*3 ..
 *		recursion lame servers get penalty
 *	UNKNOWN_SERVER_NICENESS 
 *		If no information is known about the server, this is
 *		returned. 376 msec or so.
 *	+BLACKLIST_PENALTY (of USEFUL_TOP_TIMEOUT*4) for dnssec failed IPs.
 *
 * When a final value is chosen that is dnsseclame ; dnsseclameness checking
 * is turned off (so we do not discard the reply).
 * When a final value is chosen that is recursionlame; RD bit is set on query.
 * Because of the numbers this means recursionlame also have dnssec lameness
 * checking turned off. 
 */
static int
iter_filter_unsuitable(struct iter_env* iter_env, struct module_env* env,
	uint8_t* name, size_t namelen, uint16_t qtype, time_t now, 
	struct delegpt_addr* a)
{
	int rtt, lame, reclame, dnsseclame;
	if(a->bogus)
		return -1; /* address of server is bogus */
	if(donotq_lookup(iter_env->donotq, &a->addr, a->addrlen)) {
		log_addr(VERB_ALGO, "skip addr on the donotquery list",
			&a->addr, a->addrlen);
		return -1; /* server is on the donotquery list */
	}
	if(!iter_env->supports_ipv6 && addr_is_ip6(&a->addr, a->addrlen)) {
		return -1; /* there is no ip6 available */
	}
	if(!iter_env->supports_ipv4 && !addr_is_ip6(&a->addr, a->addrlen)) {
		return -1; /* there is no ip4 available */
	}
	/* check lameness - need zone , class info */
	if(infra_get_lame_rtt(env->infra_cache, &a->addr, a->addrlen, 
		name, namelen, qtype, &lame, &dnsseclame, &reclame, 
		&rtt, now)) {
		log_addr(VERB_ALGO, "servselect", &a->addr, a->addrlen);
		verbose(VERB_ALGO, "   rtt=%d%s%s%s%s", rtt,
			lame?" LAME":"",
			dnsseclame?" DNSSEC_LAME":"",
			reclame?" REC_LAME":"",
			a->lame?" ADDR_LAME":"");
		if(lame)
			return -1; /* server is lame */
		else if(rtt >= USEFUL_SERVER_TOP_TIMEOUT)
			/* server is unresponsive,
			 * we used to return TOP_TIMEOUT, but fairly useless,
			 * because if == TOP_TIMEOUT is dropped because
			 * blacklisted later, instead, remove it here, so
			 * other choices (that are not blacklisted) can be
			 * tried */
			return -1;
		/* select remainder from worst to best */
		else if(reclame)
			return rtt+USEFUL_SERVER_TOP_TIMEOUT*3; /* nonpref */
		else if(dnsseclame || a->dnsseclame)
			return rtt+USEFUL_SERVER_TOP_TIMEOUT*2; /* nonpref */
		else if(a->lame)
			return rtt+USEFUL_SERVER_TOP_TIMEOUT+1; /* nonpref */
		else	return rtt;
	}
	/* no server information present */
	if(a->dnsseclame)
		return UNKNOWN_SERVER_NICENESS+USEFUL_SERVER_TOP_TIMEOUT*2; /* nonpref */
	else if(a->lame)
		return USEFUL_SERVER_TOP_TIMEOUT+1+UNKNOWN_SERVER_NICENESS; /* nonpref */
	return UNKNOWN_SERVER_NICENESS;
}
Example #2
0
/** print details on a delegation point */
static void
print_dp_details(SSL* ssl, struct worker* worker, struct delegpt* dp)
{
	char buf[257];
	struct delegpt_addr* a;
	int lame, dlame, rlame, rto, edns_vs, to, delay,
		tA = 0, tAAAA = 0, tother = 0;
	long long entry_ttl;
	struct rtt_info ri;
	uint8_t edns_lame_known;
	for(a = dp->target_list; a; a = a->next_target) {
		addr_to_str(&a->addr, a->addrlen, buf, sizeof(buf));
		if(!ssl_printf(ssl, "%-16s\t", buf))
			return;
		if(a->bogus) {
			if(!ssl_printf(ssl, "Address is BOGUS. ")) 
				return;
		}
		/* lookup in infra cache */
		delay=0;
		entry_ttl = infra_get_host_rto(worker->env.infra_cache,
			&a->addr, a->addrlen, dp->name, dp->namelen,
			&ri, &delay, *worker->env.now, &tA, &tAAAA, &tother);
		if(entry_ttl == -2 && ri.rto >= USEFUL_SERVER_TOP_TIMEOUT) {
			if(!ssl_printf(ssl, "expired, rto %d msec, tA %d "
				"tAAAA %d tother %d.\n", ri.rto, tA, tAAAA,
				tother))
				return;
			continue;
		}
		if(entry_ttl == -1 || entry_ttl == -2) {
			if(!ssl_printf(ssl, "not in infra cache.\n"))
				return;
			continue; /* skip stuff not in infra cache */
		}

		/* uses type_A because most often looked up, but other
		 * lameness won't be reported then */
		if(!infra_get_lame_rtt(worker->env.infra_cache, 
			&a->addr, a->addrlen, dp->name, dp->namelen,
			LDNS_RR_TYPE_A, &lame, &dlame, &rlame, &rto,
			*worker->env.now)) {
			if(!ssl_printf(ssl, "not in infra cache.\n"))
				return;
			continue; /* skip stuff not in infra cache */
		}
		if(!ssl_printf(ssl, "%s%s%s%srto %d msec, ttl " ARG_LL "d, "
			"ping %d var %d rtt %d, tA %d, tAAAA %d, tother %d",
			lame?"LAME ":"", dlame?"NoDNSSEC ":"",
			a->lame?"AddrWasParentSide ":"",
			rlame?"NoAuthButRecursive ":"", rto, entry_ttl,
			ri.srtt, ri.rttvar, rtt_notimeout(&ri),
			tA, tAAAA, tother))
			return;
		if(delay)
			if(!ssl_printf(ssl, ", probedelay %d", delay))
				return;
		if(infra_host(worker->env.infra_cache, &a->addr, a->addrlen,
			dp->name, dp->namelen, *worker->env.now, &edns_vs,
			&edns_lame_known, &to)) {
			if(edns_vs == -1) {
				if(!ssl_printf(ssl, ", noEDNS%s.",
					edns_lame_known?" probed":" assumed"))
					return;
			} else {
				if(!ssl_printf(ssl, ", EDNS %d%s.", edns_vs,
					edns_lame_known?" probed":" assumed"))
					return;
			}
		}
		if(!ssl_printf(ssl, "\n"))
			return;
	}
}