fake_port_allocator.h 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252
  1. /*
  2. * Copyright 2010 The WebRTC Project Authors. All rights reserved.
  3. *
  4. * Use of this source code is governed by a BSD-style license
  5. * that can be found in the LICENSE file in the root of the source
  6. * tree. An additional intellectual property rights grant can be found
  7. * in the file PATENTS. All contributing project authors may
  8. * be found in the AUTHORS file in the root of the source tree.
  9. */
  10. #ifndef P2P_BASE_FAKE_PORT_ALLOCATOR_H_
  11. #define P2P_BASE_FAKE_PORT_ALLOCATOR_H_
  12. #include <memory>
  13. #include <string>
  14. #include <vector>
  15. #include "p2p/base/basic_packet_socket_factory.h"
  16. #include "p2p/base/port_allocator.h"
  17. #include "p2p/base/udp_port.h"
  18. #include "rtc_base/bind.h"
  19. #include "rtc_base/net_helpers.h"
  20. #include "rtc_base/thread.h"
  21. namespace rtc {
  22. class SocketFactory;
  23. }
  24. namespace cricket {
  25. class TestUDPPort : public UDPPort {
  26. public:
  27. static TestUDPPort* Create(rtc::Thread* thread,
  28. rtc::PacketSocketFactory* factory,
  29. rtc::Network* network,
  30. uint16_t min_port,
  31. uint16_t max_port,
  32. const std::string& username,
  33. const std::string& password,
  34. const std::string& origin,
  35. bool emit_localhost_for_anyaddress) {
  36. TestUDPPort* port =
  37. new TestUDPPort(thread, factory, network, min_port, max_port, username,
  38. password, origin, emit_localhost_for_anyaddress);
  39. if (!port->Init()) {
  40. delete port;
  41. port = nullptr;
  42. }
  43. return port;
  44. }
  45. protected:
  46. TestUDPPort(rtc::Thread* thread,
  47. rtc::PacketSocketFactory* factory,
  48. rtc::Network* network,
  49. uint16_t min_port,
  50. uint16_t max_port,
  51. const std::string& username,
  52. const std::string& password,
  53. const std::string& origin,
  54. bool emit_localhost_for_anyaddress)
  55. : UDPPort(thread,
  56. factory,
  57. network,
  58. min_port,
  59. max_port,
  60. username,
  61. password,
  62. origin,
  63. emit_localhost_for_anyaddress) {}
  64. };
  65. // A FakePortAllocatorSession can be used with either a real or fake socket
  66. // factory. It gathers a single loopback port, using IPv6 if available and
  67. // not disabled.
  68. class FakePortAllocatorSession : public PortAllocatorSession {
  69. public:
  70. FakePortAllocatorSession(PortAllocator* allocator,
  71. rtc::Thread* network_thread,
  72. rtc::PacketSocketFactory* factory,
  73. const std::string& content_name,
  74. int component,
  75. const std::string& ice_ufrag,
  76. const std::string& ice_pwd)
  77. : PortAllocatorSession(content_name,
  78. component,
  79. ice_ufrag,
  80. ice_pwd,
  81. allocator->flags()),
  82. network_thread_(network_thread),
  83. factory_(factory),
  84. ipv4_network_("network",
  85. "unittest",
  86. rtc::IPAddress(INADDR_LOOPBACK),
  87. 32),
  88. ipv6_network_("network",
  89. "unittest",
  90. rtc::IPAddress(in6addr_loopback),
  91. 64),
  92. port_(),
  93. port_config_count_(0),
  94. stun_servers_(allocator->stun_servers()),
  95. turn_servers_(allocator->turn_servers()) {
  96. ipv4_network_.AddIP(rtc::IPAddress(INADDR_LOOPBACK));
  97. ipv6_network_.AddIP(rtc::IPAddress(in6addr_loopback));
  98. }
  99. void SetCandidateFilter(uint32_t filter) override {
  100. candidate_filter_ = filter;
  101. }
  102. void StartGettingPorts() override {
  103. if (!port_) {
  104. rtc::Network& network =
  105. (rtc::HasIPv6Enabled() && (flags() & PORTALLOCATOR_ENABLE_IPV6))
  106. ? ipv6_network_
  107. : ipv4_network_;
  108. port_.reset(TestUDPPort::Create(network_thread_, factory_, &network, 0, 0,
  109. username(), password(), std::string(),
  110. false));
  111. RTC_DCHECK(port_);
  112. port_->SignalDestroyed.connect(
  113. this, &FakePortAllocatorSession::OnPortDestroyed);
  114. AddPort(port_.get());
  115. }
  116. ++port_config_count_;
  117. running_ = true;
  118. }
  119. void StopGettingPorts() override { running_ = false; }
  120. bool IsGettingPorts() override { return running_; }
  121. void ClearGettingPorts() override { is_cleared = true; }
  122. bool IsCleared() const override { return is_cleared; }
  123. void RegatherOnFailedNetworks() override {
  124. SignalIceRegathering(this, IceRegatheringReason::NETWORK_FAILURE);
  125. }
  126. std::vector<PortInterface*> ReadyPorts() const override {
  127. return ready_ports_;
  128. }
  129. std::vector<Candidate> ReadyCandidates() const override {
  130. return candidates_;
  131. }
  132. void PruneAllPorts() override { port_->Prune(); }
  133. bool CandidatesAllocationDone() const override { return allocation_done_; }
  134. int port_config_count() { return port_config_count_; }
  135. const ServerAddresses& stun_servers() const { return stun_servers_; }
  136. const std::vector<RelayServerConfig>& turn_servers() const {
  137. return turn_servers_;
  138. }
  139. uint32_t candidate_filter() const { return candidate_filter_; }
  140. int transport_info_update_count() const {
  141. return transport_info_update_count_;
  142. }
  143. protected:
  144. void UpdateIceParametersInternal() override {
  145. // Since this class is a fake and this method only is overridden for tests,
  146. // we don't need to actually update the transport info.
  147. ++transport_info_update_count_;
  148. }
  149. private:
  150. void AddPort(cricket::Port* port) {
  151. port->set_component(component());
  152. port->set_generation(generation());
  153. port->SignalPortComplete.connect(this,
  154. &FakePortAllocatorSession::OnPortComplete);
  155. port->PrepareAddress();
  156. ready_ports_.push_back(port);
  157. SignalPortReady(this, port);
  158. port->KeepAliveUntilPruned();
  159. }
  160. void OnPortComplete(cricket::Port* port) {
  161. const std::vector<Candidate>& candidates = port->Candidates();
  162. candidates_.insert(candidates_.end(), candidates.begin(), candidates.end());
  163. SignalCandidatesReady(this, candidates);
  164. allocation_done_ = true;
  165. SignalCandidatesAllocationDone(this);
  166. }
  167. void OnPortDestroyed(cricket::PortInterface* port) {
  168. // Don't want to double-delete port if it deletes itself.
  169. port_.release();
  170. }
  171. rtc::Thread* network_thread_;
  172. rtc::PacketSocketFactory* factory_;
  173. rtc::Network ipv4_network_;
  174. rtc::Network ipv6_network_;
  175. std::unique_ptr<cricket::Port> port_;
  176. int port_config_count_;
  177. std::vector<Candidate> candidates_;
  178. std::vector<PortInterface*> ready_ports_;
  179. bool allocation_done_ = false;
  180. bool is_cleared = false;
  181. ServerAddresses stun_servers_;
  182. std::vector<RelayServerConfig> turn_servers_;
  183. uint32_t candidate_filter_ = CF_ALL;
  184. int transport_info_update_count_ = 0;
  185. bool running_ = false;
  186. };
  187. class FakePortAllocator : public cricket::PortAllocator {
  188. public:
  189. FakePortAllocator(rtc::Thread* network_thread,
  190. rtc::PacketSocketFactory* factory)
  191. : network_thread_(network_thread), factory_(factory) {
  192. if (factory_ == NULL) {
  193. owned_factory_.reset(new rtc::BasicPacketSocketFactory(network_thread_));
  194. factory_ = owned_factory_.get();
  195. }
  196. if (network_thread_ == nullptr) {
  197. network_thread_ = rtc::Thread::Current();
  198. Initialize();
  199. return;
  200. }
  201. network_thread_->Invoke<void>(RTC_FROM_HERE,
  202. rtc::Bind(&PortAllocator::Initialize,
  203. static_cast<PortAllocator*>(this)));
  204. }
  205. void SetNetworkIgnoreMask(int network_ignore_mask) override {}
  206. cricket::PortAllocatorSession* CreateSessionInternal(
  207. const std::string& content_name,
  208. int component,
  209. const std::string& ice_ufrag,
  210. const std::string& ice_pwd) override {
  211. return new FakePortAllocatorSession(this, network_thread_, factory_,
  212. content_name, component, ice_ufrag,
  213. ice_pwd);
  214. }
  215. bool initialized() const { return initialized_; }
  216. private:
  217. rtc::Thread* network_thread_;
  218. rtc::PacketSocketFactory* factory_;
  219. std::unique_ptr<rtc::BasicPacketSocketFactory> owned_factory_;
  220. };
  221. } // namespace cricket
  222. #endif // P2P_BASE_FAKE_PORT_ALLOCATOR_H_