⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 getnameinfo.c

📁 unix网络编程第一卷socket编程书上的全部源代码
💻 C
字号:
/* * Copyright (c) 1996 W. Richard Stevens.  All rights reserved.  * * Permission to use or modify this software for educational or * for commercial purposes, and without fee, is hereby granted, * provided that the above copyright notice appears in connection * with any and all uses, with clear indication as to any * modifications made.  The author RESERVES the sole rights of * reproduction, publication and distribution and hence permission * to print this source code in any book, reference manual, * magazine, or other type of publication, including any digital * medium, must be granted in writing by W. Richard Stevens. * * The author makes no representations about the suitability of this  * software for any purpose.  It is provided "as is" without express * or implied warranty.  *//* tabs set for 4 spaces, not 8 */#include	<sys/types.h>#include	<sys/socket.h>#include	<netinet/in.h>#include	<netdb.h>		/* hostent{}, servent{}, etc. */#include	<string.h>		/* strncpy() *//* We need a way to determine if the compiling host supports IPv4/IPv6.   Cannot test for AF_INET6, as some vendors #define it, even though   they don't support it. */#ifdef	AF_INET#define	IPV4	/* this is tested throughout the code that follows */#endif#ifdef	IPV6ADDR_ANY_INIT#define	IPV6	/* this is tested throughout the code that follows */#endif/* Define following if the reentrant versions of get{host|serv}byaddr   are to be used.   Note that getaddrinfo{} must be reentrant if the underlying   get{host|serv}byaddr_r functions are provided. *//* #define	REENTRANT */#define	HENTBUFSIZ	8*1024		/* function prototypes for our own internal functions */static int	do_ipv46(char *, size_t, char *, size_t,					 void *, size_t, int, int);intgetnameinfo(const struct sockaddr *sa, size_t salen,		    char *host, size_t hostlen, char *serv, size_t servlen){	switch (sa->sa_family) {#ifdef	IPV4	case AF_INET: {		struct sockaddr_in	*sain = (struct sockaddr_in *) sa;		return(do_ipv46(host, hostlen, serv, servlen,					 &sain->sin_addr, sizeof(struct in_addr), AF_INET,					 sain->sin_port));	}#endif	/* IPV4 */#ifdef	IPV6	case AF_INET6: {		struct sockaddr_in6	*sain = (struct sockaddr_in6 *) sa;		return(do_ipv46(host, hostlen, serv, servlen,					 &sain->sin6_addr, sizeof(struct in6_addr), AF_INET6,					 sain->sin6_port));	}#endif	/* IPV6 */	default:		return(1);	}}/* * Handle either an IPv4 or an IPv6 address and port. */static intdo_ipv46(char *host, size_t hostlen, char *serv, size_t servlen,		 void *aptr, size_t alen, int family, int port){	struct hostent		*hptr, hent;	struct servent		*sptr, sent;	char				hentbuf[HENTBUFSIZ];	if (hostlen > 0) {#ifdef	REENTRANT		hptr = gethostbyaddr_r(aptr, alen, family,							   &hent, hentbuf, HENTBUFSIZ, &h_errno);#else		hptr = gethostbyaddr(aptr, alen, family);#endif		if (hptr != NULL && hptr->h_name != NULL)			strncpy(host, hptr->h_name, hostlen);		else			return(1);	}	if (servlen > 0) {		/*		 * Notice that we do not have enough information to pass a		 * "protocol" argument to getservbyport(), so the assumption		 * is that the protocol (TCP or UDP) does not matter.		 */#ifdef	REENTRANT		sptr = getservbyport_r(port, NULL,							   &sent, hentbuf, HENTBUFSIZ);#else		sptr = getservbyport(port, NULL);#endif		if (sptr != NULL && sptr->s_name != NULL)			strncpy(serv, sptr->s_name, servlen);		else			return(1);	}	return(0);}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -