diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/network/getservbyname.c | 2 | ||||
| -rw-r--r-- | src/network/getservbyname_r.c | 36 | 
2 files changed, 16 insertions, 22 deletions
diff --git a/src/network/getservbyname.c b/src/network/getservbyname.c index 0b00ce11..dd303767 100644 --- a/src/network/getservbyname.c +++ b/src/network/getservbyname.c @@ -4,7 +4,7 @@  struct servent *getservbyname(const char *name, const char *prots)  {  	static struct servent se; -	static long buf[32/sizeof(long)]; +	static char *buf[2];  	struct servent *res;  	if (getservbyname_r(name, prots, &se, (void *)buf, sizeof buf, &res))  		return 0; diff --git a/src/network/getservbyname_r.c b/src/network/getservbyname_r.c index 811c174c..8cdf622c 100644 --- a/src/network/getservbyname_r.c +++ b/src/network/getservbyname_r.c @@ -5,49 +5,43 @@  #include <inttypes.h>  #include <errno.h>  #include <string.h> +#include "lookup.h" + +#define ALIGN (sizeof(struct { char a; char *b; }) - sizeof(char *))  int getservbyname_r(const char *name, const char *prots,  	struct servent *se, char *buf, size_t buflen, struct servent **res)  { -	struct addrinfo *ai, hint = { .ai_family = AF_INET }; -	int i; - -	if (!prots) { -		int r = getservbyname_r(name, "tcp", se, buf, buflen, res); -		if (r) r = getservbyname_r(name, "udp", se, buf, buflen, res); -		return r; -	} +	struct service servs[MAXSERVS]; +	int cnt, proto, align;  	/* Align buffer */ -	i = (uintptr_t)buf & sizeof(char *)-1; -	if (!i) i = sizeof(char *); -	if (buflen < 3*sizeof(char *)-i) +	align = -(uintptr_t)buf & ALIGN-1; +	if (buflen < 2*sizeof(char *)+align)  		return ERANGE; -	buf += sizeof(char *)-i; -	buflen -= sizeof(char *)-i; +	buf += align; -	if (!strcmp(prots, "tcp")) hint.ai_protocol = IPPROTO_TCP; -	else if (!strcmp(prots, "udp")) hint.ai_protocol = IPPROTO_UDP; +	if (!prots) proto = 0; +	else if (!strcmp(prots, "tcp")) proto = IPPROTO_TCP; +	else if (!strcmp(prots, "udp")) proto = IPPROTO_UDP;  	else return EINVAL; -	switch (getaddrinfo(0, name, &hint, &ai)) { +	cnt = __lookup_serv(servs, name, proto, 0); +	if (cnt<0) switch (cnt) {  	case EAI_MEMORY:  	case EAI_SYSTEM:  		return ENOMEM;  	default:  		return ENOENT; -	case 0: -		break;  	}  	se->s_name = (char *)name;  	se->s_aliases = (void *)buf;  	se->s_aliases[0] = se->s_name;  	se->s_aliases[1] = 0; -	se->s_port = ((struct sockaddr_in *)ai->ai_addr)->sin_port; -	se->s_proto = (char *)prots; +	se->s_port = htons(servs[0].port); +	se->s_proto = servs[0].proto == IPPROTO_TCP ? "tcp" : "udp"; -	freeaddrinfo(ai);  	*res = se;  	return 0;  }  | 
