Unix Network Programming Episode 78

'getaddrinfo' Function

The gethostbyname and gethostbyaddr functions only support IPv4. The API for resolving IPv6 addresses went through several iterations, as will be described in Section 11.20(See 8.9.20); the final result is the getaddrinfo function.

The POSIX definition of this function comes from an earlier proposal by Keith Sklower for a function named getconninfo. This function was the result of discussions with Eric Allman, William Durst, Michael Karels, and Steven Wise, and from an early implementation written by Eric Allman. The observation that specifying a hostname and a service name would suffice for connecting to a service independent of protocol details was made by Marshall Rose in a proposal to X/Open.

复制代码
#include <netdb.h>
int getaddrinfo (const char *hostname, const char *service, const struct addrinfo *hints, struct addrinfo **result) ;

This function returns through the result pointer a pointer to a linked list of addrinfo structures, which is defined by including <netdb.h>.

复制代码
struct addrinfo {
	int ai_flags; /* AI_PASSIVE, AI_CANONNAME */
	int ai_family; /* AF_xxx */
	int ai_socktype; /* SOCK_xxx */
	int ai_protocol; /* 0 or IPPROTO_xxx for IPv4 and IPv6 */
	socklen_t ai_addrlen; /* length of ai_addr */
	char *ai_canonname; /* ptr to canonical name for host */
	struct sockaddr *ai_addr; /* ptr to socket address structure */
	struct addrinfo *ai_next; /* ptr to next structure in linked list */
};

The members of the hints structure that can be set by the caller are:

  • ai_flags (zero or more AI_XXX values OR'ed together)
  • ai_family (an AF_xxx value)
  • ai_socktype (a SOCK_xxx value)
  • ai_protocol

If the function returns success (0), the variable pointed to by the result argument is filled in with a pointer to a linked list of addrinfo structures, linked through the ai_next pointer. There are two ways that multiple structures can be returned:

1.If there are multiple addresses associated with the hostname, one structure is returned for each address that is usable with the requested address family (the ai_family hint, if specified).

2.If the service is provided for multiple socket types, one structure can be returned for each socket type, depending on the ai_socktype hint. (Note that most getaddrinfo implementations consider a port number string to be implemented only by the socket type requested in ai_socktype; if ai_socktype is not specified, an error is returned instead.)

For example, if no hints are provided and if the domain service is looked up for a host with two IP addresses, four addrinfo structures are returned:

  • One for the first IP address and a socket type of SOCK_STREAM
  • One for the first IP address and a socket type of SOCK_DGRAM
  • One for the second IP address and a socket type of SOCK_STREAM
  • One for the second IP address and a socket type of SOCK_DGRAM

If we were to enumerate all 64 possible inputs to getaddrinfo (there are six input variables), many would be invalid and some would make little sense. Instead, we will look at the common cases.

  • Specify the hostname and service. This is normal for a TCP or UDP client. On return, a TCP client loops through all returned IP addresses, calling socket and connect for each one, until the connection succeeds or until all addresses have been tried. We will show an example of this with our tcp_connect function in Figure 11.10(See 8.9.12).
  • For a UDP client, the socket address structure filled in by getaddrinfo would be used in a call to sendto or connect. If the client can tell that the first address doesn't appear to work (either by receiving an error on a connected UDP socket or by experiencing a timeout on an unconnected socket), additional addresses can be tried.
  • If the client knows it handles only one type of socket (e.g., Telnet and FTP clients handle only TCP; TFTP clients handle only UDP), then the ai_socktype member of the hints structure should be specified as either SOCK_STREAM or SOCK_DGRAM.
  • A typical server specifies the service but not the hostname, and specifies the AI_PASSIVE flag in the hints structure. The socket address structures returned should contain an IP address of INADDR_ANY (for IPv4) or IN6ADDR_ANY_INIT (for IPv6). A TCP server then calls socket, bind, and listen. If the server wants to malloc another socket address structure to obtain the client's address from accept, the returned ai_addrlen value specifies this size.
  • A UDP server would call socket, bind, and then recvfrom. If the server wants to malloc another socket address structure to obtain the client's address from recvfrom, the returned ai_addrlen value specifies this size.
  • As with the typical client code, if the server knows it only handles one type of socket, the ai_socktype member of the hints structure should be set to either SOCK_STREAM or SOCK_DGRAM. This avoids having multiple structures returned, possibly with the wrong ai_socktype value.
  • The TCP servers that we have shown so far create one listening socket, and the UDP servers create one datagram socket. That is what we assume in the previous item. An alternate server design is for the server to handle multiple sockets using select or poll. In this scenario, the server would go through the entire list of structures returned by getaddrinfo, create one socket per structure, and use select or poll.
相关推荐
GOWIN革文品牌咨询1 分钟前
机器人企业品牌语言体系怎么搭建:一句话定位、产品逻辑与解决方案表达
人工智能·机器人
techdashen2 分钟前
Unweight:Cloudflare 如何在不损失精度的情况下把大模型压缩 22%
网络·人工智能
yyuuuzz2 分钟前
独立站部署的几个常见技术问题
运维·服务器·网络·云计算·aws
前端不太难3 分钟前
AI 能力如何变成鸿蒙 App 的基础设施
人工智能·状态模式·harmonyos
龙山云仓7 分钟前
无忧智脑-让企业拥抱智能,让管理回归简单
人工智能·深度学习·机器学习
a珍爱上了a强10 分钟前
配置uboot启动参数,linux启动过程打印每个模块初始化的耗时时间
linux·运维·服务器
2501_9333295510 分钟前
Infoseek数字公关AI中台技术解析:基于DeepSeek+NLP的全网舆情监测与智能处置系统
人工智能·架构·数据库开发
QFIUNE11 分钟前
【文献阅读】化学空间边缘的分子深度学习
论文阅读·人工智能·笔记·深度学习
新新学长搞科研11 分钟前
【最新】2026年能源方向学术会议征稿/交流资讯
人工智能·功能测试·计算机视觉·自动化·能源·新能源·材料工程
Coovally AI模型快速验证14 分钟前
多校联合提出LLM-as-Judge:大模型评判无人机电力线分割,无真值场景下守护安全
人工智能·计算机视觉·电力巡检