diff options
author | ume <ume@FreeBSD.org> | 2006-04-15 16:20:27 +0000 |
---|---|---|
committer | ume <ume@FreeBSD.org> | 2006-04-15 16:20:27 +0000 |
commit | b6bb84cf9e6c9d871a17bcf962cf63180af70e95 (patch) | |
tree | 7f8977d8ba3a31812862992c940fc48d67e9a71c /lib/libc/net/gethostbyht.c | |
parent | 65a640e4f05dfa0b6ed9cf426628b7a1106b767b (diff) | |
download | FreeBSD-src-b6bb84cf9e6c9d871a17bcf962cf63180af70e95.zip FreeBSD-src-b6bb84cf9e6c9d871a17bcf962cf63180af70e95.tar.gz |
- make reentrant version of netdb functions glibc style API, and
expose them to outside of libc.
- make netdb functions NSS friendly.
Reviewed by: arch@ and current@ (no objection)
Diffstat (limited to 'lib/libc/net/gethostbyht.c')
-rw-r--r-- | lib/libc/net/gethostbyht.c | 162 |
1 files changed, 115 insertions, 47 deletions
diff --git a/lib/libc/net/gethostbyht.c b/lib/libc/net/gethostbyht.c index 462cd5c..0782518 100644 --- a/lib/libc/net/gethostbyht.c +++ b/lib/libc/net/gethostbyht.c @@ -91,7 +91,8 @@ _endhosthtent(struct hostent_data *hed) } static int -gethostent_p(struct hostent *he, struct hostent_data *hed, int mapped) +gethostent_p(struct hostent *he, struct hostent_data *hed, int mapped, + res_state statp) { char *p, *bp, *ep; char *cp, **q; @@ -99,13 +100,13 @@ gethostent_p(struct hostent *he, struct hostent_data *hed, int mapped) char hostbuf[BUFSIZ + 1]; if (!hed->hostf && !(hed->hostf = fopen(_PATH_HOSTS, "r"))) { - RES_SET_H_ERRNO(hed->res, NETDB_INTERNAL); - return -1; + RES_SET_H_ERRNO(statp, NETDB_INTERNAL); + return (-1); } again: if (!(p = fgets(hostbuf, sizeof hostbuf, hed->hostf))) { - RES_SET_H_ERRNO(hed->res, HOST_NOT_FOUND); - return -1; + RES_SET_H_ERRNO(statp, HOST_NOT_FOUND); + return (-1); } if (*p == '#') goto again; @@ -146,8 +147,8 @@ gethostent_p(struct hostent *he, struct hostent_data *hed, int mapped) *p++ = '\0'; len = strlen(cp) + 1; if (ep - bp < len) { - RES_SET_H_ERRNO(hed->res, NO_RECOVERY); - return -1; + RES_SET_H_ERRNO(statp, NO_RECOVERY); + return (-1); } strlcpy(bp, cp, ep - bp); bp += len; @@ -170,31 +171,50 @@ gethostent_p(struct hostent *he, struct hostent_data *hed, int mapped) cp = p; } *q = NULL; - RES_SET_H_ERRNO(hed->res, NETDB_SUCCESS); - return 0; + RES_SET_H_ERRNO(statp, NETDB_SUCCESS); + return (0); } int -gethostent_r(struct hostent *he, struct hostent_data *hed) +gethostent_r(struct hostent *hptr, char *buffer, size_t buflen, + struct hostent **result, int *h_errnop) { - hed->res = __res_state(); - if ((hed->res->options & RES_INIT) == 0 && res_ninit(hed->res) == -1) { - RES_SET_H_ERRNO(hed->res, NETDB_INTERNAL); - return -1; + struct hostent_data *hed; + struct hostent he; + res_state statp; + + statp = __res_state(); + if ((statp->options & RES_INIT) == 0 && res_ninit(statp) == -1) { + RES_SET_H_ERRNO(statp, NETDB_INTERNAL); + *h_errnop = statp->res_h_errno; + return (-1); + } + if ((hed = __hostent_data_init()) == NULL) { + RES_SET_H_ERRNO(statp, NETDB_INTERNAL); + *h_errnop = statp->res_h_errno; + return (-1); } - return gethostent_p(he, hed, hed->res->options & RES_USE_INET6); + if (gethostent_p(&he, hed, statp->options & RES_USE_INET6, statp) != 0) + return (-1); + if (__copy_hostent(&he, hptr, buffer, buflen) != 0) + return (-1); + *result = hptr; + return (0); } struct hostent * gethostent(void) { struct hostdata *hd; + struct hostent *rval; + int ret_h_errno; if ((hd = __hostdata_init()) == NULL) - return NULL; - if (gethostent_r(&hd->host, &hd->data) != 0) - return NULL; - return &hd->host; + return (NULL); + if (gethostent_r(&hd->host, hd->data, sizeof(hd->data), &rval, + &ret_h_errno) != 0) + return (NULL); + return (rval); } int @@ -202,36 +222,61 @@ _ht_gethostbyname(void *rval, void *cb_data, va_list ap) { const char *name; int af; - struct hostent *he; + char *buffer; + size_t buflen; + int *errnop, *h_errnop; + struct hostent *hptr, he; struct hostent_data *hed; char **cp; + res_state statp; int error; name = va_arg(ap, const char *); af = va_arg(ap, int); - he = va_arg(ap, struct hostent *); - hed = va_arg(ap, struct hostent_data *); + hptr = va_arg(ap, struct hostent *); + buffer = va_arg(ap, char *); + buflen = va_arg(ap, size_t); + errnop = va_arg(ap, int *); + h_errnop = va_arg(ap, int *); + + *((struct hostent **)rval) = NULL; + + statp = __res_state(); + if ((hed = __hostent_data_init()) == NULL) { + RES_SET_H_ERRNO(statp, NETDB_INTERNAL); + *h_errnop = statp->res_h_errno; + return (NS_NOTFOUND); + } - sethostent_r(0, hed); - while ((error = gethostent_p(he, hed, 0)) == 0) { - if (he->h_addrtype != af) + _sethosthtent(0, hed); + while ((error = gethostent_p(&he, hed, 0, statp)) == 0) { + if (he.h_addrtype != af) continue; - if (he->h_addrtype == AF_INET && - hed->res->options & RES_USE_INET6) { - _map_v4v6_address(he->h_addr, he->h_addr); - he->h_length = IN6ADDRSZ; - he->h_addrtype = AF_INET6; + if (he.h_addrtype == AF_INET && + statp->options & RES_USE_INET6) { + _map_v4v6_address(he.h_addr, he.h_addr); + he.h_length = IN6ADDRSZ; + he.h_addrtype = AF_INET6; } - if (strcasecmp(he->h_name, name) == 0) + if (strcasecmp(he.h_name, name) == 0) break; - for (cp = he->h_aliases; *cp != 0; cp++) + for (cp = he.h_aliases; *cp != 0; cp++) if (strcasecmp(*cp, name) == 0) goto found; } found: - endhostent_r(hed); + _endhosthtent(hed); - return (error == 0) ? NS_SUCCESS : NS_NOTFOUND; + if (error != 0) { + *h_errnop = statp->res_h_errno; + return (NS_NOTFOUND); + } + if (__copy_hostent(&he, hptr, buffer, buflen) != 0) { + *h_errnop = statp->res_h_errno; + return (NS_NOTFOUND); + } + *((struct hostent **)rval) = hptr; + return (NS_SUCCESS); } int @@ -239,28 +284,51 @@ _ht_gethostbyaddr(void *rval, void *cb_data, va_list ap) { const char *addr; int len, af; - struct hostent *he; + char *buffer; + size_t buflen; + int *errnop, *h_errnop; + struct hostent *hptr, he; struct hostent_data *hed; + res_state statp; int error; addr = va_arg(ap, const char *); len = va_arg(ap, int); af = va_arg(ap, int); - he = va_arg(ap, struct hostent *); - hed = va_arg(ap, struct hostent_data *); + hptr = va_arg(ap, struct hostent *); + buffer = va_arg(ap, char *); + buflen = va_arg(ap, size_t); + errnop = va_arg(ap, int *); + h_errnop = va_arg(ap, int *); + + *((struct hostent **)rval) = NULL; - sethostent_r(0, hed); - while ((error = gethostent_p(he, hed, 0)) == 0) - if (he->h_addrtype == af && !bcmp(he->h_addr, addr, len)) { - if (he->h_addrtype == AF_INET && - hed->res->options & RES_USE_INET6) { - _map_v4v6_address(he->h_addr, he->h_addr); - he->h_length = IN6ADDRSZ; - he->h_addrtype = AF_INET6; + statp = __res_state(); + if ((hed = __hostent_data_init()) == NULL) { + RES_SET_H_ERRNO(statp, NETDB_INTERNAL); + *h_errnop = statp->res_h_errno; + return (NS_NOTFOUND); + } + + _sethosthtent(0, hed); + while ((error = gethostent_p(&he, hed, 0, statp)) == 0) + if (he.h_addrtype == af && !bcmp(he.h_addr, addr, len)) { + if (he.h_addrtype == AF_INET && + statp->options & RES_USE_INET6) { + _map_v4v6_address(he.h_addr, he.h_addr); + he.h_length = IN6ADDRSZ; + he.h_addrtype = AF_INET6; } break; } - endhostent_r(hed); + _endhosthtent(hed); - return (error == 0) ? NS_SUCCESS : NS_NOTFOUND; + if (error != 0) + return (NS_NOTFOUND); + if (__copy_hostent(&he, hptr, buffer, buflen) != 0) { + *h_errnop = statp->res_h_errno; + return (NS_NOTFOUND); + } + *((struct hostent **)rval) = hptr; + return (NS_SUCCESS); } |