158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui/*	$NetBSD: sethostent.c,v 1.20 2014/03/17 13:24:23 christos Exp $	*/
258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui/*
458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * Copyright (c) 1985, 1993
558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *	The Regents of the University of California.  All rights reserved.
658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *
758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * Redistribution and use in source and binary forms, with or without
858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * modification, are permitted provided that the following conditions
958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * are met:
1058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * 1. Redistributions of source code must retain the above copyright
1158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *    notice, this list of conditions and the following disclaimer.
1258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * 2. Redistributions in binary form must reproduce the above copyright
1358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *    notice, this list of conditions and the following disclaimer in the
1458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *    documentation and/or other materials provided with the distribution.
1558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * 3. Neither the name of the University nor the names of its contributors
1658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *    may be used to endorse or promote products derived from this software
1758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *    without specific prior written permission.
1858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui *
1958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
2058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
2158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
2258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
2358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
2458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
2558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
2658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
2758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
2858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
2958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui * SUCH DAMAGE.
3058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui */
3158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
3258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <sys/cdefs.h>
3358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#if defined(LIBC_SCCS) && !defined(lint)
3458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#if 0
3558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuistatic char sccsid[] = "@(#)sethostent.c	8.1 (Berkeley) 6/4/93";
3658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuistatic char rcsid[] = "Id: sethostent.c,v 8.5 1996/09/28 06:51:07 vixie Exp ";
3758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#else
3858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui__RCSID("$NetBSD: sethostent.c,v 1.20 2014/03/17 13:24:23 christos Exp $");
3958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#endif
4058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#endif /* LIBC_SCCS and not lint */
4158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
4258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include "namespace.h"
4358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <sys/param.h>
4458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <netinet/in.h>
4558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <arpa/nameser.h>
4658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <arpa/inet.h>
4758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <assert.h>
4858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <string.h>
4958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <nsswitch.h>
5058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <netdb.h>
5158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <resolv.h>
5258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <errno.h>
5358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include <stdlib.h>
5458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
5558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include "hostent.h"
5658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#include "resolv_private.h"
5758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
5858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#define ALIGNBYTES (sizeof(uintptr_t) - 1)
5958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#define ALIGN(p) (((uintptr_t)(p) + ALIGNBYTES) &~ ALIGNBYTES)
6058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
6158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#ifndef _REENTRANT
6258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuivoid	res_close(void);
6358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#endif
6458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
6558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuistatic struct hostent *_hf_gethtbyname2(const char *, int, struct getnamaddr *);
6658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
675033918092f27179b0c2bbe3babceaed509d4935Elliott Hughesvoid
685033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes/*ARGSUSED*/
695033918092f27179b0c2bbe3babceaed509d4935Elliott Hughessethostent(int stayopen)
705033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes{
715033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes	res_static rs = __res_get_static();
725033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes	if (rs) sethostent_r(&rs->hostf);
735033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes}
745033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes
755033918092f27179b0c2bbe3babceaed509d4935Elliott Hughesvoid
765033918092f27179b0c2bbe3babceaed509d4935Elliott Hughesendhostent(void)
775033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes{
785033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes	res_static rs = __res_get_static();
795033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes	if (rs) endhostent_r(&rs->hostf);
805033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes}
8158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
8258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuivoid
8358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuisethostent_r(FILE **hf)
8458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui{
8558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (!*hf)
865033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes		*hf = fopen(_PATH_HOSTS, "re");
8758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	else
8858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		rewind(*hf);
8958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui}
9058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
9158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuivoid
9258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuiendhostent_r(FILE **hf)
9358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui{
9458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (*hf) {
9558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		(void)fclose(*hf);
9658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*hf = NULL;
9758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
9858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui}
9958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
10058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui/*ARGSUSED*/
10158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuiint
10258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui_hf_gethtbyname(void *rv, void *cb_data, va_list ap)
10358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui{
10458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	struct hostent *hp;
10558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	const char *name;
10658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	int af;
10758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	struct getnamaddr *info = rv;
10858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
10958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	_DIAGASSERT(rv != NULL);
11058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
11158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	name = va_arg(ap, char *);
11258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	/* NOSTRICT skip string len */(void)va_arg(ap, int);
11358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	af = va_arg(ap, int);
11458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
11558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#if 0
11658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	{
11758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		res_state res = __res_get_state();
11858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (res == NULL)
11958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			return NS_NOTFOUND;
12058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (res->options & RES_USE_INET6)
12158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			hp = _hf_gethtbyname2(name, AF_INET6, info);
12258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		else
12358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			hp = NULL;
12458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (hp == NULL)
12558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			hp = _hf_gethtbyname2(name, AF_INET, info);
12658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		__res_put_state(res);
12758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
12858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#else
12958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp = _hf_gethtbyname2(name, af, info);
13058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui#endif
13158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (hp == NULL) {
132bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes		if (*info->he == NETDB_INTERNAL && errno == ENOSPC) {
133bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes			return NS_UNAVAIL; // glibc compatibility.
134bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes		}
1355033918092f27179b0c2bbe3babceaed509d4935Elliott Hughes		*info->he = HOST_NOT_FOUND;
13658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NS_NOTFOUND;
13758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
13858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	return NS_SUCCESS;
13958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui}
14058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
1415033918092f27179b0c2bbe3babceaed509d4935Elliott Hughesstruct hostent *
14258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui_hf_gethtbyname2(const char *name, int af, struct getnamaddr *info)
14358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui{
14458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	struct hostent *hp, hent;
14558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	char *buf, *ptr;
14658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	size_t len, anum, num, i;
14758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	FILE *hf;
14858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	char *aliases[MAXALIASES];
14958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	char *addr_ptrs[MAXADDRS];
15058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
15158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	_DIAGASSERT(name != NULL);
15258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
15358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hf = NULL;
15458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	sethostent_r(&hf);
15558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (hf == NULL) {
15658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		errno = EINVAL;
15758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*info->he = NETDB_INTERNAL;
15858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NULL;
15958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
16058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
16158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if ((ptr = buf = malloc(len = info->buflen)) == NULL) {
16258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*info->he = NETDB_INTERNAL;
16358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NULL;
16458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
16558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
16658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	anum = 0;		/* XXX: gcc */
16758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hent.h_name = NULL;	/* XXX: gcc */
16858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hent.h_addrtype = 0;	/* XXX: gcc */
16958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hent.h_length = 0;	/* XXX: gcc */
17058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
17158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	for (num = 0; num < MAXADDRS;) {
17258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		info->hp->h_addrtype = af;
17358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		info->hp->h_length = 0;
17458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
17558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		hp = netbsd_gethostent_r(hf, info->hp, info->buf, info->buflen,
17658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		    info->he);
177bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes		if (hp == NULL) {
178bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes			if (*info->he == NETDB_INTERNAL && errno == ENOSPC) {
179bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes				goto nospc; // glibc compatibility.
180bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes			}
18158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			break;
182bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes		}
18358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
18458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (strcasecmp(hp->h_name, name) != 0) {
18558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			char **cp;
18658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			for (cp = hp->h_aliases; *cp != NULL; cp++)
18758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui				if (strcasecmp(*cp, name) == 0)
18858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui					break;
18958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			if (*cp == NULL) continue;
19058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		}
19158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
19258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (num == 0) {
19358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			hent.h_addrtype = af = hp->h_addrtype;
19458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			hent.h_length = hp->h_length;
19558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
19658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			HENT_SCOPY(hent.h_name, hp->h_name, ptr, len);
19758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			for (anum = 0; hp->h_aliases[anum]; anum++) {
19858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui				if (anum >= MAXALIASES)
19958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui					goto nospc;
20058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui				HENT_SCOPY(aliases[anum], hp->h_aliases[anum],
20158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui				    ptr, len);
20258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			}
20358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			ptr = (void *)ALIGN(ptr);
20458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			if ((size_t)(ptr - buf) >= info->buflen)
20558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui				goto nospc;
20658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		}
20758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
20858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (num >= MAXADDRS)
20958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			goto nospc;
21058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		HENT_COPY(addr_ptrs[num], hp->h_addr_list[0], hp->h_length, ptr,
21158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		    len);
21258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		num++;
21358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
21458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	endhostent_r(&hf);
21558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
21658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (num == 0) {
21758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*info->he = HOST_NOT_FOUND;
21858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		free(buf);
21958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NULL;
22058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
22158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
22258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp = info->hp;
22358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	ptr = info->buf;
22458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	len = info->buflen;
22558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
22658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp->h_addrtype = hent.h_addrtype;
22758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp->h_length = hent.h_length;
22858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
22958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	HENT_ARRAY(hp->h_aliases, anum, ptr, len);
23058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	HENT_ARRAY(hp->h_addr_list, num, ptr, len);
23158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
23258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	for (i = 0; i < num; i++)
23358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		HENT_COPY(hp->h_addr_list[i], addr_ptrs[i], hp->h_length, ptr,
23458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		    len);
23558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp->h_addr_list[num] = NULL;
23658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
23758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	HENT_SCOPY(hp->h_name, hent.h_name, ptr, len);
23858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
23958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	for (i = 0; i < anum; i++)
24058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		HENT_SCOPY(hp->h_aliases[i], aliases[i], ptr, len);
24158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hp->h_aliases[anum] = NULL;
24258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
24358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	free(buf);
24458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	return hp;
24558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuinospc:
24658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	*info->he = NETDB_INTERNAL;
24758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	free(buf);
24858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	errno = ENOSPC;
24958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	return NULL;
25058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui}
25158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
25258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui/*ARGSUSED*/
25358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cuiint
25458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui_hf_gethtbyaddr(void *rv, void *cb_data, va_list ap)
25558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui{
25658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	struct hostent *hp;
25758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	const unsigned char *addr;
25858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	struct getnamaddr *info = rv;
25958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	FILE *hf;
26058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
26158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	_DIAGASSERT(rv != NULL);
26258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
26358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	addr = va_arg(ap, unsigned char *);
26458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	info->hp->h_length = va_arg(ap, int);
26558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	info->hp->h_addrtype = va_arg(ap, int);
26658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
26758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	hf = NULL;
26858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	sethostent_r(&hf);
26958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (hf == NULL) {
27058d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*info->he = NETDB_INTERNAL;
27158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NS_UNAVAIL;
27258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
27358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	while ((hp = netbsd_gethostent_r(hf, info->hp, info->buf, info->buflen,
27458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	    info->he)) != NULL)
27558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		if (!memcmp(hp->h_addr_list[0], addr, (size_t)hp->h_length))
27658d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui			break;
27758d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	endhostent_r(&hf);
27858d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui
27958d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	if (hp == NULL) {
280bb7d9fb5d438c7477c404f97e07e145d49335947Elliott Hughes		if (errno == ENOSPC) return NS_UNAVAIL; // glibc compatibility.
28158d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		*info->he = HOST_NOT_FOUND;
28258d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui		return NS_NOTFOUND;
28358d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	}
28458d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui	return NS_SUCCESS;
28558d33a51f336d6823ef1ec915949a5884699ff5fYabin Cui}
286