GETNAMEINFO(3) GETNAMEINFO(3) NAME getnameinfo - address-to-nodename translation in a protocol-independent manner. SYNOPSIS #include <sys/types.h> #include <sys/socket.h> #include <netdb.h> int getnameinfo (const struct sockaddr *sa, socklen_t salen, char *node, socklen_t nodelen, char *serv, socklen_t servlen, unsigned int flags) DESCRIPTION The getnameinfo function is defined for protocol-independent address-to-nodename translation. Its functionality is a reverse conversion of getaddrinfo(3), and implements such functionality by calling gethostbyaddr(3N) and getservbyport(3N), in a more sophisticated manner. This function looks up an IP address and port number provided by the caller in the DNS and system-specific database, and returns text strings for both in buffers provided by the caller. The function indicates successful completion by a zero return value; a non-zero return value indicates failure. The first argument, sa, points to either a sockaddr_in structure (for IPv4) or a sockaddr_in6 structure (for IPv6) that holds the IP address and port number. The salen argument gives the length of the sockaddr_in or sockaddr_in6 structure. If the socket address structure contains IPv6 unspecified address ("::"), a lookup is not performed, and the [EAI_NONAME] error is returned. If the argument node is non-NULL and the argument nodelen is nonzero, then the argument node points to a buffer able to contain up to nodelen characters that will receive the node name as a null-terminated string. If the argument node is NULL or the argument nodelen is zero, the node name will not be returned. If the node's name cannot be located, the numeric form of the node's address is returned instead of its name. If the argument serv is non-NULL and the argument servlen is nonzero, then the argument serv points to a buffer able to contain up to servlen characters that will receive the service name as a null-terminated string. If the argument serv is NULL or the argument servlen is zero, the service name will not be returned. If the service name cannot be located, the numeric form of the service address (for example, its port number) is returned instead of its name. Unfortunately most systems do not provide constants that specify the maximum size of either a fully-qualified domain name or a service name. Therefore to aid the application in allocating buffers for these two returned strings the following constants are defined in <netdb.h>: #define NI_MAXHOST 1025 #define NI_NAXSERV 32 The arguments node and serv cannot both be NULL. The flags argument is a flag that changes the default actions of this function. By default the fully-qualified domain name (FQDN) for the node is returned, but - If the flag bit NI_NOFQDN is set, only the nodename portion of the FQDN is returned for local hosts. - If the flag bit NI_NUMERICHOST is set, the numeric form of the node's address is returned instead of its name, under all circumstances. - If the flag bit NI_NAMEREQD is set, an error is returned if the node's name cannot be located. - If the flag bit NI_NUMERICSERV is set, the numeric form of the service address is returned (for example, its port number) instead of its name, under all circumstances. - If the flag bit NI_DGRAM is set, this indicates that the service is a datagram service (SOCK_DGRAM). The default behavior is to assume that the service is a stream service (SOCK_STREAM). These NI_xxx flags are defined in <netdb.h>. Function getnameinfo() is thread safe. EXAMPLE The following code tries to get nodename, and service name, for a given socket address. #include <stdio.h> #include <sys/socket.h> #include <netdb.h> main(){ struct addrinfo hints, *res, *res0; int error; int s; const char *cause = NULL; char hbuf[NI_MAXHOST], sbuf[NI_MAXSERV]; memset(&hints, 0, sizeof(hints)); hints.ai_family = AF_UNSPEC; hints.ai_socktype = SOCK_STREAM; error = getaddrinfo("www.company.example", "ftp", &hints, &res0); if(error){ fprintf(stderr, "%s", gai_strerror(error)); exit(1); } s = -1; for (res = res0; res; res = res->ai_next) { s = socket(res->ai_family, res->ai_socktype, res->ai_protocol); if (s < 0) { cause = "Error: socket"; continue; } if(connect(s, res->ai_addr, res->ai_addrlen) < 0 ) { cause = "Error: connect"; close(s); s = -1; continue; } cause = "Success"; if(res->ai_family == AF_INET6){ inet_ntop(AF_INET6, &(((struct sockaddr_in6 *)res->ai_addr)->sin6_addr), hbuf, sizeof(hbuf)); } else if(res->ai_family == AF_INET){ inet_ntop(AF_INET, &(((struct sockaddr_in *)res->ai_addr)->sin_addr), hbuf, sizeof(hbuf)); } printf("Getaddrinfo: Address = %s ", hbuf); bzero(hbuf, sizeof(hbuf)); if (getnameinfo(res->ai_addr, res->ai_addrlen, hbuf, sizeof(hbuf), sbuf, sizeof(sbuf), NI_NAMEREQD)) { fprintf(stderr, "could not resolve hostname"); exit(1); } printf("Getnameinfo: host = %s, serv = %s ", hbuf, sbuf); close(s); break; /*okay we got one*/ } fprintf(stderr, cause); freeaddrinfo(res0); } FILES /etc/hosts /etc/ipnodes /etc/resolv.conf DIAGNOSTICS The function indicates successful completion by a zero return value; a non-zero return value indicates failure. Error codes are as below: EAI_AGAIN The name could not be resolved at this time. Future attempts may succeed. EAI_BADFLAGS The flags had an invalid value. EAI_FAIL A non-recoverable error occurred. EAI_FAMILY The address family was not recognized or the address length is invalid for the specified family. EAI_MEMORY There was a memory allocation failure. EAI_NONAME The name does not resolve for the supplied parameters. NI_NAMEREQD is set and the node's name cannot be located, or both nodename and servname were null. EAI_OVERFLOW Argument buffer overflowed. EAI_SYSTEM A system error occurred. The error code can be found in errno. SEE ALSO getaddrinfo(3), getipnodebyaddr(3), gethostbyaddr(3), getservbyport(3), getservbyname(3), inet_ntop(3), hosts(5), services(5). STANDARDS The getnameinfo() function is defined in IEEE POSIX 1003.1g draft specification, draft-ietf-ipngwg-rfc2553bis-03.txt, and documented in "Basic Socket Interface Extensions for IPv6" (RFC2553). Page 4