summaryrefslogtreecommitdiffstats
path: root/lib/libc/net/gethostbydns.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libc/net/gethostbydns.c')
-rw-r--r--lib/libc/net/gethostbydns.c124
1 files changed, 67 insertions, 57 deletions
diff --git a/lib/libc/net/gethostbydns.c b/lib/libc/net/gethostbydns.c
index 6cb43f0..b4c80d4 100644
--- a/lib/libc/net/gethostbydns.c
+++ b/lib/libc/net/gethostbydns.c
@@ -88,11 +88,11 @@ static const char AskedForGot[] =
"gethostby*.gethostanswer: asked for \"%s\", got \"%s\"";
#ifdef RESOLVSORT
-static void addrsort(char **, int);
+static void addrsort(char **, int, res_state);
#endif
#ifdef DEBUG
-static void dprintf(char *, int) __printflike(1, 0);
+static void dprintf(char *, int, res_state) __printflike(1, 0);
#endif
#define MAXPACKET (64*1024)
@@ -111,11 +111,12 @@ int _dns_ttl_;
#ifdef DEBUG
static void
-dprintf(msg, num)
+dprintf(msg, num, res)
char *msg;
int num;
+ res_state res;
{
- if (_res.options & RES_DEBUG) {
+ if (res->options & RES_DEBUG) {
int save = errno;
printf(msg, num);
@@ -123,14 +124,14 @@ dprintf(msg, num)
}
}
#else
-# define dprintf(msg, num) /*nada*/
+# define dprintf(msg, num, res) /*nada*/
#endif
#define BOUNDED_INCR(x) \
do { \
cp += x; \
if (cp > eom) { \
- h_errno = NO_RECOVERY; \
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY); \
return -1; \
} \
} while (0)
@@ -138,7 +139,7 @@ dprintf(msg, num)
#define BOUNDS_CHECK(ptr, count) \
do { \
if ((ptr) + (count) > eom) { \
- h_errno = NO_RECOVERY; \
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY); \
return -1; \
} \
} while (0)
@@ -171,7 +172,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
name_ok = res_dnok;
break;
default:
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1; /* XXX should be abort(); */
}
/*
@@ -185,12 +186,12 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
cp = answer->buf;
BOUNDED_INCR(HFIXEDSZ);
if (qdcount != 1) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
n = dn_expand(answer->buf, eom, cp, bp, ep - bp);
if ((n < 0) || !(*name_ok)(bp)) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
BOUNDED_INCR(n + QFIXEDSZ);
@@ -201,7 +202,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
*/
n = strlen(bp) + 1; /* for the \0 */
if (n >= MAXHOSTNAMELEN) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
he->h_name = bp;
@@ -252,7 +253,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
}
cp += n;
if (cp != erdata) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
/* Store alias. */
@@ -282,7 +283,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
}
cp += n;
if (cp != erdata) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
/* Get canonical name. */
@@ -321,7 +322,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
#if MULTI_PTRS_ARE_ALIASES
cp += n;
if (cp != erdata) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
if (!haveanswer)
@@ -341,7 +342,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
break;
#else
he->h_name = bp;
- if (_res.options & RES_USE_INET6) {
+ if (hed->res->options & RES_USE_INET6) {
n = strlen(bp) + 1; /* for the \0 */
if (n >= MAXHOSTNAMELEN) {
had_error++;
@@ -350,7 +351,7 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
bp += n;
_map_v4v6_hostent(he, &bp, ep);
}
- h_errno = NETDB_SUCCESS;
+ RES_SET_H_ERRNO(hed->res, NETDB_SUCCESS);
return 0;
#endif
case T_A:
@@ -376,14 +377,14 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
bp += sizeof(align) - ((u_long)bp % sizeof(align));
if (bp + n >= ep) {
- dprintf("size (%d) too big\n", n);
+ dprintf("size (%d) too big\n", n, hed->res);
had_error++;
continue;
}
if (hap >= &hed->h_addr_ptrs[_MAXADDRS-1]) {
if (!toobig++)
dprintf("Too many addresses (%d)\n",
- _MAXADDRS);
+ _MAXADDRS, hed->res);
cp += n;
continue;
}
@@ -391,13 +392,14 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
bp += n;
cp += n;
if (cp != erdata) {
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
break;
default:
- dprintf("Impossible condition (type=%d)\n", type);
- h_errno = NO_RECOVERY;
+ dprintf("Impossible condition (type=%d)\n", type,
+ hed->res);
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
/* BIND has abort() here, too risky on bad data */
}
@@ -413,8 +415,8 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
* in its return structures - should give it the "best"
* address in that case, not some random one
*/
- if (_res.nsort && haveanswer > 1 && qtype == T_A)
- addrsort(hed->h_addr_ptrs, haveanswer);
+ if (hed->res->nsort && haveanswer > 1 && qtype == T_A)
+ addrsort(hed->h_addr_ptrs, haveanswer, hed->res);
# endif /*RESOLVSORT*/
if (!he->h_name) {
n = strlen(qname) + 1; /* for the \0 */
@@ -424,13 +426,13 @@ gethostanswer(const querybuf *answer, int anslen, const char *qname, int qtype,
he->h_name = bp;
bp += n;
}
- if (_res.options & RES_USE_INET6)
+ if (hed->res->options & RES_USE_INET6)
_map_v4v6_hostent(he, &bp, ep);
- h_errno = NETDB_SUCCESS;
+ RES_SET_H_ERRNO(hed->res, NETDB_SUCCESS);
return 0;
}
no_recovery:
- h_errno = NO_RECOVERY;
+ RES_SET_H_ERRNO(hed->res, NO_RECOVERY);
return -1;
}
@@ -440,11 +442,14 @@ __dns_getanswer(const char *answer, int anslen, const char *qname, int qtype)
{
struct hostdata *hd;
int error;
+ res_state statp;
+ statp = __res_state();
if ((hd = __hostdata_init()) == NULL) {
- h_errno = NETDB_INTERNAL;
+ RES_SET_H_ERRNO(statp, NETDB_INTERNAL);
return NULL;
}
+ hd->data.res = statp;
switch (qtype) {
case T_AAAA:
hd->host.h_addrtype = AF_INET6;
@@ -487,7 +492,7 @@ _dns_gethostbyname(void *rval, void *cb_data, va_list ap)
type = T_AAAA;
break;
default:
- h_errno = NETDB_INTERNAL;
+ RES_SET_H_ERRNO(hed->res, NETDB_INTERNAL);
errno = EAFNOSUPPORT;
return NS_UNAVAIL;
}
@@ -496,17 +501,17 @@ _dns_gethostbyname(void *rval, void *cb_data, va_list ap)
he->h_length = size;
if ((buf = malloc(sizeof(*buf))) == NULL) {
- h_errno = NETDB_INTERNAL;
+ RES_SET_H_ERRNO(hed->res, NETDB_INTERNAL);
return NS_NOTFOUND;
}
- n = res_search(name, C_IN, type, buf->buf, sizeof(buf->buf));
+ n = res_nsearch(hed->res, name, C_IN, type, buf->buf, sizeof(buf->buf));
if (n < 0) {
free(buf);
- dprintf("res_search failed (%d)\n", n);
+ dprintf("res_nsearch failed (%d)\n", n, hed->res);
return (0);
} else if (n > sizeof(buf->buf)) {
free(buf);
- dprintf("static buffer is too small (%d)\n", n);
+ dprintf("static buffer is too small (%d)\n", n, hed->res);
return (0);
}
error = gethostanswer(buf, n, name, type, he, hed);
@@ -538,10 +543,6 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
he = va_arg(ap, struct hostent *);
hed = va_arg(ap, struct hostent_data *);
- if ((_res.options & RES_INIT) == 0 && res_init() == -1) {
- h_errno = NETDB_INTERNAL;
- return NS_UNAVAIL;
- }
switch (af) {
case AF_INET:
(void) sprintf(qbuf, "%u.%u.%u.%u.in-addr.arpa",
@@ -563,18 +564,19 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
abort();
}
if ((buf = malloc(sizeof(*buf))) == NULL) {
- h_errno = NETDB_INTERNAL;
+ RES_SET_H_ERRNO(hed->res, NETDB_INTERNAL);
return NS_NOTFOUND;
}
- n = res_query(qbuf, C_IN, T_PTR, (u_char *)buf->buf, sizeof buf->buf);
+ n = res_nquery(hed->res, qbuf, C_IN, T_PTR, (u_char *)buf->buf,
+ sizeof buf->buf);
if (n < 0) {
free(buf);
- dprintf("res_query failed (%d)\n", n);
+ dprintf("res_nquery failed (%d)\n", n, hed->res);
return NS_UNAVAIL;
}
if (n > sizeof buf->buf) {
free(buf);
- dprintf("static buffer is too small (%d)\n", n);
+ dprintf("static buffer is too small (%d)\n", n, hed->res);
return NS_UNAVAIL;
}
if ((error = gethostanswer(buf, n, qbuf, T_PTR, he, hed)) != 0) {
@@ -590,9 +592,9 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
*/
strncpy(hname2, he->h_name, MAXDNAME);
hname2[MAXDNAME] = '\0';
- old_options = _res.options;
- _res.options &= ~RES_DNSRCH;
- _res.options |= RES_DEFNAMES;
+ old_options = hed->res->options;
+ hed->res->options &= ~RES_DNSRCH;
+ hed->res->options |= RES_DEFNAMES;
memset(&rhd, 0, sizeof rhd);
if (!(rhe = gethostbyname_r(hname2, &rhd.host, &rhd.data))) {
if (inet_ntop(af, addr, numaddr, sizeof(numaddr)) == NULL)
@@ -600,11 +602,11 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
syslog(LOG_NOTICE|LOG_AUTH,
"gethostbyaddr: No A record for %s (verifying [%s])",
hname2, numaddr);
- _res.options = old_options;
- h_errno = HOST_NOT_FOUND;
+ hed->res->options = old_options;
+ RES_SET_H_ERRNO(hed->res, HOST_NOT_FOUND);
return NS_NOTFOUND;
}
- _res.options = old_options;
+ hed->res->options = old_options;
for (haddr = rhe->h_addr_list; *haddr; haddr++)
if (!memcmp(*haddr, addr, INADDRSZ))
break;
@@ -614,7 +616,7 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
syslog(LOG_NOTICE|LOG_AUTH,
"gethostbyaddr: A record of %s != PTR record [%s]",
hname2, numaddr);
- h_errno = HOST_NOT_FOUND;
+ RES_SET_H_ERRNO(hed->res, HOST_NOT_FOUND);
return NS_NOTFOUND;
}
}
@@ -624,20 +626,21 @@ _dns_gethostbyaddr(void *rval, void *cb_data, va_list ap)
memcpy(hed->host_addr, uaddr, len);
hed->h_addr_ptrs[0] = (char *)hed->host_addr;
hed->h_addr_ptrs[1] = NULL;
- if (af == AF_INET && (_res.options & RES_USE_INET6)) {
+ if (af == AF_INET && (hed->res->options & RES_USE_INET6)) {
_map_v4v6_address((char*)hed->host_addr, (char*)hed->host_addr);
he->h_addrtype = AF_INET6;
he->h_length = IN6ADDRSZ;
}
- h_errno = NETDB_SUCCESS;
+ RES_SET_H_ERRNO(hed->res, NETDB_SUCCESS);
return (error == 0) ? NS_SUCCESS : NS_NOTFOUND;
}
#ifdef RESOLVSORT
static void
-addrsort(ap, num)
+addrsort(ap, num, res)
char **ap;
int num;
+ res_state res;
{
int i, j;
char **p;
@@ -646,9 +649,9 @@ addrsort(ap, num)
p = ap;
for (i = 0; i < num; i++, p++) {
- for (j = 0 ; (unsigned)j < _res.nsort; j++)
- if (_res.sort_list[j].addr.s_addr ==
- (((struct in_addr *)(*p))->s_addr & _res.sort_list[j].mask))
+ for (j = 0 ; (unsigned)j < res->nsort; j++)
+ if (res->sort_list[j].addr.s_addr ==
+ (((struct in_addr *)(*p))->s_addr & res->sort_list[j].mask))
break;
aval[i] = j;
if (needsort == 0 && i > 0 && j < aval[i-1])
@@ -677,19 +680,26 @@ addrsort(ap, num)
}
}
#endif
+
void
_sethostdnsent(stayopen)
int stayopen;
{
- if ((_res.options & RES_INIT) == 0 && res_init() == -1)
+ res_state statp;
+
+ statp = __res_state();
+ if ((statp->options & RES_INIT) == 0 && res_ninit(statp) == -1)
return;
if (stayopen)
- _res.options |= RES_STAYOPEN | RES_USEVC;
+ statp->options |= RES_STAYOPEN | RES_USEVC;
}
void
_endhostdnsent()
{
- _res.options &= ~(RES_STAYOPEN | RES_USEVC);
- res_close();
+ res_state statp;
+
+ statp = __res_state();
+ statp->options &= ~(RES_STAYOPEN | RES_USEVC);
+ res_nclose(statp);
}
OpenPOWER on IntegriCloud