我正在撰写UPnP AV / DLNA DMS,需要发送和接收SSDP条消息。为了响应一些M-SEARCH
数据包,我需要使用资源的URL(在本例中为HTTP服务器)发送回复,我已选择将其绑定到INADDR_ANY
(0.0.0.0
)。当然,这个地址对M-SEARCH
数据包的发送者毫无意义:收到M-SEARCH
的接口的地址是最合适的。
如何确定在回复包中发送的适当地址?
我考虑过的一些想法是:
M-SEARCH
数据包时,回复地址可以在回复中使用套接字的本地地址。但是,这需要了解并迭代所有接口,并在接口可用性发生变化时添加和删除接收器。INADDR_ANY
上放置一个接收器,并迭代接口网络掩码以确定可能的来源。但是,多个接口可能共享同一个子网。答案 0 :(得分:2)
getsockname(2)
后跟getnameinfo(3)
报告您的TCP / IP堆栈已分配给套接字的IP地址。 (显然,如果服务器和客户端位于NAT系统的两侧,这将与客户端可以使用的内容不匹配;在这种情况下,可能有聪明的UPnP技巧来发现客户端可用于联系服务器的IP地址。)
我认为您的服务器看起来像这样:
lfd = socket();
ret = bind(lfd,...);
connection = listen(lfd, 10);
/* add connection to your select queue or poll queue */
您可以附加与此类似的代码:
struct sockaddr_storage me;
socklen_t *len = sizeof(me);
char name[40];
ret = getsockname(connection, &me, &len);
ret = getnameinfo(&me, &len, name, sizeof(name), NULL, 0, NI_NUMERICHOST);
getnameinfo(3)
检查struct sockaddr_storage
me
您的IP地址。因为这些是通用接口,所以它适用于IPv4或IPv6地址。