From 036ae3dd790971f07f3cf41e19e087973d0de986 Mon Sep 17 00:00:00 2001 From: Hajimu UMEMOTO Date: Sun, 15 May 2005 20:15:15 +0000 Subject: [PATCH] - The ai_addrlen of a struct addrinfo used to be a size_t, per RFC 2553. In XNS5.2, and subsequently in POSIX-2001 and RFC 3493, it was changed to a socklen_t. And, the n_net of a struct netent used to be an unsigned long integer. In XNS5, and subsequently in POSIX-2001, it was changed to an uint32_t. To accomodate for this while preserving ABI compatibility with the old interface, we need to prepend or append 32 bits of padding, depending on the (LP64) architecture's endianness. - Correct 1st argument of getnetbyaddr() to uint32_t on 32 bit arch. Stay as is on 64 bit arch for ABI backward compatibility for now. Reviewed by: das, peter MFC after: 2 weeks --- include/netdb.h | 51 ++++++++++++++++++++++++++++++++---- lib/libc/net/getaddrinfo.c | 5 +++- lib/libc/net/getnetbydns.c | 20 ++++++++------ lib/libc/net/getnetbyht.c | 7 +++-- lib/libc/net/getnetbynis.c | 11 +++++--- lib/libc/net/getnetnamadr.c | 11 +++++--- lib/libc/net/netdb_private.h | 8 +----- 7 files changed, 83 insertions(+), 30 deletions(-) diff --git a/include/netdb.h b/include/netdb.h index 6a2bd27cf43a..35fa2b1e2402 100644 --- a/include/netdb.h +++ b/include/netdb.h @@ -63,6 +63,8 @@ #include #include +#include +#include #ifndef _SIZE_T_DECLARED typedef __size_t size_t; @@ -74,6 +76,11 @@ typedef __socklen_t socklen_t; #define _SOCKLEN_T_DECLARED #endif +#ifndef _UINT32_T_DECLARED +typedef __uint32_t uint32_t; +#define _UINT32_T_DECLARED +#endif + #ifndef _PATH_HEQUIV # define _PATH_HEQUIV "/etc/hosts.equiv" #endif @@ -99,14 +106,27 @@ struct hostent { }; /* - * Assumption here is that a network number - * fits in an unsigned long -- probably a poor one. + * Note: n_net used to be an unsigned long integer. + * In XNS5, and subsequently in POSIX-2001 it was changed to an + * uint32_t. + * To accomodate for this while preserving binary compatibility with + * the old interface, we prepend or append 32 bits of padding, + * depending on the (LP64) architecture's endianness. + * + * This should be deleted the next time the libc major number is + * incremented. */ struct netent { char *n_name; /* official name of net */ char **n_aliases; /* alias list */ int n_addrtype; /* net address type */ - unsigned long n_net; /* network # */ +#if __LONG_BIT == 64 && _BYTE_ORDER == _BIG_ENDIAN + uint32_t __n_pad0; /* ABI compatibility */ +#endif + uint32_t n_net; /* network # */ +#if __LONG_BIT == 64 && _BYTE_ORDER == _LITTLE_ENDIAN + uint32_t __n_pad0; /* ABI compatibility */ +#endif }; struct servent { @@ -122,12 +142,29 @@ struct protoent { int p_proto; /* protocol # */ }; +/* + * Note: ai_addrlen used to be a size_t, per RFC 2553. + * In XNS5.2, and subsequently in POSIX-2001 and RFC 3493 it was + * changed to a socklen_t. + * To accomodate for this while preserving binary compatibility with the + * old interface, we prepend or append 32 bits of padding, depending on + * the (LP64) architecture's endianness. + * + * This should be deleted the next time the libc major number is + * incremented. + */ struct addrinfo { int ai_flags; /* AI_PASSIVE, AI_CANONNAME, AI_NUMERICHOST */ int ai_family; /* PF_xxx */ int ai_socktype; /* SOCK_xxx */ int ai_protocol; /* 0 or IPPROTO_xxx for IPv4 and IPv6 */ - size_t ai_addrlen; /* length of ai_addr */ +#if __LONG_BIT == 64 && _BYTE_ORDER == _BIG_ENDIAN + uint32_t __ai_pad0; /* ABI compatibility */ +#endif + socklen_t ai_addrlen; /* length of ai_addr */ +#if __LONG_BIT == 64 && _BYTE_ORDER == _LITTLE_ENDIAN + uint32_t __ai_pad0; /* ABI compatibility */ +#endif char *ai_canonname; /* canonical name for hostname */ struct sockaddr *ai_addr; /* binary address */ struct addrinfo *ai_next; /* next structure in linked list */ @@ -225,7 +262,11 @@ struct hostent *gethostbyname2(const char *, int); struct hostent *gethostent(void); struct hostent *getipnodebyaddr(const void *, size_t, int, int *); struct hostent *getipnodebyname(const char *, int, int, int *); -struct netent *getnetbyaddr(unsigned long, int); +#if __LONG_BIT == 64 +struct netent *getnetbyaddr(unsigned long, int); /* ABI compatibility */ +#else +struct netent *getnetbyaddr(uint32_t, int); +#endif struct netent *getnetbyname(const char *); struct netent *getnetent(void); int getnetgrent(char **, char **, char **); diff --git a/lib/libc/net/getaddrinfo.c b/lib/libc/net/getaddrinfo.c index a7ab1286eec6..5d6ca2f8e914 100644 --- a/lib/libc/net/getaddrinfo.c +++ b/lib/libc/net/getaddrinfo.c @@ -135,7 +135,7 @@ TAILQ_HEAD(policyhead, policyqueue); static const struct afd { int a_af; int a_addrlen; - int a_socklen; + socklen_t a_socklen; int a_off; const char *a_addrany; const char *a_loopback; @@ -1352,6 +1352,9 @@ get_ai(pai, afd, addr) memset(ai->ai_addr, 0, (size_t)afd->a_socklen); ai->ai_addr->sa_len = afd->a_socklen; ai->ai_addrlen = afd->a_socklen; +#if __LONG_BIT == 64 + ai->__ai_pad0 = 0; /* ABI compatibility */ +#endif ai->ai_addr->sa_family = ai->ai_family = afd->a_af; p = (char *)(void *)(ai->ai_addr); #ifdef FAITH diff --git a/lib/libc/net/getnetbydns.c b/lib/libc/net/getnetbydns.c index e4f0ae8a85fe..5eca2685cefa 100644 --- a/lib/libc/net/getnetbydns.c +++ b/lib/libc/net/getnetbydns.c @@ -259,6 +259,9 @@ getnetanswer(querybuf *answer, int anslen, int net_i, struct netent *ne, break; } ne->n_aliases++; +#if __LONG_BIT == 64 + ne->__n_pad0 = 0; /* ABI compatibility */ +#endif return 0; } h_errno = TRY_AGAIN; @@ -268,7 +271,7 @@ getnetanswer(querybuf *answer, int anslen, int net_i, struct netent *ne, int _dns_getnetbyaddr(void *rval, void *cb_data, va_list ap) { - unsigned long net; + uint32_t net; int net_type; struct netent *ne; struct netent_data *ned; @@ -276,9 +279,9 @@ _dns_getnetbyaddr(void *rval, void *cb_data, va_list ap) int nn, anslen, error; querybuf *buf; char qbuf[MAXDNAME]; - unsigned long net2; + uint32_t net2; - net = va_arg(ap, unsigned long); + net = va_arg(ap, uint32_t); net_type = va_arg(ap, int); ne = va_arg(ap, struct netent *); ned = va_arg(ap, struct netent_data *); @@ -327,12 +330,13 @@ _dns_getnetbyaddr(void *rval, void *cb_data, va_list ap) error = getnetanswer(buf, anslen, BYADDR, ne, ned); free(buf); if (error == 0) { - unsigned u_net = net; /* maybe net should be unsigned ? */ - /* Strip trailing zeros */ - while ((u_net & 0xff) == 0 && u_net != 0) - u_net >>= 8; - ne->n_net = u_net; + while ((net & 0xff) == 0 && net != 0) + net >>= 8; + ne->n_net = net; +#if __LONG_BIT == 64 + ne->__n_pad0 = 0; /* ABI compatibility */ +#endif return NS_SUCCESS; } return NS_NOTFOUND; diff --git a/lib/libc/net/getnetbyht.c b/lib/libc/net/getnetbyht.c index fb6ee4dcaf3a..f4dcd98a424a 100644 --- a/lib/libc/net/getnetbyht.c +++ b/lib/libc/net/getnetbyht.c @@ -122,6 +122,9 @@ getnetent_r(struct netent *ne, struct netent_data *ned) if (p != NULL) *p++ = '\0'; ne->n_net = inet_network(cp); +#if __LONG_BIT == 64 + ne->__n_pad0 = 0; /* ABI compatibility */ +#endif ne->n_addrtype = AF_INET; q = ne->n_aliases = ned->net_aliases; if (p != NULL) { @@ -191,13 +194,13 @@ _ht_getnetbyname(void *rval, void *cb_data, va_list ap) int _ht_getnetbyaddr(void *rval, void *cb_data, va_list ap) { - unsigned long net; + uint32_t net; int type; struct netent *ne; struct netent_data *ned; int error; - net = va_arg(ap, unsigned long); + net = va_arg(ap, uint32_t); type = va_arg(ap, int); ne = va_arg(ap, struct netent *); ned = va_arg(ap, struct netent_data *); diff --git a/lib/libc/net/getnetbynis.c b/lib/libc/net/getnetbynis.c index 4725cfb09c9d..70785ac5bd5e 100644 --- a/lib/libc/net/getnetbynis.c +++ b/lib/libc/net/getnetbynis.c @@ -99,6 +99,9 @@ _getnetbynis(const char *name, char *map, int af, struct netent *ne, cp++; ne->n_net = inet_network(cp); +#if __LONG_BIT == 64 + ne->__n_pad0 = 0; /* ABI compatibility */ +#endif ne->n_addrtype = AF_INET; q = ne->n_aliases = ned->net_aliases; @@ -149,22 +152,22 @@ _nis_getnetbyname(void *rval, void *cb_data, va_list ap) } -int +int _nis_getnetbyaddr(void *rval, void *cb_data, va_list ap) { #ifdef YP - unsigned long addr; + uint32_t addr; int af; struct netent *ne; struct netent_data *ned; char *str, *cp; - unsigned long net2; + uint32_t net2; int nn; unsigned int netbr[4]; char buf[MAXDNAME]; int error; - addr = va_arg(ap, unsigned long); + addr = va_arg(ap, uint32_t); af = va_arg(ap, int); ne = va_arg(ap, struct netent *); ned = va_arg(ap, struct netent_data *); diff --git a/lib/libc/net/getnetnamadr.c b/lib/libc/net/getnetnamadr.c index 7b8aaa68943f..eb8c9ae69538 100644 --- a/lib/libc/net/getnetnamadr.c +++ b/lib/libc/net/getnetnamadr.c @@ -120,7 +120,8 @@ getnetbyname_r(const char *name, struct netent *ne, struct netent_data *ned) } int -getnetbyaddr_r(u_long addr, int af, struct netent *ne, struct netent_data *ned) +getnetbyaddr_r(uint32_t addr, int af, struct netent *ne, + struct netent_data *ned) { int rval; @@ -164,13 +165,17 @@ getnetbyname(const char *name) } struct netent * -getnetbyaddr(u_long addr, int af) +#if __LONG_BIT == 64 +getnetbyaddr(u_long addr, int af) /* ABI compatibility */ +#else +getnetbyaddr(uint32_t addr, int af) +#endif { struct netdata *nd; if ((nd = __netdata_init()) == NULL) return NULL; - if (getnetbyaddr_r(addr, af, &nd->net, &nd->data) != 0) + if (getnetbyaddr_r((uint32_t)addr, af, &nd->net, &nd->data) != 0) return NULL; return &nd->net; } diff --git a/lib/libc/net/netdb_private.h b/lib/libc/net/netdb_private.h index e5a55ec79d7c..0b3278015ab0 100644 --- a/lib/libc/net/netdb_private.h +++ b/lib/libc/net/netdb_private.h @@ -28,14 +28,8 @@ #ifndef _NETDB_PRIVATE_H_ #define _NETDB_PRIVATE_H_ -#include #include /* XXX: for FILE */ -#ifndef _UINT32_T_DECLARED -typedef __uint32_t uint32_t; -#define _UINT32_T_DECLARED -#endif - #define _MAXALIASES 35 #define _MAXLINELEN 1024 #define _MAXADDRS 35 @@ -155,7 +149,7 @@ int gethostbyname_r(const char *, struct hostent *, struct hostent_data *); int gethostbyname2_r(const char *, int, struct hostent *, struct hostent_data *); int gethostent_r(struct hostent *, struct hostent_data *); -int getnetbyaddr_r(unsigned long addr, int af, struct netent *, +int getnetbyaddr_r(uint32_t addr, int af, struct netent *, struct netent_data *); int getnetbyname_r(const char *, struct netent *, struct netent_data *); int getnetent_r(struct netent *, struct netent_data *);