bin/51827: getaddrinfo() is broken with numeric service

Mark Andrews marka at isc.org
Mon May 5 22:30:17 PDT 2003


>Number:         51827
>Category:       bin
>Synopsis:       getaddrinfo() is broken with numeric service
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Mon May 05 22:30:09 PDT 2003
>Closed-Date:
>Last-Modified:
>Originator:     Mark Andrews
>Release:        FreeBSD 4.8-RC i386
>Organization:
ISC
>Environment:
System: FreeBSD drugs.dv.isc.org 4.8-RC FreeBSD 4.8-RC #6: Sun Mar 30 11:45:29 EST 2003 marka at drugs.dv.isc.org:/usr/obj/usr/src/sys/DRUGS i386


>Description:

	getaddrinfo() should accept numeric when ai_socktype is not
	specified in hint or hints is NULL.

	RFC 3493:

   If servname is null, the call shall return network-level addresses
   for the specified nodename.  If servname is not null, it is a null-
   terminated character string identifying the requested service.  This
   can be either a descriptive name or a numeric representation suitable
   for use with the address family or families.  If the specified
   address family is AF_INET, AF_INET6 or AF_UNSPEC, the service can be
   specified as a string specifying a decimal port number.

	While I havn't checked the posix spec nothing in RFC 3493
	indicates that numeric values are only to be accepted when
	ai_socktype is specified.

>How-To-Repeat:

% ./a.out
53/NULL
servname not supported for ai_socktype
53/hint
servname not supported for ai_socktype
domain/hint
28 2 17
2 2 17
28 1 6
2 1 6
domain/hint
28 2 17
2 2 17
28 1 6
2 1 6
% 

#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h>
#include <stdio.h>

main() {
	int error;
	struct addrinfo *res, *res0;
	struct addrinfo hint;

	memset(&hint, 0, sizeof(hint));
	hint.ai_family = AF_UNSPEC;

	printf("53/NULL\n");
	error = getaddrinfo("rc.isc.org", "53", NULL,  &res0);

	if (error) {
		printf("%s\n", gai_strerror(error));
	} else {

		for (res = res0; res; res = res->ai_next) {
			printf("%d %u %u\n", res->ai_family, res->ai_socktype,
			       res->ai_protocol);
		}

		freeaddrinfo(res0);
	}

	printf("53/hint\n");
	error = getaddrinfo("rc.isc.org", "53", &hint,  &res0);

	if (error) {
		printf("%s\n", gai_strerror(error));
	} else {

		for (res = res0; res; res = res->ai_next) {
			printf("%d %u %u\n", res->ai_family, res->ai_socktype,
			       res->ai_protocol);
		}

		freeaddrinfo(res0);
	}

	printf("domain/hint\n");
	error = getaddrinfo("rc.isc.org", "domain", NULL,  &res0);

	if (error) {
		printf("%s\n", gai_strerror(error));
	} else {

		for (res = res0; res; res = res->ai_next) {
			printf("%d %u %u\n", res->ai_family, res->ai_socktype,
			       res->ai_protocol);
		}

		freeaddrinfo(res0);
	}

	printf("domain/hint\n");
	error = getaddrinfo("rc.isc.org", "domain", &hint,  &res0);

	if (error) {
		printf("%s\n", gai_strerror(error));
	} else {

		for (res = res0; res; res = res->ai_next) {
			printf("%d %u %u\n", res->ai_family, res->ai_socktype,
			       res->ai_protocol);
		}

		freeaddrinfo(res0);
	}
	exit(0);
}

>Fix:

	The following if from the BIND 8 source but should apply.

Index: lib/irs/getaddrinfo.c
===================================================================
RCS file: /proj/cvs/isc/bind8/src/lib/irs/getaddrinfo.c,v
retrieving revision 8.12
diff -u -r8.12 getaddrinfo.c
--- lib/irs/getaddrinfo.c	3 Dec 2002 05:26:49 -0000	8.12
+++ lib/irs/getaddrinfo.c	6 May 2003 05:10:26 -0000
@@ -987,7 +987,17 @@
 		allownumeric = 1;
 		break;
 	case ANY:
-		allownumeric = 0;
+		switch (ai->ai_family) {
+		case AF_INET:
+#ifdef AF_INET6
+		case AF_INET6:
+#endif
+			allownumeric = 1;
+			break;
+		default:
+			allownumeric = 0;
+			break;
+		}
 		break;
 	default:
 		return EAI_SOCKTYPE;
>Release-Note:
>Audit-Trail:
>Unformatted:


More information about the freebsd-bugs mailing list