我已经使用以下内容相当一段时间来创建netlink套接字:
NetLinkLocalNetworkInfo::NetLinkSocket::NetLinkSocket() :
fd(0)
{
fd = socket(PF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
if(fd < 0)
{
throw std::runtime_error("Failed to create NetLink socket");
}
struct sockaddr_nl addr;
memset(&addr, 0, sizeof(addr));
addr.nl_family = AF_NETLINK;
int err = bind(fd, (struct sockaddr*)&addr, sizeof(addr));
if(err < 0)
{
close(fd);
throw std::runtime_error("Failed to bind NetLink socket");
}
}
这是我们在网络逻辑中使用的一部分,以使用ICE执行自动NAT遍历。当目标API为30时,对bind
的调用现在返回-1,并且errno
为“Permission Denied”。
针对API 30的应用程序行为变化意味着bind()
现在是受限制的调用。(有一个文档在Google开发者页面上,但是我现在找不到它了。它曾经存在于此处,但自从我几个月前第一次遇到此问题以来,该页面已经更改。)据说这应该影响所有目标为API 30的应用程序,但我发现只有在运行Android 11的设备(物理或模拟器)上运行的目标为API 30的应用程序受到影响。我初次遇到此问题时的笔记还提到了那篇文章建议使用ConnectivityManager,但这将要求设计一些方法将信息传递到本机代码中或通过JNI使本机代码调用Android平台代码。如果必须这样做,我可以接受其中的任何一种,但我想知道是否有其他替代方法。
我还看到了这个类似问题,但其中一个答案中有一个链接表明,至少在API 30之前是可以实现的。
既然我们不允许调用bind()
,那么还有哪些选项可用?
fd
绑定到 sockaddr_nladdr
。 - Jordan