我试图从任何字符串地址获取ipv4和ipv6地址,无论是通过ipv4,ipv6还是DNS地址。
我可以创建自己的功能,但我尝试使用expert advice并使用内置功能。</ p>
答案 0 :(得分:3)
从DNS名称获取地址涉及...查询命名服务器(DNS!)。如果要枚举结果,请在asio中使用解析器:
简单示例:
#include <boost/asio.hpp>
#include <boost/function_output_iterator.hpp>
#include <set>
using boost::asio::ip::address;
std::set<address> unique_endpoints(std::string const& ip)
{
using resolver = boost::asio::ip::tcp::resolver;
boost::asio::io_service ios; // TODO use existing service / resolver
resolver r(ios);
std::set<address> unique;
for (auto it = r.resolve({ip, ""}); it != resolver::iterator {}; ++it)
{
//std::cout << "Resolved: " << it->host_name() << " -> " << it->endpoint() << " " << it->service_name() << "\n";
address a = it->endpoint().address();
if (a.is_v4())
unique.insert(boost::asio::ip::address_v6::v4_mapped(a.to_v4()));
else
unique.insert(a);
}
return unique;
}
template <typename S>
bool endpoints_overlap(S const& a, S const& b)
{
bool matching_found = false;
std::set_intersection(
a.begin(), a.end(), b.begin(), b.end(),
boost::make_function_output_iterator([&](address const&) { matching_found = true; }));
return matching_found;
}
int main()
{
auto h = unique_endpoints("bbs2.fritz.box");
auto a = unique_endpoints("192.168.2.111");
auto b = unique_endpoints("::ffff:192.168.2.111");
auto c = unique_endpoints("::ffff:c0a8:026f");
assert(endpoints_overlap(a, b));
assert(endpoints_overlap(a, c));
assert(endpoints_overlap(b, c));
assert(endpoints_overlap(h, a));
assert(endpoints_overlap(h, b));
assert(endpoints_overlap(h, c));
}
请注意,当其中一个DNS响应匹配时,此测试将确定端点重叠。在群集设置中,可能并非总是如此(?没有专家),您可能 想要在使用此算法之前检测广播地址(未经测试)。
另请注意,我认为没有办法检测实际 主机 的等效性(意味着,如果主机有多个物理/逻辑) NIC,它们将在传输级别显示为单独的服务器。)
最后,在实际应用程序中,您需要异步进行解析(使用async_resolve
)
答案 1 :(得分:1)
boost :: ip :: address提供了这种类型的功能。
您可以使用from_string函数从任一格式的字符串构造地址(ipv4为十进制,ipv6为十六进制):
boost::ip::address address( boost::ip::address::from_string( myIpAddress ) );
然后你应该能够返回v4或v6 ip地址:
boost::asio::ip::address_v4 ipv4 = address.to_v4();
boost::asio::ip::address_v6 ipv6 = address.to_v6();