socks5_transfer.hpp 4.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. /*
  2. * Copyright (c) 2017-2023 zhllxt
  3. *
  4. * author : zhllxt
  5. * email : 37792738@qq.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. #ifndef __ASIO2_SOCKS5_TRANSFER_HPP__
  11. #define __ASIO2_SOCKS5_TRANSFER_HPP__
  12. #if defined(_MSC_VER) && (_MSC_VER >= 1200)
  13. #pragma once
  14. #endif // defined(_MSC_VER) && (_MSC_VER >= 1200)
  15. #include <asio2/base/detail/push_options.hpp>
  16. #include <asio2/tcp/tcp_client.hpp>
  17. #include <asio2/udp/udp_cast.hpp>
  18. namespace asio2::detail
  19. {
  20. ASIO2_CLASS_FORWARD_DECLARE_BASE;
  21. ASIO2_CLASS_FORWARD_DECLARE_TCP_BASE;
  22. ASIO2_CLASS_FORWARD_DECLARE_UDP_BASE;
  23. ASIO2_CLASS_FORWARD_DECLARE_TCP_CLIENT;
  24. ASIO2_CLASS_FORWARD_DECLARE_UDP_CLIENT;
  25. template<class, class> class socks5_session_impl_t;
  26. template<class derived_t, class executor_t>
  27. class socks5_transfer_impl_t
  28. : public executor_t
  29. {
  30. ASIO2_CLASS_FRIEND_DECLARE_BASE;
  31. ASIO2_CLASS_FRIEND_DECLARE_TCP_BASE;
  32. ASIO2_CLASS_FRIEND_DECLARE_UDP_BASE;
  33. ASIO2_CLASS_FRIEND_DECLARE_TCP_CLIENT;
  34. ASIO2_CLASS_FRIEND_DECLARE_UDP_CLIENT;
  35. template<class, class> friend class socks5_session_impl_t;
  36. public:
  37. using super = executor_t;
  38. using self = socks5_transfer_impl_t<derived_t, executor_t>;
  39. using executor_type = executor_t;
  40. using args_type = typename executor_t::args_type;
  41. using super::async_start;
  42. public:
  43. /**
  44. * @brief constructor
  45. */
  46. template<class... Args>
  47. explicit socks5_transfer_impl_t(Args&&... args)
  48. : super(std::forward<Args>(args)...)
  49. {
  50. this->connect_finish_timer_ = std::make_shared<asio::steady_timer>(this->io_->context());
  51. }
  52. /**
  53. * @brief destructor
  54. */
  55. ~socks5_transfer_impl_t()
  56. {
  57. this->stop();
  58. }
  59. /**
  60. * @brief destroy the content of all member variables, this is used for solve the memory leaks.
  61. * After this function is called, this class object cannot be used again.
  62. */
  63. inline void destroy()
  64. {
  65. derived_t& derive = this->derived();
  66. derive.connect_finish_timer_.reset();
  67. super::destroy();
  68. }
  69. /**
  70. * @brief async start the client, asynchronous connect to server.
  71. * @param host - A string identifying a location. May be a descriptive name or
  72. * a numeric address string.
  73. * @param port - A string identifying the requested service. This may be a
  74. * descriptive name or a numeric string corresponding to a port number.
  75. */
  76. template<typename String, typename StrOrInt, typename CompletionToken, typename... Args>
  77. auto async_start(String&& host, StrOrInt&& port, CompletionToken&& token, Args&&... args)
  78. {
  79. derived_t& derive = this->derived();
  80. bool f = executor_t::template async_start(
  81. std::forward<String>(host), std::forward<StrOrInt>(port), std::forward<Args>(args)...);
  82. derive.connect_finish_timer_->expires_after(f ?
  83. std::chrono::steady_clock::duration::max() :
  84. std::chrono::steady_clock::duration::zero());
  85. return asio::async_compose<CompletionToken, void(asio::error_code)>(
  86. detail::wait_timer_op{*(derive.connect_finish_timer_)},
  87. token, derive.socket());
  88. }
  89. protected:
  90. template<typename C, typename DeferEvent>
  91. inline void _handle_connect(
  92. const error_code& ec,
  93. std::shared_ptr<derived_t> this_ptr, std::shared_ptr<ecs_t<C>> ecs, DeferEvent chain)
  94. {
  95. detail::cancel_timer(*(this->derived().connect_finish_timer_));
  96. super::_handle_connect(ec, std::move(this_ptr), std::move(ecs), std::move(chain));
  97. }
  98. protected:
  99. std::shared_ptr<asio::steady_timer> connect_finish_timer_;
  100. };
  101. }
  102. namespace asio2
  103. {
  104. template<class derived_t, class executor_t>
  105. using socks5_transfer_impl_t = detail::socks5_transfer_impl_t<derived_t, executor_t>;
  106. /**
  107. * @brief socks5 tcp transfer
  108. */
  109. template<class derived_t>
  110. class socks5_tcp_transfer_t : public detail::socks5_transfer_impl_t<derived_t, tcp_client_t<derived_t>>
  111. {
  112. public:
  113. using detail::socks5_transfer_impl_t<derived_t, tcp_client_t<derived_t>>::socks5_transfer_impl_t;
  114. };
  115. /**
  116. * @brief socks5 tcp transfer
  117. */
  118. class socks5_tcp_transfer : public socks5_tcp_transfer_t<socks5_tcp_transfer>
  119. {
  120. public:
  121. using socks5_tcp_transfer_t<socks5_tcp_transfer>::socks5_tcp_transfer_t;
  122. };
  123. /**
  124. * @brief socks5 udp transfer
  125. */
  126. template<class derived_t>
  127. class socks5_udp_transfer_t : public detail::socks5_transfer_impl_t<derived_t, udp_cast_t<derived_t>>
  128. {
  129. public:
  130. using detail::socks5_transfer_impl_t<derived_t, udp_cast_t<derived_t>>::socks5_transfer_impl_t;
  131. };
  132. /**
  133. * @brief socks5 udp transfer
  134. */
  135. class socks5_udp_transfer : public socks5_udp_transfer_t<socks5_udp_transfer>
  136. {
  137. public:
  138. using socks5_udp_transfer_t<socks5_udp_transfer>::socks5_udp_transfer_t;
  139. };
  140. }
  141. #include <asio2/base/detail/pop_options.hpp>
  142. #endif // !__ASIO2_SOCKS5_TRANSFER_HPP__