asio 0.3.8rc3 | Home | Reference | Tutorial | Examples | Design

Examples |

# services/stream_socket_service.hpp

Go to the documentation of this file.

    00001 //
    00002 // stream_socket_service.hpp
    00003 // ~~~~~~~~~~~~~~~~~~~~~~~~~
    00004 //
    00005 // Copyright (c) 2003-2007 Christopher M. Kohlhoff (chris at kohlhoff dot com)
    00006 //
    00007 // Distributed under the Boost Software License, Version 1.0. (See accompanying
    00008 // file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
    00009 //
    00010
    00011 #ifndef SERVICES_STREAM_SOCKET_SERVICE_HPP
    00012 #define SERVICES_STREAM_SOCKET_SERVICE_HPP
    00013
    00014 #include <asio.hpp>
    00015 #include <boost/noncopyable.hpp>
    00016 #include <boost/lexical_cast.hpp>
    00017 #include "logger.hpp"
    00018
    00019 namespace services {
    00020
    00022 template <typename Protocol>
    00023 class stream_socket_service
    00024   : public asio::io_service::service
    00025 {
    00026 private:
    00028   typedef asio::stream_socket_service<Protocol> service_impl_type;
    00029
    00030 public:
    00032   static asio::io_service::id id;
    00033
    00035   typedef Protocol protocol_type;
    00036
    00038   typedef typename Protocol::endpoint endpoint_type;
    00039
    00041   typedef typename service_impl_type::implementation_type implementation_type;
    00042
    00044   typedef typename service_impl_type::native_type native_type;
    00045
    00047   explicit stream_socket_service(asio::io_service& io_service)
    00048     : asio::io_service::service(io_service),
    00049       service_impl_(asio::use_service<service_impl_type>(io_service)),
    00050       logger_(io_service, "stream_socket")
    00051   {
    00052   }
    00053
    00055   void shutdown_service()
    00056   {
    00057   }
    00058
    00060   void construct(implementation_type& impl)
    00061   {
    00062     service_impl_.construct(impl);
    00063   }
    00064
    00066   void destroy(implementation_type& impl)
    00067   {
    00068     service_impl_.destroy(impl);
    00069   }
    00070
    00072   asio::error_code open(implementation_type& impl,
    00073       const protocol_type& protocol, asio::error_code& ec)
    00074   {
    00075     logger_.log("Opening new socket");
    00076     return service_impl_.open(impl, protocol, ec);
    00077   }
    00078
    00080   asio::error_code assign(implementation_type& impl,
    00081       const protocol_type& protocol, const native_type& native_socket,
    00082       asio::error_code& ec)
    00083   {
    00084     logger_.log("Assigning from a native socket");
    00085     return service_impl_.assign(impl, protocol, native_socket, ec);
    00086   }
    00087
    00089   bool is_open(const implementation_type& impl) const
    00090   {
    00091     logger_.log("Checking if socket is open");
    00092     return service_impl_.is_open(impl);
    00093   }
    00094
    00096   asio::error_code close(implementation_type& impl,
    00097       asio::error_code& ec)
    00098   {
    00099     logger_.log("Closing socket");
    00100     return service_impl_.close(impl, ec);
    00101   }
    00102
    00104   bool at_mark(const implementation_type& impl,
    00105       asio::error_code& ec) const
    00106   {
    00107     logger_.log("Checking if socket is at out-of-band data mark");
    00108     return service_impl_.at_mark(impl, ec);
    00109   }
    00110
    00112   std::size_t available(const implementation_type& impl,
    00113       asio::error_code& ec) const
    00114   {
    00115     logger_.log("Determining number of bytes available for reading");
    00116     return service_impl_.available(impl, ec);
    00117   }
    00118
    00120   asio::error_code bind(implementation_type& impl,
    00121       const endpoint_type& endpoint, asio::error_code& ec)
    00122   {
    00123     logger_.log("Binding socket");
    00124     return service_impl_.bind(impl, endpoint, ec);
    00125   }
    00126
    00128   asio::error_code connect(implementation_type& impl,
    00129       const endpoint_type& peer_endpoint, asio::error_code& ec)
    00130   {
    00131     logger_.log("Connecting socket to " +
    00132         boost::lexical_cast<std::string>(peer_endpoint));
    00133     return service_impl_.connect(impl, peer_endpoint, ec);
    00134   }
    00135
    00137   template <typename Handler>
    00138   class connect_handler
    00139   {
    00140   public:
    00141     connect_handler(Handler h, logger& l)
    00142       : handler_(h),
    00143         logger_(l)
    00144     {
    00145     }
    00146
    00147     void operator()(const asio::error_code& e)
    00148     {
    00149       if (e)
    00150       {
    00151         std::string msg = "Asynchronous connect failed: ";
    00152         msg += e.message();
    00153         logger_.log(msg);
    00154       }
    00155       else
    00156       {
    00157         logger_.log("Asynchronous connect succeeded");
    00158       }
    00159
    00160       handler_(e);
    00161     }
    00162
    00163   private:
    00164     Handler handler_;
    00165     logger& logger_;
    00166   };
    00167
    00169   template <typename Handler>
    00170   void async_connect(implementation_type& impl,
    00171       const endpoint_type& peer_endpoint, Handler handler)
    00172   {
    00173     logger_.log("Starting asynchronous connect to " +
    00174         boost::lexical_cast<std::string>(peer_endpoint));
    00175     service_impl_.async_connect(impl, peer_endpoint,
    00176         connect_handler<Handler>(handler, logger_));
    00177   }
    00178
    00180   template <typename Option>
    00181   asio::error_code set_option(implementation_type& impl,
    00182       const Option& option, asio::error_code& ec)
    00183   {
    00184     logger_.log("Setting socket option");
    00185     return service_impl_.set_option(impl, option, ec);
    00186   }
    00187
    00189   template <typename Option>
    00190   asio::error_code get_option(const implementation_type& impl,
    00191       Option& option, asio::error_code& ec) const
    00192   {
    00193     logger_.log("Getting socket option");
    00194     return service_impl_.get_option(impl, option, ec);
    00195   }
    00196
    00198   template <typename IO_Control_Command>
    00199   asio::error_code io_control(implementation_type& impl,
    00200       IO_Control_Command& command, asio::error_code& ec)
    00201   {
    00202     logger_.log("Performing IO control command on socket");
    00203     return service_impl_.io_control(impl, command, ec);
    00204   }
    00205
    00207   endpoint_type local_endpoint(const implementation_type& impl,
    00208       asio::error_code& ec) const
    00209   {
    00210     logger_.log("Getting socket's local endpoint");
    00211     return service_impl_.local_endpoint(impl, ec);
    00212   }
    00213
    00215   endpoint_type remote_endpoint(const implementation_type& impl,
    00216       asio::error_code& ec) const
    00217   {
    00218     logger_.log("Getting socket's remote endpoint");
    00219     return service_impl_.remote_endpoint(impl, ec);
    00220   }
    00221
    00223   asio::error_code shutdown(implementation_type& impl,
    00224       asio::socket_base::shutdown_type what,
    00225       asio::error_code& ec)
    00226   {
    00227     logger_.log("Shutting down socket");
    00228     return service_impl_.shutdown(impl, what, ec);
    00229   }
    00230
    00232   template <typename Const_Buffers>
    00233   std::size_t send(implementation_type& impl, const Const_Buffers& buffers,
    00234       asio::socket_base::message_flags flags,
    00235       asio::error_code& ec)
    00236   {
    00237     logger_.log("Sending data on socket");
    00238     return service_impl_.send(impl, buffers, flags, ec);
    00239   }
    00240
    00242   template <typename Handler>
    00243   class send_handler
    00244   {
    00245   public:
    00246     send_handler(Handler h, logger& l)
    00247       : handler_(h),
    00248         logger_(l)
    00249     {
    00250     }
    00251
    00252     void operator()(const asio::error_code& e,
    00253         std::size_t bytes_transferred)
    00254     {
    00255       if (e)
    00256       {
    00257         std::string msg = "Asynchronous send failed: ";
    00258         msg += e.message();
    00259         logger_.log(msg);
    00260       }
    00261       else
    00262       {
    00263         logger_.log("Asynchronous send succeeded");
    00264       }
    00265
    00266       handler_(e, bytes_transferred);
    00267     }
    00268
    00269   private:
    00270     Handler handler_;
    00271     logger& logger_;
    00272   };
    00273
    00275   template <typename Const_Buffers, typename Handler>
    00276   void async_send(implementation_type& impl, const Const_Buffers& buffers,
    00277       asio::socket_base::message_flags flags, Handler handler)
    00278   {
    00279     logger_.log("Starting asynchronous send");
    00280     service_impl_.async_send(impl, buffers, flags,
    00281         send_handler<Handler>(handler, logger_));
    00282   }
    00283
    00285   template <typename Mutable_Buffers>
    00286   std::size_t receive(implementation_type& impl,
    00287       const Mutable_Buffers& buffers,
    00288       asio::socket_base::message_flags flags,
    00289       asio::error_code& ec)
    00290   {
    00291     logger_.log("Receiving data on socket");
    00292     return service_impl_.receive(impl, buffers, flags, ec);
    00293   }
    00294
    00296   template <typename Handler>
    00297   class receive_handler
    00298   {
    00299   public:
    00300     receive_handler(Handler h, logger& l)
    00301       : handler_(h),
    00302         logger_(l)
    00303     {
    00304     }
    00305
    00306     void operator()(const asio::error_code& e,
    00307         std::size_t bytes_transferred)
    00308     {
    00309       if (e)
    00310       {
    00311         std::string msg = "Asynchronous receive failed: ";
    00312         msg += e.message();
    00313         logger_.log(msg);
    00314       }
    00315       else
    00316       {
    00317         logger_.log("Asynchronous receive succeeded");
    00318       }
    00319
    00320       handler_(e, bytes_transferred);
    00321     }
    00322
    00323   private:
    00324     Handler handler_;
    00325     logger& logger_;
    00326   };
    00327
    00329   template <typename Mutable_Buffers, typename Handler>
    00330   void async_receive(implementation_type& impl, const Mutable_Buffers& buffers,
    00331       asio::socket_base::message_flags flags, Handler handler)
    00332   {
    00333     logger_.log("Starting asynchronous receive");
    00334     service_impl_.async_receive(impl, buffers, flags,
    00335         receive_handler<Handler>(handler, logger_));
    00336   }
    00337
    00338 private:
    00340   service_impl_type& service_impl_;
    00341
    00343   mutable logger logger_;
    00344 };
    00345
    00346 template <typename Protocol>
    00347 asio::io_service::id stream_socket_service<Protocol>::id;
    00348
    00349 } // namespace services
    00350
    00351 #endif // SERVICES_STREAM_SOCKET_SERVICE_HPP

asio 0.3.8rc3 | Home | Reference | Tutorial | Examples | Design