Module Name:    src
Committed By:   christos
Date:           Tue Aug 27 09:53:33 UTC 2013

Modified Files:
        src/distrib/utils/libhack: Makefile Makefile.inc gethost.c

Log Message:
avoid copying most of libc (except gethostent_r, which unfortunately
adds a resolver dependency) by callling the internal nsswitch functions.


To generate a diff of this commit:
cvs rdiff -u -r1.23 -r1.24 src/distrib/utils/libhack/Makefile
cvs rdiff -u -r1.24 -r1.25 src/distrib/utils/libhack/Makefile.inc
cvs rdiff -u -r1.10 -r1.11 src/distrib/utils/libhack/gethost.c

Please note that diffs are not public domain; they are subject to the
copyright notices on the relevant files.

Modified files:

Index: src/distrib/utils/libhack/Makefile
diff -u src/distrib/utils/libhack/Makefile:1.23 src/distrib/utils/libhack/Makefile:1.24
--- src/distrib/utils/libhack/Makefile:1.23	Thu Oct 11 13:11:16 2012
+++ src/distrib/utils/libhack/Makefile	Tue Aug 27 05:53:33 2013
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile,v 1.23 2012/10/11 17:11:16 christos Exp $
+# $NetBSD: Makefile,v 1.24 2013/08/27 09:53:33 christos Exp $
 #
 # Stubs to kill off some things from libc:
 # This save space on a boot system.
@@ -13,11 +13,12 @@ CPPFLAGS+=	-DSMALL
 CPPFLAGS.runetable.c+=	-I${HACKSRC}/../../../lib/libc/citrus \
 			-DALL_80_TO_FF_SW1
 CPPFLAGS.syslog.c+=	-I${HACKSRC}/../../../lib/libc/include
+CPPFLAGS.gethost.c+=	-I${HACKSRC}/../../../lib/libc/net
 
 LIB=		hack
 SRCS=		getcap.c getgrent.c getnet.c getnetgr.c getpwent.c \
 		localeconv.c multibyte.c perror.c runetable.c setlocale.c \
-		strerror.c strsignal.c syslog.c utmp.c yplib.c
+		strerror.c strsignal.c syslog.c utmp.c yplib.c gethost.c
 
 WARNS=		1
 NOLINKLIB=	# defined

Index: src/distrib/utils/libhack/Makefile.inc
diff -u src/distrib/utils/libhack/Makefile.inc:1.24 src/distrib/utils/libhack/Makefile.inc:1.25
--- src/distrib/utils/libhack/Makefile.inc:1.24	Thu Oct 11 13:11:16 2012
+++ src/distrib/utils/libhack/Makefile.inc	Tue Aug 27 05:53:33 2013
@@ -1,4 +1,4 @@
-# $NetBSD: Makefile.inc,v 1.24 2012/10/11 17:11:16 christos Exp $
+# $NetBSD: Makefile.inc,v 1.25 2013/08/27 09:53:33 christos Exp $
 #
 # Include this fragment to build libhack.o
 # It is .o and not .a to make sure these are the
@@ -25,6 +25,7 @@ CPPFLAGS.runetable.c+= -I${HACKSRC}/../.
 			-DALL_80_TO_FF_SW1
 
 CPPFLAGS.syslog.c+= -I${HACKSRC}/../../../lib/libc/include
+CPPFLAGS.gethost.c+= -I${HACKSRC}/../../../lib/libc/net
 
 libhack.o: ${HACKOBJS}
 	${LD} -r -o $@ ${HACKOBJS}

Index: src/distrib/utils/libhack/gethost.c
diff -u src/distrib/utils/libhack/gethost.c:1.10 src/distrib/utils/libhack/gethost.c:1.11
--- src/distrib/utils/libhack/gethost.c:1.10	Sun Aug 25 04:46:34 2013
+++ src/distrib/utils/libhack/gethost.c	Tue Aug 27 05:53:33 2013
@@ -1,4 +1,4 @@
-/*	$NetBSD: gethost.c,v 1.10 2013/08/25 08:46:34 christos Exp $	*/
+/*	$NetBSD: gethost.c,v 1.11 2013/08/27 09:53:33 christos Exp $	*/
 
 /*-
  * Copyright (c) 1985, 1988, 1993
@@ -49,10 +49,7 @@
  * --Copyright--
  */
 
-/*
- * Copied from:  lib/libc/net/gethostnamadr.c
- * and then gutted, leaving only /etc/hosts support.
- */
+/* Provide just /etc/hosts lookup support */
 
 #include <sys/cdefs.h>
 
@@ -61,217 +58,175 @@
 #define gethostbyname		_gethostbyname
 #endif
 
-#include <sys/param.h>
-#include <sys/socket.h>
-#include <netinet/in.h>
-#include <arpa/inet.h>
-#include <arpa/nameser.h>
 #include <netdb.h>
-#include <resolv.h>
-#include <stdio.h>
-#include <ctype.h>
-#include <errno.h>
 #include <string.h>
+#include <nsswitch.h>
+#include <errno.h>
+#include <arpa/nameser.h>
+#include <arpa/inet.h>
+#include <sys/socket.h>
+
+#include "hostent.h"
 
 #ifdef __weak_alias
 __weak_alias(gethostbyaddr,_gethostbyaddr);
 __weak_alias(gethostbyname,_gethostbyname);
 #endif
 
-#define	MAXALIASES	35
-#define	MAXADDRS	35
-
-static char *h_addr_ptrs[MAXADDRS + 1];
-
-static struct hostent host;
-static char *host_aliases[MAXALIASES];
-static char hostbuf[BUFSIZ+1];
-static struct in_addr host_addr;
-
-FILE *_h_file = NULL;
-void sethostent_r(FILE **);
-void endhostent_r(FILE **);
-
-struct hostent *_gethtent(void);
-struct hostent *_gethtbyname(const char *);
-struct hostent *_gethtbyaddr(const void *, socklen_t, int);
-
-
-#if PACKETSZ > 1024
-#define	MAXPACKET	PACKETSZ
-#else
-#define	MAXPACKET	1024
-#endif
-
 extern int h_errno;
+FILE *_h_file;
+static struct hostent h_ent;
+static char h_buf[4096]; 
+
+static struct hostent *
+getby(int (*f)(void *, void *, va_list), struct getnamaddr *info, ...)
+{
+        va_list ap;
+        int e;
+        
+        va_start(ap, info);
+        e = (*f)(info, NULL, ap);
+        va_end(ap); 
+        switch (e) {
+        case NS_SUCCESS: 
+                return info->hp;  
+        default:
+		return NULL;
+        }       
+}                       
 
 struct hostent *
-gethostbyname(const char *name)
+gethostbyname_r(const char *name, struct hostent *hp, char *buf, size_t bufsiz,
+    int *he)
 {
-	const char *cp;
-
-	/*
-	 * disallow names consisting only of digits/dots, unless
-	 * they end in a dot.
-	 */
-	if (isdigit((unsigned char)name[0]))
-		for (cp = name;; ++cp) {
-			if (!*cp) {
-				if (*--cp == '.')
-					break;
-				/*
-				 * All-numeric, no dot at the end.
-				 * Fake up a hostent as if we'd actually
-				 * done a lookup.
-				 */
-				if (!inet_aton(name, &host_addr)) {
-					h_errno = HOST_NOT_FOUND;
-					return((struct hostent *) NULL);
-				}
-				host.h_name = (char *)name;
-				host.h_aliases = host_aliases;
-				host_aliases[0] = NULL;
-				host.h_addrtype = AF_INET;
-				host.h_length = sizeof(u_int32_t);
-				h_addr_ptrs[0] = (char *)&host_addr;
-				h_addr_ptrs[1] = NULL;
-				host.h_addr_list = h_addr_ptrs;
-				return &host;
-			}
-			if (!isdigit((unsigned char)*cp) && *cp != '.') 
-				break;
-		}
-
-	/* XXX - Force host table lookup. */
-	return _gethtbyname(name);
+	struct getnamaddr info;
+	info.hp = hp;
+	info.buf = buf;
+	info.buflen = bufsiz;
+	info.he = he;
+	return getby(_hf_gethtbyname, &info, name, 0, AF_INET);
 }
 
