1 #pragma once 2 #include "dbus_singleton.hpp" 3 #include "logging.hpp" 4 5 #include <boost/asio/ip/address.hpp> 6 #include <boost/asio/ip/basic_endpoint.hpp> 7 #include <boost/asio/ip/tcp.hpp> 8 #include <sdbusplus/message.hpp> 9 10 #include <charconv> 11 #include <iostream> 12 #include <memory> 13 14 namespace crow 15 { 16 17 namespace async_resolve 18 { 19 20 class Resolver 21 { 22 public: 23 Resolver() = default; 24 25 ~Resolver() = default; 26 27 Resolver(const Resolver&) = delete; 28 Resolver(Resolver&&) = delete; 29 Resolver& operator=(const Resolver&) = delete; 30 Resolver& operator=(Resolver&&) = delete; 31 32 template <typename ResolveHandler> 33 void asyncResolve(const std::string& host, uint16_t port, 34 ResolveHandler&& handler) 35 { 36 BMCWEB_LOG_DEBUG << "Trying to resolve: " << host << ":" << port; 37 uint64_t flag = 0; 38 crow::connections::systemBus->async_method_call( 39 [host, port, handler{std::forward<ResolveHandler>(handler)}]( 40 const boost::system::error_code ec, 41 const std::vector< 42 std::tuple<int32_t, int32_t, std::vector<uint8_t>>>& resp, 43 const std::string& hostName, const uint64_t flagNum) { 44 std::vector<boost::asio::ip::tcp::endpoint> endpointList; 45 if (ec) 46 { 47 BMCWEB_LOG_ERROR << "Resolve failed: " << ec.message(); 48 handler(ec, endpointList); 49 return; 50 } 51 BMCWEB_LOG_DEBUG << "ResolveHostname returned: " << hostName << ":" 52 << flagNum; 53 // Extract the IP address from the response 54 for (auto resolveList : resp) 55 { 56 std::vector<uint8_t> ipAddress = std::get<2>(resolveList); 57 boost::asio::ip::tcp::endpoint endpoint; 58 if (ipAddress.size() == 4) // ipv4 address 59 { 60 BMCWEB_LOG_DEBUG << "ipv4 address"; 61 boost::asio::ip::address_v4 ipv4Addr( 62 {ipAddress[0], ipAddress[1], ipAddress[2], 63 ipAddress[3]}); 64 endpoint.address(ipv4Addr); 65 } 66 else if (ipAddress.size() == 16) // ipv6 address 67 { 68 BMCWEB_LOG_DEBUG << "ipv6 address"; 69 boost::asio::ip::address_v6 ipv6Addr( 70 {ipAddress[0], ipAddress[1], ipAddress[2], ipAddress[3], 71 ipAddress[4], ipAddress[5], ipAddress[6], ipAddress[7], 72 ipAddress[8], ipAddress[9], ipAddress[10], 73 ipAddress[11], ipAddress[12], ipAddress[13], 74 ipAddress[14], ipAddress[15]}); 75 endpoint.address(ipv6Addr); 76 } 77 else 78 { 79 BMCWEB_LOG_ERROR 80 << "Resolve failed to fetch the IP address"; 81 handler(ec, endpointList); 82 return; 83 } 84 endpoint.port(port); 85 BMCWEB_LOG_DEBUG << "resolved endpoint is : " << endpoint; 86 endpointList.push_back(endpoint); 87 } 88 // All the resolved data is filled in the endpointList 89 handler(ec, endpointList); 90 }, 91 "org.freedesktop.resolve1", "/org/freedesktop/resolve1", 92 "org.freedesktop.resolve1.Manager", "ResolveHostname", 0, host, 93 AF_UNSPEC, flag); 94 } 95 }; 96 97 } // namespace async_resolve 98 } // namespace crow 99