1 // 2 // detail/resolver_service.hpp 3 // ~~~~~~~~~~~~~~~~~~~~~~~~~~~ 4 // 5 // Copyright (c) 2003-2015 Christopher M. Kohlhoff (chris at kohlhoff dot com) 6 // 7 // Distributed under the Boost Software License, Version 1.0. (See accompanying 8 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt) 9 // 10 11 #ifndef ASIO_DETAIL_RESOLVER_SERVICE_HPP 12 #define ASIO_DETAIL_RESOLVER_SERVICE_HPP 13 14 15 #include "asio/detail/config.hpp" 16 17 18 #include "asio/ip/basic_resolver_iterator.hpp" 19 #include "asio/ip/basic_resolver_query.hpp" 20 #include "asio/detail/addressof.hpp" 21 #include "asio/detail/resolve_endpoint_op.hpp" 22 #include "asio/detail/resolve_op.hpp" 23 #include "asio/detail/resolver_service_base.hpp" 24 25 #include "asio/detail/push_options.hpp" 26 27 namespace asio { 28 namespace detail { 29 30 template <typename Protocol> 31 class resolver_service : public resolver_service_base 32 { 33 public: 34 // The implementation type of the resolver. A cancellation token is used to 35 // indicate to the background thread that the operation has been cancelled. 36 typedef socket_ops::shared_cancel_token_type implementation_type; 37 38 // The endpoint type. 39 typedef typename Protocol::endpoint endpoint_type; 40 41 // The query type. 42 typedef asio::ip::basic_resolver_query<Protocol> query_type; 43 44 // The iterator type. 45 typedef asio::ip::basic_resolver_iterator<Protocol> iterator_type; 46 47 // Constructor. 48 resolver_service(asio::io_service& io_service) 49 : resolver_service_base(io_service) 50 { 51 } 52 53 // Resolve a query to a list of entries. 54 iterator_type resolve(implementation_type&, const query_type& query, 55 asio::error_code& ec) 56 { 57 asio::detail::addrinfo_type* address_info = 0; 58 59 socket_ops::getaddrinfo(query.host_name().c_str(), 60 query.service_name().c_str(), query.hints(), &address_info, ec); 61 auto_addrinfo auto_address_info(address_info); 62 63 return ec ? iterator_type() : iterator_type::create( 64 address_info, query.host_name(), query.service_name()); 65 } 66 67 // Asynchronously resolve a query to a list of entries. 68 template <typename Handler> 69 void async_resolve(implementation_type& impl, 70 const query_type& query, Handler& handler) 71 { 72 // Allocate and construct an operation to wrap the handler. 73 typedef resolve_op<Protocol, Handler> op; 74 typename op::ptr p = { asio::detail::addressof(handler), 75 asio_handler_alloc_helpers::allocate( 76 sizeof(op), handler), 0 }; 77 p.p = new (p.v) op(impl, query, io_service_impl_, handler); 78 79 ASIO_HANDLER_CREATION((p.p, "resolver", &impl, "async_resolve")); 80 81 start_resolve_op(p.p); 82 p.v = p.p = 0; 83 } 84 85 // Resolve an endpoint to a list of entries. 86 iterator_type resolve(implementation_type&, 87 const endpoint_type& endpoint, asio::error_code& ec) 88 { 89 char host_name[NI_MAXHOST]; 90 char service_name[NI_MAXSERV]; 91 socket_ops::sync_getnameinfo(endpoint.data(), endpoint.size(), 92 host_name, NI_MAXHOST, service_name, NI_MAXSERV, 93 endpoint.protocol().type(), ec); 94 95 return ec ? iterator_type() : iterator_type::create( 96 endpoint, host_name, service_name); 97 } 98 99 // Asynchronously resolve an endpoint to a list of entries. 100 template <typename Handler> 101 void async_resolve(implementation_type& impl, 102 const endpoint_type& endpoint, Handler& handler) 103 { 104 // Allocate and construct an operation to wrap the handler. 105 typedef resolve_endpoint_op<Protocol, Handler> op; 106 typename op::ptr p = { asio::detail::addressof(handler), 107 asio_handler_alloc_helpers::allocate( 108 sizeof(op), handler), 0 }; 109 p.p = new (p.v) op(impl, endpoint, io_service_impl_, handler); 110 111 ASIO_HANDLER_CREATION((p.p, "resolver", &impl, "async_resolve")); 112 113 start_resolve_op(p.p); 114 p.v = p.p = 0; 115 } 116 }; 117 118 } // namespace detail 119 } // namespace asio 120 121 #include "asio/detail/pop_options.hpp" 122 123 124 #endif // ASIO_DETAIL_RESOLVER_SERVICE_HPP 125