+
 struct hostent *
-gethostbyaddr(const void *addr, socklen_t len, int type)
+gethostbyname(const char *name)
 {
-#if 0
-	char qbuf[MAXDNAME];
-#endif
-
-	if (type != AF_INET)
-		return NULL;
-#if 0
-	(void)snprintf(qbuf, sizeof(qbuf), "%u.%u.%u.%u.in-addr.arpa",
-	    ((unsigned)addr[3] & 0xff), ((unsigned)addr[2] & 0xff),
-	    ((unsigned)addr[1] & 0xff), ((unsigned)addr[0] & 0xff));
-#endif
-
-	/* XXX - Force host table lookup. */
-	return _gethtbyaddr(addr, len, type);
+	return gethostbyname_r(name, &h_ent, h_buf, sizeof(h_buf), &h_errno);
 }
 
-void
-sethostent_r(FILE **hf)
+struct hostent *
+gethostbyaddr_r(const void *addr, socklen_t len, int type, struct hostent *hp,
+    char *buf, size_t bufsiz, int *he)
 {
-	if (*hf == NULL)
-		*hf = fopen(_PATH_HOSTS, "r");
-	else
-		rewind(*hf);
+	struct getnamaddr info;
+	info.hp = hp;
+	info.buf = buf;
+	info.buflen = bufsiz;
+	info.he = he;
+	return getby(_hf_gethtbyaddr, &info, addr, len, type);
 }
 
-void
-endhostent_r(FILE **hf)
+struct hostent *
+gethostbyaddr(const void *addr, socklen_t len, int type)
 {
-	if (*hf) {
-		(void)fclose(*hf);
-		*hf = NULL;
-	}
+	return gethostbyaddr_r(addr, len, type, &h_ent, h_buf, sizeof(h_buf),
+	    &h_errno);
 }
 
 struct hostent *
