qry->flags.NO_MINIMIZE = true;
}
break;
+ case KR_SELECTION_LAME_DELEGATION:
+ if (qry->flags.NO_MINIMIZE) {
+ /* Lame delegations are weird, they breed more lame delegations on broken
+ * zones since trying another server from the same set usualy doesn't help.
+ * We force resolution of another NS name in hope of getting somewhere. */
+ qry->server_selection.local_state->force_resolve = true;
+ addr_state->broken = true;
+ } else {
+ qry->flags.NO_MINIMIZE = true;
+ }
+ break;
case KR_SELECTION_NOTIMPL:
case KR_SELECTION_OTHER_RCODE:
case KR_SELECTION_DNSSEC_ERROR:
- case KR_SELECTION_LAME_DELEGATION:
case KR_SELECTION_BAD_CNAME:
case KR_SELECTION_MALFORMED:
/* These errors are fatal, no point in trying this server again. */
struct local_state {
int timeouts; /**< Number of timeouts that occured resolving this query.*/
bool truncated; /**< Query was truncated, switch to TCP. */
+ /** Force resolution of a new NS name (if possible)
+ * Done by selection.c:error in some cases. */
+ bool force_resolve;
void *private; /**< Inner state of the implementation.*/
};
int choices_len = get_valid_addresses(local_state, choices);
int resolvable_len = get_resolvable_names(local_state, resolvable, qry);
+ if (qry->server_selection.local_state->force_resolve && resolvable_len) {
+ choices_len = 0;
+ qry->server_selection.local_state->force_resolve = false;
+ }
+
bool tcp = qry->flags.TCP || qry->server_selection.local_state->truncated;
*transport = select_transport(choices, choices_len, resolvable, resolvable_len,
qry->server_selection.local_state->timeouts,