/* *Formulateanormalquery,send,andawaitanswer. *Returnedanswerisplacedinsuppliedbuffer"answer". *Performpreliminarycheckofanswer,returningsuccessonly *ifnoerrorisindicatedandtheanswercountisnonzero. *Returnthesizeoftheresponseonsuccess,-1onerror. *ErrornumberisleftinH_ERRNO. * *Callermustparseansweranddeterminewhetheritanswersthequestion.
*/ int
res_nquery(res_state statp, constchar *name, /* domain name */ intclass, int type, /* class and type of query */
u_char *answer, /* buffer to put answer */ int anslen) /* size of answer buffer */
{
u_char buf[MAXPACKET];
HEADER *hp = (HEADER *)(void *)answer; int n;
u_int oflags;
n = res_nmkquery(statp, QUERY, name, class, type, NULL, 0, NULL,
buf, sizeof(buf)); #ifdef RES_USE_EDNS0 if (n > 0 && (statp->_flags & RES_F_EDNS0ERR) == 0 &&
(statp->options & (RES_USE_EDNS0|RES_USE_DNSSEC)) != 0U)
n = res_nopt(statp, n, buf, sizeof(buf), anslen); #endif if (n <= 0) { #ifdef DEBUG if (statp->options & RES_DEBUG)
printf(";; res_query: mkquery failed\n"); #endif
RES_SET_H_ERRNO(statp, NO_RECOVERY); return (n);
}
n = res_nsend(statp, buf, n, answer, anslen); if (n < 0) { #ifdef RES_USE_EDNS0 /* if the query choked with EDNS0, retry without EDNS0 */ if ((statp->options & (RES_USE_EDNS0|RES_USE_DNSSEC)) != 0U &&
((oflags ^ statp->_flags) & RES_F_EDNS0ERR) != 0) {
statp->_flags |= RES_F_EDNS0ERR; if (statp->options & RES_DEBUG)
printf(";; res_nquery: retry without EDNS0\n"); goto again;
} #endif #ifdef DEBUG if (statp->options & RES_DEBUG)
printf(";; res_query: send error\n"); #endif
RES_SET_H_ERRNO(statp, TRY_AGAIN); return (n);
}
if (hp->rcode != NOERROR || ntohs(hp->ancount) == 0) { #ifdef DEBUG if (statp->options & RES_DEBUG)
printf(";; rcode = (%s), counts = an:%d ns:%d ar:%d\n",
p_rcode(hp->rcode),
ntohs(hp->ancount),
ntohs(hp->nscount),
ntohs(hp->arcount)); #endif switch (hp->rcode) { case NXDOMAIN:
RES_SET_H_ERRNO(statp, HOST_NOT_FOUND); break; case SERVFAIL:
RES_SET_H_ERRNO(statp, TRY_AGAIN); break; case NOERROR:
RES_SET_H_ERRNO(statp, NO_DATA); break; case FORMERR: case NOTIMP: case REFUSED: default:
RES_SET_H_ERRNO(statp, NO_RECOVERY); break;
} return (-1);
} return (n);
}
/* *Formulateanormalquery,send,andretrieveanswerinsuppliedbuffer. *Returnthesizeoftheresponseonsuccess,-1onerror. *Ifenabled,implementsearchrulesuntilanswerorunrecoverablefailure *isdetected.Errorcode,ifany,isleftinH_ERRNO.
*/ int
res_nsearch(res_state statp, constchar *name, /* domain name */ intclass, int type, /* class and type of query */
u_char *answer, /* buffer to put answer */ int anslen) /* size of answer */
{ constchar *cp, * const *domain;
HEADER *hp = (HEADER *)(void *)answer; char tmp[NS_MAXDNAME];
u_int dots; int trailing_dot, ret, saved_herrno; int got_nodata = 0, got_servfail = 0, root_on_list = 0; int tried_as_is = 0; int searched = 0;
errno = 0;
RES_SET_H_ERRNO(statp, HOST_NOT_FOUND); /* True if we never query. */
dots = 0; for (cp = name; *cp != '\0'; cp++)
dots += (*cp == '.');
trailing_dot = 0; if (cp > name && *--cp == '.')
trailing_dot++;
/* If there aren't any dots, it could be a user-level alias. */ if (!dots && (cp = res_hostalias(statp, name, tmp, sizeof tmp))!= NULL) return (res_nquery(statp, cp, class, type, answer, anslen));
/* Unfortunately we need to load network-specific info *(dnsservers,searchdomains)before *thedomainstuffistried.Willhaveabetter *fixafterthreadpoolsareusedasthiswill *beloadedonceforthethreadinsteadofeach *timeaqueryistried.
*/
_resolv_populate_res_for_net(statp);
switch (statp->res_h_errno) { case NO_DATA:
got_nodata++; /* FALLTHROUGH */ case HOST_NOT_FOUND: /* keep trying */ break; case TRY_AGAIN: if (hp->rcode == SERVFAIL) { /* try next search element, if any */
got_servfail++; break;
} /* FALLTHROUGH */ default: /* anything else implies that we're done */
done++;
}
/* if we got here for some reason other than DNSRCH, *weonlywantedoneiterationoftheloop,sostop.
*/ if ((statp->options & RES_DNSRCH) == 0U)
done++;
}
}
/* if we got here, we didn't satisfy the search. *ifwedidaninitialfullquery,returnthatquery'sH_ERRNO *(notethatwewouldn'tbehereifthatqueryhadsucceeded). *elseifweevergotanodata,sendthatbackasthereason. *elsesendbackmeaninglessH_ERRNO,thatbeingtheonefrom *thelastDNSRCHwedid.
*/ if (saved_herrno != -1)
RES_SET_H_ERRNO(statp, saved_herrno); elseif (got_nodata)
RES_SET_H_ERRNO(statp, NO_DATA); elseif (got_servfail)
RES_SET_H_ERRNO(statp, TRY_AGAIN); return (-1);
}
/* *Performacallonres_queryontheconcatenationofnameanddomain, *removingatrailingdotfromnameifdomainisNULL.
*/ int
res_nquerydomain(res_state statp, constchar *name, constchar *domain, intclass, int type, /* class and type of query */
u_char *answer, /* buffer to put answer */ int anslen) /* size of answer */
{ char nbuf[MAXDNAME]; constchar *longname = nbuf; int n, d;
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.