-_gethtent(void)
+gethostent_r(FILE *hf, struct hostent *hent, char *buf, size_t buflen, int *he)
 {
-	char *p;
+	char *p, *name;
 	char *cp, **q;
-
-	if (_h_file == NULL && (_h_file = fopen(_PATH_HOSTS, "r" )) == NULL)
+	int af, len;
+	size_t llen, anum;
+	char *aliases[MAXALIASES];
+	struct in6_addr host_addr;
+
+	if (hf == NULL) {
+		*he = NETDB_INTERNAL;
+		errno = EINVAL;
 		return NULL;
-again:
-	if ((p = fgets(hostbuf, BUFSIZ, _h_file)) == NULL)
+	}
+ again:
+	if ((p = fgetln(hf, &llen)) == NULL) {
+		*he = HOST_NOT_FOUND;
 		return NULL;
+	}
+	if (llen < 1)
+		goto again;
 	if (*p == '#')
 		goto again;
-	cp = strpbrk(p, "#\n");
-	if (cp == NULL)
+	p[llen] = '\0';
+	if (!(cp = strpbrk(p, "#\n")))
 		goto again;
 	*cp = '\0';
-	cp = strpbrk(p, " \t");
-	if (cp == NULL)
+	if (!(cp = strpbrk(p, " \t")))
 		goto again;
 	*cp++ = '\0';
-	/* THIS STUFF IS INTERNET SPECIFIC */
-	h_addr_ptrs[0] = (char *)&host_addr;
-	h_addr_ptrs[1] = NULL;
-	(void) inet_aton(p, &host_addr);
-	host.h_addr_list = h_addr_ptrs;
-	host.h_length = sizeof(u_int32_t);
-	host.h_addrtype = AF_INET;
+	if (inet_pton(AF_INET6, p, &host_addr) > 0) {
+		af = AF_INET6;
+		len = NS_IN6ADDRSZ;
+	} else if (inet_pton(AF_INET, p, &host_addr) > 0) {
+#if 0
+		res_state res = __res_get_state();
+		if (res == NULL)
+			return NULL;
+		if (res->options & RES_USE_INET6) {
+			map_v4v6_address(buf, buf);
+			af = AF_INET6;
+			len = NS_IN6ADDRSZ;
+		} else {
+#endif
+			af = AF_INET;
+			len = NS_INADDRSZ;
+#if 0
+		}
+		__res_put_state(res);
+#endif
+	} else {
+		goto again;
+	}
+	/* if this is not something we're looking for, skip it. */
+	if (hent->h_addrtype != 0 && hent->h_addrtype != af)
+		goto again;
+	if (hent->h_length != 0 && hent->h_length != len)
+		goto again;
+
 	while (*cp == ' ' || *cp == '\t')
 		cp++;
-	host.h_name = cp;
-	q = host.h_aliases = host_aliases;
-	cp = strpbrk(cp, " \t");
-	if (cp != NULL) 
+	if ((cp = strpbrk(name = cp, " \t")) != NULL)
 		*cp++ = '\0';
+	q = aliases;
 	while (cp && *cp) {
 		if (*cp == ' ' || *cp == '\t') {
 			cp++;
 			continue;
 		}
-		if (q < &host_aliases[MAXALIASES - 1])
-			*q++ = cp;
-		cp = strpbrk(cp, " \t");
-		if (cp != NULL)
+		if (q >= &aliases[__arraycount(aliases)])
+			goto nospc;
+		*q++ = cp;
+		if ((cp = strpbrk(cp, " \t")) != NULL)
 			*cp++ = '\0';
 	}
-	*q = NULL;
-	return &host;
+	hent->h_length = len;
+	hent->h_addrtype = af;
+	HENT_ARRAY(hent->h_addr_list, 1, buf, buflen);
+	anum = (size_t)(q - aliases);
+	HENT_ARRAY(hent->h_aliases, anum, buf, buflen);
+	HENT_COPY(hent->h_addr_list[0], &host_addr, hent->h_length, buf,
+	    buflen);
+	hent->h_addr_list[1] = NULL;
+
+	HENT_SCOPY(hent->h_name, name, buf, buflen);
+	for (size_t i = 0; i < anum; i++)
+		HENT_SCOPY(hent->h_aliases[i], aliases[i], buf, buflen);
+	hent->h_aliases[anum] = NULL;
+
+	*he = NETDB_SUCCESS;
+	return hent;
+nospc:
+	errno = ENOSPC;
+	*he = NETDB_INTERNAL;
+	return NULL;
 }
-
-struct hostent *
-_gethtbyname(const char *name)
-{
-	struct hostent *p;
-	char **cp;
-	FILE *hf = NULL;
-	
-	sethostent_r(&hf);
-	if (hf == NULL)
-		return NULL;
-	while ((p = _gethtent()) != NULL) {
-		if (strcasecmp(p->h_name, name) == 0)
-			break;
-		for (cp = p->h_aliases; *cp != 0; cp++)
-			if (strcasecmp(*cp, name) == 0)
-				goto found;
-	}
-found:
-	endhostent_r(&hf);
-	if (p == NULL)
-		h_errno = HOST_NOT_FOUND;
-	return p;
-}
-
-struct hostent *
-_gethtbyaddr(const void *addr, socklen_t len, int type)
-{
-	struct hostent *p;
-	FILE *hf = NULL;
-	
-	sethostent_r(&hf);
-	if (hf == NULL)
-		return NULL;
-	while ((p = _gethtent()) != NULL)
-		if (p->h_addrtype == type && !memcmp(p->h_addr, addr, len))
-			break;
-	endhostent_r(&hf);
-	if (p == NULL)
-		h_errno = HOST_NOT_FOUND;
-	return p;
-}
-

Reply via email to