1 /*
2 * Copyright 2009 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
11 #include "p2p/base/p2p_transport_channel.h"
12
13 #include <list>
14 #include <memory>
15 #include <utility>
16
17 #include "p2p/base/basic_ice_controller.h"
18 #include "p2p/base/connection.h"
19 #include "p2p/base/fake_port_allocator.h"
20 #include "p2p/base/ice_transport_internal.h"
21 #include "p2p/base/mock_async_resolver.h"
22 #include "p2p/base/packet_transport_internal.h"
23 #include "p2p/base/test_stun_server.h"
24 #include "p2p/base/test_turn_server.h"
25 #include "p2p/client/basic_port_allocator.h"
26 #include "rtc_base/checks.h"
27 #include "rtc_base/dscp.h"
28 #include "rtc_base/fake_clock.h"
29 #include "rtc_base/fake_mdns_responder.h"
30 #include "rtc_base/fake_network.h"
31 #include "rtc_base/firewall_socket_server.h"
32 #include "rtc_base/gunit.h"
33 #include "rtc_base/helpers.h"
34 #include "rtc_base/logging.h"
35 #include "rtc_base/mdns_responder_interface.h"
36 #include "rtc_base/nat_server.h"
37 #include "rtc_base/nat_socket_factory.h"
38 #include "rtc_base/proxy_server.h"
39 #include "rtc_base/socket_address.h"
40 #include "rtc_base/ssl_adapter.h"
41 #include "rtc_base/thread.h"
42 #include "rtc_base/virtual_socket_server.h"
43 #include "system_wrappers/include/metrics.h"
44 #include "test/field_trial.h"
45
46 namespace {
47
48 using rtc::SocketAddress;
49 using ::testing::_;
50 using ::testing::Assign;
51 using ::testing::Contains;
52 using ::testing::DoAll;
53 using ::testing::InSequence;
54 using ::testing::InvokeWithoutArgs;
55 using ::testing::NiceMock;
56 using ::testing::Return;
57 using ::testing::SetArgPointee;
58 using ::testing::SizeIs;
59
60 // Default timeout for tests in this file.
61 // Should be large enough for slow buildbots to run the tests reliably.
62 static const int kDefaultTimeout = 10000;
63 static const int kMediumTimeout = 3000;
64 static const int kShortTimeout = 1000;
65
66 static const int kOnlyLocalPorts = cricket::PORTALLOCATOR_DISABLE_STUN |
67 cricket::PORTALLOCATOR_DISABLE_RELAY |
68 cricket::PORTALLOCATOR_DISABLE_TCP;
69 static const int LOW_RTT = 20;
70 // Addresses on the public internet.
71 static const SocketAddress kPublicAddrs[2] = {SocketAddress("11.11.11.11", 0),
72 SocketAddress("22.22.22.22", 0)};
73 // IPv6 Addresses on the public internet.
74 static const SocketAddress kIPv6PublicAddrs[2] = {
75 SocketAddress("2400:4030:1:2c00:be30:abcd:efab:cdef", 0),
76 SocketAddress("2600:0:1000:1b03:2e41:38ff:fea6:f2a4", 0)};
77 // For configuring multihomed clients.
78 static const SocketAddress kAlternateAddrs[2] = {
79 SocketAddress("101.101.101.101", 0), SocketAddress("202.202.202.202", 0)};
80 static const SocketAddress kIPv6AlternateAddrs[2] = {
81 SocketAddress("2401:4030:1:2c00:be30:abcd:efab:cdef", 0),
82 SocketAddress("2601:0:1000:1b03:2e41:38ff:fea6:f2a4", 0)};
83 // Addresses for HTTP proxy servers.
84 static const SocketAddress kHttpsProxyAddrs[2] = {
85 SocketAddress("11.11.11.1", 443), SocketAddress("22.22.22.1", 443)};
86 // Addresses for SOCKS proxy servers.
87 static const SocketAddress kSocksProxyAddrs[2] = {
88 SocketAddress("11.11.11.1", 1080), SocketAddress("22.22.22.1", 1080)};
89 // Internal addresses for NAT boxes.
90 static const SocketAddress kNatAddrs[2] = {SocketAddress("192.168.1.1", 0),
91 SocketAddress("192.168.2.1", 0)};
92 // Private addresses inside the NAT private networks.
93 static const SocketAddress kPrivateAddrs[2] = {
94 SocketAddress("192.168.1.11", 0), SocketAddress("192.168.2.22", 0)};
95 // For cascaded NATs, the internal addresses of the inner NAT boxes.
96 static const SocketAddress kCascadedNatAddrs[2] = {
97 SocketAddress("192.168.10.1", 0), SocketAddress("192.168.20.1", 0)};
98 // For cascaded NATs, private addresses inside the inner private networks.
99 static const SocketAddress kCascadedPrivateAddrs[2] = {
100 SocketAddress("192.168.10.11", 0), SocketAddress("192.168.20.22", 0)};
101 // The address of the public STUN server.
102 static const SocketAddress kStunAddr("99.99.99.1", cricket::STUN_SERVER_PORT);
103 // The addresses for the public turn server.
104 static const SocketAddress kTurnUdpIntAddr("99.99.99.3",
105 cricket::STUN_SERVER_PORT);
106 static const SocketAddress kTurnTcpIntAddr("99.99.99.4",
107 cricket::STUN_SERVER_PORT + 1);
108 static const SocketAddress kTurnUdpExtAddr("99.99.99.5", 0);
109 static const cricket::RelayCredentials kRelayCredentials("test", "test");
110
111 // Based on ICE_UFRAG_LENGTH
112 const char* kIceUfrag[4] = {"UF00", "UF01", "UF02", "UF03"};
113 // Based on ICE_PWD_LENGTH
114 const char* kIcePwd[4] = {
115 "TESTICEPWD00000000000000", "TESTICEPWD00000000000001",
116 "TESTICEPWD00000000000002", "TESTICEPWD00000000000003"};
117 const cricket::IceParameters kIceParams[4] = {
118 {kIceUfrag[0], kIcePwd[0], false},
119 {kIceUfrag[1], kIcePwd[1], false},
120 {kIceUfrag[2], kIcePwd[2], false},
121 {kIceUfrag[3], kIcePwd[3], false}};
122
123 const uint64_t kLowTiebreaker = 11111;
124 const uint64_t kHighTiebreaker = 22222;
125
126 enum { MSG_ADD_CANDIDATES, MSG_REMOVE_CANDIDATES };
127
CreateIceConfig(int receiving_timeout,cricket::ContinualGatheringPolicy continual_gathering_policy,absl::optional<int> backup_ping_interval=absl::nullopt)128 cricket::IceConfig CreateIceConfig(
129 int receiving_timeout,
130 cricket::ContinualGatheringPolicy continual_gathering_policy,
131 absl::optional<int> backup_ping_interval = absl::nullopt) {
132 cricket::IceConfig config;
133 config.receiving_timeout = receiving_timeout;
134 config.continual_gathering_policy = continual_gathering_policy;
135 config.backup_connection_ping_interval = backup_ping_interval;
136 return config;
137 }
138
CreateUdpCandidate(const std::string & type,const std::string & ip,int port,int priority,const std::string & ufrag="")139 cricket::Candidate CreateUdpCandidate(const std::string& type,
140 const std::string& ip,
141 int port,
142 int priority,
143 const std::string& ufrag = "") {
144 cricket::Candidate c;
145 c.set_address(rtc::SocketAddress(ip, port));
146 c.set_component(cricket::ICE_CANDIDATE_COMPONENT_DEFAULT);
147 c.set_protocol(cricket::UDP_PROTOCOL_NAME);
148 c.set_priority(priority);
149 c.set_username(ufrag);
150 c.set_type(type);
151 return c;
152 }
153
CreateBasicPortAllocator(rtc::NetworkManager * network_manager,const cricket::ServerAddresses & stun_servers,const rtc::SocketAddress & turn_server_udp,const rtc::SocketAddress & turn_server_tcp)154 cricket::BasicPortAllocator* CreateBasicPortAllocator(
155 rtc::NetworkManager* network_manager,
156 const cricket::ServerAddresses& stun_servers,
157 const rtc::SocketAddress& turn_server_udp,
158 const rtc::SocketAddress& turn_server_tcp) {
159 cricket::RelayServerConfig turn_server;
160 turn_server.credentials = kRelayCredentials;
161 if (!turn_server_udp.IsNil()) {
162 turn_server.ports.push_back(
163 cricket::ProtocolAddress(turn_server_udp, cricket::PROTO_UDP));
164 }
165 if (!turn_server_tcp.IsNil()) {
166 turn_server.ports.push_back(
167 cricket::ProtocolAddress(turn_server_tcp, cricket::PROTO_TCP));
168 }
169 std::vector<cricket::RelayServerConfig> turn_servers(1, turn_server);
170
171 cricket::BasicPortAllocator* allocator =
172 new cricket::BasicPortAllocator(network_manager);
173 allocator->Initialize();
174 allocator->SetConfiguration(stun_servers, turn_servers, 0, webrtc::NO_PRUNE);
175 return allocator;
176 }
177
178 class MockIceControllerFactory : public cricket::IceControllerFactoryInterface {
179 public:
180 ~MockIceControllerFactory() override = default;
Create(const cricket::IceControllerFactoryArgs & args)181 std::unique_ptr<cricket::IceControllerInterface> Create(
182 const cricket::IceControllerFactoryArgs& args) override {
183 RecordIceControllerCreated();
184 return std::make_unique<cricket::BasicIceController>(args);
185 }
186
187 MOCK_METHOD(void, RecordIceControllerCreated, ());
188 };
189
190 } // namespace
191
192 namespace cricket {
193
194 // This test simulates 2 P2P endpoints that want to establish connectivity
195 // with each other over various network topologies and conditions, which can be
196 // specified in each individial test.
197 // A virtual network (via VirtualSocketServer) along with virtual firewalls and
198 // NATs (via Firewall/NATSocketServer) are used to simulate the various network
199 // conditions. We can configure the IP addresses of the endpoints,
200 // block various types of connectivity, or add arbitrary levels of NAT.
201 // We also run a STUN server and a relay server on the virtual network to allow
202 // our typical P2P mechanisms to do their thing.
203 // For each case, we expect the P2P stack to eventually settle on a specific
204 // form of connectivity to the other side. The test checks that the P2P
205 // negotiation successfully establishes connectivity within a certain time,
206 // and that the result is what we expect.
207 // Note that this class is a base class for use by other tests, who will provide
208 // specialized test behavior.
209 class P2PTransportChannelTestBase : public ::testing::Test,
210 public rtc::MessageHandler,
211 public sigslot::has_slots<> {
212 public:
P2PTransportChannelTestBase()213 P2PTransportChannelTestBase()
214 : vss_(new rtc::VirtualSocketServer()),
215 nss_(new rtc::NATSocketServer(vss_.get())),
216 ss_(new rtc::FirewallSocketServer(nss_.get())),
217 main_(ss_.get()),
218 stun_server_(TestStunServer::Create(&main_, kStunAddr)),
219 turn_server_(&main_, kTurnUdpIntAddr, kTurnUdpExtAddr),
220 socks_server1_(ss_.get(),
221 kSocksProxyAddrs[0],
222 ss_.get(),
223 kSocksProxyAddrs[0]),
224 socks_server2_(ss_.get(),
225 kSocksProxyAddrs[1],
226 ss_.get(),
227 kSocksProxyAddrs[1]),
228 force_relay_(false) {
229 ep1_.role_ = ICEROLE_CONTROLLING;
230 ep2_.role_ = ICEROLE_CONTROLLED;
231
232 ServerAddresses stun_servers;
233 stun_servers.insert(kStunAddr);
234 ep1_.allocator_.reset(
235 CreateBasicPortAllocator(&ep1_.network_manager_, stun_servers,
236 kTurnUdpIntAddr, rtc::SocketAddress()));
237 ep2_.allocator_.reset(
238 CreateBasicPortAllocator(&ep2_.network_manager_, stun_servers,
239 kTurnUdpIntAddr, rtc::SocketAddress()));
240 webrtc::metrics::Reset();
241 }
242
243 protected:
244 enum Config {
245 OPEN, // Open to the Internet
246 NAT_FULL_CONE, // NAT, no filtering
247 NAT_ADDR_RESTRICTED, // NAT, must send to an addr to recv
248 NAT_PORT_RESTRICTED, // NAT, must send to an addr+port to recv
249 NAT_SYMMETRIC, // NAT, endpoint-dependent bindings
250 NAT_DOUBLE_CONE, // Double NAT, both cone
251 NAT_SYMMETRIC_THEN_CONE, // Double NAT, symmetric outer, cone inner
252 BLOCK_UDP, // Firewall, UDP in/out blocked
253 BLOCK_UDP_AND_INCOMING_TCP, // Firewall, UDP in/out and TCP in blocked
254 BLOCK_ALL_BUT_OUTGOING_HTTP, // Firewall, only TCP out on 80/443
255 PROXY_HTTPS, // All traffic through HTTPS proxy
256 PROXY_SOCKS, // All traffic through SOCKS proxy
257 NUM_CONFIGS
258 };
259
260 struct Result {
Resultcricket::P2PTransportChannelTestBase::Result261 Result(const std::string& controlling_type,
262 const std::string& controlling_protocol,
263 const std::string& controlled_type,
264 const std::string& controlled_protocol,
265 int wait)
266 : controlling_type(controlling_type),
267 controlling_protocol(controlling_protocol),
268 controlled_type(controlled_type),
269 controlled_protocol(controlled_protocol),
270 connect_wait(wait) {}
271
272 // The expected candidate type and protocol of the controlling ICE agent.
273 std::string controlling_type;
274 std::string controlling_protocol;
275 // The expected candidate type and protocol of the controlled ICE agent.
276 std::string controlled_type;
277 std::string controlled_protocol;
278 // How long to wait before the correct candidate pair is selected.
279 int connect_wait;
280 };
281
282 struct ChannelData {
CheckDatacricket::P2PTransportChannelTestBase::ChannelData283 bool CheckData(const char* data, int len) {
284 bool ret = false;
285 if (!ch_packets_.empty()) {
286 std::string packet = ch_packets_.front();
287 ret = (packet == std::string(data, len));
288 ch_packets_.pop_front();
289 }
290 return ret;
291 }
292
293 std::string name_; // TODO(?) - Currently not used.
294 std::list<std::string> ch_packets_;
295 std::unique_ptr<P2PTransportChannel> ch_;
296 };
297
298 struct CandidatesData : public rtc::MessageData {
CandidatesDatacricket::P2PTransportChannelTestBase::CandidatesData299 CandidatesData(IceTransportInternal* ch, const Candidate& c)
300 : channel(ch), candidates(1, c) {}
CandidatesDatacricket::P2PTransportChannelTestBase::CandidatesData301 CandidatesData(IceTransportInternal* ch, const std::vector<Candidate>& cc)
302 : channel(ch), candidates(cc) {}
303 IceTransportInternal* channel;
304 Candidates candidates;
305 };
306
307 struct Endpoint : public sigslot::has_slots<> {
Endpointcricket::P2PTransportChannelTestBase::Endpoint308 Endpoint()
309 : role_(ICEROLE_UNKNOWN),
310 tiebreaker_(0),
311 role_conflict_(false),
312 save_candidates_(false) {}
HasTransportcricket::P2PTransportChannelTestBase::Endpoint313 bool HasTransport(const rtc::PacketTransportInternal* transport) {
314 return (transport == cd1_.ch_.get() || transport == cd2_.ch_.get());
315 }
GetChannelDatacricket::P2PTransportChannelTestBase::Endpoint316 ChannelData* GetChannelData(rtc::PacketTransportInternal* transport) {
317 if (!HasTransport(transport))
318 return NULL;
319 if (cd1_.ch_.get() == transport)
320 return &cd1_;
321 else
322 return &cd2_;
323 }
324
SetIceRolecricket::P2PTransportChannelTestBase::Endpoint325 void SetIceRole(IceRole role) { role_ = role; }
ice_rolecricket::P2PTransportChannelTestBase::Endpoint326 IceRole ice_role() { return role_; }
SetIceTiebreakercricket::P2PTransportChannelTestBase::Endpoint327 void SetIceTiebreaker(uint64_t tiebreaker) { tiebreaker_ = tiebreaker; }
GetIceTiebreakercricket::P2PTransportChannelTestBase::Endpoint328 uint64_t GetIceTiebreaker() { return tiebreaker_; }
OnRoleConflictcricket::P2PTransportChannelTestBase::Endpoint329 void OnRoleConflict(bool role_conflict) { role_conflict_ = role_conflict; }
role_conflictcricket::P2PTransportChannelTestBase::Endpoint330 bool role_conflict() { return role_conflict_; }
SetAllocationStepDelaycricket::P2PTransportChannelTestBase::Endpoint331 void SetAllocationStepDelay(uint32_t delay) {
332 allocator_->set_step_delay(delay);
333 }
SetAllowTcpListencricket::P2PTransportChannelTestBase::Endpoint334 void SetAllowTcpListen(bool allow_tcp_listen) {
335 allocator_->set_allow_tcp_listen(allow_tcp_listen);
336 }
337
OnIceRegatheringcricket::P2PTransportChannelTestBase::Endpoint338 void OnIceRegathering(PortAllocatorSession*, IceRegatheringReason reason) {
339 ++ice_regathering_counter_[reason];
340 }
341
GetIceRegatheringCountForReasoncricket::P2PTransportChannelTestBase::Endpoint342 int GetIceRegatheringCountForReason(IceRegatheringReason reason) {
343 return ice_regathering_counter_[reason];
344 }
345
346 rtc::FakeNetworkManager network_manager_;
347 std::unique_ptr<BasicPortAllocator> allocator_;
348 webrtc::AsyncResolverFactory* async_resolver_factory_;
349 ChannelData cd1_;
350 ChannelData cd2_;
351 IceRole role_;
352 uint64_t tiebreaker_;
353 bool role_conflict_;
354 bool save_candidates_;
355 std::vector<std::unique_ptr<CandidatesData>> saved_candidates_;
356 bool ready_to_send_ = false;
357 std::map<IceRegatheringReason, int> ice_regathering_counter_;
358 };
359
GetChannelData(rtc::PacketTransportInternal * transport)360 ChannelData* GetChannelData(rtc::PacketTransportInternal* transport) {
361 if (ep1_.HasTransport(transport))
362 return ep1_.GetChannelData(transport);
363 else
364 return ep2_.GetChannelData(transport);
365 }
366
IceParamsWithRenomination(const IceParameters & ice,bool renomination)367 IceParameters IceParamsWithRenomination(const IceParameters& ice,
368 bool renomination) {
369 IceParameters new_ice = ice;
370 new_ice.renomination = renomination;
371 return new_ice;
372 }
373
CreateChannels(const IceConfig & ep1_config,const IceConfig & ep2_config,bool renomination=false)374 void CreateChannels(const IceConfig& ep1_config,
375 const IceConfig& ep2_config,
376 bool renomination = false) {
377 IceParameters ice_ep1_cd1_ch =
378 IceParamsWithRenomination(kIceParams[0], renomination);
379 IceParameters ice_ep2_cd1_ch =
380 IceParamsWithRenomination(kIceParams[1], renomination);
381 ep1_.cd1_.ch_.reset(CreateChannel(0, ICE_CANDIDATE_COMPONENT_DEFAULT,
382 ice_ep1_cd1_ch, ice_ep2_cd1_ch));
383 ep2_.cd1_.ch_.reset(CreateChannel(1, ICE_CANDIDATE_COMPONENT_DEFAULT,
384 ice_ep2_cd1_ch, ice_ep1_cd1_ch));
385 ep1_.cd1_.ch_->SetIceConfig(ep1_config);
386 ep2_.cd1_.ch_->SetIceConfig(ep2_config);
387 ep1_.cd1_.ch_->MaybeStartGathering();
388 ep2_.cd1_.ch_->MaybeStartGathering();
389 ep1_.cd1_.ch_->allocator_session()->SignalIceRegathering.connect(
390 &ep1_, &Endpoint::OnIceRegathering);
391 ep2_.cd1_.ch_->allocator_session()->SignalIceRegathering.connect(
392 &ep2_, &Endpoint::OnIceRegathering);
393 }
394
CreateChannels()395 void CreateChannels() {
396 IceConfig default_config;
397 CreateChannels(default_config, default_config, false);
398 }
399
CreateChannel(int endpoint,int component,const IceParameters & local_ice,const IceParameters & remote_ice)400 P2PTransportChannel* CreateChannel(int endpoint,
401 int component,
402 const IceParameters& local_ice,
403 const IceParameters& remote_ice) {
404 P2PTransportChannel* channel = new P2PTransportChannel(
405 "test content name", component, GetAllocator(endpoint),
406 GetEndpoint(endpoint)->async_resolver_factory_);
407 channel->SignalReadyToSend.connect(
408 this, &P2PTransportChannelTestBase::OnReadyToSend);
409 channel->SignalCandidateGathered.connect(
410 this, &P2PTransportChannelTestBase::OnCandidateGathered);
411 channel->SignalCandidatesRemoved.connect(
412 this, &P2PTransportChannelTestBase::OnCandidatesRemoved);
413 channel->SignalReadPacket.connect(
414 this, &P2PTransportChannelTestBase::OnReadPacket);
415 channel->SignalRoleConflict.connect(
416 this, &P2PTransportChannelTestBase::OnRoleConflict);
417 channel->SignalNetworkRouteChanged.connect(
418 this, &P2PTransportChannelTestBase::OnNetworkRouteChanged);
419 channel->SignalSentPacket.connect(
420 this, &P2PTransportChannelTestBase::OnSentPacket);
421 channel->SetIceParameters(local_ice);
422 if (remote_ice_parameter_source_ == FROM_SETICEPARAMETERS) {
423 channel->SetRemoteIceParameters(remote_ice);
424 }
425 channel->SetIceRole(GetEndpoint(endpoint)->ice_role());
426 channel->SetIceTiebreaker(GetEndpoint(endpoint)->GetIceTiebreaker());
427 return channel;
428 }
429
DestroyChannels()430 void DestroyChannels() {
431 main_.Clear(this);
432 ep1_.cd1_.ch_.reset();
433 ep2_.cd1_.ch_.reset();
434 ep1_.cd2_.ch_.reset();
435 ep2_.cd2_.ch_.reset();
436 }
ep1_ch1()437 P2PTransportChannel* ep1_ch1() { return ep1_.cd1_.ch_.get(); }
ep1_ch2()438 P2PTransportChannel* ep1_ch2() { return ep1_.cd2_.ch_.get(); }
ep2_ch1()439 P2PTransportChannel* ep2_ch1() { return ep2_.cd1_.ch_.get(); }
ep2_ch2()440 P2PTransportChannel* ep2_ch2() { return ep2_.cd2_.ch_.get(); }
441
test_turn_server()442 TestTurnServer* test_turn_server() { return &turn_server_; }
virtual_socket_server()443 rtc::VirtualSocketServer* virtual_socket_server() { return vss_.get(); }
444
445 // Common results.
446 static const Result kLocalUdpToLocalUdp;
447 static const Result kLocalUdpToStunUdp;
448 static const Result kLocalUdpToPrflxUdp;
449 static const Result kPrflxUdpToLocalUdp;
450 static const Result kStunUdpToLocalUdp;
451 static const Result kStunUdpToStunUdp;
452 static const Result kStunUdpToPrflxUdp;
453 static const Result kPrflxUdpToStunUdp;
454 static const Result kLocalUdpToRelayUdp;
455 static const Result kPrflxUdpToRelayUdp;
456 static const Result kRelayUdpToPrflxUdp;
457 static const Result kLocalTcpToLocalTcp;
458 static const Result kLocalTcpToPrflxTcp;
459 static const Result kPrflxTcpToLocalTcp;
460
nat()461 rtc::NATSocketServer* nat() { return nss_.get(); }
fw()462 rtc::FirewallSocketServer* fw() { return ss_.get(); }
463
GetEndpoint(int endpoint)464 Endpoint* GetEndpoint(int endpoint) {
465 if (endpoint == 0) {
466 return &ep1_;
467 } else if (endpoint == 1) {
468 return &ep2_;
469 } else {
470 return NULL;
471 }
472 }
GetAllocator(int endpoint)473 BasicPortAllocator* GetAllocator(int endpoint) {
474 return GetEndpoint(endpoint)->allocator_.get();
475 }
AddAddress(int endpoint,const SocketAddress & addr)476 void AddAddress(int endpoint, const SocketAddress& addr) {
477 GetEndpoint(endpoint)->network_manager_.AddInterface(addr);
478 }
AddAddress(int endpoint,const SocketAddress & addr,const std::string & ifname,rtc::AdapterType adapter_type)479 void AddAddress(int endpoint,
480 const SocketAddress& addr,
481 const std::string& ifname,
482 rtc::AdapterType adapter_type) {
483 GetEndpoint(endpoint)->network_manager_.AddInterface(addr, ifname,
484 adapter_type);
485 }
RemoveAddress(int endpoint,const SocketAddress & addr)486 void RemoveAddress(int endpoint, const SocketAddress& addr) {
487 GetEndpoint(endpoint)->network_manager_.RemoveInterface(addr);
488 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, addr);
489 }
SetProxy(int endpoint,rtc::ProxyType type)490 void SetProxy(int endpoint, rtc::ProxyType type) {
491 rtc::ProxyInfo info;
492 info.type = type;
493 info.address = (type == rtc::PROXY_HTTPS) ? kHttpsProxyAddrs[endpoint]
494 : kSocksProxyAddrs[endpoint];
495 GetAllocator(endpoint)->set_proxy("unittest/1.0", info);
496 }
SetAllocatorFlags(int endpoint,int flags)497 void SetAllocatorFlags(int endpoint, int flags) {
498 GetAllocator(endpoint)->set_flags(flags);
499 }
SetIceRole(int endpoint,IceRole role)500 void SetIceRole(int endpoint, IceRole role) {
501 GetEndpoint(endpoint)->SetIceRole(role);
502 }
SetIceTiebreaker(int endpoint,uint64_t tiebreaker)503 void SetIceTiebreaker(int endpoint, uint64_t tiebreaker) {
504 GetEndpoint(endpoint)->SetIceTiebreaker(tiebreaker);
505 }
GetRoleConflict(int endpoint)506 bool GetRoleConflict(int endpoint) {
507 return GetEndpoint(endpoint)->role_conflict();
508 }
SetAllocationStepDelay(int endpoint,uint32_t delay)509 void SetAllocationStepDelay(int endpoint, uint32_t delay) {
510 return GetEndpoint(endpoint)->SetAllocationStepDelay(delay);
511 }
SetAllowTcpListen(int endpoint,bool allow_tcp_listen)512 void SetAllowTcpListen(int endpoint, bool allow_tcp_listen) {
513 return GetEndpoint(endpoint)->SetAllowTcpListen(allow_tcp_listen);
514 }
515
516 // Return true if the approprite parts of the expected Result, based
517 // on the local and remote candidate of ep1_ch1, match. This can be
518 // used in an EXPECT_TRUE_WAIT.
CheckCandidate1(const Result & expected)519 bool CheckCandidate1(const Result& expected) {
520 const std::string& local_type = LocalCandidate(ep1_ch1())->type();
521 const std::string& local_protocol = LocalCandidate(ep1_ch1())->protocol();
522 const std::string& remote_type = RemoteCandidate(ep1_ch1())->type();
523 const std::string& remote_protocol = RemoteCandidate(ep1_ch1())->protocol();
524 return (local_protocol == expected.controlling_protocol &&
525 remote_protocol == expected.controlled_protocol &&
526 local_type == expected.controlling_type &&
527 remote_type == expected.controlled_type);
528 }
529
530 // EXPECT_EQ on the approprite parts of the expected Result, based
531 // on the local and remote candidate of ep1_ch1. This is like
532 // CheckCandidate1, except that it will provide more detail about
533 // what didn't match.
ExpectCandidate1(const Result & expected)534 void ExpectCandidate1(const Result& expected) {
535 if (CheckCandidate1(expected)) {
536 return;
537 }
538
539 const std::string& local_type = LocalCandidate(ep1_ch1())->type();
540 const std::string& local_protocol = LocalCandidate(ep1_ch1())->protocol();
541 const std::string& remote_type = RemoteCandidate(ep1_ch1())->type();
542 const std::string& remote_protocol = RemoteCandidate(ep1_ch1())->protocol();
543 EXPECT_EQ(expected.controlling_type, local_type);
544 EXPECT_EQ(expected.controlled_type, remote_type);
545 EXPECT_EQ(expected.controlling_protocol, local_protocol);
546 EXPECT_EQ(expected.controlled_protocol, remote_protocol);
547 }
548
549 // Return true if the approprite parts of the expected Result, based
550 // on the local and remote candidate of ep2_ch1, match. This can be
551 // used in an EXPECT_TRUE_WAIT.
CheckCandidate2(const Result & expected)552 bool CheckCandidate2(const Result& expected) {
553 const std::string& local_type = LocalCandidate(ep2_ch1())->type();
554 const std::string& local_protocol = LocalCandidate(ep2_ch1())->protocol();
555 const std::string& remote_type = RemoteCandidate(ep2_ch1())->type();
556 const std::string& remote_protocol = RemoteCandidate(ep2_ch1())->protocol();
557 return (local_protocol == expected.controlled_protocol &&
558 remote_protocol == expected.controlling_protocol &&
559 local_type == expected.controlled_type &&
560 remote_type == expected.controlling_type);
561 }
562
563 // EXPECT_EQ on the approprite parts of the expected Result, based
564 // on the local and remote candidate of ep2_ch1. This is like
565 // CheckCandidate2, except that it will provide more detail about
566 // what didn't match.
ExpectCandidate2(const Result & expected)567 void ExpectCandidate2(const Result& expected) {
568 if (CheckCandidate2(expected)) {
569 return;
570 }
571
572 const std::string& local_type = LocalCandidate(ep2_ch1())->type();
573 const std::string& local_protocol = LocalCandidate(ep2_ch1())->protocol();
574 const std::string& remote_type = RemoteCandidate(ep2_ch1())->type();
575 const std::string& remote_protocol = RemoteCandidate(ep2_ch1())->protocol();
576 EXPECT_EQ(expected.controlled_type, local_type);
577 EXPECT_EQ(expected.controlling_type, remote_type);
578 EXPECT_EQ(expected.controlled_protocol, local_protocol);
579 EXPECT_EQ(expected.controlling_protocol, remote_protocol);
580 }
581
CheckCandidate(P2PTransportChannel * channel,SocketAddress from,SocketAddress to)582 static bool CheckCandidate(P2PTransportChannel* channel,
583 SocketAddress from,
584 SocketAddress to) {
585 auto local_candidate = LocalCandidate(channel);
586 auto remote_candidate = RemoteCandidate(channel);
587 return local_candidate != nullptr &&
588 local_candidate->address().EqualIPs(from) &&
589 remote_candidate != nullptr &&
590 remote_candidate->address().EqualIPs(to);
591 }
592
CheckCandidatePair(P2PTransportChannel * ch1,P2PTransportChannel * ch2,SocketAddress from,SocketAddress to)593 static bool CheckCandidatePair(P2PTransportChannel* ch1,
594 P2PTransportChannel* ch2,
595 SocketAddress from,
596 SocketAddress to) {
597 return CheckCandidate(ch1, from, to) && CheckCandidate(ch2, to, from);
598 }
599
CheckConnected(P2PTransportChannel * ch1,P2PTransportChannel * ch2)600 static bool CheckConnected(P2PTransportChannel* ch1,
601 P2PTransportChannel* ch2) {
602 return ch1 != nullptr && ch1->receiving() && ch1->writable() &&
603 ch2 != nullptr && ch2->receiving() && ch2->writable();
604 }
605
CheckCandidatePairAndConnected(P2PTransportChannel * ch1,P2PTransportChannel * ch2,SocketAddress from,SocketAddress to)606 static bool CheckCandidatePairAndConnected(P2PTransportChannel* ch1,
607 P2PTransportChannel* ch2,
608 SocketAddress from,
609 SocketAddress to) {
610 return CheckConnected(ch1, ch2) && CheckCandidatePair(ch1, ch2, from, to);
611 }
612
Test(const Result & expected)613 virtual void Test(const Result& expected) {
614 rtc::ScopedFakeClock clock;
615 int64_t connect_start = rtc::TimeMillis();
616 int64_t connect_time;
617
618 // Create the channels and wait for them to connect.
619 CreateChannels();
620 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
621 expected.connect_wait + kShortTimeout, clock);
622 connect_time = rtc::TimeMillis() - connect_start;
623 if (connect_time < expected.connect_wait) {
624 RTC_LOG(LS_INFO) << "Connect time: " << connect_time << " ms";
625 } else {
626 RTC_LOG(LS_INFO) << "Connect time: TIMEOUT (" << expected.connect_wait
627 << " ms)";
628 }
629
630 // Allow a few turns of the crank for the selected connections to emerge.
631 // This may take up to 2 seconds.
632 if (ep1_ch1()->selected_connection() && ep2_ch1()->selected_connection()) {
633 int64_t converge_start = rtc::TimeMillis();
634 int64_t converge_time;
635 // Verifying local and remote channel selected connection information.
636 // This is done only for the RFC 5245 as controlled agent will use
637 // USE-CANDIDATE from controlling (ep1) agent. We can easily predict from
638 // EP1 result matrix.
639 EXPECT_TRUE_SIMULATED_WAIT(
640 CheckCandidate1(expected) && CheckCandidate2(expected),
641 kDefaultTimeout, clock);
642 // Also do EXPECT_EQ on each part so that failures are more verbose.
643 ExpectCandidate1(expected);
644 ExpectCandidate2(expected);
645
646 converge_time = rtc::TimeMillis() - converge_start;
647 int64_t converge_wait = 2000;
648 if (converge_time < converge_wait) {
649 RTC_LOG(LS_INFO) << "Converge time: " << converge_time << " ms";
650 } else {
651 RTC_LOG(LS_INFO) << "Converge time: TIMEOUT (" << converge_time
652 << " ms)";
653 }
654 }
655 // Try sending some data to other end.
656 TestSendRecv(&clock);
657
658 // Destroy the channels, and wait for them to be fully cleaned up.
659 DestroyChannels();
660 }
661
TestSendRecv(rtc::ThreadProcessingFakeClock * clock)662 void TestSendRecv(rtc::ThreadProcessingFakeClock* clock) {
663 for (int i = 0; i < 10; ++i) {
664 const char* data = "ABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890";
665 int len = static_cast<int>(strlen(data));
666 // local_channel1 <==> remote_channel1
667 EXPECT_EQ_SIMULATED_WAIT(len, SendData(ep1_ch1(), data, len),
668 kMediumTimeout, *clock);
669 EXPECT_TRUE_SIMULATED_WAIT(CheckDataOnChannel(ep2_ch1(), data, len),
670 kMediumTimeout, *clock);
671 EXPECT_EQ_SIMULATED_WAIT(len, SendData(ep2_ch1(), data, len),
672 kMediumTimeout, *clock);
673 EXPECT_TRUE_SIMULATED_WAIT(CheckDataOnChannel(ep1_ch1(), data, len),
674 kMediumTimeout, *clock);
675 }
676 }
677
678 // This test waits for the transport to become receiving and writable on both
679 // end points. Once they are, the end points set new local ice parameters and
680 // restart the ice gathering. Finally it waits for the transport to select a
681 // new connection using the newly generated ice candidates.
682 // Before calling this function the end points must be configured.
TestHandleIceUfragPasswordChanged()683 void TestHandleIceUfragPasswordChanged() {
684 rtc::ScopedFakeClock clock;
685 ep1_ch1()->SetRemoteIceParameters(kIceParams[1]);
686 ep2_ch1()->SetRemoteIceParameters(kIceParams[0]);
687 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
688 kMediumTimeout, clock);
689
690 const Candidate* old_local_candidate1 = LocalCandidate(ep1_ch1());
691 const Candidate* old_local_candidate2 = LocalCandidate(ep2_ch1());
692 const Candidate* old_remote_candidate1 = RemoteCandidate(ep1_ch1());
693 const Candidate* old_remote_candidate2 = RemoteCandidate(ep2_ch1());
694
695 ep1_ch1()->SetIceParameters(kIceParams[2]);
696 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
697 ep1_ch1()->MaybeStartGathering();
698 ep2_ch1()->SetIceParameters(kIceParams[3]);
699
700 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
701 ep2_ch1()->MaybeStartGathering();
702
703 EXPECT_TRUE_SIMULATED_WAIT(LocalCandidate(ep1_ch1())->generation() !=
704 old_local_candidate1->generation(),
705 kMediumTimeout, clock);
706 EXPECT_TRUE_SIMULATED_WAIT(LocalCandidate(ep2_ch1())->generation() !=
707 old_local_candidate2->generation(),
708 kMediumTimeout, clock);
709 EXPECT_TRUE_SIMULATED_WAIT(RemoteCandidate(ep1_ch1())->generation() !=
710 old_remote_candidate1->generation(),
711 kMediumTimeout, clock);
712 EXPECT_TRUE_SIMULATED_WAIT(RemoteCandidate(ep2_ch1())->generation() !=
713 old_remote_candidate2->generation(),
714 kMediumTimeout, clock);
715 EXPECT_EQ(1u, RemoteCandidate(ep2_ch1())->generation());
716 EXPECT_EQ(1u, RemoteCandidate(ep1_ch1())->generation());
717 }
718
TestSignalRoleConflict()719 void TestSignalRoleConflict() {
720 rtc::ScopedFakeClock clock;
721 // Default EP1 is in controlling state.
722 SetIceTiebreaker(0, kLowTiebreaker);
723
724 SetIceRole(1, ICEROLE_CONTROLLING);
725 SetIceTiebreaker(1, kHighTiebreaker);
726
727 // Creating channels with both channels role set to CONTROLLING.
728 CreateChannels();
729 // Since both the channels initiated with controlling state and channel2
730 // has higher tiebreaker value, channel1 should receive SignalRoleConflict.
731 EXPECT_TRUE_SIMULATED_WAIT(GetRoleConflict(0), kShortTimeout, clock);
732 EXPECT_FALSE(GetRoleConflict(1));
733
734 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
735 kShortTimeout, clock);
736
737 EXPECT_TRUE(ep1_ch1()->selected_connection() &&
738 ep2_ch1()->selected_connection());
739
740 TestSendRecv(&clock);
741 DestroyChannels();
742 }
743
TestPacketInfoIsSet(rtc::PacketInfo info)744 void TestPacketInfoIsSet(rtc::PacketInfo info) {
745 EXPECT_NE(info.packet_type, rtc::PacketType::kUnknown);
746 EXPECT_NE(info.protocol, rtc::PacketInfoProtocolType::kUnknown);
747 EXPECT_TRUE(info.network_id.has_value());
748 }
749
OnReadyToSend(rtc::PacketTransportInternal * transport)750 void OnReadyToSend(rtc::PacketTransportInternal* transport) {
751 GetEndpoint(transport)->ready_to_send_ = true;
752 }
753
754 // We pass the candidates directly to the other side.
OnCandidateGathered(IceTransportInternal * ch,const Candidate & c)755 void OnCandidateGathered(IceTransportInternal* ch, const Candidate& c) {
756 if (force_relay_ && c.type() != RELAY_PORT_TYPE)
757 return;
758
759 if (GetEndpoint(ch)->save_candidates_) {
760 GetEndpoint(ch)->saved_candidates_.push_back(
761 std::unique_ptr<CandidatesData>(new CandidatesData(ch, c)));
762 } else {
763 main_.Post(RTC_FROM_HERE, this, MSG_ADD_CANDIDATES,
764 new CandidatesData(ch, c));
765 }
766 }
767
OnNetworkRouteChanged(absl::optional<rtc::NetworkRoute> network_route)768 void OnNetworkRouteChanged(absl::optional<rtc::NetworkRoute> network_route) {
769 // If the |network_route| is unset, don't count. This is used in the case
770 // when the network on remote side is down, the signal will be fired with an
771 // unset network route and it shouldn't trigger a connection switch.
772 if (network_route) {
773 ++selected_candidate_pair_switches_;
774 }
775 }
776
reset_selected_candidate_pair_switches()777 int reset_selected_candidate_pair_switches() {
778 int switches = selected_candidate_pair_switches_;
779 selected_candidate_pair_switches_ = 0;
780 return switches;
781 }
782
PauseCandidates(int endpoint)783 void PauseCandidates(int endpoint) {
784 GetEndpoint(endpoint)->save_candidates_ = true;
785 }
786
OnCandidatesRemoved(IceTransportInternal * ch,const std::vector<Candidate> & candidates)787 void OnCandidatesRemoved(IceTransportInternal* ch,
788 const std::vector<Candidate>& candidates) {
789 // Candidate removals are not paused.
790 CandidatesData* candidates_data = new CandidatesData(ch, candidates);
791 main_.Post(RTC_FROM_HERE, this, MSG_REMOVE_CANDIDATES, candidates_data);
792 }
793
794 // Tcp candidate verification has to be done when they are generated.
VerifySavedTcpCandidates(int endpoint,const std::string & tcptype)795 void VerifySavedTcpCandidates(int endpoint, const std::string& tcptype) {
796 for (auto& data : GetEndpoint(endpoint)->saved_candidates_) {
797 for (auto& candidate : data->candidates) {
798 EXPECT_EQ(candidate.protocol(), TCP_PROTOCOL_NAME);
799 EXPECT_EQ(candidate.tcptype(), tcptype);
800 if (candidate.tcptype() == TCPTYPE_ACTIVE_STR) {
801 EXPECT_EQ(candidate.address().port(), DISCARD_PORT);
802 } else if (candidate.tcptype() == TCPTYPE_PASSIVE_STR) {
803 EXPECT_NE(candidate.address().port(), DISCARD_PORT);
804 } else {
805 FAIL() << "Unknown tcptype: " << candidate.tcptype();
806 }
807 }
808 }
809 }
810
ResumeCandidates(int endpoint)811 void ResumeCandidates(int endpoint) {
812 Endpoint* ed = GetEndpoint(endpoint);
813 for (auto& candidate : ed->saved_candidates_) {
814 main_.Post(RTC_FROM_HERE, this, MSG_ADD_CANDIDATES, candidate.release());
815 }
816 ed->saved_candidates_.clear();
817 ed->save_candidates_ = false;
818 }
819
OnMessage(rtc::Message * msg)820 void OnMessage(rtc::Message* msg) {
821 switch (msg->message_id) {
822 case MSG_ADD_CANDIDATES: {
823 std::unique_ptr<CandidatesData> data(
824 static_cast<CandidatesData*>(msg->pdata));
825 P2PTransportChannel* rch = GetRemoteChannel(data->channel);
826 if (!rch) {
827 return;
828 }
829 for (auto& c : data->candidates) {
830 if (remote_ice_parameter_source_ != FROM_CANDIDATE) {
831 c.set_username("");
832 c.set_password("");
833 }
834 RTC_LOG(LS_INFO) << "Candidate(" << data->channel->component() << "->"
835 << rch->component() << "): " << c.ToString();
836 rch->AddRemoteCandidate(c);
837 }
838 break;
839 }
840 case MSG_REMOVE_CANDIDATES: {
841 std::unique_ptr<CandidatesData> data(
842 static_cast<CandidatesData*>(msg->pdata));
843 P2PTransportChannel* rch = GetRemoteChannel(data->channel);
844 if (!rch) {
845 return;
846 }
847 for (Candidate& c : data->candidates) {
848 RTC_LOG(LS_INFO) << "Removed remote candidate " << c.ToString();
849 rch->RemoveRemoteCandidate(c);
850 }
851 break;
852 }
853 }
854 }
855
OnReadPacket(rtc::PacketTransportInternal * transport,const char * data,size_t len,const int64_t &,int flags)856 void OnReadPacket(rtc::PacketTransportInternal* transport,
857 const char* data,
858 size_t len,
859 const int64_t& /* packet_time_us */,
860 int flags) {
861 std::list<std::string>& packets = GetPacketList(transport);
862 packets.push_front(std::string(data, len));
863 }
864
OnRoleConflict(IceTransportInternal * channel)865 void OnRoleConflict(IceTransportInternal* channel) {
866 GetEndpoint(channel)->OnRoleConflict(true);
867 IceRole new_role = GetEndpoint(channel)->ice_role() == ICEROLE_CONTROLLING
868 ? ICEROLE_CONTROLLED
869 : ICEROLE_CONTROLLING;
870 channel->SetIceRole(new_role);
871 }
872
OnSentPacket(rtc::PacketTransportInternal * transport,const rtc::SentPacket & packet)873 void OnSentPacket(rtc::PacketTransportInternal* transport,
874 const rtc::SentPacket& packet) {
875 TestPacketInfoIsSet(packet.info);
876 }
877
SendData(IceTransportInternal * channel,const char * data,size_t len)878 int SendData(IceTransportInternal* channel, const char* data, size_t len) {
879 rtc::PacketOptions options;
880 return channel->SendPacket(data, len, options, 0);
881 }
CheckDataOnChannel(IceTransportInternal * channel,const char * data,int len)882 bool CheckDataOnChannel(IceTransportInternal* channel,
883 const char* data,
884 int len) {
885 return GetChannelData(channel)->CheckData(data, len);
886 }
LocalCandidate(P2PTransportChannel * ch)887 static const Candidate* LocalCandidate(P2PTransportChannel* ch) {
888 return (ch && ch->selected_connection())
889 ? &ch->selected_connection()->local_candidate()
890 : NULL;
891 }
RemoteCandidate(P2PTransportChannel * ch)892 static const Candidate* RemoteCandidate(P2PTransportChannel* ch) {
893 return (ch && ch->selected_connection())
894 ? &ch->selected_connection()->remote_candidate()
895 : NULL;
896 }
GetEndpoint(rtc::PacketTransportInternal * transport)897 Endpoint* GetEndpoint(rtc::PacketTransportInternal* transport) {
898 if (ep1_.HasTransport(transport)) {
899 return &ep1_;
900 } else if (ep2_.HasTransport(transport)) {
901 return &ep2_;
902 } else {
903 return NULL;
904 }
905 }
GetRemoteChannel(IceTransportInternal * ch)906 P2PTransportChannel* GetRemoteChannel(IceTransportInternal* ch) {
907 if (ch == ep1_ch1())
908 return ep2_ch1();
909 else if (ch == ep1_ch2())
910 return ep2_ch2();
911 else if (ch == ep2_ch1())
912 return ep1_ch1();
913 else if (ch == ep2_ch2())
914 return ep1_ch2();
915 else
916 return NULL;
917 }
GetPacketList(rtc::PacketTransportInternal * transport)918 std::list<std::string>& GetPacketList(
919 rtc::PacketTransportInternal* transport) {
920 return GetChannelData(transport)->ch_packets_;
921 }
922
923 enum RemoteIceParameterSource { FROM_CANDIDATE, FROM_SETICEPARAMETERS };
924
925 // How does the test pass ICE parameters to the P2PTransportChannel?
926 // On the candidate itself, or through SetRemoteIceParameters?
927 // Goes through the candidate itself by default.
set_remote_ice_parameter_source(RemoteIceParameterSource source)928 void set_remote_ice_parameter_source(RemoteIceParameterSource source) {
929 remote_ice_parameter_source_ = source;
930 }
931
set_force_relay(bool relay)932 void set_force_relay(bool relay) { force_relay_ = relay; }
933
ConnectSignalNominated(Connection * conn)934 void ConnectSignalNominated(Connection* conn) {
935 conn->SignalNominated.connect(this,
936 &P2PTransportChannelTestBase::OnNominated);
937 }
938
OnNominated(Connection * conn)939 void OnNominated(Connection* conn) { nominated_ = true; }
nominated()940 bool nominated() { return nominated_; }
941
942 private:
943 std::unique_ptr<rtc::VirtualSocketServer> vss_;
944 std::unique_ptr<rtc::NATSocketServer> nss_;
945 std::unique_ptr<rtc::FirewallSocketServer> ss_;
946 rtc::AutoSocketServerThread main_;
947 std::unique_ptr<TestStunServer> stun_server_;
948 TestTurnServer turn_server_;
949 rtc::SocksProxyServer socks_server1_;
950 rtc::SocksProxyServer socks_server2_;
951 Endpoint ep1_;
952 Endpoint ep2_;
953 RemoteIceParameterSource remote_ice_parameter_source_ = FROM_CANDIDATE;
954 bool force_relay_;
955 int selected_candidate_pair_switches_ = 0;
956
957 bool nominated_ = false;
958 };
959
960 // The tests have only a few outcomes, which we predefine.
961 const P2PTransportChannelTestBase::Result
962 P2PTransportChannelTestBase::kLocalUdpToLocalUdp("local",
963 "udp",
964 "local",
965 "udp",
966 1000);
967 const P2PTransportChannelTestBase::Result
968 P2PTransportChannelTestBase::kLocalUdpToStunUdp("local",
969 "udp",
970 "stun",
971 "udp",
972 1000);
973 const P2PTransportChannelTestBase::Result
974 P2PTransportChannelTestBase::kLocalUdpToPrflxUdp("local",
975 "udp",
976 "prflx",
977 "udp",
978 1000);
979 const P2PTransportChannelTestBase::Result
980 P2PTransportChannelTestBase::kPrflxUdpToLocalUdp("prflx",
981 "udp",
982 "local",
983 "udp",
984 1000);
985 const P2PTransportChannelTestBase::Result
986 P2PTransportChannelTestBase::kStunUdpToLocalUdp("stun",
987 "udp",
988 "local",
989 "udp",
990 1000);
991 const P2PTransportChannelTestBase::Result
992 P2PTransportChannelTestBase::kStunUdpToStunUdp("stun",
993 "udp",
994 "stun",
995 "udp",
996 1000);
997 const P2PTransportChannelTestBase::Result
998 P2PTransportChannelTestBase::kStunUdpToPrflxUdp("stun",
999 "udp",
1000 "prflx",
1001 "udp",
1002 1000);
1003 const P2PTransportChannelTestBase::Result
1004 P2PTransportChannelTestBase::kPrflxUdpToStunUdp("prflx",
1005 "udp",
1006 "stun",
1007 "udp",
1008 1000);
1009 const P2PTransportChannelTestBase::Result
1010 P2PTransportChannelTestBase::kLocalUdpToRelayUdp("local",
1011 "udp",
1012 "relay",
1013 "udp",
1014 2000);
1015 const P2PTransportChannelTestBase::Result
1016 P2PTransportChannelTestBase::kPrflxUdpToRelayUdp("prflx",
1017 "udp",
1018 "relay",
1019 "udp",
1020 2000);
1021 const P2PTransportChannelTestBase::Result
1022 P2PTransportChannelTestBase::kRelayUdpToPrflxUdp("relay",
1023 "udp",
1024 "prflx",
1025 "udp",
1026 2000);
1027 const P2PTransportChannelTestBase::Result
1028 P2PTransportChannelTestBase::kLocalTcpToLocalTcp("local",
1029 "tcp",
1030 "local",
1031 "tcp",
1032 3000);
1033 const P2PTransportChannelTestBase::Result
1034 P2PTransportChannelTestBase::kLocalTcpToPrflxTcp("local",
1035 "tcp",
1036 "prflx",
1037 "tcp",
1038 3000);
1039 const P2PTransportChannelTestBase::Result
1040 P2PTransportChannelTestBase::kPrflxTcpToLocalTcp("prflx",
1041 "tcp",
1042 "local",
1043 "tcp",
1044 3000);
1045
1046 // Test the matrix of all the connectivity types we expect to see in the wild.
1047 // Just test every combination of the configs in the Config enum.
1048 class P2PTransportChannelTest : public P2PTransportChannelTestBase {
1049 protected:
1050 static const Result* kMatrix[NUM_CONFIGS][NUM_CONFIGS];
ConfigureEndpoints(Config config1,Config config2,int allocator_flags1,int allocator_flags2)1051 void ConfigureEndpoints(Config config1,
1052 Config config2,
1053 int allocator_flags1,
1054 int allocator_flags2) {
1055 ConfigureEndpoint(0, config1);
1056 SetAllocatorFlags(0, allocator_flags1);
1057 SetAllocationStepDelay(0, kMinimumStepDelay);
1058 ConfigureEndpoint(1, config2);
1059 SetAllocatorFlags(1, allocator_flags2);
1060 SetAllocationStepDelay(1, kMinimumStepDelay);
1061
1062 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
1063 }
ConfigureEndpoint(int endpoint,Config config)1064 void ConfigureEndpoint(int endpoint, Config config) {
1065 switch (config) {
1066 case OPEN:
1067 AddAddress(endpoint, kPublicAddrs[endpoint]);
1068 break;
1069 case NAT_FULL_CONE:
1070 case NAT_ADDR_RESTRICTED:
1071 case NAT_PORT_RESTRICTED:
1072 case NAT_SYMMETRIC:
1073 AddAddress(endpoint, kPrivateAddrs[endpoint]);
1074 // Add a single NAT of the desired type
1075 nat()
1076 ->AddTranslator(kPublicAddrs[endpoint], kNatAddrs[endpoint],
1077 static_cast<rtc::NATType>(config - NAT_FULL_CONE))
1078 ->AddClient(kPrivateAddrs[endpoint]);
1079 break;
1080 case NAT_DOUBLE_CONE:
1081 case NAT_SYMMETRIC_THEN_CONE:
1082 AddAddress(endpoint, kCascadedPrivateAddrs[endpoint]);
1083 // Add a two cascaded NATs of the desired types
1084 nat()
1085 ->AddTranslator(kPublicAddrs[endpoint], kNatAddrs[endpoint],
1086 (config == NAT_DOUBLE_CONE) ? rtc::NAT_OPEN_CONE
1087 : rtc::NAT_SYMMETRIC)
1088 ->AddTranslator(kPrivateAddrs[endpoint],
1089 kCascadedNatAddrs[endpoint], rtc::NAT_OPEN_CONE)
1090 ->AddClient(kCascadedPrivateAddrs[endpoint]);
1091 break;
1092 case BLOCK_UDP:
1093 case BLOCK_UDP_AND_INCOMING_TCP:
1094 case BLOCK_ALL_BUT_OUTGOING_HTTP:
1095 case PROXY_HTTPS:
1096 case PROXY_SOCKS:
1097 AddAddress(endpoint, kPublicAddrs[endpoint]);
1098 // Block all UDP
1099 fw()->AddRule(false, rtc::FP_UDP, rtc::FD_ANY, kPublicAddrs[endpoint]);
1100 if (config == BLOCK_UDP_AND_INCOMING_TCP) {
1101 // Block TCP inbound to the endpoint
1102 fw()->AddRule(false, rtc::FP_TCP, SocketAddress(),
1103 kPublicAddrs[endpoint]);
1104 } else if (config == BLOCK_ALL_BUT_OUTGOING_HTTP) {
1105 // Block all TCP to/from the endpoint except 80/443 out
1106 fw()->AddRule(true, rtc::FP_TCP, kPublicAddrs[endpoint],
1107 SocketAddress(rtc::IPAddress(INADDR_ANY), 80));
1108 fw()->AddRule(true, rtc::FP_TCP, kPublicAddrs[endpoint],
1109 SocketAddress(rtc::IPAddress(INADDR_ANY), 443));
1110 fw()->AddRule(false, rtc::FP_TCP, rtc::FD_ANY,
1111 kPublicAddrs[endpoint]);
1112 } else if (config == PROXY_HTTPS) {
1113 // Block all TCP to/from the endpoint except to the proxy server
1114 fw()->AddRule(true, rtc::FP_TCP, kPublicAddrs[endpoint],
1115 kHttpsProxyAddrs[endpoint]);
1116 fw()->AddRule(false, rtc::FP_TCP, rtc::FD_ANY,
1117 kPublicAddrs[endpoint]);
1118 SetProxy(endpoint, rtc::PROXY_HTTPS);
1119 } else if (config == PROXY_SOCKS) {
1120 // Block all TCP to/from the endpoint except to the proxy server
1121 fw()->AddRule(true, rtc::FP_TCP, kPublicAddrs[endpoint],
1122 kSocksProxyAddrs[endpoint]);
1123 fw()->AddRule(false, rtc::FP_TCP, rtc::FD_ANY,
1124 kPublicAddrs[endpoint]);
1125 SetProxy(endpoint, rtc::PROXY_SOCKS5);
1126 }
1127 break;
1128 default:
1129 RTC_NOTREACHED();
1130 break;
1131 }
1132 }
1133 };
1134
1135 // Shorthands for use in the test matrix.
1136 #define LULU &kLocalUdpToLocalUdp
1137 #define LUSU &kLocalUdpToStunUdp
1138 #define LUPU &kLocalUdpToPrflxUdp
1139 #define PULU &kPrflxUdpToLocalUdp
1140 #define SULU &kStunUdpToLocalUdp
1141 #define SUSU &kStunUdpToStunUdp
1142 #define SUPU &kStunUdpToPrflxUdp
1143 #define PUSU &kPrflxUdpToStunUdp
1144 #define LURU &kLocalUdpToRelayUdp
1145 #define PURU &kPrflxUdpToRelayUdp
1146 #define RUPU &kRelayUdpToPrflxUdp
1147 #define LTLT &kLocalTcpToLocalTcp
1148 #define LTPT &kLocalTcpToPrflxTcp
1149 #define PTLT &kPrflxTcpToLocalTcp
1150 // TODO(?): Enable these once TestRelayServer can accept external TCP.
1151 #define LTRT NULL
1152 #define LSRS NULL
1153
1154 // Test matrix. Originator behavior defined by rows, receiever by columns.
1155
1156 // TODO(?): Fix NULLs caused by lack of TCP support in NATSocket.
1157 // TODO(?): Fix NULLs caused by no HTTP proxy support.
1158 // TODO(?): Rearrange rows/columns from best to worst.
1159 const P2PTransportChannelTest::Result*
1160 P2PTransportChannelTest::kMatrix[NUM_CONFIGS][NUM_CONFIGS] = {
1161 // OPEN CONE ADDR PORT SYMM 2CON SCON !UDP !TCP HTTP PRXH
1162 // PRXS
1163 /*OP*/ {LULU, LUSU, LUSU, LUSU, LUPU, LUSU, LUPU, LTPT, LTPT, LSRS,
1164 NULL, LTPT},
1165 /*CO*/
1166 {SULU, SUSU, SUSU, SUSU, SUPU, SUSU, SUPU, NULL, NULL, LSRS, NULL,
1167 LTRT},
1168 /*AD*/
1169 {SULU, SUSU, SUSU, SUSU, SUPU, SUSU, SUPU, NULL, NULL, LSRS, NULL,
1170 LTRT},
1171 /*PO*/
1172 {SULU, SUSU, SUSU, SUSU, RUPU, SUSU, RUPU, NULL, NULL, LSRS, NULL,
1173 LTRT},
1174 /*SY*/
1175 {PULU, PUSU, PUSU, PURU, PURU, PUSU, PURU, NULL, NULL, LSRS, NULL,
1176 LTRT},
1177 /*2C*/
1178 {SULU, SUSU, SUSU, SUSU, SUPU, SUSU, SUPU, NULL, NULL, LSRS, NULL,
1179 LTRT},
1180 /*SC*/
1181 {PULU, PUSU, PUSU, PURU, PURU, PUSU, PURU, NULL, NULL, LSRS, NULL,
1182 LTRT},
1183 /*!U*/
1184 {LTPT, NULL, NULL, NULL, NULL, NULL, NULL, LTPT, LTPT, LSRS, NULL,
1185 LTRT},
1186 /*!T*/
1187 {PTLT, NULL, NULL, NULL, NULL, NULL, NULL, PTLT, LTRT, LSRS, NULL,
1188 LTRT},
1189 /*HT*/
1190 {LSRS, LSRS, LSRS, LSRS, LSRS, LSRS, LSRS, LSRS, LSRS, LSRS, NULL,
1191 LSRS},
1192 /*PR*/
1193 {NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL,
1194 NULL},
1195 /*PR*/
1196 {LTRT, LTRT, LTRT, LTRT, LTRT, LTRT, LTRT, LTRT, LTRT, LSRS, NULL,
1197 LTRT},
1198 };
1199
1200 class P2PTransportChannelTestWithFieldTrials
1201 : public P2PTransportChannelTest,
1202 public ::testing::WithParamInterface<std::string> {
1203 public:
Test(const Result & expected)1204 void Test(const Result& expected) override {
1205 webrtc::test::ScopedFieldTrials field_trials(GetParam());
1206 P2PTransportChannelTest::Test(expected);
1207 }
1208 };
1209
1210 // The actual tests that exercise all the various configurations.
1211 // Test names are of the form P2PTransportChannelTest_TestOPENToNAT_FULL_CONE
1212 #define P2P_TEST_DECLARATION(x, y, z) \
1213 TEST_P(P2PTransportChannelTestWithFieldTrials, z##Test##x##To##y) { \
1214 ConfigureEndpoints(x, y, PORTALLOCATOR_ENABLE_SHARED_SOCKET, \
1215 PORTALLOCATOR_ENABLE_SHARED_SOCKET); \
1216 if (kMatrix[x][y] != NULL) \
1217 Test(*kMatrix[x][y]); \
1218 else \
1219 RTC_LOG(LS_WARNING) << "Not yet implemented"; \
1220 }
1221
1222 #define P2P_TEST(x, y) P2P_TEST_DECLARATION(x, y, /* empty argument */)
1223
1224 #define P2P_TEST_SET(x) \
1225 P2P_TEST(x, OPEN) \
1226 P2P_TEST(x, NAT_FULL_CONE) \
1227 P2P_TEST(x, NAT_ADDR_RESTRICTED) \
1228 P2P_TEST(x, NAT_PORT_RESTRICTED) \
1229 P2P_TEST(x, NAT_SYMMETRIC) \
1230 P2P_TEST(x, NAT_DOUBLE_CONE) \
1231 P2P_TEST(x, NAT_SYMMETRIC_THEN_CONE) \
1232 P2P_TEST(x, BLOCK_UDP) \
1233 P2P_TEST(x, BLOCK_UDP_AND_INCOMING_TCP) \
1234 P2P_TEST(x, BLOCK_ALL_BUT_OUTGOING_HTTP) \
1235 P2P_TEST(x, PROXY_HTTPS) \
1236 P2P_TEST(x, PROXY_SOCKS)
1237
1238 P2P_TEST_SET(OPEN)
1239 P2P_TEST_SET(NAT_FULL_CONE)
1240 P2P_TEST_SET(NAT_ADDR_RESTRICTED)
1241 P2P_TEST_SET(NAT_PORT_RESTRICTED)
1242 P2P_TEST_SET(NAT_SYMMETRIC)
1243 P2P_TEST_SET(NAT_DOUBLE_CONE)
1244 P2P_TEST_SET(NAT_SYMMETRIC_THEN_CONE)
1245 P2P_TEST_SET(BLOCK_UDP)
1246 P2P_TEST_SET(BLOCK_UDP_AND_INCOMING_TCP)
1247 P2P_TEST_SET(BLOCK_ALL_BUT_OUTGOING_HTTP)
1248 P2P_TEST_SET(PROXY_HTTPS)
1249 P2P_TEST_SET(PROXY_SOCKS)
1250
1251 INSTANTIATE_TEST_SUITE_P(
1252 P2PTransportChannelTestWithFieldTrials,
1253 P2PTransportChannelTestWithFieldTrials,
1254 // Each field-trial is ~144 tests (some return not-yet-implemented).
1255 testing::Values("", "WebRTC-IceFieldTrials/enable_goog_ping:true/"));
1256
1257 // Test that we restart candidate allocation when local ufrag&pwd changed.
1258 // Standard Ice protocol is used.
TEST_F(P2PTransportChannelTest,HandleUfragPwdChange)1259 TEST_F(P2PTransportChannelTest, HandleUfragPwdChange) {
1260 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1261 kDefaultPortAllocatorFlags);
1262 CreateChannels();
1263 TestHandleIceUfragPasswordChanged();
1264 DestroyChannels();
1265 }
1266
1267 // Same as above test, but with a symmetric NAT.
1268 // We should end up with relay<->prflx candidate pairs, with generation "1".
TEST_F(P2PTransportChannelTest,HandleUfragPwdChangeSymmetricNat)1269 TEST_F(P2PTransportChannelTest, HandleUfragPwdChangeSymmetricNat) {
1270 ConfigureEndpoints(NAT_SYMMETRIC, NAT_SYMMETRIC, kDefaultPortAllocatorFlags,
1271 kDefaultPortAllocatorFlags);
1272 CreateChannels();
1273 TestHandleIceUfragPasswordChanged();
1274 DestroyChannels();
1275 }
1276
1277 // Test the operation of GetStats.
TEST_F(P2PTransportChannelTest,GetStats)1278 TEST_F(P2PTransportChannelTest, GetStats) {
1279 rtc::ScopedFakeClock clock;
1280 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1281 kDefaultPortAllocatorFlags);
1282 CreateChannels();
1283 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->receiving() && ep1_ch1()->writable() &&
1284 ep2_ch1()->receiving() &&
1285 ep2_ch1()->writable(),
1286 kMediumTimeout, clock);
1287 // Sends and receives 10 packets.
1288 TestSendRecv(&clock);
1289 IceTransportStats ice_transport_stats;
1290 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
1291 ASSERT_GE(ice_transport_stats.connection_infos.size(), 1u);
1292 ASSERT_GE(ice_transport_stats.candidate_stats_list.size(), 1u);
1293 EXPECT_EQ(ice_transport_stats.selected_candidate_pair_changes, 1u);
1294 ConnectionInfo* best_conn_info = nullptr;
1295 for (ConnectionInfo& info : ice_transport_stats.connection_infos) {
1296 if (info.best_connection) {
1297 best_conn_info = &info;
1298 break;
1299 }
1300 }
1301 ASSERT_TRUE(best_conn_info != nullptr);
1302 EXPECT_TRUE(best_conn_info->new_connection);
1303 EXPECT_TRUE(best_conn_info->receiving);
1304 EXPECT_TRUE(best_conn_info->writable);
1305 EXPECT_FALSE(best_conn_info->timeout);
1306 EXPECT_EQ(10U, best_conn_info->sent_total_packets);
1307 EXPECT_EQ(0U, best_conn_info->sent_discarded_packets);
1308 EXPECT_EQ(10 * 36U, best_conn_info->sent_total_bytes);
1309 EXPECT_EQ(10 * 36U, best_conn_info->recv_total_bytes);
1310 EXPECT_EQ(10U, best_conn_info->packets_received);
1311 DestroyChannels();
1312 }
1313
1314 // Tests that UMAs are recorded when ICE restarts while the channel
1315 // is disconnected.
TEST_F(P2PTransportChannelTest,TestUMAIceRestartWhileDisconnected)1316 TEST_F(P2PTransportChannelTest, TestUMAIceRestartWhileDisconnected) {
1317 rtc::ScopedFakeClock clock;
1318 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1319
1320 CreateChannels();
1321 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1322 kDefaultTimeout, clock);
1323
1324 // Drop all packets so that both channels become not writable.
1325 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[0]);
1326 const int kWriteTimeoutDelay = 8000;
1327 EXPECT_TRUE_SIMULATED_WAIT(!ep1_ch1()->writable() && !ep2_ch1()->writable(),
1328 kWriteTimeoutDelay, clock);
1329
1330 ep1_ch1()->SetIceParameters(kIceParams[2]);
1331 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1332 ep1_ch1()->MaybeStartGathering();
1333 EXPECT_METRIC_EQ(1, webrtc::metrics::NumEvents(
1334 "WebRTC.PeerConnection.IceRestartState",
1335 static_cast<int>(IceRestartState::DISCONNECTED)));
1336
1337 ep2_ch1()->SetIceParameters(kIceParams[3]);
1338 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
1339 ep2_ch1()->MaybeStartGathering();
1340 EXPECT_METRIC_EQ(2, webrtc::metrics::NumEvents(
1341 "WebRTC.PeerConnection.IceRestartState",
1342 static_cast<int>(IceRestartState::DISCONNECTED)));
1343
1344 DestroyChannels();
1345 }
1346
1347 // Tests that UMAs are recorded when ICE restarts while the channel
1348 // is connected.
TEST_F(P2PTransportChannelTest,TestUMAIceRestartWhileConnected)1349 TEST_F(P2PTransportChannelTest, TestUMAIceRestartWhileConnected) {
1350 rtc::ScopedFakeClock clock;
1351 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1352
1353 CreateChannels();
1354 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1355 kDefaultTimeout, clock);
1356
1357 ep1_ch1()->SetIceParameters(kIceParams[2]);
1358 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1359 ep1_ch1()->MaybeStartGathering();
1360 EXPECT_METRIC_EQ(1, webrtc::metrics::NumEvents(
1361 "WebRTC.PeerConnection.IceRestartState",
1362 static_cast<int>(IceRestartState::CONNECTED)));
1363
1364 ep2_ch1()->SetIceParameters(kIceParams[3]);
1365 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
1366 ep2_ch1()->MaybeStartGathering();
1367 EXPECT_METRIC_EQ(2, webrtc::metrics::NumEvents(
1368 "WebRTC.PeerConnection.IceRestartState",
1369 static_cast<int>(IceRestartState::CONNECTED)));
1370
1371 DestroyChannels();
1372 }
1373
1374 // Tests that UMAs are recorded when ICE restarts while the channel
1375 // is connecting.
TEST_F(P2PTransportChannelTest,TestUMAIceRestartWhileConnecting)1376 TEST_F(P2PTransportChannelTest, TestUMAIceRestartWhileConnecting) {
1377 rtc::ScopedFakeClock clock;
1378 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1379
1380 // Create the channels without waiting for them to become connected.
1381 CreateChannels();
1382
1383 ep1_ch1()->SetIceParameters(kIceParams[2]);
1384 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1385 ep1_ch1()->MaybeStartGathering();
1386 EXPECT_METRIC_EQ(1, webrtc::metrics::NumEvents(
1387 "WebRTC.PeerConnection.IceRestartState",
1388 static_cast<int>(IceRestartState::CONNECTING)));
1389
1390 ep2_ch1()->SetIceParameters(kIceParams[3]);
1391 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
1392 ep2_ch1()->MaybeStartGathering();
1393 EXPECT_METRIC_EQ(2, webrtc::metrics::NumEvents(
1394 "WebRTC.PeerConnection.IceRestartState",
1395 static_cast<int>(IceRestartState::CONNECTING)));
1396
1397 DestroyChannels();
1398 }
1399
1400 // Tests that a UMA on ICE regathering is recorded when there is a network
1401 // change if and only if continual gathering is enabled.
TEST_F(P2PTransportChannelTest,TestIceRegatheringReasonContinualGatheringByNetworkChange)1402 TEST_F(P2PTransportChannelTest,
1403 TestIceRegatheringReasonContinualGatheringByNetworkChange) {
1404 rtc::ScopedFakeClock clock;
1405 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1406
1407 // ep1 gathers continually but ep2 does not.
1408 IceConfig continual_gathering_config =
1409 CreateIceConfig(1000, GATHER_CONTINUALLY);
1410 IceConfig default_config;
1411 CreateChannels(continual_gathering_config, default_config);
1412
1413 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1414 kDefaultTimeout, clock);
1415
1416 // Adding address in ep1 will trigger continual gathering.
1417 AddAddress(0, kAlternateAddrs[0]);
1418 EXPECT_EQ_SIMULATED_WAIT(1,
1419 GetEndpoint(0)->GetIceRegatheringCountForReason(
1420 IceRegatheringReason::NETWORK_CHANGE),
1421 kDefaultTimeout, clock);
1422
1423 ep2_ch1()->SetIceParameters(kIceParams[3]);
1424 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
1425 ep2_ch1()->MaybeStartGathering();
1426
1427 AddAddress(1, kAlternateAddrs[1]);
1428 SIMULATED_WAIT(false, kDefaultTimeout, clock);
1429 // ep2 has not enabled continual gathering.
1430 EXPECT_EQ(0, GetEndpoint(1)->GetIceRegatheringCountForReason(
1431 IceRegatheringReason::NETWORK_CHANGE));
1432
1433 DestroyChannels();
1434 }
1435
1436 // Tests that a UMA on ICE regathering is recorded when there is a network
1437 // failure if and only if continual gathering is enabled.
TEST_F(P2PTransportChannelTest,TestIceRegatheringReasonContinualGatheringByNetworkFailure)1438 TEST_F(P2PTransportChannelTest,
1439 TestIceRegatheringReasonContinualGatheringByNetworkFailure) {
1440 rtc::ScopedFakeClock clock;
1441 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1442
1443 // ep1 gathers continually but ep2 does not.
1444 IceConfig config1 = CreateIceConfig(1000, GATHER_CONTINUALLY);
1445 config1.regather_on_failed_networks_interval = 2000;
1446 IceConfig config2;
1447 config2.regather_on_failed_networks_interval = 2000;
1448 CreateChannels(config1, config2);
1449
1450 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1451 kDefaultTimeout, clock);
1452
1453 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[0]);
1454 // Timeout value such that all connections are deleted.
1455 const int kNetworkFailureTimeout = 35000;
1456 SIMULATED_WAIT(false, kNetworkFailureTimeout, clock);
1457 EXPECT_LE(1, GetEndpoint(0)->GetIceRegatheringCountForReason(
1458 IceRegatheringReason::NETWORK_FAILURE));
1459 EXPECT_METRIC_LE(
1460 1, webrtc::metrics::NumEvents(
1461 "WebRTC.PeerConnection.IceRegatheringReason",
1462 static_cast<int>(IceRegatheringReason::NETWORK_FAILURE)));
1463 EXPECT_EQ(0, GetEndpoint(1)->GetIceRegatheringCountForReason(
1464 IceRegatheringReason::NETWORK_FAILURE));
1465
1466 DestroyChannels();
1467 }
1468
1469 // Test that we properly create a connection on a STUN ping from unknown address
1470 // when the signaling is slow.
TEST_F(P2PTransportChannelTest,PeerReflexiveCandidateBeforeSignaling)1471 TEST_F(P2PTransportChannelTest, PeerReflexiveCandidateBeforeSignaling) {
1472 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1473 kDefaultPortAllocatorFlags);
1474 // Emulate no remote parameters coming in.
1475 set_remote_ice_parameter_source(FROM_CANDIDATE);
1476 CreateChannels();
1477 // Only have remote parameters come in for ep2, not ep1.
1478 ep2_ch1()->SetRemoteIceParameters(kIceParams[0]);
1479
1480 // Pause sending ep2's candidates to ep1 until ep1 receives the peer reflexive
1481 // candidate.
1482 PauseCandidates(1);
1483
1484 // Wait until the callee becomes writable to make sure that a ping request is
1485 // received by the caller before their remote ICE credentials are set.
1486 ASSERT_TRUE_WAIT(ep2_ch1()->selected_connection() != nullptr, kMediumTimeout);
1487 // Add two sets of remote ICE credentials, so that the ones used by the
1488 // candidate will be generation 1 instead of 0.
1489 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1490 ep1_ch1()->SetRemoteIceParameters(kIceParams[1]);
1491 // The caller should have the selected connection connected to the peer
1492 // reflexive candidate.
1493 const Connection* selected_connection = nullptr;
1494 ASSERT_TRUE_WAIT(
1495 (selected_connection = ep1_ch1()->selected_connection()) != nullptr,
1496 kMediumTimeout);
1497 EXPECT_EQ(PRFLX_PORT_TYPE, selected_connection->remote_candidate().type());
1498 EXPECT_EQ(kIceUfrag[1], selected_connection->remote_candidate().username());
1499 EXPECT_EQ(kIcePwd[1], selected_connection->remote_candidate().password());
1500 EXPECT_EQ(1u, selected_connection->remote_candidate().generation());
1501
1502 ResumeCandidates(1);
1503 // Verify ep1's selected connection is updated to use the 'local' candidate.
1504 EXPECT_EQ_WAIT(LOCAL_PORT_TYPE,
1505 ep1_ch1()->selected_connection()->remote_candidate().type(),
1506 kMediumTimeout);
1507 EXPECT_EQ(selected_connection, ep1_ch1()->selected_connection());
1508 DestroyChannels();
1509 }
1510
1511 // Test that if we learn a prflx remote candidate, its address is concealed in
1512 // 1. the selected candidate pair accessed via the public API, and
1513 // 2. the candidate pair stats
1514 // until we learn the same address from signaling.
TEST_F(P2PTransportChannelTest,PeerReflexiveRemoteCandidateIsSanitized)1515 TEST_F(P2PTransportChannelTest, PeerReflexiveRemoteCandidateIsSanitized) {
1516 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
1517 // Emulate no remote parameters coming in.
1518 set_remote_ice_parameter_source(FROM_CANDIDATE);
1519 CreateChannels();
1520 // Only have remote parameters come in for ep2, not ep1.
1521 ep2_ch1()->SetRemoteIceParameters(kIceParams[0]);
1522
1523 // Pause sending ep2's candidates to ep1 until ep1 receives the peer reflexive
1524 // candidate.
1525 PauseCandidates(1);
1526
1527 ASSERT_TRUE_WAIT(ep2_ch1()->selected_connection() != nullptr, kMediumTimeout);
1528 ep1_ch1()->SetRemoteIceParameters(kIceParams[1]);
1529 ASSERT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr, kMediumTimeout);
1530
1531 // Check the selected candidate pair.
1532 auto pair_ep1 = ep1_ch1()->GetSelectedCandidatePair();
1533 ASSERT_TRUE(pair_ep1.has_value());
1534 EXPECT_EQ(PRFLX_PORT_TYPE, pair_ep1->remote_candidate().type());
1535 EXPECT_TRUE(pair_ep1->remote_candidate().address().ipaddr().IsNil());
1536
1537 IceTransportStats ice_transport_stats;
1538 ep1_ch1()->GetStats(&ice_transport_stats);
1539 // Check the candidate pair stats.
1540 ASSERT_EQ(1u, ice_transport_stats.connection_infos.size());
1541 EXPECT_EQ(PRFLX_PORT_TYPE,
1542 ice_transport_stats.connection_infos[0].remote_candidate.type());
1543 EXPECT_TRUE(ice_transport_stats.connection_infos[0]
1544 .remote_candidate.address()
1545 .ipaddr()
1546 .IsNil());
1547
1548 // Let ep1 receive the remote candidate to update its type from prflx to host.
1549 ResumeCandidates(1);
1550 ASSERT_TRUE_WAIT(
1551 ep1_ch1()->selected_connection() != nullptr &&
1552 ep1_ch1()->selected_connection()->remote_candidate().type() ==
1553 LOCAL_PORT_TYPE,
1554 kMediumTimeout);
1555
1556 // We should be able to reveal the address after it is learnt via
1557 // AddIceCandidate.
1558 //
1559 // Check the selected candidate pair.
1560 auto updated_pair_ep1 = ep1_ch1()->GetSelectedCandidatePair();
1561 ASSERT_TRUE(updated_pair_ep1.has_value());
1562 EXPECT_EQ(LOCAL_PORT_TYPE, updated_pair_ep1->remote_candidate().type());
1563 EXPECT_TRUE(
1564 updated_pair_ep1->remote_candidate().address().EqualIPs(kPublicAddrs[1]));
1565
1566 ep1_ch1()->GetStats(&ice_transport_stats);
1567 // Check the candidate pair stats.
1568 ASSERT_EQ(1u, ice_transport_stats.connection_infos.size());
1569 EXPECT_EQ(LOCAL_PORT_TYPE,
1570 ice_transport_stats.connection_infos[0].remote_candidate.type());
1571 EXPECT_TRUE(ice_transport_stats.connection_infos[0]
1572 .remote_candidate.address()
1573 .EqualIPs(kPublicAddrs[1]));
1574
1575 DestroyChannels();
1576 }
1577
1578 // Test that we properly create a connection on a STUN ping from unknown address
1579 // when the signaling is slow and the end points are behind NAT.
TEST_F(P2PTransportChannelTest,PeerReflexiveCandidateBeforeSignalingWithNAT)1580 TEST_F(P2PTransportChannelTest, PeerReflexiveCandidateBeforeSignalingWithNAT) {
1581 ConfigureEndpoints(OPEN, NAT_SYMMETRIC, kDefaultPortAllocatorFlags,
1582 kDefaultPortAllocatorFlags);
1583 // Emulate no remote parameters coming in.
1584 set_remote_ice_parameter_source(FROM_CANDIDATE);
1585 CreateChannels();
1586 // Only have remote parameters come in for ep2, not ep1.
1587 ep2_ch1()->SetRemoteIceParameters(kIceParams[0]);
1588 // Pause sending ep2's candidates to ep1 until ep1 receives the peer reflexive
1589 // candidate.
1590 PauseCandidates(1);
1591
1592 // Wait until the callee becomes writable to make sure that a ping request is
1593 // received by the caller before their remote ICE credentials are set.
1594 ASSERT_TRUE_WAIT(ep2_ch1()->selected_connection() != nullptr, kMediumTimeout);
1595 // Add two sets of remote ICE credentials, so that the ones used by the
1596 // candidate will be generation 1 instead of 0.
1597 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1598 ep1_ch1()->SetRemoteIceParameters(kIceParams[1]);
1599
1600 // The caller's selected connection should be connected to the peer reflexive
1601 // candidate.
1602 const Connection* selected_connection = nullptr;
1603 ASSERT_TRUE_WAIT(
1604 (selected_connection = ep1_ch1()->selected_connection()) != nullptr,
1605 kMediumTimeout);
1606 EXPECT_EQ(PRFLX_PORT_TYPE, selected_connection->remote_candidate().type());
1607 EXPECT_EQ(kIceUfrag[1], selected_connection->remote_candidate().username());
1608 EXPECT_EQ(kIcePwd[1], selected_connection->remote_candidate().password());
1609 EXPECT_EQ(1u, selected_connection->remote_candidate().generation());
1610
1611 ResumeCandidates(1);
1612
1613 EXPECT_EQ_WAIT(PRFLX_PORT_TYPE,
1614 ep1_ch1()->selected_connection()->remote_candidate().type(),
1615 kMediumTimeout);
1616 EXPECT_EQ(selected_connection, ep1_ch1()->selected_connection());
1617 DestroyChannels();
1618 }
1619
1620 // Test that we properly create a connection on a STUN ping from unknown address
1621 // when the signaling is slow, even if the new candidate is created due to the
1622 // remote peer doing an ICE restart, pairing this candidate across generations.
1623 //
1624 // Previously this wasn't working due to a bug where the peer reflexive
1625 // candidate was only updated for the newest generation candidate pairs, and
1626 // not older-generation candidate pairs created by pairing candidates across
1627 // generations. This resulted in the old-generation prflx candidate being
1628 // prioritized above new-generation candidate pairs.
TEST_F(P2PTransportChannelTest,PeerReflexiveCandidateBeforeSignalingWithIceRestart)1629 TEST_F(P2PTransportChannelTest,
1630 PeerReflexiveCandidateBeforeSignalingWithIceRestart) {
1631 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1632 kDefaultPortAllocatorFlags);
1633 // Only gather relay candidates, so that when the prflx candidate arrives
1634 // it's prioritized above the current candidate pair.
1635 GetEndpoint(0)->allocator_->SetCandidateFilter(CF_RELAY);
1636 GetEndpoint(1)->allocator_->SetCandidateFilter(CF_RELAY);
1637 // Setting this allows us to control when SetRemoteIceParameters is called.
1638 set_remote_ice_parameter_source(FROM_CANDIDATE);
1639 CreateChannels();
1640 // Wait for the initial connection to be made.
1641 ep1_ch1()->SetRemoteIceParameters(kIceParams[1]);
1642 ep2_ch1()->SetRemoteIceParameters(kIceParams[0]);
1643 EXPECT_TRUE_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()), kDefaultTimeout);
1644
1645 // Simulate an ICE restart on ep2, but don't signal the candidate or new
1646 // ICE parameters until after a prflx connection has been made.
1647 PauseCandidates(1);
1648 ep2_ch1()->SetIceParameters(kIceParams[3]);
1649
1650 ep1_ch1()->SetRemoteIceParameters(kIceParams[3]);
1651 ep2_ch1()->MaybeStartGathering();
1652
1653 // The caller should have the selected connection connected to the peer
1654 // reflexive candidate.
1655 EXPECT_EQ_WAIT(PRFLX_PORT_TYPE,
1656 ep1_ch1()->selected_connection()->remote_candidate().type(),
1657 kDefaultTimeout);
1658 const Connection* prflx_selected_connection =
1659 ep1_ch1()->selected_connection();
1660
1661 // Now simulate the ICE restart on ep1.
1662 ep1_ch1()->SetIceParameters(kIceParams[2]);
1663
1664 ep2_ch1()->SetRemoteIceParameters(kIceParams[2]);
1665 ep1_ch1()->MaybeStartGathering();
1666
1667 // Finally send the candidates from ep2's ICE restart and verify that ep1 uses
1668 // their information to update the peer reflexive candidate.
1669 ResumeCandidates(1);
1670
1671 EXPECT_EQ_WAIT(RELAY_PORT_TYPE,
1672 ep1_ch1()->selected_connection()->remote_candidate().type(),
1673 kDefaultTimeout);
1674 EXPECT_EQ(prflx_selected_connection, ep1_ch1()->selected_connection());
1675 DestroyChannels();
1676 }
1677
1678 // Test that if remote candidates don't have ufrag and pwd, we still work.
TEST_F(P2PTransportChannelTest,RemoteCandidatesWithoutUfragPwd)1679 TEST_F(P2PTransportChannelTest, RemoteCandidatesWithoutUfragPwd) {
1680 rtc::ScopedFakeClock clock;
1681 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
1682 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1683 kDefaultPortAllocatorFlags);
1684 CreateChannels();
1685 const Connection* selected_connection = NULL;
1686 // Wait until the callee's connections are created.
1687 EXPECT_TRUE_SIMULATED_WAIT(
1688 (selected_connection = ep2_ch1()->selected_connection()) != NULL,
1689 kMediumTimeout, clock);
1690 // Wait to make sure the selected connection is not changed.
1691 SIMULATED_WAIT(ep2_ch1()->selected_connection() != selected_connection,
1692 kShortTimeout, clock);
1693 EXPECT_TRUE(ep2_ch1()->selected_connection() == selected_connection);
1694 DestroyChannels();
1695 }
1696
1697 // Test that a host behind NAT cannot be reached when incoming_only
1698 // is set to true.
TEST_F(P2PTransportChannelTest,IncomingOnlyBlocked)1699 TEST_F(P2PTransportChannelTest, IncomingOnlyBlocked) {
1700 rtc::ScopedFakeClock clock;
1701 ConfigureEndpoints(NAT_FULL_CONE, OPEN, kDefaultPortAllocatorFlags,
1702 kDefaultPortAllocatorFlags);
1703
1704 SetAllocatorFlags(0, kOnlyLocalPorts);
1705 CreateChannels();
1706 ep1_ch1()->set_incoming_only(true);
1707
1708 // Pump for 1 second and verify that the channels are not connected.
1709 SIMULATED_WAIT(false, kShortTimeout, clock);
1710
1711 EXPECT_FALSE(ep1_ch1()->receiving());
1712 EXPECT_FALSE(ep1_ch1()->writable());
1713 EXPECT_FALSE(ep2_ch1()->receiving());
1714 EXPECT_FALSE(ep2_ch1()->writable());
1715
1716 DestroyChannels();
1717 }
1718
1719 // Test that a peer behind NAT can connect to a peer that has
1720 // incoming_only flag set.
TEST_F(P2PTransportChannelTest,IncomingOnlyOpen)1721 TEST_F(P2PTransportChannelTest, IncomingOnlyOpen) {
1722 rtc::ScopedFakeClock clock;
1723 ConfigureEndpoints(OPEN, NAT_FULL_CONE, kDefaultPortAllocatorFlags,
1724 kDefaultPortAllocatorFlags);
1725
1726 SetAllocatorFlags(0, kOnlyLocalPorts);
1727 CreateChannels();
1728 ep1_ch1()->set_incoming_only(true);
1729
1730 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1731 kMediumTimeout, clock);
1732
1733 DestroyChannels();
1734 }
1735
1736 // Test that two peers can connect when one can only make outgoing TCP
1737 // connections. This has been observed in some scenarios involving
1738 // VPNs/firewalls.
TEST_F(P2PTransportChannelTest,CanOnlyMakeOutgoingTcpConnections)1739 TEST_F(P2PTransportChannelTest, CanOnlyMakeOutgoingTcpConnections) {
1740 // The PORTALLOCATOR_ENABLE_ANY_ADDRESS_PORTS flag is required if the
1741 // application needs this use case to work, since the application must accept
1742 // the tradeoff that more candidates need to be allocated.
1743 //
1744 // TODO(deadbeef): Later, make this flag the default, and do more elegant
1745 // things to ensure extra candidates don't waste resources?
1746 ConfigureEndpoints(
1747 OPEN, OPEN,
1748 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_ANY_ADDRESS_PORTS,
1749 kDefaultPortAllocatorFlags);
1750 // In order to simulate nothing working but outgoing TCP connections, prevent
1751 // the endpoint from binding to its interface's address as well as the
1752 // "any" addresses. It can then only make a connection by using "Connect()".
1753 fw()->SetUnbindableIps({rtc::GetAnyIP(AF_INET), rtc::GetAnyIP(AF_INET6),
1754 kPublicAddrs[0].ipaddr()});
1755 CreateChannels();
1756 // Expect a "prflx" candidate on the side that can only make outgoing
1757 // connections, endpoint 0.
1758 Test(kPrflxTcpToLocalTcp);
1759 DestroyChannels();
1760 }
1761
TEST_F(P2PTransportChannelTest,TestTcpConnectionsFromActiveToPassive)1762 TEST_F(P2PTransportChannelTest, TestTcpConnectionsFromActiveToPassive) {
1763 rtc::ScopedFakeClock clock;
1764 AddAddress(0, kPublicAddrs[0]);
1765 AddAddress(1, kPublicAddrs[1]);
1766
1767 SetAllocationStepDelay(0, kMinimumStepDelay);
1768 SetAllocationStepDelay(1, kMinimumStepDelay);
1769
1770 int kOnlyLocalTcpPorts = PORTALLOCATOR_DISABLE_UDP |
1771 PORTALLOCATOR_DISABLE_STUN |
1772 PORTALLOCATOR_DISABLE_RELAY;
1773 // Disable all protocols except TCP.
1774 SetAllocatorFlags(0, kOnlyLocalTcpPorts);
1775 SetAllocatorFlags(1, kOnlyLocalTcpPorts);
1776
1777 SetAllowTcpListen(0, true); // actpass.
1778 SetAllowTcpListen(1, false); // active.
1779
1780 // We want SetRemoteIceParameters to be called as it normally would.
1781 // Otherwise we won't know what parameters to use for the expected
1782 // prflx TCP candidates.
1783 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
1784
1785 // Pause candidate so we could verify the candidate properties.
1786 PauseCandidates(0);
1787 PauseCandidates(1);
1788 CreateChannels();
1789
1790 // Verify tcp candidates.
1791 VerifySavedTcpCandidates(0, TCPTYPE_PASSIVE_STR);
1792 VerifySavedTcpCandidates(1, TCPTYPE_ACTIVE_STR);
1793
1794 // Resume candidates.
1795 ResumeCandidates(0);
1796 ResumeCandidates(1);
1797
1798 EXPECT_TRUE_SIMULATED_WAIT(
1799 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
1800 kPublicAddrs[1]),
1801 kShortTimeout, clock);
1802
1803 TestSendRecv(&clock);
1804 DestroyChannels();
1805 }
1806
1807 // Test that tcptype is set on all candidates for a connection running over TCP.
TEST_F(P2PTransportChannelTest,TestTcpConnectionTcptypeSet)1808 TEST_F(P2PTransportChannelTest, TestTcpConnectionTcptypeSet) {
1809 rtc::ScopedFakeClock clock;
1810 ConfigureEndpoints(BLOCK_UDP_AND_INCOMING_TCP, OPEN,
1811 PORTALLOCATOR_ENABLE_SHARED_SOCKET,
1812 PORTALLOCATOR_ENABLE_SHARED_SOCKET);
1813
1814 SetAllowTcpListen(0, false); // active.
1815 SetAllowTcpListen(1, true); // actpass.
1816 CreateChannels();
1817
1818 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1819 kMediumTimeout, clock);
1820 SIMULATED_WAIT(false, kDefaultTimeout, clock);
1821
1822 EXPECT_EQ(RemoteCandidate(ep1_ch1())->tcptype(), "passive");
1823 EXPECT_EQ(LocalCandidate(ep1_ch1())->tcptype(), "active");
1824 EXPECT_EQ(RemoteCandidate(ep2_ch1())->tcptype(), "active");
1825 EXPECT_EQ(LocalCandidate(ep2_ch1())->tcptype(), "passive");
1826
1827 DestroyChannels();
1828 }
1829
TEST_F(P2PTransportChannelTest,TestIceRoleConflict)1830 TEST_F(P2PTransportChannelTest, TestIceRoleConflict) {
1831 AddAddress(0, kPublicAddrs[0]);
1832 AddAddress(1, kPublicAddrs[1]);
1833 TestSignalRoleConflict();
1834 }
1835
1836 // Tests that the ice configs (protocol, tiebreaker and role) can be passed
1837 // down to ports.
TEST_F(P2PTransportChannelTest,TestIceConfigWillPassDownToPort)1838 TEST_F(P2PTransportChannelTest, TestIceConfigWillPassDownToPort) {
1839 rtc::ScopedFakeClock clock;
1840 AddAddress(0, kPublicAddrs[0]);
1841 AddAddress(1, kPublicAddrs[1]);
1842
1843 // Give the first connection the higher tiebreaker so its role won't
1844 // change unless we tell it to.
1845 SetIceRole(0, ICEROLE_CONTROLLING);
1846 SetIceTiebreaker(0, kHighTiebreaker);
1847 SetIceRole(1, ICEROLE_CONTROLLING);
1848 SetIceTiebreaker(1, kLowTiebreaker);
1849
1850 CreateChannels();
1851
1852 EXPECT_EQ_SIMULATED_WAIT(2u, ep1_ch1()->ports().size(), kShortTimeout, clock);
1853
1854 const std::vector<PortInterface*> ports_before = ep1_ch1()->ports();
1855 for (size_t i = 0; i < ports_before.size(); ++i) {
1856 EXPECT_EQ(ICEROLE_CONTROLLING, ports_before[i]->GetIceRole());
1857 EXPECT_EQ(kHighTiebreaker, ports_before[i]->IceTiebreaker());
1858 }
1859
1860 ep1_ch1()->SetIceRole(ICEROLE_CONTROLLED);
1861 ep1_ch1()->SetIceTiebreaker(kLowTiebreaker);
1862
1863 const std::vector<PortInterface*> ports_after = ep1_ch1()->ports();
1864 for (size_t i = 0; i < ports_after.size(); ++i) {
1865 EXPECT_EQ(ICEROLE_CONTROLLED, ports_before[i]->GetIceRole());
1866 // SetIceTiebreaker after ports have been created will fail. So expect the
1867 // original value.
1868 EXPECT_EQ(kHighTiebreaker, ports_before[i]->IceTiebreaker());
1869 }
1870
1871 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1872 kShortTimeout, clock);
1873
1874 EXPECT_TRUE(ep1_ch1()->selected_connection() &&
1875 ep2_ch1()->selected_connection());
1876
1877 TestSendRecv(&clock);
1878 DestroyChannels();
1879 }
1880
1881 // Verify that we can set DSCP value and retrieve properly from P2PTC.
TEST_F(P2PTransportChannelTest,TestDefaultDscpValue)1882 TEST_F(P2PTransportChannelTest, TestDefaultDscpValue) {
1883 AddAddress(0, kPublicAddrs[0]);
1884 AddAddress(1, kPublicAddrs[1]);
1885
1886 CreateChannels();
1887 EXPECT_EQ(rtc::DSCP_NO_CHANGE, GetEndpoint(0)->cd1_.ch_->DefaultDscpValue());
1888 EXPECT_EQ(rtc::DSCP_NO_CHANGE, GetEndpoint(1)->cd1_.ch_->DefaultDscpValue());
1889 GetEndpoint(0)->cd1_.ch_->SetOption(rtc::Socket::OPT_DSCP, rtc::DSCP_CS6);
1890 GetEndpoint(1)->cd1_.ch_->SetOption(rtc::Socket::OPT_DSCP, rtc::DSCP_CS6);
1891 EXPECT_EQ(rtc::DSCP_CS6, GetEndpoint(0)->cd1_.ch_->DefaultDscpValue());
1892 EXPECT_EQ(rtc::DSCP_CS6, GetEndpoint(1)->cd1_.ch_->DefaultDscpValue());
1893 GetEndpoint(0)->cd1_.ch_->SetOption(rtc::Socket::OPT_DSCP, rtc::DSCP_AF41);
1894 GetEndpoint(1)->cd1_.ch_->SetOption(rtc::Socket::OPT_DSCP, rtc::DSCP_AF41);
1895 EXPECT_EQ(rtc::DSCP_AF41, GetEndpoint(0)->cd1_.ch_->DefaultDscpValue());
1896 EXPECT_EQ(rtc::DSCP_AF41, GetEndpoint(1)->cd1_.ch_->DefaultDscpValue());
1897 DestroyChannels();
1898 }
1899
1900 // Verify IPv6 connection is preferred over IPv4.
TEST_F(P2PTransportChannelTest,TestIPv6Connections)1901 TEST_F(P2PTransportChannelTest, TestIPv6Connections) {
1902 rtc::ScopedFakeClock clock;
1903 AddAddress(0, kIPv6PublicAddrs[0]);
1904 AddAddress(0, kPublicAddrs[0]);
1905 AddAddress(1, kIPv6PublicAddrs[1]);
1906 AddAddress(1, kPublicAddrs[1]);
1907
1908 SetAllocationStepDelay(0, kMinimumStepDelay);
1909 SetAllocationStepDelay(1, kMinimumStepDelay);
1910
1911 // Enable IPv6
1912 SetAllocatorFlags(
1913 0, PORTALLOCATOR_ENABLE_IPV6 | PORTALLOCATOR_ENABLE_IPV6_ON_WIFI);
1914 SetAllocatorFlags(
1915 1, PORTALLOCATOR_ENABLE_IPV6 | PORTALLOCATOR_ENABLE_IPV6_ON_WIFI);
1916
1917 CreateChannels();
1918
1919 EXPECT_TRUE_SIMULATED_WAIT(
1920 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kIPv6PublicAddrs[0],
1921 kIPv6PublicAddrs[1]),
1922 kShortTimeout, clock);
1923
1924 TestSendRecv(&clock);
1925 DestroyChannels();
1926 }
1927
1928 // Testing forceful TURN connections.
TEST_F(P2PTransportChannelTest,TestForceTurn)1929 TEST_F(P2PTransportChannelTest, TestForceTurn) {
1930 rtc::ScopedFakeClock clock;
1931 ConfigureEndpoints(
1932 NAT_PORT_RESTRICTED, NAT_SYMMETRIC,
1933 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
1934 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
1935 set_force_relay(true);
1936
1937 SetAllocationStepDelay(0, kMinimumStepDelay);
1938 SetAllocationStepDelay(1, kMinimumStepDelay);
1939
1940 CreateChannels();
1941
1942 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1943 kMediumTimeout, clock);
1944
1945 EXPECT_TRUE(ep1_ch1()->selected_connection() &&
1946 ep2_ch1()->selected_connection());
1947
1948 EXPECT_EQ(RELAY_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
1949 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
1950 EXPECT_EQ(RELAY_PORT_TYPE, RemoteCandidate(ep2_ch1())->type());
1951 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep2_ch1())->type());
1952
1953 TestSendRecv(&clock);
1954 DestroyChannels();
1955 }
1956
1957 // Test that if continual gathering is set to true, ICE gathering state will
1958 // not change to "Complete", and vice versa.
TEST_F(P2PTransportChannelTest,TestContinualGathering)1959 TEST_F(P2PTransportChannelTest, TestContinualGathering) {
1960 rtc::ScopedFakeClock clock;
1961 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1962 kDefaultPortAllocatorFlags);
1963 SetAllocationStepDelay(0, kDefaultStepDelay);
1964 SetAllocationStepDelay(1, kDefaultStepDelay);
1965 IceConfig continual_gathering_config =
1966 CreateIceConfig(1000, GATHER_CONTINUALLY);
1967 // By default, ep2 does not gather continually.
1968 IceConfig default_config;
1969 CreateChannels(continual_gathering_config, default_config);
1970
1971 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
1972 kMediumTimeout, clock);
1973 SIMULATED_WAIT(
1974 IceGatheringState::kIceGatheringComplete == ep1_ch1()->gathering_state(),
1975 kShortTimeout, clock);
1976 EXPECT_EQ(IceGatheringState::kIceGatheringGathering,
1977 ep1_ch1()->gathering_state());
1978 // By now, ep2 should have completed gathering.
1979 EXPECT_EQ(IceGatheringState::kIceGatheringComplete,
1980 ep2_ch1()->gathering_state());
1981
1982 DestroyChannels();
1983 }
1984
1985 // Test that a connection succeeds when the P2PTransportChannel uses a pooled
1986 // PortAllocatorSession that has not yet finished gathering candidates.
TEST_F(P2PTransportChannelTest,TestUsingPooledSessionBeforeDoneGathering)1987 TEST_F(P2PTransportChannelTest, TestUsingPooledSessionBeforeDoneGathering) {
1988 rtc::ScopedFakeClock clock;
1989 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
1990 kDefaultPortAllocatorFlags);
1991 // First create a pooled session for each endpoint.
1992 auto& allocator_1 = GetEndpoint(0)->allocator_;
1993 auto& allocator_2 = GetEndpoint(1)->allocator_;
1994 int pool_size = 1;
1995 allocator_1->SetConfiguration(allocator_1->stun_servers(),
1996 allocator_1->turn_servers(), pool_size,
1997 webrtc::NO_PRUNE);
1998 allocator_2->SetConfiguration(allocator_2->stun_servers(),
1999 allocator_2->turn_servers(), pool_size,
2000 webrtc::NO_PRUNE);
2001 const PortAllocatorSession* pooled_session_1 =
2002 allocator_1->GetPooledSession();
2003 const PortAllocatorSession* pooled_session_2 =
2004 allocator_2->GetPooledSession();
2005 ASSERT_NE(nullptr, pooled_session_1);
2006 ASSERT_NE(nullptr, pooled_session_2);
2007 // Sanity check that pooled sessions haven't gathered anything yet.
2008 EXPECT_TRUE(pooled_session_1->ReadyPorts().empty());
2009 EXPECT_TRUE(pooled_session_1->ReadyCandidates().empty());
2010 EXPECT_TRUE(pooled_session_2->ReadyPorts().empty());
2011 EXPECT_TRUE(pooled_session_2->ReadyCandidates().empty());
2012 // Now let the endpoints connect and try exchanging some data.
2013 CreateChannels();
2014 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2015 kMediumTimeout, clock);
2016 TestSendRecv(&clock);
2017 // Make sure the P2PTransportChannels are actually using ports from the
2018 // pooled sessions.
2019 auto pooled_ports_1 = pooled_session_1->ReadyPorts();
2020 auto pooled_ports_2 = pooled_session_2->ReadyPorts();
2021 EXPECT_THAT(pooled_ports_1,
2022 Contains(ep1_ch1()->selected_connection()->PortForTest()));
2023 EXPECT_THAT(pooled_ports_2,
2024 Contains(ep2_ch1()->selected_connection()->PortForTest()));
2025 DestroyChannels();
2026 }
2027
2028 // Test that a connection succeeds when the P2PTransportChannel uses a pooled
2029 // PortAllocatorSession that already finished gathering candidates.
TEST_F(P2PTransportChannelTest,TestUsingPooledSessionAfterDoneGathering)2030 TEST_F(P2PTransportChannelTest, TestUsingPooledSessionAfterDoneGathering) {
2031 rtc::ScopedFakeClock clock;
2032 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
2033 kDefaultPortAllocatorFlags);
2034 // First create a pooled session for each endpoint.
2035 auto& allocator_1 = GetEndpoint(0)->allocator_;
2036 auto& allocator_2 = GetEndpoint(1)->allocator_;
2037 int pool_size = 1;
2038 allocator_1->SetConfiguration(allocator_1->stun_servers(),
2039 allocator_1->turn_servers(), pool_size,
2040 webrtc::NO_PRUNE);
2041 allocator_2->SetConfiguration(allocator_2->stun_servers(),
2042 allocator_2->turn_servers(), pool_size,
2043 webrtc::NO_PRUNE);
2044 const PortAllocatorSession* pooled_session_1 =
2045 allocator_1->GetPooledSession();
2046 const PortAllocatorSession* pooled_session_2 =
2047 allocator_2->GetPooledSession();
2048 ASSERT_NE(nullptr, pooled_session_1);
2049 ASSERT_NE(nullptr, pooled_session_2);
2050 // Wait for the pooled sessions to finish gathering before the
2051 // P2PTransportChannels try to use them.
2052 EXPECT_TRUE_SIMULATED_WAIT(pooled_session_1->CandidatesAllocationDone() &&
2053 pooled_session_2->CandidatesAllocationDone(),
2054 kDefaultTimeout, clock);
2055 // Now let the endpoints connect and try exchanging some data.
2056 CreateChannels();
2057 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2058 kMediumTimeout, clock);
2059 TestSendRecv(&clock);
2060 // Make sure the P2PTransportChannels are actually using ports from the
2061 // pooled sessions.
2062 auto pooled_ports_1 = pooled_session_1->ReadyPorts();
2063 auto pooled_ports_2 = pooled_session_2->ReadyPorts();
2064 EXPECT_THAT(pooled_ports_1,
2065 Contains(ep1_ch1()->selected_connection()->PortForTest()));
2066 EXPECT_THAT(pooled_ports_2,
2067 Contains(ep2_ch1()->selected_connection()->PortForTest()));
2068 DestroyChannels();
2069 }
2070
2071 // Test that when the "presume_writable_when_fully_relayed" flag is set to
2072 // true and there's a TURN-TURN candidate pair, it's presumed to be writable
2073 // as soon as it's created.
2074 // TODO(deadbeef): Move this and other "presumed writable" tests into a test
2075 // class that operates on a single P2PTransportChannel, once an appropriate one
2076 // (which supports TURN servers and TURN candidate gathering) is available.
TEST_F(P2PTransportChannelTest,TurnToTurnPresumedWritable)2077 TEST_F(P2PTransportChannelTest, TurnToTurnPresumedWritable) {
2078 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
2079 kDefaultPortAllocatorFlags);
2080 // Only configure one channel so we can control when the remote candidate
2081 // is added.
2082 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
2083 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
2084 IceConfig config;
2085 config.presume_writable_when_fully_relayed = true;
2086 ep1_ch1()->SetIceConfig(config);
2087 ep1_ch1()->MaybeStartGathering();
2088 EXPECT_EQ_WAIT(IceGatheringState::kIceGatheringComplete,
2089 ep1_ch1()->gathering_state(), kDefaultTimeout);
2090 // Add two remote candidates; a host candidate (with higher priority)
2091 // and TURN candidate.
2092 ep1_ch1()->AddRemoteCandidate(
2093 CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
2094 ep1_ch1()->AddRemoteCandidate(
2095 CreateUdpCandidate(RELAY_PORT_TYPE, "2.2.2.2", 2, 0));
2096 // Expect that the TURN-TURN candidate pair will be prioritized since it's
2097 // "probably writable".
2098 EXPECT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr, kShortTimeout);
2099 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
2100 EXPECT_EQ(RELAY_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
2101 // Also expect that the channel instantly indicates that it's writable since
2102 // it has a TURN-TURN pair.
2103 EXPECT_TRUE(ep1_ch1()->writable());
2104 EXPECT_TRUE(GetEndpoint(0)->ready_to_send_);
2105 // Also make sure we can immediately send packets.
2106 const char* data = "test";
2107 int len = static_cast<int>(strlen(data));
2108 EXPECT_EQ(len, SendData(ep1_ch1(), data, len));
2109 // Prevent pending messages to access endpoints after their destruction.
2110 DestroyChannels();
2111 }
2112
2113 // Test that a TURN/peer reflexive candidate pair is also presumed writable.
TEST_F(P2PTransportChannelTest,TurnToPrflxPresumedWritable)2114 TEST_F(P2PTransportChannelTest, TurnToPrflxPresumedWritable) {
2115 rtc::ScopedFakeClock fake_clock;
2116
2117 // We need to add artificial network delay to verify that the connection
2118 // is presumed writable before it's actually writable. Without this delay
2119 // it would become writable instantly.
2120 virtual_socket_server()->set_delay_mean(50);
2121 virtual_socket_server()->UpdateDelayDistribution();
2122
2123 ConfigureEndpoints(NAT_SYMMETRIC, NAT_SYMMETRIC, kDefaultPortAllocatorFlags,
2124 kDefaultPortAllocatorFlags);
2125 // We want the remote TURN candidate to show up as prflx. To do this we need
2126 // to configure the server to accept packets from an address we haven't
2127 // explicitly installed permission for.
2128 test_turn_server()->set_enable_permission_checks(false);
2129 IceConfig config;
2130 config.presume_writable_when_fully_relayed = true;
2131 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
2132 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
2133 GetEndpoint(1)->cd1_.ch_.reset(CreateChannel(
2134 1, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[1], kIceParams[0]));
2135 ep1_ch1()->SetIceConfig(config);
2136 ep2_ch1()->SetIceConfig(config);
2137 // Don't signal candidates from channel 2, so that channel 1 sees the TURN
2138 // candidate as peer reflexive.
2139 PauseCandidates(1);
2140 ep1_ch1()->MaybeStartGathering();
2141 ep2_ch1()->MaybeStartGathering();
2142
2143 // Wait for the TURN<->prflx connection.
2144 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->receiving() && ep1_ch1()->writable(),
2145 kShortTimeout, fake_clock);
2146 ASSERT_NE(nullptr, ep1_ch1()->selected_connection());
2147 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
2148 EXPECT_EQ(PRFLX_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
2149 // Make sure that at this point the connection is only presumed writable,
2150 // not fully writable.
2151 EXPECT_FALSE(ep1_ch1()->selected_connection()->writable());
2152
2153 // Now wait for it to actually become writable.
2154 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection()->writable(),
2155 kShortTimeout, fake_clock);
2156
2157 // Explitly destroy channels, before fake clock is destroyed.
2158 DestroyChannels();
2159 }
2160
2161 // Test that a presumed-writable TURN<->TURN connection is preferred above an
2162 // unreliable connection (one that has failed to be pinged for some time).
TEST_F(P2PTransportChannelTest,PresumedWritablePreferredOverUnreliable)2163 TEST_F(P2PTransportChannelTest, PresumedWritablePreferredOverUnreliable) {
2164 rtc::ScopedFakeClock fake_clock;
2165
2166 ConfigureEndpoints(NAT_SYMMETRIC, NAT_SYMMETRIC, kDefaultPortAllocatorFlags,
2167 kDefaultPortAllocatorFlags);
2168 IceConfig config;
2169 config.presume_writable_when_fully_relayed = true;
2170 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
2171 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
2172 GetEndpoint(1)->cd1_.ch_.reset(CreateChannel(
2173 1, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[1], kIceParams[0]));
2174 ep1_ch1()->SetIceConfig(config);
2175 ep2_ch1()->SetIceConfig(config);
2176 ep1_ch1()->MaybeStartGathering();
2177 ep2_ch1()->MaybeStartGathering();
2178 // Wait for initial connection as usual.
2179 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2180 kShortTimeout, fake_clock);
2181 const Connection* old_selected_connection = ep1_ch1()->selected_connection();
2182 // Destroy the second channel and wait for the current connection on the
2183 // first channel to become "unreliable", making it no longer writable.
2184 GetEndpoint(1)->cd1_.ch_.reset();
2185 EXPECT_TRUE_SIMULATED_WAIT(!ep1_ch1()->writable(), kDefaultTimeout,
2186 fake_clock);
2187 EXPECT_NE(nullptr, ep1_ch1()->selected_connection());
2188 // Add a remote TURN candidate. The first channel should still have a TURN
2189 // port available to make a TURN<->TURN pair that's presumed writable.
2190 ep1_ch1()->AddRemoteCandidate(
2191 CreateUdpCandidate(RELAY_PORT_TYPE, "2.2.2.2", 2, 0));
2192 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
2193 EXPECT_EQ(RELAY_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
2194 EXPECT_TRUE(ep1_ch1()->writable());
2195 EXPECT_TRUE(GetEndpoint(0)->ready_to_send_);
2196 EXPECT_NE(old_selected_connection, ep1_ch1()->selected_connection());
2197 // Explitly destroy channels, before fake clock is destroyed.
2198 DestroyChannels();
2199 }
2200
2201 // Ensure that "SignalReadyToSend" is fired as expected with a "presumed
2202 // writable" connection. Previously this did not work.
TEST_F(P2PTransportChannelTest,SignalReadyToSendWithPresumedWritable)2203 TEST_F(P2PTransportChannelTest, SignalReadyToSendWithPresumedWritable) {
2204 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
2205 kDefaultPortAllocatorFlags);
2206 // Only test one endpoint, so we can ensure the connection doesn't receive a
2207 // binding response and advance beyond being "presumed" writable.
2208 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
2209 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
2210 IceConfig config;
2211 config.presume_writable_when_fully_relayed = true;
2212 ep1_ch1()->SetIceConfig(config);
2213 ep1_ch1()->MaybeStartGathering();
2214 EXPECT_EQ_WAIT(IceGatheringState::kIceGatheringComplete,
2215 ep1_ch1()->gathering_state(), kDefaultTimeout);
2216 ep1_ch1()->AddRemoteCandidate(
2217 CreateUdpCandidate(RELAY_PORT_TYPE, "1.1.1.1", 1, 0));
2218 // Sanity checking the type of the connection.
2219 EXPECT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr, kShortTimeout);
2220 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
2221 EXPECT_EQ(RELAY_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
2222
2223 // Tell the socket server to block packets (returning EWOULDBLOCK).
2224 virtual_socket_server()->SetSendingBlocked(true);
2225 const char* data = "test";
2226 int len = static_cast<int>(strlen(data));
2227 EXPECT_EQ(-1, SendData(ep1_ch1(), data, len));
2228
2229 // Reset |ready_to_send_| flag, which is set to true if the event fires as it
2230 // should.
2231 GetEndpoint(0)->ready_to_send_ = false;
2232 virtual_socket_server()->SetSendingBlocked(false);
2233 EXPECT_TRUE(GetEndpoint(0)->ready_to_send_);
2234 EXPECT_EQ(len, SendData(ep1_ch1(), data, len));
2235 DestroyChannels();
2236 }
2237
2238 // Test that role conflict error responses are sent as expected when receiving a
2239 // ping from an unknown address over a TURN connection. Regression test for
2240 // crbug.com/webrtc/9034.
TEST_F(P2PTransportChannelTest,TurnToPrflxSelectedAfterResolvingIceControllingRoleConflict)2241 TEST_F(P2PTransportChannelTest,
2242 TurnToPrflxSelectedAfterResolvingIceControllingRoleConflict) {
2243 rtc::ScopedFakeClock clock;
2244 // Gather only relay candidates.
2245 ConfigureEndpoints(NAT_SYMMETRIC, NAT_SYMMETRIC,
2246 kDefaultPortAllocatorFlags | PORTALLOCATOR_DISABLE_UDP |
2247 PORTALLOCATOR_DISABLE_STUN | PORTALLOCATOR_DISABLE_TCP,
2248 kDefaultPortAllocatorFlags | PORTALLOCATOR_DISABLE_UDP |
2249 PORTALLOCATOR_DISABLE_STUN |
2250 PORTALLOCATOR_DISABLE_TCP);
2251 // With conflicting ICE roles, endpoint 1 has the higher tie breaker and will
2252 // send a binding error response.
2253 SetIceRole(0, ICEROLE_CONTROLLING);
2254 SetIceTiebreaker(0, kHighTiebreaker);
2255 SetIceRole(1, ICEROLE_CONTROLLING);
2256 SetIceTiebreaker(1, kLowTiebreaker);
2257 // We want the remote TURN candidate to show up as prflx. To do this we need
2258 // to configure the server to accept packets from an address we haven't
2259 // explicitly installed permission for.
2260 test_turn_server()->set_enable_permission_checks(false);
2261 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
2262 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
2263 GetEndpoint(1)->cd1_.ch_.reset(CreateChannel(
2264 1, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[1], kIceParams[0]));
2265 // Don't signal candidates from channel 2, so that channel 1 sees the TURN
2266 // candidate as peer reflexive.
2267 PauseCandidates(1);
2268 ep1_ch1()->MaybeStartGathering();
2269 ep2_ch1()->MaybeStartGathering();
2270
2271 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->receiving() && ep1_ch1()->writable(),
2272 kMediumTimeout, clock);
2273
2274 ASSERT_NE(nullptr, ep1_ch1()->selected_connection());
2275
2276 EXPECT_EQ(RELAY_PORT_TYPE, LocalCandidate(ep1_ch1())->type());
2277 EXPECT_EQ(PRFLX_PORT_TYPE, RemoteCandidate(ep1_ch1())->type());
2278
2279 DestroyChannels();
2280 }
2281
2282 // Test that the writability can be established with the piggyback
2283 // acknowledgement in the connectivity check from the remote peer.
TEST_F(P2PTransportChannelTest,CanConnectWithPiggybackCheckAcknowledgementWhenCheckResponseBlocked)2284 TEST_F(P2PTransportChannelTest,
2285 CanConnectWithPiggybackCheckAcknowledgementWhenCheckResponseBlocked) {
2286 webrtc::test::ScopedFieldTrials field_trials(
2287 "WebRTC-PiggybackIceCheckAcknowledgement/Enabled/");
2288 rtc::ScopedFakeClock clock;
2289 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
2290 IceConfig ep1_config;
2291 IceConfig ep2_config = CreateIceConfig(1000, GATHER_CONTINUALLY);
2292 // Let ep2 be tolerable of the loss of connectivity checks, so that it keeps
2293 // sending pings even after ep1 becomes unwritable as we configure the
2294 // firewall below.
2295 ep2_config.receiving_timeout = 30 * 1000;
2296 ep2_config.ice_unwritable_timeout = 30 * 1000;
2297 ep2_config.ice_unwritable_min_checks = 30;
2298 ep2_config.ice_inactive_timeout = 60 * 1000;
2299
2300 CreateChannels(ep1_config, ep2_config);
2301
2302 // Wait until both sides become writable for the first time.
2303 EXPECT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2304 kDefaultTimeout, clock);
2305 // Block the ingress traffic to ep1 so that there is no check response from
2306 // ep2.
2307 ASSERT_NE(nullptr, LocalCandidate(ep1_ch1()));
2308 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_IN,
2309 LocalCandidate(ep1_ch1())->address());
2310 // Wait until ep1 becomes unwritable. At the same time ep2 should be still
2311 // fine so that it will keep sending pings.
2312 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1() != nullptr && !ep1_ch1()->writable(),
2313 kDefaultTimeout, clock);
2314 EXPECT_TRUE(ep2_ch1() != nullptr && ep2_ch1()->writable());
2315 // Now let the pings from ep2 to flow but block any pings from ep1, so that
2316 // ep1 can only become writable again after receiving an incoming ping from
2317 // ep2 with piggyback acknowledgement of its previously sent pings. Note
2318 // though that ep1 should have stopped sending pings after becoming unwritable
2319 // in the current design.
2320 fw()->ClearRules();
2321 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_OUT,
2322 LocalCandidate(ep1_ch1())->address());
2323 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1() != nullptr && ep1_ch1()->writable(),
2324 kDefaultTimeout, clock);
2325 DestroyChannels();
2326 }
2327
2328 // Test what happens when we have 2 users behind the same NAT. This can lead
2329 // to interesting behavior because the STUN server will only give out the
2330 // address of the outermost NAT.
2331 class P2PTransportChannelSameNatTest : public P2PTransportChannelTestBase {
2332 protected:
ConfigureEndpoints(Config nat_type,Config config1,Config config2)2333 void ConfigureEndpoints(Config nat_type, Config config1, Config config2) {
2334 RTC_CHECK_GE(nat_type, NAT_FULL_CONE);
2335 RTC_CHECK_LE(nat_type, NAT_SYMMETRIC);
2336 rtc::NATSocketServer::Translator* outer_nat = nat()->AddTranslator(
2337 kPublicAddrs[0], kNatAddrs[0],
2338 static_cast<rtc::NATType>(nat_type - NAT_FULL_CONE));
2339 ConfigureEndpoint(outer_nat, 0, config1);
2340 ConfigureEndpoint(outer_nat, 1, config2);
2341 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
2342 }
ConfigureEndpoint(rtc::NATSocketServer::Translator * nat,int endpoint,Config config)2343 void ConfigureEndpoint(rtc::NATSocketServer::Translator* nat,
2344 int endpoint,
2345 Config config) {
2346 RTC_CHECK(config <= NAT_SYMMETRIC);
2347 if (config == OPEN) {
2348 AddAddress(endpoint, kPrivateAddrs[endpoint]);
2349 nat->AddClient(kPrivateAddrs[endpoint]);
2350 } else {
2351 AddAddress(endpoint, kCascadedPrivateAddrs[endpoint]);
2352 nat->AddTranslator(kPrivateAddrs[endpoint], kCascadedNatAddrs[endpoint],
2353 static_cast<rtc::NATType>(config - NAT_FULL_CONE))
2354 ->AddClient(kCascadedPrivateAddrs[endpoint]);
2355 }
2356 }
2357 };
2358
TEST_F(P2PTransportChannelSameNatTest,TestConesBehindSameCone)2359 TEST_F(P2PTransportChannelSameNatTest, TestConesBehindSameCone) {
2360 ConfigureEndpoints(NAT_FULL_CONE, NAT_FULL_CONE, NAT_FULL_CONE);
2361 Test(
2362 P2PTransportChannelTestBase::Result("prflx", "udp", "stun", "udp", 1000));
2363 }
2364
2365 // Test what happens when we have multiple available pathways.
2366 // In the future we will try different RTTs and configs for the different
2367 // interfaces, so that we can simulate a user with Ethernet and VPN networks.
2368 class P2PTransportChannelMultihomedTest : public P2PTransportChannelTestBase {
2369 public:
GetConnectionWithRemoteAddress(P2PTransportChannel * channel,const SocketAddress & address)2370 const Connection* GetConnectionWithRemoteAddress(
2371 P2PTransportChannel* channel,
2372 const SocketAddress& address) {
2373 for (Connection* conn : channel->connections()) {
2374 if (conn->remote_candidate().address().EqualIPs(address)) {
2375 return conn;
2376 }
2377 }
2378 return nullptr;
2379 }
2380
GetConnectionWithLocalAddress(P2PTransportChannel * channel,const SocketAddress & address)2381 Connection* GetConnectionWithLocalAddress(P2PTransportChannel* channel,
2382 const SocketAddress& address) {
2383 for (Connection* conn : channel->connections()) {
2384 if (conn->local_candidate().address().EqualIPs(address)) {
2385 return conn;
2386 }
2387 }
2388 return nullptr;
2389 }
2390
GetConnection(P2PTransportChannel * channel,const SocketAddress & local,const SocketAddress & remote)2391 Connection* GetConnection(P2PTransportChannel* channel,
2392 const SocketAddress& local,
2393 const SocketAddress& remote) {
2394 for (Connection* conn : channel->connections()) {
2395 if (conn->local_candidate().address().EqualIPs(local) &&
2396 conn->remote_candidate().address().EqualIPs(remote)) {
2397 return conn;
2398 }
2399 }
2400 return nullptr;
2401 }
2402
DestroyAllButBestConnection(P2PTransportChannel * channel)2403 void DestroyAllButBestConnection(P2PTransportChannel* channel) {
2404 const Connection* selected_connection = channel->selected_connection();
2405 for (Connection* conn : channel->connections()) {
2406 if (conn != selected_connection) {
2407 conn->Destroy();
2408 }
2409 }
2410 }
2411 };
2412
2413 // Test that we can establish connectivity when both peers are multihomed.
TEST_F(P2PTransportChannelMultihomedTest,TestBasic)2414 TEST_F(P2PTransportChannelMultihomedTest, TestBasic) {
2415 AddAddress(0, kPublicAddrs[0]);
2416 AddAddress(0, kAlternateAddrs[0]);
2417 AddAddress(1, kPublicAddrs[1]);
2418 AddAddress(1, kAlternateAddrs[1]);
2419 Test(kLocalUdpToLocalUdp);
2420 }
2421
2422 // Test that we can quickly switch links if an interface goes down.
2423 // The controlled side has two interfaces and one will die.
TEST_F(P2PTransportChannelMultihomedTest,TestFailoverControlledSide)2424 TEST_F(P2PTransportChannelMultihomedTest, TestFailoverControlledSide) {
2425 rtc::ScopedFakeClock clock;
2426 AddAddress(0, kPublicAddrs[0]);
2427 // Simulate failing over from Wi-Fi to cell interface.
2428 AddAddress(1, kPublicAddrs[1], "eth0", rtc::ADAPTER_TYPE_WIFI);
2429 AddAddress(1, kAlternateAddrs[1], "wlan0", rtc::ADAPTER_TYPE_CELLULAR);
2430
2431 // Use only local ports for simplicity.
2432 SetAllocatorFlags(0, kOnlyLocalPorts);
2433 SetAllocatorFlags(1, kOnlyLocalPorts);
2434
2435 // Make the receiving timeout shorter for testing.
2436 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
2437 // Create channels and let them go writable, as usual.
2438 CreateChannels(config, config);
2439
2440 EXPECT_TRUE_SIMULATED_WAIT(
2441 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
2442 kPublicAddrs[1]),
2443 kMediumTimeout, clock);
2444
2445 // Blackhole any traffic to or from the public addrs.
2446 RTC_LOG(LS_INFO) << "Failing over...";
2447 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[1]);
2448 // The selected connections may switch, so keep references to them.
2449 const Connection* selected_connection1 = ep1_ch1()->selected_connection();
2450 // We should detect loss of receiving within 1 second or so.
2451 EXPECT_TRUE_SIMULATED_WAIT(!selected_connection1->receiving(), kMediumTimeout,
2452 clock);
2453
2454 // We should switch over to use the alternate addr on both sides
2455 // when we are not receiving.
2456 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection()->receiving() &&
2457 ep2_ch1()->selected_connection()->receiving(),
2458 kMediumTimeout, clock);
2459 EXPECT_TRUE(LocalCandidate(ep1_ch1())->address().EqualIPs(kPublicAddrs[0]));
2460 EXPECT_TRUE(
2461 RemoteCandidate(ep1_ch1())->address().EqualIPs(kAlternateAddrs[1]));
2462 EXPECT_TRUE(
2463 LocalCandidate(ep2_ch1())->address().EqualIPs(kAlternateAddrs[1]));
2464
2465 DestroyChannels();
2466 }
2467
2468 // Test that we can quickly switch links if an interface goes down.
2469 // The controlling side has two interfaces and one will die.
TEST_F(P2PTransportChannelMultihomedTest,TestFailoverControllingSide)2470 TEST_F(P2PTransportChannelMultihomedTest, TestFailoverControllingSide) {
2471 rtc::ScopedFakeClock clock;
2472 // Simulate failing over from Wi-Fi to cell interface.
2473 AddAddress(0, kPublicAddrs[0], "eth0", rtc::ADAPTER_TYPE_WIFI);
2474 AddAddress(0, kAlternateAddrs[0], "wlan0", rtc::ADAPTER_TYPE_CELLULAR);
2475 AddAddress(1, kPublicAddrs[1]);
2476
2477 // Use only local ports for simplicity.
2478 SetAllocatorFlags(0, kOnlyLocalPorts);
2479 SetAllocatorFlags(1, kOnlyLocalPorts);
2480
2481 // Make the receiving timeout shorter for testing.
2482 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
2483 // Create channels and let them go writable, as usual.
2484 CreateChannels(config, config);
2485 EXPECT_TRUE_SIMULATED_WAIT(
2486 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
2487 kPublicAddrs[1]),
2488 kMediumTimeout, clock);
2489
2490 // Blackhole any traffic to or from the public addrs.
2491 RTC_LOG(LS_INFO) << "Failing over...";
2492 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[0]);
2493
2494 // We should detect loss of receiving within 1 second or so.
2495 // We should switch over to use the alternate addr on both sides
2496 // when we are not receiving.
2497 EXPECT_TRUE_SIMULATED_WAIT(
2498 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kAlternateAddrs[0],
2499 kPublicAddrs[1]),
2500 kMediumTimeout, clock);
2501
2502 DestroyChannels();
2503 }
2504
2505 // Tests that we can quickly switch links if an interface goes down when
2506 // there are many connections.
TEST_F(P2PTransportChannelMultihomedTest,TestFailoverWithManyConnections)2507 TEST_F(P2PTransportChannelMultihomedTest, TestFailoverWithManyConnections) {
2508 rtc::ScopedFakeClock clock;
2509 test_turn_server()->AddInternalSocket(kTurnTcpIntAddr, PROTO_TCP);
2510 RelayServerConfig turn_server;
2511 turn_server.credentials = kRelayCredentials;
2512 turn_server.ports.push_back(ProtocolAddress(kTurnTcpIntAddr, PROTO_TCP));
2513 GetAllocator(0)->AddTurnServer(turn_server);
2514 GetAllocator(1)->AddTurnServer(turn_server);
2515 // Enable IPv6
2516 SetAllocatorFlags(
2517 0, PORTALLOCATOR_ENABLE_IPV6 | PORTALLOCATOR_ENABLE_IPV6_ON_WIFI);
2518 SetAllocatorFlags(
2519 1, PORTALLOCATOR_ENABLE_IPV6 | PORTALLOCATOR_ENABLE_IPV6_ON_WIFI);
2520 SetAllocationStepDelay(0, kMinimumStepDelay);
2521 SetAllocationStepDelay(1, kMinimumStepDelay);
2522
2523 auto& wifi = kPublicAddrs;
2524 auto& cellular = kAlternateAddrs;
2525 auto& wifiIpv6 = kIPv6PublicAddrs;
2526 auto& cellularIpv6 = kIPv6AlternateAddrs;
2527 AddAddress(0, wifi[0], "wifi0", rtc::ADAPTER_TYPE_WIFI);
2528 AddAddress(0, wifiIpv6[0], "wifi0", rtc::ADAPTER_TYPE_WIFI);
2529 AddAddress(0, cellular[0], "cellular0", rtc::ADAPTER_TYPE_CELLULAR);
2530 AddAddress(0, cellularIpv6[0], "cellular0", rtc::ADAPTER_TYPE_CELLULAR);
2531 AddAddress(1, wifi[1], "wifi1", rtc::ADAPTER_TYPE_WIFI);
2532 AddAddress(1, wifiIpv6[1], "wifi1", rtc::ADAPTER_TYPE_WIFI);
2533 AddAddress(1, cellular[1], "cellular1", rtc::ADAPTER_TYPE_CELLULAR);
2534 AddAddress(1, cellularIpv6[1], "cellular1", rtc::ADAPTER_TYPE_CELLULAR);
2535
2536 // Set smaller delay on the TCP TURN server so that TCP TURN candidates
2537 // will be created in time.
2538 virtual_socket_server()->SetDelayOnAddress(kTurnTcpIntAddr, 1);
2539 virtual_socket_server()->SetDelayOnAddress(kTurnUdpExtAddr, 1);
2540 virtual_socket_server()->set_delay_mean(500);
2541 virtual_socket_server()->UpdateDelayDistribution();
2542
2543 // Make the receiving timeout shorter for testing.
2544 IceConfig config = CreateIceConfig(1000, GATHER_CONTINUALLY);
2545 // Create channels and let them go writable, as usual.
2546 CreateChannels(config, config, true /* ice_renomination */);
2547 EXPECT_TRUE_SIMULATED_WAIT(
2548 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), wifiIpv6[0],
2549 wifiIpv6[1]),
2550 kMediumTimeout, clock);
2551
2552 // Blackhole any traffic to or from the wifi on endpoint 1.
2553 RTC_LOG(LS_INFO) << "Failing over...";
2554 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, wifi[0]);
2555 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, wifiIpv6[0]);
2556
2557 // The selected connections may switch, so keep references to them.
2558 const Connection* selected_connection1 = ep1_ch1()->selected_connection();
2559 const Connection* selected_connection2 = ep2_ch1()->selected_connection();
2560 EXPECT_TRUE_SIMULATED_WAIT(
2561 !selected_connection1->receiving() && !selected_connection2->receiving(),
2562 kMediumTimeout, clock);
2563
2564 // Per-network best connections will be pinged at relatively higher rate when
2565 // the selected connection becomes not receiving.
2566 Connection* per_network_best_connection1 =
2567 GetConnection(ep1_ch1(), cellularIpv6[0], wifiIpv6[1]);
2568 ASSERT_NE(nullptr, per_network_best_connection1);
2569 int64_t last_ping_sent1 = per_network_best_connection1->last_ping_sent();
2570 int num_pings_sent1 = per_network_best_connection1->num_pings_sent();
2571 EXPECT_TRUE_SIMULATED_WAIT(
2572 num_pings_sent1 < per_network_best_connection1->num_pings_sent(),
2573 kMediumTimeout, clock);
2574 ASSERT_GT(per_network_best_connection1->num_pings_sent() - num_pings_sent1,
2575 0);
2576 int64_t ping_interval1 =
2577 (per_network_best_connection1->last_ping_sent() - last_ping_sent1) /
2578 (per_network_best_connection1->num_pings_sent() - num_pings_sent1);
2579 constexpr int SCHEDULING_DELAY = 200;
2580 EXPECT_LT(
2581 ping_interval1,
2582 WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL + SCHEDULING_DELAY);
2583
2584 // It should switch over to use the cellular IPv6 addr on endpoint 1 before
2585 // it timed out on writing.
2586 EXPECT_TRUE_SIMULATED_WAIT(
2587 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), cellularIpv6[0],
2588 wifiIpv6[1]),
2589 kMediumTimeout, clock);
2590
2591 DestroyChannels();
2592 }
2593
2594 // Test that when the controlling side switches the selected connection,
2595 // the nomination of the selected connection on the controlled side will
2596 // increase.
TEST_F(P2PTransportChannelMultihomedTest,TestIceRenomination)2597 TEST_F(P2PTransportChannelMultihomedTest, TestIceRenomination) {
2598 rtc::ScopedFakeClock clock;
2599 // Simulate failing over from Wi-Fi to cell interface.
2600 AddAddress(0, kPublicAddrs[0], "eth0", rtc::ADAPTER_TYPE_WIFI);
2601 AddAddress(0, kAlternateAddrs[0], "wlan0", rtc::ADAPTER_TYPE_CELLULAR);
2602 AddAddress(1, kPublicAddrs[1]);
2603
2604 // Use only local ports for simplicity.
2605 SetAllocatorFlags(0, kOnlyLocalPorts);
2606 SetAllocatorFlags(1, kOnlyLocalPorts);
2607
2608 // We want it to set the remote ICE parameters when creating channels.
2609 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
2610 // Make the receiving timeout shorter for testing.
2611 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
2612 // Create channels with ICE renomination and let them go writable as usual.
2613 CreateChannels(config, config, true);
2614 ASSERT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2615 kMediumTimeout, clock);
2616 EXPECT_TRUE_SIMULATED_WAIT(
2617 ep2_ch1()->selected_connection()->remote_nomination() > 0 &&
2618 ep1_ch1()->selected_connection()->acked_nomination() > 0,
2619 kDefaultTimeout, clock);
2620 const Connection* selected_connection1 = ep1_ch1()->selected_connection();
2621 Connection* selected_connection2 =
2622 const_cast<Connection*>(ep2_ch1()->selected_connection());
2623 uint32_t remote_nomination2 = selected_connection2->remote_nomination();
2624 // |selected_connection2| should not be nominated any more since the previous
2625 // nomination has been acknowledged.
2626 ConnectSignalNominated(selected_connection2);
2627 SIMULATED_WAIT(nominated(), kMediumTimeout, clock);
2628 EXPECT_FALSE(nominated());
2629
2630 // Blackhole any traffic to or from the public addrs.
2631 RTC_LOG(LS_INFO) << "Failing over...";
2632 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[0]);
2633
2634 // The selected connection on the controlling side should switch.
2635 EXPECT_TRUE_SIMULATED_WAIT(
2636 ep1_ch1()->selected_connection() != selected_connection1, kMediumTimeout,
2637 clock);
2638 // The connection on the controlled side should be nominated again
2639 // and have an increased nomination.
2640 EXPECT_TRUE_SIMULATED_WAIT(
2641 ep2_ch1()->selected_connection()->remote_nomination() >
2642 remote_nomination2,
2643 kDefaultTimeout, clock);
2644
2645 DestroyChannels();
2646 }
2647
2648 // Test that if an interface fails temporarily and then recovers quickly,
2649 // the selected connection will not switch.
2650 // The case that it will switch over to the backup connection if the selected
2651 // connection does not recover after enough time is covered in
2652 // TestFailoverControlledSide and TestFailoverControllingSide.
TEST_F(P2PTransportChannelMultihomedTest,TestConnectionSwitchDampeningControlledSide)2653 TEST_F(P2PTransportChannelMultihomedTest,
2654 TestConnectionSwitchDampeningControlledSide) {
2655 rtc::ScopedFakeClock clock;
2656 AddAddress(0, kPublicAddrs[0]);
2657 // Simulate failing over from Wi-Fi to cell interface.
2658 AddAddress(1, kPublicAddrs[1], "eth0", rtc::ADAPTER_TYPE_WIFI);
2659 AddAddress(1, kAlternateAddrs[1], "wlan0", rtc::ADAPTER_TYPE_CELLULAR);
2660
2661 // Use only local ports for simplicity.
2662 SetAllocatorFlags(0, kOnlyLocalPorts);
2663 SetAllocatorFlags(1, kOnlyLocalPorts);
2664
2665 // Create channels and let them go writable, as usual.
2666 CreateChannels();
2667
2668 EXPECT_TRUE_SIMULATED_WAIT(
2669 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
2670 kPublicAddrs[1]),
2671 kMediumTimeout, clock);
2672
2673 // Make the receiving timeout shorter for testing.
2674 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
2675 ep1_ch1()->SetIceConfig(config);
2676 ep2_ch1()->SetIceConfig(config);
2677 reset_selected_candidate_pair_switches();
2678
2679 // Blackhole any traffic to or from the public addrs.
2680 RTC_LOG(LS_INFO) << "Failing over...";
2681 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[1]);
2682
2683 // The selected connections may switch, so keep references to them.
2684 const Connection* selected_connection1 = ep1_ch1()->selected_connection();
2685 // We should detect loss of receiving within 1 second or so.
2686 EXPECT_TRUE_SIMULATED_WAIT(!selected_connection1->receiving(), kMediumTimeout,
2687 clock);
2688 // After a short while, the link recovers itself.
2689 SIMULATED_WAIT(false, 10, clock);
2690 fw()->ClearRules();
2691
2692 // We should remain on the public address on both sides and no connection
2693 // switches should have happened.
2694 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection()->receiving() &&
2695 ep2_ch1()->selected_connection()->receiving(),
2696 kMediumTimeout, clock);
2697 EXPECT_TRUE(RemoteCandidate(ep1_ch1())->address().EqualIPs(kPublicAddrs[1]));
2698 EXPECT_TRUE(LocalCandidate(ep2_ch1())->address().EqualIPs(kPublicAddrs[1]));
2699 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
2700
2701 DestroyChannels();
2702 }
2703
2704 // Test that if an interface fails temporarily and then recovers quickly,
2705 // the selected connection will not switch.
TEST_F(P2PTransportChannelMultihomedTest,TestConnectionSwitchDampeningControllingSide)2706 TEST_F(P2PTransportChannelMultihomedTest,
2707 TestConnectionSwitchDampeningControllingSide) {
2708 rtc::ScopedFakeClock clock;
2709 // Simulate failing over from Wi-Fi to cell interface.
2710 AddAddress(0, kPublicAddrs[0], "eth0", rtc::ADAPTER_TYPE_WIFI);
2711 AddAddress(0, kAlternateAddrs[0], "wlan0", rtc::ADAPTER_TYPE_CELLULAR);
2712 AddAddress(1, kPublicAddrs[1]);
2713
2714 // Use only local ports for simplicity.
2715 SetAllocatorFlags(0, kOnlyLocalPorts);
2716 SetAllocatorFlags(1, kOnlyLocalPorts);
2717
2718 // Create channels and let them go writable, as usual.
2719 CreateChannels();
2720 EXPECT_TRUE_SIMULATED_WAIT(
2721 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
2722 kPublicAddrs[1]),
2723 kMediumTimeout, clock);
2724
2725 // Make the receiving timeout shorter for testing.
2726 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
2727 ep1_ch1()->SetIceConfig(config);
2728 ep2_ch1()->SetIceConfig(config);
2729 reset_selected_candidate_pair_switches();
2730
2731 // Blackhole any traffic to or from the public addrs.
2732 RTC_LOG(LS_INFO) << "Failing over...";
2733 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, kPublicAddrs[0]);
2734 // The selected connections may switch, so keep references to them.
2735 const Connection* selected_connection1 = ep1_ch1()->selected_connection();
2736 // We should detect loss of receiving within 1 second or so.
2737 EXPECT_TRUE_SIMULATED_WAIT(!selected_connection1->receiving(), kMediumTimeout,
2738 clock);
2739 // The link recovers after a short while.
2740 SIMULATED_WAIT(false, 10, clock);
2741 fw()->ClearRules();
2742
2743 // We should not switch to the alternate addr on both sides because of the
2744 // dampening.
2745 EXPECT_TRUE_SIMULATED_WAIT(
2746 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
2747 kPublicAddrs[1]),
2748 kMediumTimeout, clock);
2749 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
2750 DestroyChannels();
2751 }
2752
2753 // Tests that if the remote side's network failed, it won't cause the local
2754 // side to switch connections and networks.
TEST_F(P2PTransportChannelMultihomedTest,TestRemoteFailover)2755 TEST_F(P2PTransportChannelMultihomedTest, TestRemoteFailover) {
2756 rtc::ScopedFakeClock clock;
2757 // The interface names are chosen so that |cellular| would have higher
2758 // candidate priority and higher cost.
2759 auto& wifi = kPublicAddrs;
2760 auto& cellular = kAlternateAddrs;
2761 AddAddress(0, wifi[0], "wifi0", rtc::ADAPTER_TYPE_WIFI);
2762 AddAddress(0, cellular[0], "cellular0", rtc::ADAPTER_TYPE_CELLULAR);
2763 AddAddress(1, wifi[1], "wifi0", rtc::ADAPTER_TYPE_WIFI);
2764
2765 // Use only local ports for simplicity.
2766 SetAllocatorFlags(0, kOnlyLocalPorts);
2767 SetAllocatorFlags(1, kOnlyLocalPorts);
2768 // Create channels and let them go writable, as usual.
2769 CreateChannels();
2770 // Make the receiving timeout shorter for testing.
2771 // Set the backup connection ping interval to 25s.
2772 IceConfig config = CreateIceConfig(1000, GATHER_ONCE, 25000);
2773 // Ping the best connection more frequently since we don't have traffic.
2774 config.stable_writable_connection_ping_interval = 900;
2775 ep1_ch1()->SetIceConfig(config);
2776 ep2_ch1()->SetIceConfig(config);
2777 // Need to wait to make sure the connections on both networks are writable.
2778 EXPECT_TRUE_SIMULATED_WAIT(
2779 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), wifi[0], wifi[1]),
2780 kDefaultTimeout, clock);
2781 Connection* backup_conn =
2782 GetConnectionWithLocalAddress(ep1_ch1(), cellular[0]);
2783 ASSERT_NE(nullptr, backup_conn);
2784 // After a short while, the backup connection will be writable but not
2785 // receiving because backup connection is pinged at a slower rate.
2786 EXPECT_TRUE_SIMULATED_WAIT(
2787 backup_conn->writable() && !backup_conn->receiving(), kDefaultTimeout,
2788 clock);
2789 reset_selected_candidate_pair_switches();
2790 // Blackhole any traffic to or from the remote WiFi networks.
2791 RTC_LOG(LS_INFO) << "Failing over...";
2792 fw()->AddRule(false, rtc::FP_ANY, rtc::FD_ANY, wifi[1]);
2793
2794 int num_switches = 0;
2795 SIMULATED_WAIT((num_switches = reset_selected_candidate_pair_switches()) > 0,
2796 20000, clock);
2797 EXPECT_EQ(0, num_switches);
2798 DestroyChannels();
2799 }
2800
2801 // Tests that a Wifi-Wifi connection has the highest precedence.
TEST_F(P2PTransportChannelMultihomedTest,TestPreferWifiToWifiConnection)2802 TEST_F(P2PTransportChannelMultihomedTest, TestPreferWifiToWifiConnection) {
2803 // The interface names are chosen so that |cellular| would have higher
2804 // candidate priority if it is not for the network type.
2805 auto& wifi = kAlternateAddrs;
2806 auto& cellular = kPublicAddrs;
2807 AddAddress(0, wifi[0], "test0", rtc::ADAPTER_TYPE_WIFI);
2808 AddAddress(0, cellular[0], "test1", rtc::ADAPTER_TYPE_CELLULAR);
2809 AddAddress(1, wifi[1], "test0", rtc::ADAPTER_TYPE_WIFI);
2810 AddAddress(1, cellular[1], "test1", rtc::ADAPTER_TYPE_CELLULAR);
2811
2812 // Use only local ports for simplicity.
2813 SetAllocatorFlags(0, kOnlyLocalPorts);
2814 SetAllocatorFlags(1, kOnlyLocalPorts);
2815
2816 // Create channels and let them go writable, as usual.
2817 CreateChannels();
2818
2819 EXPECT_TRUE_WAIT_MARGIN(CheckConnected(ep1_ch1(), ep2_ch1()), 1000, 1000);
2820 // Need to wait to make sure the connections on both networks are writable.
2821 EXPECT_TRUE_WAIT(
2822 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), wifi[0], wifi[1]),
2823 1000);
2824 DestroyChannels();
2825 }
2826
2827 // Tests that a Wifi-Cellular connection has higher precedence than
2828 // a Cellular-Cellular connection.
TEST_F(P2PTransportChannelMultihomedTest,TestPreferWifiOverCellularNetwork)2829 TEST_F(P2PTransportChannelMultihomedTest, TestPreferWifiOverCellularNetwork) {
2830 // The interface names are chosen so that |cellular| would have higher
2831 // candidate priority if it is not for the network type.
2832 auto& wifi = kAlternateAddrs;
2833 auto& cellular = kPublicAddrs;
2834 AddAddress(0, cellular[0], "test1", rtc::ADAPTER_TYPE_CELLULAR);
2835 AddAddress(1, wifi[1], "test0", rtc::ADAPTER_TYPE_WIFI);
2836 AddAddress(1, cellular[1], "test1", rtc::ADAPTER_TYPE_CELLULAR);
2837
2838 // Use only local ports for simplicity.
2839 SetAllocatorFlags(0, kOnlyLocalPorts);
2840 SetAllocatorFlags(1, kOnlyLocalPorts);
2841
2842 // Create channels and let them go writable, as usual.
2843 CreateChannels();
2844
2845 EXPECT_TRUE_WAIT_MARGIN(CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(),
2846 cellular[0], wifi[1]),
2847 1000, 1000);
2848 DestroyChannels();
2849 }
2850
2851 // Test that the backup connection is pinged at a rate no faster than
2852 // what was configured.
TEST_F(P2PTransportChannelMultihomedTest,TestPingBackupConnectionRate)2853 TEST_F(P2PTransportChannelMultihomedTest, TestPingBackupConnectionRate) {
2854 AddAddress(0, kPublicAddrs[0]);
2855 // Adding alternate address will make sure |kPublicAddrs| has the higher
2856 // priority than others. This is due to FakeNetwork::AddInterface method.
2857 AddAddress(1, kAlternateAddrs[1]);
2858 AddAddress(1, kPublicAddrs[1]);
2859
2860 // Use only local ports for simplicity.
2861 SetAllocatorFlags(0, kOnlyLocalPorts);
2862 SetAllocatorFlags(1, kOnlyLocalPorts);
2863
2864 // Create channels and let them go writable, as usual.
2865 CreateChannels();
2866 EXPECT_TRUE_WAIT_MARGIN(CheckConnected(ep1_ch1(), ep2_ch1()), 1000, 1000);
2867 int backup_ping_interval = 2000;
2868 ep2_ch1()->SetIceConfig(
2869 CreateIceConfig(2000, GATHER_ONCE, backup_ping_interval));
2870 // After the state becomes COMPLETED, the backup connection will be pinged
2871 // once every |backup_ping_interval| milliseconds.
2872 ASSERT_TRUE_WAIT(ep2_ch1()->GetState() == IceTransportState::STATE_COMPLETED,
2873 1000);
2874 auto connections = ep2_ch1()->connections();
2875 ASSERT_EQ(2U, connections.size());
2876 Connection* backup_conn = connections[1];
2877 EXPECT_TRUE_WAIT(backup_conn->writable(), kMediumTimeout);
2878 int64_t last_ping_response_ms = backup_conn->last_ping_response_received();
2879 EXPECT_TRUE_WAIT(
2880 last_ping_response_ms < backup_conn->last_ping_response_received(),
2881 kDefaultTimeout);
2882 int time_elapsed =
2883 backup_conn->last_ping_response_received() - last_ping_response_ms;
2884 RTC_LOG(LS_INFO) << "Time elapsed: " << time_elapsed;
2885 EXPECT_GE(time_elapsed, backup_ping_interval);
2886
2887 DestroyChannels();
2888 }
2889
TEST_F(P2PTransportChannelMultihomedTest,TestGetState)2890 TEST_F(P2PTransportChannelMultihomedTest, TestGetState) {
2891 rtc::ScopedFakeClock clock;
2892 AddAddress(0, kAlternateAddrs[0]);
2893 AddAddress(0, kPublicAddrs[0]);
2894 AddAddress(1, kPublicAddrs[1]);
2895 // Create channels and let them go writable, as usual.
2896 CreateChannels();
2897
2898 // Both transport channels will reach STATE_COMPLETED quickly.
2899 EXPECT_EQ_SIMULATED_WAIT(IceTransportState::STATE_COMPLETED,
2900 ep1_ch1()->GetState(), kShortTimeout, clock);
2901 EXPECT_EQ_SIMULATED_WAIT(IceTransportState::STATE_COMPLETED,
2902 ep2_ch1()->GetState(), kShortTimeout, clock);
2903 DestroyChannels();
2904 }
2905
2906 // Tests that when a network interface becomes inactive, if Continual Gathering
2907 // policy is GATHER_CONTINUALLY, the ports associated with that network
2908 // will be removed from the port list of the channel, and the respective
2909 // remote candidates on the other participant will be removed eventually.
TEST_F(P2PTransportChannelMultihomedTest,TestNetworkBecomesInactive)2910 TEST_F(P2PTransportChannelMultihomedTest, TestNetworkBecomesInactive) {
2911 rtc::ScopedFakeClock clock;
2912 AddAddress(0, kPublicAddrs[0]);
2913 AddAddress(1, kPublicAddrs[1]);
2914 // Create channels and let them go writable, as usual.
2915 IceConfig ep1_config = CreateIceConfig(2000, GATHER_CONTINUALLY);
2916 IceConfig ep2_config = CreateIceConfig(2000, GATHER_ONCE);
2917 CreateChannels(ep1_config, ep2_config);
2918
2919 SetAllocatorFlags(0, kOnlyLocalPorts);
2920 SetAllocatorFlags(1, kOnlyLocalPorts);
2921 ASSERT_TRUE_SIMULATED_WAIT(CheckConnected(ep1_ch1(), ep2_ch1()),
2922 kDefaultTimeout, clock);
2923 // More than one port has been created.
2924 EXPECT_LE(1U, ep1_ch1()->ports().size());
2925 // Endpoint 1 enabled continual gathering; the port will be removed
2926 // when the interface is removed.
2927 RemoveAddress(0, kPublicAddrs[0]);
2928 EXPECT_TRUE(ep1_ch1()->ports().empty());
2929 // The remote candidates will be removed eventually.
2930 EXPECT_TRUE_SIMULATED_WAIT(ep2_ch1()->remote_candidates().empty(), 1000,
2931 clock);
2932
2933 size_t num_ports = ep2_ch1()->ports().size();
2934 EXPECT_LE(1U, num_ports);
2935 size_t num_remote_candidates = ep1_ch1()->remote_candidates().size();
2936 // Endpoint 2 did not enable continual gathering; the local port will still be
2937 // removed when the interface is removed but the remote candidates on the
2938 // other participant will not be removed.
2939 RemoveAddress(1, kPublicAddrs[1]);
2940
2941 EXPECT_EQ_SIMULATED_WAIT(0U, ep2_ch1()->ports().size(), kDefaultTimeout,
2942 clock);
2943 SIMULATED_WAIT(0U == ep1_ch1()->remote_candidates().size(), 500, clock);
2944 EXPECT_EQ(num_remote_candidates, ep1_ch1()->remote_candidates().size());
2945
2946 DestroyChannels();
2947 }
2948
2949 // Tests that continual gathering will create new connections when a new
2950 // interface is added.
TEST_F(P2PTransportChannelMultihomedTest,TestContinualGatheringOnNewInterface)2951 TEST_F(P2PTransportChannelMultihomedTest,
2952 TestContinualGatheringOnNewInterface) {
2953 auto& wifi = kAlternateAddrs;
2954 auto& cellular = kPublicAddrs;
2955 AddAddress(0, wifi[0], "test_wifi0", rtc::ADAPTER_TYPE_WIFI);
2956 AddAddress(1, cellular[1], "test_cell1", rtc::ADAPTER_TYPE_CELLULAR);
2957 // Set continual gathering policy.
2958 IceConfig continual_gathering_config =
2959 CreateIceConfig(1000, GATHER_CONTINUALLY);
2960 CreateChannels(continual_gathering_config, continual_gathering_config);
2961 SetAllocatorFlags(0, kOnlyLocalPorts);
2962 SetAllocatorFlags(1, kOnlyLocalPorts);
2963 EXPECT_TRUE_WAIT_MARGIN(CheckConnected(ep1_ch1(), ep2_ch1()), kDefaultTimeout,
2964 kDefaultTimeout);
2965
2966 // Add a new wifi interface on end point 2. We should expect a new connection
2967 // to be created and the new one will be the best connection.
2968 AddAddress(1, wifi[1], "test_wifi1", rtc::ADAPTER_TYPE_WIFI);
2969 const Connection* conn;
2970 EXPECT_TRUE_WAIT((conn = ep1_ch1()->selected_connection()) != nullptr &&
2971 conn->remote_candidate().address().EqualIPs(wifi[1]),
2972 kDefaultTimeout);
2973 EXPECT_TRUE_WAIT((conn = ep2_ch1()->selected_connection()) != nullptr &&
2974 conn->local_candidate().address().EqualIPs(wifi[1]),
2975 kDefaultTimeout);
2976
2977 // Add a new cellular interface on end point 1, we should expect a new
2978 // backup connection created using this new interface.
2979 AddAddress(0, cellular[0], "test_cellular0", rtc::ADAPTER_TYPE_CELLULAR);
2980 EXPECT_TRUE_WAIT(
2981 ep1_ch1()->GetState() == IceTransportState::STATE_COMPLETED &&
2982 (conn = GetConnectionWithLocalAddress(ep1_ch1(), cellular[0])) !=
2983 nullptr &&
2984 conn != ep1_ch1()->selected_connection() && conn->writable(),
2985 kDefaultTimeout);
2986 EXPECT_TRUE_WAIT(
2987 ep2_ch1()->GetState() == IceTransportState::STATE_COMPLETED &&
2988 (conn = GetConnectionWithRemoteAddress(ep2_ch1(), cellular[0])) !=
2989 nullptr &&
2990 conn != ep2_ch1()->selected_connection() && conn->receiving(),
2991 kDefaultTimeout);
2992
2993 DestroyChannels();
2994 }
2995
2996 // Tests that we can switch links via continual gathering.
TEST_F(P2PTransportChannelMultihomedTest,TestSwitchLinksViaContinualGathering)2997 TEST_F(P2PTransportChannelMultihomedTest,
2998 TestSwitchLinksViaContinualGathering) {
2999 rtc::ScopedFakeClock clock;
3000 AddAddress(0, kPublicAddrs[0]);
3001 AddAddress(1, kPublicAddrs[1]);
3002 // Use only local ports for simplicity.
3003 SetAllocatorFlags(0, kOnlyLocalPorts);
3004 SetAllocatorFlags(1, kOnlyLocalPorts);
3005
3006 // Set continual gathering policy.
3007 IceConfig continual_gathering_config =
3008 CreateIceConfig(1000, GATHER_CONTINUALLY);
3009 // Create channels and let them go writable, as usual.
3010 CreateChannels(continual_gathering_config, continual_gathering_config);
3011 EXPECT_TRUE_SIMULATED_WAIT(
3012 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
3013 kPublicAddrs[1]),
3014 kMediumTimeout, clock);
3015
3016 // Add the new address first and then remove the other one.
3017 RTC_LOG(LS_INFO) << "Draining...";
3018 AddAddress(1, kAlternateAddrs[1]);
3019 RemoveAddress(1, kPublicAddrs[1]);
3020 // We should switch to use the alternate address after an exchange of pings.
3021 EXPECT_TRUE_SIMULATED_WAIT(
3022 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
3023 kAlternateAddrs[1]),
3024 kMediumTimeout, clock);
3025
3026 // Remove one address first and then add another address.
3027 RTC_LOG(LS_INFO) << "Draining again...";
3028 RemoveAddress(1, kAlternateAddrs[1]);
3029 AddAddress(1, kAlternateAddrs[0]);
3030 EXPECT_TRUE_SIMULATED_WAIT(
3031 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), kPublicAddrs[0],
3032 kAlternateAddrs[0]),
3033 kMediumTimeout, clock);
3034
3035 DestroyChannels();
3036 }
3037
3038 // Tests that the backup connection will be restored after it is destroyed.
TEST_F(P2PTransportChannelMultihomedTest,TestRestoreBackupConnection)3039 TEST_F(P2PTransportChannelMultihomedTest, TestRestoreBackupConnection) {
3040 rtc::ScopedFakeClock clock;
3041 auto& wifi = kAlternateAddrs;
3042 auto& cellular = kPublicAddrs;
3043 AddAddress(0, wifi[0], "test_wifi0", rtc::ADAPTER_TYPE_WIFI);
3044 AddAddress(0, cellular[0], "test_cell0", rtc::ADAPTER_TYPE_CELLULAR);
3045 AddAddress(1, wifi[1], "test_wifi1", rtc::ADAPTER_TYPE_WIFI);
3046 AddAddress(1, cellular[1], "test_cell1", rtc::ADAPTER_TYPE_CELLULAR);
3047 // Use only local ports for simplicity.
3048 SetAllocatorFlags(0, kOnlyLocalPorts);
3049 SetAllocatorFlags(1, kOnlyLocalPorts);
3050
3051 // Create channels and let them go writable, as usual.
3052 IceConfig config = CreateIceConfig(1000, GATHER_CONTINUALLY);
3053 config.regather_on_failed_networks_interval = 2000;
3054 CreateChannels(config, config);
3055 EXPECT_TRUE_SIMULATED_WAIT(
3056 CheckCandidatePairAndConnected(ep1_ch1(), ep2_ch1(), wifi[0], wifi[1]),
3057 kMediumTimeout, clock);
3058
3059 // Destroy all backup connections.
3060 DestroyAllButBestConnection(ep1_ch1());
3061 // Ensure the backup connection is removed first.
3062 EXPECT_TRUE_SIMULATED_WAIT(
3063 GetConnectionWithLocalAddress(ep1_ch1(), cellular[0]) == nullptr,
3064 kDefaultTimeout, clock);
3065 const Connection* conn;
3066 EXPECT_TRUE_SIMULATED_WAIT(
3067 (conn = GetConnectionWithLocalAddress(ep1_ch1(), cellular[0])) !=
3068 nullptr &&
3069 conn != ep1_ch1()->selected_connection() && conn->writable(),
3070 kDefaultTimeout, clock);
3071
3072 DestroyChannels();
3073 }
3074
3075 // A collection of tests which tests a single P2PTransportChannel by sending
3076 // pings.
3077 class P2PTransportChannelPingTest : public ::testing::Test,
3078 public sigslot::has_slots<> {
3079 public:
P2PTransportChannelPingTest()3080 P2PTransportChannelPingTest()
3081 : vss_(new rtc::VirtualSocketServer()), thread_(vss_.get()) {}
3082
3083 protected:
PrepareChannel(P2PTransportChannel * ch)3084 void PrepareChannel(P2PTransportChannel* ch) {
3085 ch->SetIceRole(ICEROLE_CONTROLLING);
3086 ch->SetIceParameters(kIceParams[0]);
3087 ch->SetRemoteIceParameters(kIceParams[1]);
3088 ch->SignalNetworkRouteChanged.connect(
3089 this, &P2PTransportChannelPingTest::OnNetworkRouteChanged);
3090 ch->SignalReadyToSend.connect(this,
3091 &P2PTransportChannelPingTest::OnReadyToSend);
3092 ch->SignalStateChanged.connect(
3093 this, &P2PTransportChannelPingTest::OnChannelStateChanged);
3094 ch->SignalCandidatePairChanged.connect(
3095 this, &P2PTransportChannelPingTest::OnCandidatePairChanged);
3096 }
3097
WaitForConnectionTo(P2PTransportChannel * ch,const std::string & ip,int port_num,rtc::ThreadProcessingFakeClock * clock=nullptr)3098 Connection* WaitForConnectionTo(
3099 P2PTransportChannel* ch,
3100 const std::string& ip,
3101 int port_num,
3102 rtc::ThreadProcessingFakeClock* clock = nullptr) {
3103 if (clock == nullptr) {
3104 EXPECT_TRUE_WAIT(GetConnectionTo(ch, ip, port_num) != nullptr,
3105 kMediumTimeout);
3106 } else {
3107 EXPECT_TRUE_SIMULATED_WAIT(GetConnectionTo(ch, ip, port_num) != nullptr,
3108 kMediumTimeout, *clock);
3109 }
3110 return GetConnectionTo(ch, ip, port_num);
3111 }
3112
GetPort(P2PTransportChannel * ch)3113 Port* GetPort(P2PTransportChannel* ch) {
3114 if (ch->ports().empty()) {
3115 return nullptr;
3116 }
3117 return static_cast<Port*>(ch->ports()[0]);
3118 }
3119
GetPrunedPort(P2PTransportChannel * ch)3120 Port* GetPrunedPort(P2PTransportChannel* ch) {
3121 if (ch->pruned_ports().empty()) {
3122 return nullptr;
3123 }
3124 return static_cast<Port*>(ch->pruned_ports()[0]);
3125 }
3126
GetConnectionTo(P2PTransportChannel * ch,const std::string & ip,int port_num)3127 Connection* GetConnectionTo(P2PTransportChannel* ch,
3128 const std::string& ip,
3129 int port_num) {
3130 Port* port = GetPort(ch);
3131 if (!port) {
3132 return nullptr;
3133 }
3134 return port->GetConnection(rtc::SocketAddress(ip, port_num));
3135 }
3136
FindNextPingableConnectionAndPingIt(P2PTransportChannel * ch)3137 Connection* FindNextPingableConnectionAndPingIt(P2PTransportChannel* ch) {
3138 Connection* conn = ch->FindNextPingableConnection();
3139 if (conn) {
3140 ch->MarkConnectionPinged(conn);
3141 }
3142 return conn;
3143 }
3144
SendData(IceTransportInternal * channel,const char * data,size_t len,int packet_id)3145 int SendData(IceTransportInternal* channel,
3146 const char* data,
3147 size_t len,
3148 int packet_id) {
3149 rtc::PacketOptions options;
3150 options.packet_id = packet_id;
3151 return channel->SendPacket(data, len, options, 0);
3152 }
3153
CreateConnectionWithCandidate(P2PTransportChannel * channel,rtc::ScopedFakeClock * clock,const std::string & ip_addr,int port,int priority,bool writable)3154 Connection* CreateConnectionWithCandidate(P2PTransportChannel* channel,
3155 rtc::ScopedFakeClock* clock,
3156 const std::string& ip_addr,
3157 int port,
3158 int priority,
3159 bool writable) {
3160 channel->AddRemoteCandidate(
3161 CreateUdpCandidate(LOCAL_PORT_TYPE, ip_addr, port, priority));
3162 EXPECT_TRUE_SIMULATED_WAIT(
3163 GetConnectionTo(channel, ip_addr, port) != nullptr, kMediumTimeout,
3164 *clock);
3165 Connection* conn = GetConnectionTo(channel, ip_addr, port);
3166
3167 if (conn && writable) {
3168 conn->ReceivedPingResponse(LOW_RTT, "id"); // make it writable
3169 }
3170 return conn;
3171 }
3172
NominateConnection(Connection * conn,uint32_t remote_nomination=1U)3173 void NominateConnection(Connection* conn, uint32_t remote_nomination = 1U) {
3174 conn->set_remote_nomination(remote_nomination);
3175 conn->SignalNominated(conn);
3176 }
3177
OnNetworkRouteChanged(absl::optional<rtc::NetworkRoute> network_route)3178 void OnNetworkRouteChanged(absl::optional<rtc::NetworkRoute> network_route) {
3179 last_network_route_ = network_route;
3180 if (last_network_route_) {
3181 last_sent_packet_id_ = last_network_route_->last_sent_packet_id;
3182 }
3183 ++selected_candidate_pair_switches_;
3184 }
3185
ReceivePingOnConnection(Connection * conn,const std::string & remote_ufrag,int priority,uint32_t nomination,const absl::optional<std::string> & piggyback_ping_id)3186 void ReceivePingOnConnection(
3187 Connection* conn,
3188 const std::string& remote_ufrag,
3189 int priority,
3190 uint32_t nomination,
3191 const absl::optional<std::string>& piggyback_ping_id) {
3192 IceMessage msg;
3193 msg.SetType(STUN_BINDING_REQUEST);
3194 msg.AddAttribute(std::make_unique<StunByteStringAttribute>(
3195 STUN_ATTR_USERNAME,
3196 conn->local_candidate().username() + ":" + remote_ufrag));
3197 msg.AddAttribute(
3198 std::make_unique<StunUInt32Attribute>(STUN_ATTR_PRIORITY, priority));
3199 if (nomination != 0) {
3200 msg.AddAttribute(std::make_unique<StunUInt32Attribute>(
3201 STUN_ATTR_NOMINATION, nomination));
3202 }
3203 if (piggyback_ping_id) {
3204 msg.AddAttribute(std::make_unique<StunByteStringAttribute>(
3205 STUN_ATTR_LAST_ICE_CHECK_RECEIVED, piggyback_ping_id.value()));
3206 }
3207 msg.SetTransactionID(rtc::CreateRandomString(kStunTransactionIdLength));
3208 msg.AddMessageIntegrity(conn->local_candidate().password());
3209 msg.AddFingerprint();
3210 rtc::ByteBufferWriter buf;
3211 msg.Write(&buf);
3212 conn->OnReadPacket(buf.Data(), buf.Length(), rtc::TimeMicros());
3213 }
3214
ReceivePingOnConnection(Connection * conn,const std::string & remote_ufrag,int priority,uint32_t nomination=0)3215 void ReceivePingOnConnection(Connection* conn,
3216 const std::string& remote_ufrag,
3217 int priority,
3218 uint32_t nomination = 0) {
3219 ReceivePingOnConnection(conn, remote_ufrag, priority, nomination,
3220 absl::nullopt);
3221 }
3222
OnReadyToSend(rtc::PacketTransportInternal * transport)3223 void OnReadyToSend(rtc::PacketTransportInternal* transport) {
3224 channel_ready_to_send_ = true;
3225 }
OnChannelStateChanged(IceTransportInternal * channel)3226 void OnChannelStateChanged(IceTransportInternal* channel) {
3227 channel_state_ = channel->GetState();
3228 }
OnCandidatePairChanged(const CandidatePairChangeEvent & event)3229 void OnCandidatePairChanged(const CandidatePairChangeEvent& event) {
3230 last_candidate_change_event_ = event;
3231 }
3232
last_sent_packet_id()3233 int last_sent_packet_id() { return last_sent_packet_id_; }
channel_ready_to_send()3234 bool channel_ready_to_send() { return channel_ready_to_send_; }
reset_channel_ready_to_send()3235 void reset_channel_ready_to_send() { channel_ready_to_send_ = false; }
channel_state()3236 IceTransportState channel_state() { return channel_state_; }
reset_selected_candidate_pair_switches()3237 int reset_selected_candidate_pair_switches() {
3238 int switches = selected_candidate_pair_switches_;
3239 selected_candidate_pair_switches_ = 0;
3240 return switches;
3241 }
3242
3243 // Return true if the |pair| matches the last network route.
CandidatePairMatchesNetworkRoute(CandidatePairInterface * pair)3244 bool CandidatePairMatchesNetworkRoute(CandidatePairInterface* pair) {
3245 if (!pair) {
3246 return !last_network_route_.has_value();
3247 } else {
3248 return pair->local_candidate().network_id() ==
3249 last_network_route_->local.network_id() &&
3250 pair->remote_candidate().network_id() ==
3251 last_network_route_->remote.network_id();
3252 }
3253 }
3254
ConnectionMatchesChangeEvent(Connection * conn,std::string reason)3255 bool ConnectionMatchesChangeEvent(Connection* conn, std::string reason) {
3256 if (!conn) {
3257 return !last_candidate_change_event_.has_value();
3258 } else {
3259 const auto& last_selected_pair =
3260 last_candidate_change_event_->selected_candidate_pair;
3261 return last_selected_pair.local_candidate().IsEquivalent(
3262 conn->local_candidate()) &&
3263 last_selected_pair.remote_candidate().IsEquivalent(
3264 conn->remote_candidate()) &&
3265 last_candidate_change_event_->last_data_received_ms ==
3266 conn->last_data_received() &&
3267 last_candidate_change_event_->reason == reason;
3268 }
3269 }
3270
3271 private:
3272 std::unique_ptr<rtc::VirtualSocketServer> vss_;
3273 rtc::AutoSocketServerThread thread_;
3274 int selected_candidate_pair_switches_ = 0;
3275 int last_sent_packet_id_ = -1;
3276 bool channel_ready_to_send_ = false;
3277 absl::optional<CandidatePairChangeEvent> last_candidate_change_event_;
3278 IceTransportState channel_state_ = IceTransportState::STATE_INIT;
3279 absl::optional<rtc::NetworkRoute> last_network_route_;
3280 };
3281
TEST_F(P2PTransportChannelPingTest,TestTriggeredChecks)3282 TEST_F(P2PTransportChannelPingTest, TestTriggeredChecks) {
3283 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3284 P2PTransportChannel ch("trigger checks", 1, &pa);
3285 PrepareChannel(&ch);
3286 ch.MaybeStartGathering();
3287 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3288 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
3289
3290 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3291 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3292 ASSERT_TRUE(conn1 != nullptr);
3293 ASSERT_TRUE(conn2 != nullptr);
3294
3295 // Before a triggered check, the first connection to ping is the
3296 // highest priority one.
3297 EXPECT_EQ(conn2, FindNextPingableConnectionAndPingIt(&ch));
3298
3299 // Receiving a ping causes a triggered check which should make conn1
3300 // be pinged first instead of conn2, even though conn2 has a higher
3301 // priority.
3302 conn1->ReceivedPing();
3303 EXPECT_EQ(conn1, FindNextPingableConnectionAndPingIt(&ch));
3304 }
3305
TEST_F(P2PTransportChannelPingTest,TestAllConnectionsPingedSufficiently)3306 TEST_F(P2PTransportChannelPingTest, TestAllConnectionsPingedSufficiently) {
3307 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3308 P2PTransportChannel ch("ping sufficiently", 1, &pa);
3309 PrepareChannel(&ch);
3310 ch.MaybeStartGathering();
3311 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3312 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
3313
3314 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3315 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3316 ASSERT_TRUE(conn1 != nullptr);
3317 ASSERT_TRUE(conn2 != nullptr);
3318
3319 // Low-priority connection becomes writable so that the other connection
3320 // is not pruned.
3321 conn1->ReceivedPingResponse(LOW_RTT, "id");
3322 EXPECT_TRUE_WAIT(
3323 conn1->num_pings_sent() >= MIN_PINGS_AT_WEAK_PING_INTERVAL &&
3324 conn2->num_pings_sent() >= MIN_PINGS_AT_WEAK_PING_INTERVAL,
3325 kDefaultTimeout);
3326 }
3327
3328 // Verify that the connections are pinged at the right time.
TEST_F(P2PTransportChannelPingTest,TestStunPingIntervals)3329 TEST_F(P2PTransportChannelPingTest, TestStunPingIntervals) {
3330 rtc::ScopedFakeClock clock;
3331 int RTT_RATIO = 4;
3332 int SCHEDULING_RANGE = 200;
3333 int RTT_RANGE = 10;
3334
3335 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3336 P2PTransportChannel ch("TestChannel", 1, &pa);
3337 PrepareChannel(&ch);
3338 ch.MaybeStartGathering();
3339 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3340 Connection* conn = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3341
3342 ASSERT_TRUE(conn != nullptr);
3343 SIMULATED_WAIT(conn->num_pings_sent() == 1, kDefaultTimeout, clock);
3344
3345 // Initializing.
3346
3347 int64_t start = clock.TimeNanos();
3348 SIMULATED_WAIT(conn->num_pings_sent() >= MIN_PINGS_AT_WEAK_PING_INTERVAL,
3349 kDefaultTimeout, clock);
3350 int64_t ping_interval_ms = (clock.TimeNanos() - start) /
3351 rtc::kNumNanosecsPerMillisec /
3352 (MIN_PINGS_AT_WEAK_PING_INTERVAL - 1);
3353 EXPECT_EQ(ping_interval_ms, WEAK_PING_INTERVAL);
3354
3355 // Stabilizing.
3356
3357 conn->ReceivedPingResponse(LOW_RTT, "id");
3358 int ping_sent_before = conn->num_pings_sent();
3359 start = clock.TimeNanos();
3360 // The connection becomes strong but not stable because we haven't been able
3361 // to converge the RTT.
3362 SIMULATED_WAIT(conn->num_pings_sent() == ping_sent_before + 1, kMediumTimeout,
3363 clock);
3364 ping_interval_ms = (clock.TimeNanos() - start) / rtc::kNumNanosecsPerMillisec;
3365 EXPECT_GE(ping_interval_ms,
3366 WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL);
3367 EXPECT_LE(
3368 ping_interval_ms,
3369 WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL + SCHEDULING_RANGE);
3370
3371 // Stabilized.
3372
3373 // The connection becomes stable after receiving more than RTT_RATIO rtt
3374 // samples.
3375 for (int i = 0; i < RTT_RATIO; i++) {
3376 conn->ReceivedPingResponse(LOW_RTT, "id");
3377 }
3378 ping_sent_before = conn->num_pings_sent();
3379 start = clock.TimeNanos();
3380 SIMULATED_WAIT(conn->num_pings_sent() == ping_sent_before + 1, kMediumTimeout,
3381 clock);
3382 ping_interval_ms = (clock.TimeNanos() - start) / rtc::kNumNanosecsPerMillisec;
3383 EXPECT_GE(ping_interval_ms,
3384 STRONG_AND_STABLE_WRITABLE_CONNECTION_PING_INTERVAL);
3385 EXPECT_LE(
3386 ping_interval_ms,
3387 STRONG_AND_STABLE_WRITABLE_CONNECTION_PING_INTERVAL + SCHEDULING_RANGE);
3388
3389 // Destabilized.
3390
3391 conn->ReceivedPingResponse(LOW_RTT, "id");
3392 // Create a in-flight ping.
3393 conn->Ping(clock.TimeNanos() / rtc::kNumNanosecsPerMillisec);
3394 start = clock.TimeNanos();
3395 // In-flight ping timeout and the connection will be unstable.
3396 SIMULATED_WAIT(
3397 !conn->stable(clock.TimeNanos() / rtc::kNumNanosecsPerMillisec),
3398 kMediumTimeout, clock);
3399 int64_t duration_ms =
3400 (clock.TimeNanos() - start) / rtc::kNumNanosecsPerMillisec;
3401 EXPECT_GE(duration_ms, 2 * conn->rtt() - RTT_RANGE);
3402 EXPECT_LE(duration_ms, 2 * conn->rtt() + RTT_RANGE);
3403 // The connection become unstable due to not receiving ping responses.
3404 ping_sent_before = conn->num_pings_sent();
3405 SIMULATED_WAIT(conn->num_pings_sent() == ping_sent_before + 1, kMediumTimeout,
3406 clock);
3407 // The interval is expected to be
3408 // WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL.
3409 start = clock.TimeNanos();
3410 ping_sent_before = conn->num_pings_sent();
3411 SIMULATED_WAIT(conn->num_pings_sent() == ping_sent_before + 1, kMediumTimeout,
3412 clock);
3413 ping_interval_ms = (clock.TimeNanos() - start) / rtc::kNumNanosecsPerMillisec;
3414 EXPECT_GE(ping_interval_ms,
3415 WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL);
3416 EXPECT_LE(
3417 ping_interval_ms,
3418 WEAK_OR_STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL + SCHEDULING_RANGE);
3419 }
3420
3421 // Test that we start pinging as soon as we have a connection and remote ICE
3422 // parameters.
TEST_F(P2PTransportChannelPingTest,PingingStartedAsSoonAsPossible)3423 TEST_F(P2PTransportChannelPingTest, PingingStartedAsSoonAsPossible) {
3424 rtc::ScopedFakeClock clock;
3425
3426 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3427 P2PTransportChannel ch("TestChannel", 1, &pa);
3428 ch.SetIceRole(ICEROLE_CONTROLLING);
3429 ch.SetIceParameters(kIceParams[0]);
3430 ch.MaybeStartGathering();
3431 EXPECT_EQ_WAIT(IceGatheringState::kIceGatheringComplete, ch.gathering_state(),
3432 kDefaultTimeout);
3433
3434 // Simulate a binding request being received, creating a peer reflexive
3435 // candidate pair while we still don't have remote ICE parameters.
3436 IceMessage request;
3437 request.SetType(STUN_BINDING_REQUEST);
3438 request.AddAttribute(std::make_unique<StunByteStringAttribute>(
3439 STUN_ATTR_USERNAME, kIceUfrag[1]));
3440 uint32_t prflx_priority = ICE_TYPE_PREFERENCE_PRFLX << 24;
3441 request.AddAttribute(std::make_unique<StunUInt32Attribute>(STUN_ATTR_PRIORITY,
3442 prflx_priority));
3443 Port* port = GetPort(&ch);
3444 ASSERT_NE(nullptr, port);
3445 port->SignalUnknownAddress(port, rtc::SocketAddress("1.1.1.1", 1), PROTO_UDP,
3446 &request, kIceUfrag[1], false);
3447 Connection* conn = GetConnectionTo(&ch, "1.1.1.1", 1);
3448 ASSERT_NE(nullptr, conn);
3449
3450 // Simulate waiting for a second (and change) and verify that no pings were
3451 // sent, since we don't yet have remote ICE parameters.
3452 SIMULATED_WAIT(conn->num_pings_sent() > 0, 1025, clock);
3453 EXPECT_EQ(0, conn->num_pings_sent());
3454
3455 // Set remote ICE parameters. Now we should be able to ping. Ensure that
3456 // the first ping is sent as soon as possible, within one simulated clock
3457 // tick.
3458 ch.SetRemoteIceParameters(kIceParams[1]);
3459 EXPECT_TRUE_SIMULATED_WAIT(conn->num_pings_sent() > 0, 1, clock);
3460 }
3461
TEST_F(P2PTransportChannelPingTest,TestNoTriggeredChecksWhenWritable)3462 TEST_F(P2PTransportChannelPingTest, TestNoTriggeredChecksWhenWritable) {
3463 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3464 P2PTransportChannel ch("trigger checks", 1, &pa);
3465 PrepareChannel(&ch);
3466 ch.MaybeStartGathering();
3467 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3468 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
3469
3470 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3471 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3472 ASSERT_TRUE(conn1 != nullptr);
3473 ASSERT_TRUE(conn2 != nullptr);
3474
3475 EXPECT_EQ(conn2, FindNextPingableConnectionAndPingIt(&ch));
3476 EXPECT_EQ(conn1, FindNextPingableConnectionAndPingIt(&ch));
3477 conn1->ReceivedPingResponse(LOW_RTT, "id");
3478 ASSERT_TRUE(conn1->writable());
3479 conn1->ReceivedPing();
3480
3481 // Ping received, but the connection is already writable, so no
3482 // "triggered check" and conn2 is pinged before conn1 because it has
3483 // a higher priority.
3484 EXPECT_EQ(conn2, FindNextPingableConnectionAndPingIt(&ch));
3485 }
3486
TEST_F(P2PTransportChannelPingTest,TestFailedConnectionNotPingable)3487 TEST_F(P2PTransportChannelPingTest, TestFailedConnectionNotPingable) {
3488 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3489 P2PTransportChannel ch("Do not ping failed connections", 1, &pa);
3490 PrepareChannel(&ch);
3491 ch.MaybeStartGathering();
3492 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3493
3494 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3495 ASSERT_TRUE(conn1 != nullptr);
3496
3497 EXPECT_EQ(conn1, ch.FindNextPingableConnection());
3498 conn1->Prune(); // A pruned connection may still be pingable.
3499 EXPECT_EQ(conn1, ch.FindNextPingableConnection());
3500 conn1->FailAndPrune();
3501 EXPECT_TRUE(nullptr == ch.FindNextPingableConnection());
3502 }
3503
TEST_F(P2PTransportChannelPingTest,TestSignalStateChanged)3504 TEST_F(P2PTransportChannelPingTest, TestSignalStateChanged) {
3505 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3506 P2PTransportChannel ch("state change", 1, &pa);
3507 PrepareChannel(&ch);
3508 ch.MaybeStartGathering();
3509 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3510 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3511 ASSERT_TRUE(conn1 != nullptr);
3512 // Pruning the connection reduces the set of active connections and changes
3513 // the channel state.
3514 conn1->Prune();
3515 EXPECT_EQ_WAIT(IceTransportState::STATE_FAILED, channel_state(),
3516 kDefaultTimeout);
3517 }
3518
3519 // Test adding remote candidates with different ufrags. If a remote candidate
3520 // is added with an old ufrag, it will be discarded. If it is added with a
3521 // ufrag that was not seen before, it will be used to create connections
3522 // although the ICE pwd in the remote candidate will be set when the ICE
3523 // parameters arrive. If a remote candidate is added with the current ICE
3524 // ufrag, its pwd and generation will be set properly.
TEST_F(P2PTransportChannelPingTest,TestAddRemoteCandidateWithVariousUfrags)3525 TEST_F(P2PTransportChannelPingTest, TestAddRemoteCandidateWithVariousUfrags) {
3526 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3527 P2PTransportChannel ch("add candidate", 1, &pa);
3528 PrepareChannel(&ch);
3529 ch.MaybeStartGathering();
3530 // Add a candidate with a future ufrag.
3531 ch.AddRemoteCandidate(
3532 CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1, kIceUfrag[2]));
3533 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3534 ASSERT_TRUE(conn1 != nullptr);
3535 const Candidate& candidate = conn1->remote_candidate();
3536 EXPECT_EQ(kIceUfrag[2], candidate.username());
3537 EXPECT_TRUE(candidate.password().empty());
3538 EXPECT_TRUE(FindNextPingableConnectionAndPingIt(&ch) == nullptr);
3539
3540 // Set the remote ICE parameters with the "future" ufrag.
3541 // This should set the ICE pwd in the remote candidate of |conn1|, making
3542 // it pingable.
3543 ch.SetRemoteIceParameters(kIceParams[2]);
3544 EXPECT_EQ(kIceUfrag[2], candidate.username());
3545 EXPECT_EQ(kIcePwd[2], candidate.password());
3546 EXPECT_EQ(conn1, FindNextPingableConnectionAndPingIt(&ch));
3547
3548 // Add a candidate with an old ufrag. No connection will be created.
3549 ch.AddRemoteCandidate(
3550 CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2, kIceUfrag[1]));
3551 rtc::Thread::Current()->ProcessMessages(500);
3552 EXPECT_TRUE(GetConnectionTo(&ch, "2.2.2.2", 2) == nullptr);
3553
3554 // Add a candidate with the current ufrag, its pwd and generation will be
3555 // assigned, even if the generation is not set.
3556 ch.AddRemoteCandidate(
3557 CreateUdpCandidate(LOCAL_PORT_TYPE, "3.3.3.3", 3, 0, kIceUfrag[2]));
3558 Connection* conn3 = nullptr;
3559 ASSERT_TRUE_WAIT((conn3 = GetConnectionTo(&ch, "3.3.3.3", 3)) != nullptr,
3560 kMediumTimeout);
3561 const Candidate& new_candidate = conn3->remote_candidate();
3562 EXPECT_EQ(kIcePwd[2], new_candidate.password());
3563 EXPECT_EQ(1U, new_candidate.generation());
3564
3565 // Check that the pwd of all remote candidates are properly assigned.
3566 for (const RemoteCandidate& candidate : ch.remote_candidates()) {
3567 EXPECT_TRUE(candidate.username() == kIceUfrag[1] ||
3568 candidate.username() == kIceUfrag[2]);
3569 if (candidate.username() == kIceUfrag[1]) {
3570 EXPECT_EQ(kIcePwd[1], candidate.password());
3571 } else if (candidate.username() == kIceUfrag[2]) {
3572 EXPECT_EQ(kIcePwd[2], candidate.password());
3573 }
3574 }
3575 }
3576
TEST_F(P2PTransportChannelPingTest,ConnectionResurrection)3577 TEST_F(P2PTransportChannelPingTest, ConnectionResurrection) {
3578 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3579 P2PTransportChannel ch("connection resurrection", 1, &pa);
3580 PrepareChannel(&ch);
3581 ch.MaybeStartGathering();
3582
3583 // Create conn1 and keep track of original candidate priority.
3584 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3585 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3586 ASSERT_TRUE(conn1 != nullptr);
3587 uint32_t remote_priority = conn1->remote_candidate().priority();
3588
3589 // Create a higher priority candidate and make the connection
3590 // receiving/writable. This will prune conn1.
3591 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
3592 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3593 ASSERT_TRUE(conn2 != nullptr);
3594 conn2->ReceivedPing();
3595 conn2->ReceivedPingResponse(LOW_RTT, "id");
3596
3597 // Wait for conn2 to be selected.
3598 EXPECT_EQ_WAIT(conn2, ch.selected_connection(), kMediumTimeout);
3599 // Destroy the connection to test SignalUnknownAddress.
3600 conn1->Destroy();
3601 EXPECT_TRUE_WAIT(GetConnectionTo(&ch, "1.1.1.1", 1) == nullptr,
3602 kMediumTimeout);
3603
3604 // Create a minimal STUN message with prflx priority.
3605 IceMessage request;
3606 request.SetType(STUN_BINDING_REQUEST);
3607 request.AddAttribute(std::make_unique<StunByteStringAttribute>(
3608 STUN_ATTR_USERNAME, kIceUfrag[1]));
3609 uint32_t prflx_priority = ICE_TYPE_PREFERENCE_PRFLX << 24;
3610 request.AddAttribute(std::make_unique<StunUInt32Attribute>(STUN_ATTR_PRIORITY,
3611 prflx_priority));
3612 EXPECT_NE(prflx_priority, remote_priority);
3613
3614 Port* port = GetPort(&ch);
3615 // conn1 should be resurrected with original priority.
3616 port->SignalUnknownAddress(port, rtc::SocketAddress("1.1.1.1", 1), PROTO_UDP,
3617 &request, kIceUfrag[1], false);
3618 conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3619 ASSERT_TRUE(conn1 != nullptr);
3620 EXPECT_EQ(conn1->remote_candidate().priority(), remote_priority);
3621
3622 // conn3, a real prflx connection, should have prflx priority.
3623 port->SignalUnknownAddress(port, rtc::SocketAddress("3.3.3.3", 1), PROTO_UDP,
3624 &request, kIceUfrag[1], false);
3625 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 1);
3626 ASSERT_TRUE(conn3 != nullptr);
3627 EXPECT_EQ(conn3->remote_candidate().priority(), prflx_priority);
3628 }
3629
TEST_F(P2PTransportChannelPingTest,TestReceivingStateChange)3630 TEST_F(P2PTransportChannelPingTest, TestReceivingStateChange) {
3631 rtc::ScopedFakeClock clock;
3632 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3633 P2PTransportChannel ch("receiving state change", 1, &pa);
3634 PrepareChannel(&ch);
3635 // Default receiving timeout and checking receiving interval should not be too
3636 // small.
3637 EXPECT_LE(1000, ch.config().receiving_timeout_or_default());
3638 EXPECT_LE(200, ch.check_receiving_interval());
3639 ch.SetIceConfig(CreateIceConfig(500, GATHER_ONCE));
3640 EXPECT_EQ(500, ch.config().receiving_timeout_or_default());
3641 EXPECT_EQ(50, ch.check_receiving_interval());
3642 ch.MaybeStartGathering();
3643 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3644 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
3645 ASSERT_TRUE(conn1 != nullptr);
3646
3647 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
3648 conn1->ReceivedPing();
3649 conn1->OnReadPacket("ABC", 3, rtc::TimeMicros());
3650 EXPECT_TRUE_SIMULATED_WAIT(ch.receiving(), kShortTimeout, clock);
3651 EXPECT_TRUE_SIMULATED_WAIT(!ch.receiving(), kShortTimeout, clock);
3652 }
3653
3654 // The controlled side will select a connection as the "selected connection"
3655 // based on priority until the controlling side nominates a connection, at which
3656 // point the controlled side will select that connection as the
3657 // "selected connection". Plus, SignalNetworkRouteChanged will be fired if the
3658 // selected connection changes and SignalReadyToSend will be fired if the new
3659 // selected connection is writable.
TEST_F(P2PTransportChannelPingTest,TestSelectConnectionBeforeNomination)3660 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionBeforeNomination) {
3661 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3662 P2PTransportChannel ch("receiving state change", 1, &pa);
3663 PrepareChannel(&ch);
3664 ch.SetIceRole(ICEROLE_CONTROLLED);
3665 ch.MaybeStartGathering();
3666 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3667 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3668 ASSERT_TRUE(conn1 != nullptr);
3669 // Channel is not ready to send because it is not writable.
3670 EXPECT_FALSE(channel_ready_to_send());
3671 int last_packet_id = 0;
3672 const char* data = "ABCDEFGH";
3673 int len = static_cast<int>(strlen(data));
3674 EXPECT_EQ(-1, SendData(&ch, data, len, ++last_packet_id));
3675 EXPECT_EQ(-1, last_sent_packet_id());
3676
3677 // A connection needs to be writable before it is selected for transmission.
3678 conn1->ReceivedPingResponse(LOW_RTT, "id");
3679 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kDefaultTimeout);
3680 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
3681 EXPECT_TRUE(ConnectionMatchesChangeEvent(
3682 conn1, "remote candidate generation maybe changed"));
3683 EXPECT_EQ(len, SendData(&ch, data, len, ++last_packet_id));
3684
3685 // When a higher priority candidate comes in, the new connection is chosen
3686 // as the selected connection.
3687 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 10));
3688 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3689 ASSERT_TRUE(conn2 != nullptr);
3690 conn2->ReceivedPingResponse(LOW_RTT, "id");
3691 EXPECT_EQ_WAIT(conn2, ch.selected_connection(), kDefaultTimeout);
3692 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3693 EXPECT_TRUE(
3694 ConnectionMatchesChangeEvent(conn2, "candidate pair state changed"));
3695 EXPECT_TRUE(channel_ready_to_send());
3696 EXPECT_EQ(last_packet_id, last_sent_packet_id());
3697
3698 // If a stun request with use-candidate attribute arrives, the receiving
3699 // connection will be set as the selected connection, even though
3700 // its priority is lower.
3701 EXPECT_EQ(len, SendData(&ch, data, len, ++last_packet_id));
3702 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "3.3.3.3", 3, 1));
3703 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3);
3704 ASSERT_TRUE(conn3 != nullptr);
3705 // Because it has a lower priority, the selected connection is still conn2.
3706 EXPECT_EQ(conn2, ch.selected_connection());
3707 conn3->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3708 // But if it is nominated via use_candidate, it is chosen as the selected
3709 // connection.
3710 NominateConnection(conn3);
3711 ASSERT_EQ(conn3, ch.selected_connection());
3712
3713 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn3));
3714 EXPECT_TRUE(
3715 ConnectionMatchesChangeEvent(conn3, "nomination on the controlled side"));
3716 EXPECT_EQ(last_packet_id, last_sent_packet_id());
3717 EXPECT_TRUE(channel_ready_to_send());
3718
3719 // Even if another higher priority candidate arrives, it will not be set as
3720 // the selected connection because the selected connection is nominated by
3721 // the controlling side.
3722 EXPECT_EQ(len, SendData(&ch, data, len, ++last_packet_id));
3723 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "4.4.4.4", 4, 100));
3724 Connection* conn4 = WaitForConnectionTo(&ch, "4.4.4.4", 4);
3725 ASSERT_TRUE(conn4 != nullptr);
3726 EXPECT_EQ(conn3, ch.selected_connection());
3727 // But if it is nominated via use_candidate and writable, it will be set as
3728 // the selected connection.
3729 NominateConnection(conn4);
3730 // Not switched yet because conn4 is not writable.
3731 EXPECT_EQ(conn3, ch.selected_connection());
3732 reset_channel_ready_to_send();
3733 // The selected connection switches after conn4 becomes writable.
3734 conn4->ReceivedPingResponse(LOW_RTT, "id");
3735 EXPECT_EQ_WAIT(conn4, ch.selected_connection(), kDefaultTimeout);
3736 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn4));
3737 EXPECT_TRUE(
3738 ConnectionMatchesChangeEvent(conn4, "candidate pair state changed"));
3739 EXPECT_EQ(last_packet_id, last_sent_packet_id());
3740 // SignalReadyToSend is fired again because conn4 is writable.
3741 EXPECT_TRUE(channel_ready_to_send());
3742 }
3743
3744 // Test the field trial send_ping_on_nomination_ice_controlled
3745 // that sends a ping directly when a connection has been nominated
3746 // i.e on the ICE_CONTROLLED-side.
TEST_F(P2PTransportChannelPingTest,TestPingOnNomination)3747 TEST_F(P2PTransportChannelPingTest, TestPingOnNomination) {
3748 webrtc::test::ScopedFieldTrials field_trials(
3749 "WebRTC-IceFieldTrials/send_ping_on_nomination_ice_controlled:true/");
3750 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3751 P2PTransportChannel ch("receiving state change", 1, &pa);
3752 PrepareChannel(&ch);
3753 ch.SetIceConfig(ch.config());
3754 ch.SetIceRole(ICEROLE_CONTROLLED);
3755 ch.MaybeStartGathering();
3756 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3757 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3758 ASSERT_TRUE(conn1 != nullptr);
3759
3760 // A connection needs to be writable before it is selected for transmission.
3761 conn1->ReceivedPingResponse(LOW_RTT, "id");
3762 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kDefaultTimeout);
3763 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
3764
3765 // When a higher priority candidate comes in, the new connection is chosen
3766 // as the selected connection.
3767 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 10));
3768 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3769 ASSERT_TRUE(conn2 != nullptr);
3770 conn2->ReceivedPingResponse(LOW_RTT, "id");
3771 EXPECT_EQ_WAIT(conn2, ch.selected_connection(), kDefaultTimeout);
3772 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3773
3774 // Now nominate conn1 (low prio), it shall be choosen.
3775 const int before = conn1->num_pings_sent();
3776 NominateConnection(conn1);
3777 ASSERT_EQ(conn1, ch.selected_connection());
3778 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
3779
3780 // And the additional ping should have been sent directly.
3781 EXPECT_EQ(conn1->num_pings_sent(), before + 1);
3782 }
3783
3784 // Test the field trial send_ping_on_switch_ice_controlling
3785 // that sends a ping directly when switching to a new connection
3786 // on the ICE_CONTROLLING-side.
TEST_F(P2PTransportChannelPingTest,TestPingOnSwitch)3787 TEST_F(P2PTransportChannelPingTest, TestPingOnSwitch) {
3788 webrtc::test::ScopedFieldTrials field_trials(
3789 "WebRTC-IceFieldTrials/send_ping_on_switch_ice_controlling:true/");
3790 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3791 P2PTransportChannel ch("receiving state change", 1, &pa);
3792 PrepareChannel(&ch);
3793 ch.SetIceConfig(ch.config());
3794 ch.SetIceRole(ICEROLE_CONTROLLING);
3795 ch.MaybeStartGathering();
3796 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
3797 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3798 ASSERT_TRUE(conn1 != nullptr);
3799
3800 // A connection needs to be writable before it is selected for transmission.
3801 conn1->ReceivedPingResponse(LOW_RTT, "id");
3802 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kDefaultTimeout);
3803 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
3804
3805 // When a higher priority candidate comes in, the new connection is chosen
3806 // as the selected connection.
3807 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 10));
3808 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3809 ASSERT_TRUE(conn2 != nullptr);
3810
3811 const int before = conn2->num_pings_sent();
3812
3813 conn2->ReceivedPingResponse(LOW_RTT, "id");
3814 EXPECT_EQ_WAIT(conn2, ch.selected_connection(), kDefaultTimeout);
3815 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3816
3817 // And the additional ping should have been sent directly.
3818 EXPECT_EQ(conn2->num_pings_sent(), before + 1);
3819 }
3820
3821 // The controlled side will select a connection as the "selected connection"
3822 // based on requests from an unknown address before the controlling side
3823 // nominates a connection, and will nominate a connection from an unknown
3824 // address if the request contains the use_candidate attribute. Plus, it will
3825 // also sends back a ping response and set the ICE pwd in the remote candidate
3826 // appropriately.
TEST_F(P2PTransportChannelPingTest,TestSelectConnectionFromUnknownAddress)3827 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionFromUnknownAddress) {
3828 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3829 P2PTransportChannel ch("receiving state change", 1, &pa);
3830 PrepareChannel(&ch);
3831 ch.SetIceRole(ICEROLE_CONTROLLED);
3832 ch.MaybeStartGathering();
3833 // A minimal STUN message with prflx priority.
3834 IceMessage request;
3835 request.SetType(STUN_BINDING_REQUEST);
3836 request.AddAttribute(std::make_unique<StunByteStringAttribute>(
3837 STUN_ATTR_USERNAME, kIceUfrag[1]));
3838 uint32_t prflx_priority = ICE_TYPE_PREFERENCE_PRFLX << 24;
3839 request.AddAttribute(std::make_unique<StunUInt32Attribute>(STUN_ATTR_PRIORITY,
3840 prflx_priority));
3841 TestUDPPort* port = static_cast<TestUDPPort*>(GetPort(&ch));
3842 port->SignalUnknownAddress(port, rtc::SocketAddress("1.1.1.1", 1), PROTO_UDP,
3843 &request, kIceUfrag[1], false);
3844 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3845 ASSERT_TRUE(conn1 != nullptr);
3846 EXPECT_EQ(conn1->stats().sent_ping_responses, 1u);
3847 EXPECT_NE(conn1, ch.selected_connection());
3848 conn1->ReceivedPingResponse(LOW_RTT, "id");
3849 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kDefaultTimeout);
3850
3851 // Another connection is nominated via use_candidate.
3852 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 1));
3853 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3854 ASSERT_TRUE(conn2 != nullptr);
3855 // Because it has a lower priority, the selected connection is still conn1.
3856 EXPECT_EQ(conn1, ch.selected_connection());
3857 // When it is nominated via use_candidate and writable, it is chosen as the
3858 // selected connection.
3859 conn2->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3860 NominateConnection(conn2);
3861 EXPECT_EQ(conn2, ch.selected_connection());
3862
3863 // Another request with unknown address, it will not be set as the selected
3864 // connection because the selected connection was nominated by the controlling
3865 // side.
3866 port->SignalUnknownAddress(port, rtc::SocketAddress("3.3.3.3", 3), PROTO_UDP,
3867 &request, kIceUfrag[1], false);
3868 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3);
3869 ASSERT_TRUE(conn3 != nullptr);
3870 EXPECT_EQ(conn3->stats().sent_ping_responses, 1u);
3871 conn3->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3872 EXPECT_EQ(conn2, ch.selected_connection());
3873
3874 // However if the request contains use_candidate attribute, it will be
3875 // selected as the selected connection.
3876 request.AddAttribute(
3877 std::make_unique<StunByteStringAttribute>(STUN_ATTR_USE_CANDIDATE));
3878 port->SignalUnknownAddress(port, rtc::SocketAddress("4.4.4.4", 4), PROTO_UDP,
3879 &request, kIceUfrag[1], false);
3880 Connection* conn4 = WaitForConnectionTo(&ch, "4.4.4.4", 4);
3881 ASSERT_TRUE(conn4 != nullptr);
3882 EXPECT_EQ(conn4->stats().sent_ping_responses, 1u);
3883 // conn4 is not the selected connection yet because it is not writable.
3884 EXPECT_EQ(conn2, ch.selected_connection());
3885 conn4->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3886 EXPECT_EQ_WAIT(conn4, ch.selected_connection(), kDefaultTimeout);
3887
3888 // Test that the request from an unknown address contains a ufrag from an old
3889 // generation.
3890 // port->set_sent_binding_response(false);
3891 ch.SetRemoteIceParameters(kIceParams[2]);
3892 ch.SetRemoteIceParameters(kIceParams[3]);
3893 port->SignalUnknownAddress(port, rtc::SocketAddress("5.5.5.5", 5), PROTO_UDP,
3894 &request, kIceUfrag[2], false);
3895 Connection* conn5 = WaitForConnectionTo(&ch, "5.5.5.5", 5);
3896 ASSERT_TRUE(conn5 != nullptr);
3897 EXPECT_EQ(conn5->stats().sent_ping_responses, 1u);
3898 EXPECT_EQ(kIcePwd[2], conn5->remote_candidate().password());
3899 }
3900
3901 // The controlled side will select a connection as the "selected connection"
3902 // based on media received until the controlling side nominates a connection,
3903 // at which point the controlled side will select that connection as
3904 // the "selected connection".
TEST_F(P2PTransportChannelPingTest,TestSelectConnectionBasedOnMediaReceived)3905 TEST_F(P2PTransportChannelPingTest, TestSelectConnectionBasedOnMediaReceived) {
3906 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3907 P2PTransportChannel ch("receiving state change", 1, &pa);
3908 PrepareChannel(&ch);
3909 ch.SetIceRole(ICEROLE_CONTROLLED);
3910 ch.MaybeStartGathering();
3911 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 10));
3912 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
3913 ASSERT_TRUE(conn1 != nullptr);
3914 conn1->ReceivedPingResponse(LOW_RTT, "id");
3915 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kDefaultTimeout);
3916
3917 // If a data packet is received on conn2, the selected connection should
3918 // switch to conn2 because the controlled side must mirror the media path
3919 // chosen by the controlling side.
3920 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 1));
3921 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
3922 ASSERT_TRUE(conn2 != nullptr);
3923 conn2->ReceivedPingResponse(LOW_RTT, "id"); // Become writable and receiving.
3924 conn2->OnReadPacket("ABC", 3, rtc::TimeMicros());
3925 EXPECT_EQ(conn2, ch.selected_connection());
3926 conn2->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3927
3928 // Now another STUN message with an unknown address and use_candidate will
3929 // nominate the selected connection.
3930 IceMessage request;
3931 request.SetType(STUN_BINDING_REQUEST);
3932 request.AddAttribute(std::make_unique<StunByteStringAttribute>(
3933 STUN_ATTR_USERNAME, kIceUfrag[1]));
3934 uint32_t prflx_priority = ICE_TYPE_PREFERENCE_PRFLX << 24;
3935 request.AddAttribute(std::make_unique<StunUInt32Attribute>(STUN_ATTR_PRIORITY,
3936 prflx_priority));
3937 request.AddAttribute(
3938 std::make_unique<StunByteStringAttribute>(STUN_ATTR_USE_CANDIDATE));
3939 Port* port = GetPort(&ch);
3940 port->SignalUnknownAddress(port, rtc::SocketAddress("3.3.3.3", 3), PROTO_UDP,
3941 &request, kIceUfrag[1], false);
3942 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3);
3943 ASSERT_TRUE(conn3 != nullptr);
3944 EXPECT_NE(conn3, ch.selected_connection()); // Not writable yet.
3945 conn3->ReceivedPingResponse(LOW_RTT, "id"); // Become writable.
3946 EXPECT_EQ_WAIT(conn3, ch.selected_connection(), kDefaultTimeout);
3947
3948 // Now another data packet will not switch the selected connection because the
3949 // selected connection was nominated by the controlling side.
3950 conn2->ReceivedPing();
3951 conn2->ReceivedPingResponse(LOW_RTT, "id");
3952 conn2->OnReadPacket("XYZ", 3, rtc::TimeMicros());
3953 EXPECT_EQ_WAIT(conn3, ch.selected_connection(), kDefaultTimeout);
3954 }
3955
TEST_F(P2PTransportChannelPingTest,TestControlledAgentDataReceivingTakesHigherPrecedenceThanPriority)3956 TEST_F(P2PTransportChannelPingTest,
3957 TestControlledAgentDataReceivingTakesHigherPrecedenceThanPriority) {
3958 rtc::ScopedFakeClock clock;
3959 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
3960 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
3961 P2PTransportChannel ch("SwitchSelectedConnection", 1, &pa);
3962 PrepareChannel(&ch);
3963 ch.SetIceRole(ICEROLE_CONTROLLED);
3964 ch.MaybeStartGathering();
3965 // The connections have decreasing priority.
3966 Connection* conn1 =
3967 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 10, true);
3968 ASSERT_TRUE(conn1 != nullptr);
3969 Connection* conn2 =
3970 CreateConnectionWithCandidate(&ch, &clock, "2.2.2.2", 2, 9, true);
3971 ASSERT_TRUE(conn2 != nullptr);
3972
3973 // Initially, connections are selected based on priority.
3974 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
3975 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
3976
3977 // conn2 receives data; it becomes selected.
3978 // Advance the clock by 1ms so that the last data receiving timestamp of
3979 // conn2 is larger.
3980 SIMULATED_WAIT(false, 1, clock);
3981 conn2->OnReadPacket("XYZ", 3, rtc::TimeMicros());
3982 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
3983 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3984
3985 // conn1 also receives data; it becomes selected due to priority again.
3986 conn1->OnReadPacket("XYZ", 3, rtc::TimeMicros());
3987 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
3988 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3989
3990 // conn2 received data more recently; it is selected now because it
3991 // received data more recently.
3992 SIMULATED_WAIT(false, 1, clock);
3993 // Need to become writable again because it was pruned.
3994 conn2->ReceivedPingResponse(LOW_RTT, "id");
3995 conn2->OnReadPacket("XYZ", 3, rtc::TimeMicros());
3996 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
3997 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
3998
3999 // Make sure sorting won't reselect candidate pair.
4000 SIMULATED_WAIT(false, 10, clock);
4001 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
4002 }
4003
TEST_F(P2PTransportChannelPingTest,TestControlledAgentNominationTakesHigherPrecedenceThanDataReceiving)4004 TEST_F(P2PTransportChannelPingTest,
4005 TestControlledAgentNominationTakesHigherPrecedenceThanDataReceiving) {
4006 rtc::ScopedFakeClock clock;
4007 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4008
4009 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4010 P2PTransportChannel ch("SwitchSelectedConnection", 1, &pa);
4011 PrepareChannel(&ch);
4012 ch.SetIceRole(ICEROLE_CONTROLLED);
4013 ch.MaybeStartGathering();
4014 // The connections have decreasing priority.
4015 Connection* conn1 =
4016 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 10, true);
4017 ASSERT_TRUE(conn1 != nullptr);
4018 Connection* conn2 =
4019 CreateConnectionWithCandidate(&ch, &clock, "2.2.2.2", 2, 9, true);
4020 ASSERT_TRUE(conn2 != nullptr);
4021
4022 // conn1 received data; it is the selected connection.
4023 // Advance the clock to have a non-zero last-data-receiving time.
4024 SIMULATED_WAIT(false, 1, clock);
4025 conn1->OnReadPacket("XYZ", 3, rtc::TimeMicros());
4026 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4027 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
4028
4029 // conn2 is nominated; it becomes the selected connection.
4030 NominateConnection(conn2);
4031 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4032 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
4033
4034 // conn1 is selected because it has higher priority and also nominated.
4035 NominateConnection(conn1);
4036 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4037 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
4038
4039 // Make sure sorting won't reselect candidate pair.
4040 SIMULATED_WAIT(false, 10, clock);
4041 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
4042 }
4043
TEST_F(P2PTransportChannelPingTest,TestControlledAgentSelectsConnectionWithHigherNomination)4044 TEST_F(P2PTransportChannelPingTest,
4045 TestControlledAgentSelectsConnectionWithHigherNomination) {
4046 rtc::ScopedFakeClock clock;
4047 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4048
4049 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4050 P2PTransportChannel ch("test", 1, &pa);
4051 PrepareChannel(&ch);
4052 ch.SetIceRole(ICEROLE_CONTROLLED);
4053 ch.MaybeStartGathering();
4054 // The connections have decreasing priority.
4055 Connection* conn1 =
4056 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 10, true);
4057 ASSERT_TRUE(conn1 != nullptr);
4058 Connection* conn2 =
4059 CreateConnectionWithCandidate(&ch, &clock, "2.2.2.2", 2, 9, true);
4060 ASSERT_TRUE(conn2 != nullptr);
4061
4062 // conn1 is the selected connection because it has a higher priority,
4063 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), kDefaultTimeout,
4064 clock);
4065 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
4066 reset_selected_candidate_pair_switches();
4067
4068 // conn2 is nominated; it becomes selected.
4069 NominateConnection(conn2);
4070 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4071 EXPECT_EQ(conn2, ch.selected_connection());
4072 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
4073
4074 // conn1 is selected because of its priority.
4075 NominateConnection(conn1);
4076 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4077 EXPECT_EQ(conn1, ch.selected_connection());
4078 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
4079
4080 // conn2 gets higher remote nomination; it is selected again.
4081 NominateConnection(conn2, 2U);
4082 EXPECT_EQ(1, reset_selected_candidate_pair_switches());
4083 EXPECT_EQ(conn2, ch.selected_connection());
4084 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
4085
4086 // Make sure sorting won't reselect candidate pair.
4087 SIMULATED_WAIT(false, 100, clock);
4088 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
4089 }
4090
TEST_F(P2PTransportChannelPingTest,TestControlledAgentIgnoresSmallerNomination)4091 TEST_F(P2PTransportChannelPingTest,
4092 TestControlledAgentIgnoresSmallerNomination) {
4093 rtc::ScopedFakeClock clock;
4094 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4095
4096 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4097 P2PTransportChannel ch("test", 1, &pa);
4098 PrepareChannel(&ch);
4099 ch.SetIceRole(ICEROLE_CONTROLLED);
4100 ch.MaybeStartGathering();
4101 Connection* conn =
4102 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 10, false);
4103 ReceivePingOnConnection(conn, kIceUfrag[1], 1, 2U);
4104 EXPECT_EQ(2U, conn->remote_nomination());
4105 // Smaller nomination is ignored.
4106 ReceivePingOnConnection(conn, kIceUfrag[1], 1, 1U);
4107 EXPECT_EQ(2U, conn->remote_nomination());
4108 }
4109
TEST_F(P2PTransportChannelPingTest,TestControlledAgentWriteStateTakesHigherPrecedenceThanNomination)4110 TEST_F(P2PTransportChannelPingTest,
4111 TestControlledAgentWriteStateTakesHigherPrecedenceThanNomination) {
4112 rtc::ScopedFakeClock clock;
4113
4114 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4115 P2PTransportChannel ch("SwitchSelectedConnection", 1, &pa);
4116 PrepareChannel(&ch);
4117 ch.SetIceRole(ICEROLE_CONTROLLED);
4118 ch.MaybeStartGathering();
4119 // The connections have decreasing priority.
4120 Connection* conn1 =
4121 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 10, false);
4122 ASSERT_TRUE(conn1 != nullptr);
4123 Connection* conn2 =
4124 CreateConnectionWithCandidate(&ch, &clock, "2.2.2.2", 2, 9, false);
4125 ASSERT_TRUE(conn2 != nullptr);
4126
4127 NominateConnection(conn1);
4128 // There is no selected connection because no connection is writable.
4129 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
4130
4131 // conn2 becomes writable; it is selected even though it is not nominated.
4132 conn2->ReceivedPingResponse(LOW_RTT, "id");
4133 EXPECT_EQ_SIMULATED_WAIT(1, reset_selected_candidate_pair_switches(),
4134 kDefaultTimeout, clock);
4135 EXPECT_EQ_SIMULATED_WAIT(conn2, ch.selected_connection(), kDefaultTimeout,
4136 clock);
4137 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn2));
4138
4139 // If conn1 is also writable, it will become selected.
4140 conn1->ReceivedPingResponse(LOW_RTT, "id");
4141 EXPECT_EQ_SIMULATED_WAIT(1, reset_selected_candidate_pair_switches(),
4142 kDefaultTimeout, clock);
4143 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), kDefaultTimeout,
4144 clock);
4145 EXPECT_TRUE(CandidatePairMatchesNetworkRoute(conn1));
4146
4147 // Make sure sorting won't reselect candidate pair.
4148 SIMULATED_WAIT(false, 10, clock);
4149 EXPECT_EQ(0, reset_selected_candidate_pair_switches());
4150 }
4151
4152 // Test that if a new remote candidate has the same address and port with
4153 // an old one, it will be used to create a new connection.
TEST_F(P2PTransportChannelPingTest,TestAddRemoteCandidateWithAddressReuse)4154 TEST_F(P2PTransportChannelPingTest, TestAddRemoteCandidateWithAddressReuse) {
4155 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4156 P2PTransportChannel ch("candidate reuse", 1, &pa);
4157 PrepareChannel(&ch);
4158 ch.MaybeStartGathering();
4159 const std::string host_address = "1.1.1.1";
4160 const int port_num = 1;
4161
4162 // kIceUfrag[1] is the current generation ufrag.
4163 Candidate candidate = CreateUdpCandidate(LOCAL_PORT_TYPE, host_address,
4164 port_num, 1, kIceUfrag[1]);
4165 ch.AddRemoteCandidate(candidate);
4166 Connection* conn1 = WaitForConnectionTo(&ch, host_address, port_num);
4167 ASSERT_TRUE(conn1 != nullptr);
4168 EXPECT_EQ(0u, conn1->remote_candidate().generation());
4169
4170 // Simply adding the same candidate again won't create a new connection.
4171 ch.AddRemoteCandidate(candidate);
4172 Connection* conn2 = GetConnectionTo(&ch, host_address, port_num);
4173 EXPECT_EQ(conn1, conn2);
4174
4175 // Update the ufrag of the candidate and add it again.
4176 candidate.set_username(kIceUfrag[2]);
4177 ch.AddRemoteCandidate(candidate);
4178 conn2 = GetConnectionTo(&ch, host_address, port_num);
4179 EXPECT_NE(conn1, conn2);
4180 EXPECT_EQ(kIceUfrag[2], conn2->remote_candidate().username());
4181 EXPECT_EQ(1u, conn2->remote_candidate().generation());
4182
4183 // Verify that a ping with the new ufrag can be received on the new
4184 // connection.
4185 EXPECT_EQ(0, conn2->last_ping_received());
4186 ReceivePingOnConnection(conn2, kIceUfrag[2], 1 /* priority */);
4187 EXPECT_GT(conn2->last_ping_received(), 0);
4188 }
4189
4190 // When the current selected connection is strong, lower-priority connections
4191 // will be pruned. Otherwise, lower-priority connections are kept.
TEST_F(P2PTransportChannelPingTest,TestDontPruneWhenWeak)4192 TEST_F(P2PTransportChannelPingTest, TestDontPruneWhenWeak) {
4193 rtc::ScopedFakeClock clock;
4194 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4195 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4196 P2PTransportChannel ch("test channel", 1, &pa);
4197 PrepareChannel(&ch);
4198 ch.SetIceRole(ICEROLE_CONTROLLED);
4199 ch.MaybeStartGathering();
4200 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4201 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4202 ASSERT_TRUE(conn1 != nullptr);
4203 EXPECT_EQ(nullptr, ch.selected_connection());
4204 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
4205
4206 // When a higher-priority, nominated candidate comes in, the connections with
4207 // lower-priority are pruned.
4208 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 10));
4209 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2, &clock);
4210 ASSERT_TRUE(conn2 != nullptr);
4211 conn2->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
4212 NominateConnection(conn2);
4213 EXPECT_TRUE_SIMULATED_WAIT(conn1->pruned(), kMediumTimeout, clock);
4214
4215 ch.SetIceConfig(CreateIceConfig(500, GATHER_ONCE));
4216 // Wait until conn2 becomes not receiving.
4217 EXPECT_TRUE_SIMULATED_WAIT(!conn2->receiving(), kMediumTimeout, clock);
4218
4219 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "3.3.3.3", 3, 1));
4220 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3, &clock);
4221 ASSERT_TRUE(conn3 != nullptr);
4222 // The selected connection should still be conn2. Even through conn3 has lower
4223 // priority and is not receiving/writable, it is not pruned because the
4224 // selected connection is not receiving.
4225 SIMULATED_WAIT(conn3->pruned(), kShortTimeout, clock);
4226 EXPECT_FALSE(conn3->pruned());
4227 }
4228
TEST_F(P2PTransportChannelPingTest,TestDontPruneHighPriorityConnections)4229 TEST_F(P2PTransportChannelPingTest, TestDontPruneHighPriorityConnections) {
4230 rtc::ScopedFakeClock clock;
4231 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4232 P2PTransportChannel ch("test channel", 1, &pa);
4233 PrepareChannel(&ch);
4234 ch.SetIceRole(ICEROLE_CONTROLLED);
4235 ch.MaybeStartGathering();
4236 Connection* conn1 =
4237 CreateConnectionWithCandidate(&ch, &clock, "1.1.1.1", 1, 100, true);
4238 ASSERT_TRUE(conn1 != nullptr);
4239 Connection* conn2 =
4240 CreateConnectionWithCandidate(&ch, &clock, "2.2.2.2", 2, 200, false);
4241 ASSERT_TRUE(conn2 != nullptr);
4242 // Even if conn1 is writable, nominated, receiving data, it should not prune
4243 // conn2.
4244 NominateConnection(conn1);
4245 SIMULATED_WAIT(false, 1, clock);
4246 conn1->OnReadPacket("XYZ", 3, rtc::TimeMicros());
4247 SIMULATED_WAIT(conn2->pruned(), 100, clock);
4248 EXPECT_FALSE(conn2->pruned());
4249 }
4250
4251 // Test that GetState returns the state correctly.
TEST_F(P2PTransportChannelPingTest,TestGetState)4252 TEST_F(P2PTransportChannelPingTest, TestGetState) {
4253 rtc::ScopedFakeClock clock;
4254 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4255 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4256 P2PTransportChannel ch("test channel", 1, &pa);
4257 EXPECT_EQ(webrtc::IceTransportState::kNew, ch.GetIceTransportState());
4258 PrepareChannel(&ch);
4259 ch.MaybeStartGathering();
4260 // After gathering we are still in the kNew state because we aren't checking
4261 // any connections yet.
4262 EXPECT_EQ(webrtc::IceTransportState::kNew, ch.GetIceTransportState());
4263 EXPECT_EQ(IceTransportState::STATE_INIT, ch.GetState());
4264 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
4265 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 1));
4266 // Checking candidates that have been added with gathered candidates.
4267 ASSERT_GT(ch.connections().size(), 0u);
4268 EXPECT_EQ(webrtc::IceTransportState::kChecking, ch.GetIceTransportState());
4269 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
4270 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2, &clock);
4271 ASSERT_TRUE(conn1 != nullptr);
4272 ASSERT_TRUE(conn2 != nullptr);
4273 // Now there are two connections, so the transport channel is connecting.
4274 EXPECT_EQ(IceTransportState::STATE_CONNECTING, ch.GetState());
4275 // No connections are writable yet, so we should still be in the kChecking
4276 // state.
4277 EXPECT_EQ(webrtc::IceTransportState::kChecking, ch.GetIceTransportState());
4278 // |conn1| becomes writable and receiving; it then should prune |conn2|.
4279 conn1->ReceivedPingResponse(LOW_RTT, "id");
4280 EXPECT_TRUE_SIMULATED_WAIT(conn2->pruned(), kShortTimeout, clock);
4281 EXPECT_EQ(IceTransportState::STATE_COMPLETED, ch.GetState());
4282 EXPECT_EQ(webrtc::IceTransportState::kConnected, ch.GetIceTransportState());
4283 conn1->Prune(); // All connections are pruned.
4284 // Need to wait until the channel state is updated.
4285 EXPECT_EQ_SIMULATED_WAIT(IceTransportState::STATE_FAILED, ch.GetState(),
4286 kShortTimeout, clock);
4287 EXPECT_EQ(webrtc::IceTransportState::kFailed, ch.GetIceTransportState());
4288 }
4289
4290 // Test that when a low-priority connection is pruned, it is not deleted
4291 // right away, and it can become active and be pruned again.
TEST_F(P2PTransportChannelPingTest,TestConnectionPrunedAgain)4292 TEST_F(P2PTransportChannelPingTest, TestConnectionPrunedAgain) {
4293 rtc::ScopedFakeClock clock;
4294 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4295
4296 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4297 P2PTransportChannel ch("test channel", 1, &pa);
4298 PrepareChannel(&ch);
4299 IceConfig config = CreateIceConfig(1000, GATHER_ONCE);
4300 config.receiving_switching_delay = 800;
4301 ch.SetIceConfig(config);
4302 ch.MaybeStartGathering();
4303 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
4304 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
4305 ASSERT_TRUE(conn1 != nullptr);
4306 EXPECT_EQ(nullptr, ch.selected_connection());
4307 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
4308 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), kDefaultTimeout,
4309 clock);
4310
4311 // Add a low-priority connection |conn2|, which will be pruned, but it will
4312 // not be deleted right away. Once the current selected connection becomes not
4313 // receiving, |conn2| will start to ping and upon receiving the ping response,
4314 // it will become the selected connection.
4315 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 1));
4316 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2, &clock);
4317 ASSERT_TRUE(conn2 != nullptr);
4318 EXPECT_TRUE_SIMULATED_WAIT(!conn2->active(), kDefaultTimeout, clock);
4319 // |conn2| should not send a ping yet.
4320 EXPECT_EQ(IceCandidatePairState::WAITING, conn2->state());
4321 EXPECT_EQ(IceTransportState::STATE_COMPLETED, ch.GetState());
4322 // Wait for |conn1| becoming not receiving.
4323 EXPECT_TRUE_SIMULATED_WAIT(!conn1->receiving(), kMediumTimeout, clock);
4324 // Make sure conn2 is not deleted.
4325 conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2, &clock);
4326 ASSERT_TRUE(conn2 != nullptr);
4327 EXPECT_EQ_SIMULATED_WAIT(IceCandidatePairState::IN_PROGRESS, conn2->state(),
4328 kDefaultTimeout, clock);
4329 conn2->ReceivedPingResponse(LOW_RTT, "id");
4330 EXPECT_EQ_SIMULATED_WAIT(conn2, ch.selected_connection(), kDefaultTimeout,
4331 clock);
4332 EXPECT_EQ(IceTransportState::STATE_CONNECTING, ch.GetState());
4333
4334 // When |conn1| comes back again, |conn2| will be pruned again.
4335 conn1->ReceivedPingResponse(LOW_RTT, "id");
4336 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), kDefaultTimeout,
4337 clock);
4338 EXPECT_TRUE_SIMULATED_WAIT(!conn2->active(), kDefaultTimeout, clock);
4339 EXPECT_EQ(IceTransportState::STATE_COMPLETED, ch.GetState());
4340 }
4341
4342 // Test that if all connections in a channel has timed out on writing, they
4343 // will all be deleted. We use Prune to simulate write_time_out.
TEST_F(P2PTransportChannelPingTest,TestDeleteConnectionsIfAllWriteTimedout)4344 TEST_F(P2PTransportChannelPingTest, TestDeleteConnectionsIfAllWriteTimedout) {
4345 rtc::ScopedFakeClock clock;
4346 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4347 P2PTransportChannel ch("test channel", 1, &pa);
4348 PrepareChannel(&ch);
4349 ch.MaybeStartGathering();
4350 // Have one connection only but later becomes write-time-out.
4351 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
4352 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
4353 ASSERT_TRUE(conn1 != nullptr);
4354 conn1->ReceivedPing(); // Becomes receiving
4355 conn1->Prune();
4356 EXPECT_TRUE_SIMULATED_WAIT(ch.connections().empty(), kShortTimeout, clock);
4357
4358 // Have two connections but both become write-time-out later.
4359 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 1));
4360 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2, &clock);
4361 ASSERT_TRUE(conn2 != nullptr);
4362 conn2->ReceivedPing(); // Becomes receiving
4363 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "3.3.3.3", 3, 2));
4364 Connection* conn3 = WaitForConnectionTo(&ch, "3.3.3.3", 3, &clock);
4365 ASSERT_TRUE(conn3 != nullptr);
4366 conn3->ReceivedPing(); // Becomes receiving
4367 // Now prune both conn2 and conn3; they will be deleted soon.
4368 conn2->Prune();
4369 conn3->Prune();
4370 EXPECT_TRUE_SIMULATED_WAIT(ch.connections().empty(), kShortTimeout, clock);
4371 }
4372
4373 // Tests that after a port allocator session is started, it will be stopped
4374 // when a new connection becomes writable and receiving. Also tests that if a
4375 // connection belonging to an old session becomes writable, it won't stop
4376 // the current port allocator session.
TEST_F(P2PTransportChannelPingTest,TestStopPortAllocatorSessions)4377 TEST_F(P2PTransportChannelPingTest, TestStopPortAllocatorSessions) {
4378 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4379 P2PTransportChannel ch("test channel", 1, &pa);
4380 PrepareChannel(&ch);
4381 ch.SetIceConfig(CreateIceConfig(2000, GATHER_ONCE));
4382 ch.MaybeStartGathering();
4383 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
4384 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4385 ASSERT_TRUE(conn1 != nullptr);
4386 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
4387 EXPECT_TRUE(!ch.allocator_session()->IsGettingPorts());
4388
4389 // Start a new session. Even though conn1, which belongs to an older
4390 // session, becomes unwritable and writable again, it should not stop the
4391 // current session.
4392 ch.SetIceParameters(kIceParams[1]);
4393 ch.MaybeStartGathering();
4394 conn1->Prune();
4395 conn1->ReceivedPingResponse(LOW_RTT, "id");
4396 EXPECT_TRUE(ch.allocator_session()->IsGettingPorts());
4397
4398 // But if a new connection created from the new session becomes writable,
4399 // it will stop the current session.
4400 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 100));
4401 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
4402 ASSERT_TRUE(conn2 != nullptr);
4403 conn2->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
4404 EXPECT_TRUE(!ch.allocator_session()->IsGettingPorts());
4405 }
4406
4407 // Test that the ICE role is updated even on ports that has been removed.
4408 // These ports may still have connections that need a correct role, in case that
4409 // the connections on it may still receive stun pings.
TEST_F(P2PTransportChannelPingTest,TestIceRoleUpdatedOnRemovedPort)4410 TEST_F(P2PTransportChannelPingTest, TestIceRoleUpdatedOnRemovedPort) {
4411 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4412 P2PTransportChannel ch("test channel", ICE_CANDIDATE_COMPONENT_DEFAULT, &pa);
4413 // Starts with ICEROLE_CONTROLLING.
4414 PrepareChannel(&ch);
4415 IceConfig config = CreateIceConfig(1000, GATHER_CONTINUALLY);
4416 ch.SetIceConfig(config);
4417 ch.MaybeStartGathering();
4418 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4419
4420 Connection* conn = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4421 ASSERT_TRUE(conn != nullptr);
4422
4423 // Make a fake signal to remove the ports in the p2ptransportchannel. then
4424 // change the ICE role and expect it to be updated.
4425 std::vector<PortInterface*> ports(1, conn->PortForTest());
4426 ch.allocator_session()->SignalPortsPruned(ch.allocator_session(), ports);
4427 ch.SetIceRole(ICEROLE_CONTROLLED);
4428 EXPECT_EQ(ICEROLE_CONTROLLED, conn->PortForTest()->GetIceRole());
4429 }
4430
4431 // Test that the ICE role is updated even on ports with inactive networks.
4432 // These ports may still have connections that need a correct role, for the
4433 // pings sent by those connections until they're replaced by newer-generation
4434 // connections.
TEST_F(P2PTransportChannelPingTest,TestIceRoleUpdatedOnPortAfterIceRestart)4435 TEST_F(P2PTransportChannelPingTest, TestIceRoleUpdatedOnPortAfterIceRestart) {
4436 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4437 P2PTransportChannel ch("test channel", ICE_CANDIDATE_COMPONENT_DEFAULT, &pa);
4438 // Starts with ICEROLE_CONTROLLING.
4439 PrepareChannel(&ch);
4440 ch.MaybeStartGathering();
4441 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4442
4443 Connection* conn = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4444 ASSERT_TRUE(conn != nullptr);
4445
4446 // Do an ICE restart, change the role, and expect the old port to have its
4447 // role updated.
4448 ch.SetIceParameters(kIceParams[1]);
4449 ch.MaybeStartGathering();
4450 ch.SetIceRole(ICEROLE_CONTROLLED);
4451 EXPECT_EQ(ICEROLE_CONTROLLED, conn->PortForTest()->GetIceRole());
4452 }
4453
4454 // Test that after some amount of time without receiving data, the connection
4455 // will be destroyed. The port will only be destroyed after it is marked as
4456 // "pruned."
TEST_F(P2PTransportChannelPingTest,TestPortDestroyedAfterTimeoutAndPruned)4457 TEST_F(P2PTransportChannelPingTest, TestPortDestroyedAfterTimeoutAndPruned) {
4458 rtc::ScopedFakeClock fake_clock;
4459
4460 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4461 P2PTransportChannel ch("test channel", ICE_CANDIDATE_COMPONENT_DEFAULT, &pa);
4462 PrepareChannel(&ch);
4463 ch.SetIceRole(ICEROLE_CONTROLLED);
4464 ch.MaybeStartGathering();
4465 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4466
4467 Connection* conn = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4468 ASSERT_TRUE(conn != nullptr);
4469
4470 // Simulate 2 minutes going by. This should be enough time for the port to
4471 // time out.
4472 for (int second = 0; second < 120; ++second) {
4473 fake_clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
4474 }
4475 EXPECT_EQ(nullptr, GetConnectionTo(&ch, "1.1.1.1", 1));
4476 // Port will not be removed because it is not pruned yet.
4477 PortInterface* port = GetPort(&ch);
4478 ASSERT_NE(nullptr, port);
4479
4480 // If the session prunes all ports, the port will be destroyed.
4481 ch.allocator_session()->PruneAllPorts();
4482 EXPECT_EQ_SIMULATED_WAIT(nullptr, GetPort(&ch), 1, fake_clock);
4483 EXPECT_EQ_SIMULATED_WAIT(nullptr, GetPrunedPort(&ch), 1, fake_clock);
4484 }
4485
TEST_F(P2PTransportChannelPingTest,TestMaxOutstandingPingsFieldTrial)4486 TEST_F(P2PTransportChannelPingTest, TestMaxOutstandingPingsFieldTrial) {
4487 webrtc::test::ScopedFieldTrials field_trials(
4488 "WebRTC-IceFieldTrials/max_outstanding_pings:3/");
4489 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
4490 P2PTransportChannel ch("max", 1, &pa);
4491 ch.SetIceConfig(ch.config());
4492 PrepareChannel(&ch);
4493 ch.MaybeStartGathering();
4494 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4495 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
4496
4497 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4498 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
4499 ASSERT_TRUE(conn1 != nullptr);
4500 ASSERT_TRUE(conn2 != nullptr);
4501
4502 EXPECT_TRUE_WAIT(conn1->num_pings_sent() == 3 && conn2->num_pings_sent() == 3,
4503 kDefaultTimeout);
4504
4505 // Check that these connections don't send any more pings.
4506 EXPECT_EQ(nullptr, ch.FindNextPingableConnection());
4507 }
4508
4509 class P2PTransportChannelMostLikelyToWorkFirstTest
4510 : public P2PTransportChannelPingTest {
4511 public:
P2PTransportChannelMostLikelyToWorkFirstTest()4512 P2PTransportChannelMostLikelyToWorkFirstTest()
4513 : turn_server_(rtc::Thread::Current(), kTurnUdpIntAddr, kTurnUdpExtAddr) {
4514 network_manager_.AddInterface(kPublicAddrs[0]);
4515 allocator_.reset(
4516 CreateBasicPortAllocator(&network_manager_, ServerAddresses(),
4517 kTurnUdpIntAddr, rtc::SocketAddress()));
4518 allocator_->set_flags(allocator_->flags() | PORTALLOCATOR_DISABLE_STUN |
4519 PORTALLOCATOR_DISABLE_TCP);
4520 allocator_->set_step_delay(kMinimumStepDelay);
4521 }
4522
StartTransportChannel(bool prioritize_most_likely_to_work,int stable_writable_connection_ping_interval)4523 P2PTransportChannel& StartTransportChannel(
4524 bool prioritize_most_likely_to_work,
4525 int stable_writable_connection_ping_interval) {
4526 channel_.reset(new P2PTransportChannel("checks", 1, allocator()));
4527 IceConfig config = channel_->config();
4528 config.prioritize_most_likely_candidate_pairs =
4529 prioritize_most_likely_to_work;
4530 config.stable_writable_connection_ping_interval =
4531 stable_writable_connection_ping_interval;
4532 channel_->SetIceConfig(config);
4533 PrepareChannel(channel_.get());
4534 channel_->MaybeStartGathering();
4535 return *channel_.get();
4536 }
4537
allocator()4538 BasicPortAllocator* allocator() { return allocator_.get(); }
turn_server()4539 TestTurnServer* turn_server() { return &turn_server_; }
4540
4541 // This verifies the next pingable connection has the expected candidates'
4542 // types and, for relay local candidate, the expected relay protocol and ping
4543 // it.
VerifyNextPingableConnection(const std::string & local_candidate_type,const std::string & remote_candidate_type,const std::string & relay_protocol_type=UDP_PROTOCOL_NAME)4544 void VerifyNextPingableConnection(
4545 const std::string& local_candidate_type,
4546 const std::string& remote_candidate_type,
4547 const std::string& relay_protocol_type = UDP_PROTOCOL_NAME) {
4548 Connection* conn = FindNextPingableConnectionAndPingIt(channel_.get());
4549 ASSERT_TRUE(conn != nullptr);
4550 EXPECT_EQ(conn->local_candidate().type(), local_candidate_type);
4551 if (conn->local_candidate().type() == RELAY_PORT_TYPE) {
4552 EXPECT_EQ(conn->local_candidate().relay_protocol(), relay_protocol_type);
4553 }
4554 EXPECT_EQ(conn->remote_candidate().type(), remote_candidate_type);
4555 }
4556
4557 private:
4558 std::unique_ptr<BasicPortAllocator> allocator_;
4559 rtc::FakeNetworkManager network_manager_;
4560 TestTurnServer turn_server_;
4561 std::unique_ptr<P2PTransportChannel> channel_;
4562 };
4563
4564 // Test that Relay/Relay connections will be pinged first when no other
4565 // connections have been pinged yet, unless we need to ping a trigger check or
4566 // we have a selected connection.
TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,TestRelayRelayFirstWhenNothingPingedYet)4567 TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,
4568 TestRelayRelayFirstWhenNothingPingedYet) {
4569 const int max_strong_interval = 500;
4570 P2PTransportChannel& ch = StartTransportChannel(true, max_strong_interval);
4571 EXPECT_TRUE_WAIT(ch.ports().size() == 2, kDefaultTimeout);
4572 EXPECT_EQ(ch.ports()[0]->Type(), LOCAL_PORT_TYPE);
4573 EXPECT_EQ(ch.ports()[1]->Type(), RELAY_PORT_TYPE);
4574
4575 ch.AddRemoteCandidate(CreateUdpCandidate(RELAY_PORT_TYPE, "1.1.1.1", 1, 1));
4576 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
4577
4578 EXPECT_TRUE_WAIT(ch.connections().size() == 4, kDefaultTimeout);
4579
4580 // Relay/Relay should be the first pingable connection.
4581 Connection* conn = FindNextPingableConnectionAndPingIt(&ch);
4582 ASSERT_TRUE(conn != nullptr);
4583 EXPECT_EQ(conn->local_candidate().type(), RELAY_PORT_TYPE);
4584 EXPECT_EQ(conn->remote_candidate().type(), RELAY_PORT_TYPE);
4585
4586 // Unless that we have a trigger check waiting to be pinged.
4587 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
4588 ASSERT_TRUE(conn2 != nullptr);
4589 EXPECT_EQ(conn2->local_candidate().type(), LOCAL_PORT_TYPE);
4590 EXPECT_EQ(conn2->remote_candidate().type(), LOCAL_PORT_TYPE);
4591 conn2->ReceivedPing();
4592 EXPECT_EQ(conn2, FindNextPingableConnectionAndPingIt(&ch));
4593
4594 // Make conn3 the selected connection.
4595 Connection* conn3 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
4596 ASSERT_TRUE(conn3 != nullptr);
4597 EXPECT_EQ(conn3->local_candidate().type(), LOCAL_PORT_TYPE);
4598 EXPECT_EQ(conn3->remote_candidate().type(), RELAY_PORT_TYPE);
4599 conn3->ReceivedPingResponse(LOW_RTT, "id");
4600 ASSERT_TRUE(conn3->writable());
4601 conn3->ReceivedPing();
4602
4603 /*
4604
4605 TODO(honghaiz): Re-enable this once we use fake clock for this test to fix
4606 the flakiness. The following test becomes flaky because we now ping the
4607 connections with fast rates until every connection is pinged at least three
4608 times. The selected connection may have been pinged before
4609 |max_strong_interval|, so it may not be the next connection to be pinged as
4610 expected in the test.
4611
4612 // Verify that conn3 will be the "selected connection" since it is readable
4613 // and writable. After |MAX_CURRENT_STRONG_INTERVAL|, it should be the next
4614 // pingable connection.
4615 EXPECT_TRUE_WAIT(conn3 == ch.selected_connection(), kDefaultTimeout);
4616 WAIT(false, max_strong_interval + 100);
4617 conn3->ReceivedPingResponse(LOW_RTT, "id");
4618 ASSERT_TRUE(conn3->writable());
4619 EXPECT_EQ(conn3, FindNextPingableConnectionAndPingIt(&ch));
4620
4621 */
4622 }
4623
4624 // Test that Relay/Relay connections will be pinged first when everything has
4625 // been pinged even if the Relay/Relay connection wasn't the first to be pinged
4626 // in the first round.
TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,TestRelayRelayFirstWhenEverythingPinged)4627 TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,
4628 TestRelayRelayFirstWhenEverythingPinged) {
4629 P2PTransportChannel& ch = StartTransportChannel(true, 500);
4630 EXPECT_TRUE_WAIT(ch.ports().size() == 2, kDefaultTimeout);
4631 EXPECT_EQ(ch.ports()[0]->Type(), LOCAL_PORT_TYPE);
4632 EXPECT_EQ(ch.ports()[1]->Type(), RELAY_PORT_TYPE);
4633
4634 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
4635 EXPECT_TRUE_WAIT(ch.connections().size() == 2, kDefaultTimeout);
4636
4637 // Initially, only have Local/Local and Local/Relay.
4638 VerifyNextPingableConnection(LOCAL_PORT_TYPE, LOCAL_PORT_TYPE);
4639 VerifyNextPingableConnection(RELAY_PORT_TYPE, LOCAL_PORT_TYPE);
4640
4641 // Remote Relay candidate arrives.
4642 ch.AddRemoteCandidate(CreateUdpCandidate(RELAY_PORT_TYPE, "2.2.2.2", 2, 2));
4643 EXPECT_TRUE_WAIT(ch.connections().size() == 4, kDefaultTimeout);
4644
4645 // Relay/Relay should be the first since it hasn't been pinged before.
4646 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE);
4647
4648 // Local/Relay is the final one.
4649 VerifyNextPingableConnection(LOCAL_PORT_TYPE, RELAY_PORT_TYPE);
4650
4651 // Now, every connection has been pinged once. The next one should be
4652 // Relay/Relay.
4653 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE);
4654 }
4655
4656 // Test that when we receive a new remote candidate, they will be tried first
4657 // before we re-ping Relay/Relay connections again.
TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,TestNoStarvationOnNonRelayConnection)4658 TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,
4659 TestNoStarvationOnNonRelayConnection) {
4660 P2PTransportChannel& ch = StartTransportChannel(true, 500);
4661 EXPECT_TRUE_WAIT(ch.ports().size() == 2, kDefaultTimeout);
4662 EXPECT_EQ(ch.ports()[0]->Type(), LOCAL_PORT_TYPE);
4663 EXPECT_EQ(ch.ports()[1]->Type(), RELAY_PORT_TYPE);
4664
4665 ch.AddRemoteCandidate(CreateUdpCandidate(RELAY_PORT_TYPE, "1.1.1.1", 1, 1));
4666 EXPECT_TRUE_WAIT(ch.connections().size() == 2, kDefaultTimeout);
4667
4668 // Initially, only have Relay/Relay and Local/Relay. Ping Relay/Relay first.
4669 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE);
4670
4671 // Next, ping Local/Relay.
4672 VerifyNextPingableConnection(LOCAL_PORT_TYPE, RELAY_PORT_TYPE);
4673
4674 // Remote Local candidate arrives.
4675 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
4676 EXPECT_TRUE_WAIT(ch.connections().size() == 4, kDefaultTimeout);
4677
4678 // Local/Local should be the first since it hasn't been pinged before.
4679 VerifyNextPingableConnection(LOCAL_PORT_TYPE, LOCAL_PORT_TYPE);
4680
4681 // Relay/Local is the final one.
4682 VerifyNextPingableConnection(RELAY_PORT_TYPE, LOCAL_PORT_TYPE);
4683
4684 // Now, every connection has been pinged once. The next one should be
4685 // Relay/Relay.
4686 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE);
4687 }
4688
4689 // Test skip_relay_to_non_relay_connections field-trial.
4690 // I.e that we never create connection between relay and non-relay.
TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,TestSkipRelayToNonRelayConnectionsFieldTrial)4691 TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,
4692 TestSkipRelayToNonRelayConnectionsFieldTrial) {
4693 webrtc::test::ScopedFieldTrials field_trials(
4694 "WebRTC-IceFieldTrials/skip_relay_to_non_relay_connections:true/");
4695 P2PTransportChannel& ch = StartTransportChannel(true, 500);
4696 EXPECT_TRUE_WAIT(ch.ports().size() == 2, kDefaultTimeout);
4697 EXPECT_EQ(ch.ports()[0]->Type(), LOCAL_PORT_TYPE);
4698 EXPECT_EQ(ch.ports()[1]->Type(), RELAY_PORT_TYPE);
4699
4700 // Remote Relay candidate arrives.
4701 ch.AddRemoteCandidate(CreateUdpCandidate(RELAY_PORT_TYPE, "1.1.1.1", 1, 1));
4702 EXPECT_TRUE_WAIT(ch.connections().size() == 1, kDefaultTimeout);
4703
4704 // Remote Local candidate arrives.
4705 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
4706 EXPECT_TRUE_WAIT(ch.connections().size() == 2, kDefaultTimeout);
4707 }
4708
4709 // Test the ping sequence is UDP Relay/Relay followed by TCP Relay/Relay,
4710 // followed by the rest.
TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest,TestTcpTurn)4711 TEST_F(P2PTransportChannelMostLikelyToWorkFirstTest, TestTcpTurn) {
4712 // Add a Tcp Turn server.
4713 turn_server()->AddInternalSocket(kTurnTcpIntAddr, PROTO_TCP);
4714 RelayServerConfig config;
4715 config.credentials = kRelayCredentials;
4716 config.ports.push_back(ProtocolAddress(kTurnTcpIntAddr, PROTO_TCP));
4717 allocator()->AddTurnServer(config);
4718
4719 P2PTransportChannel& ch = StartTransportChannel(true, 500);
4720 EXPECT_TRUE_WAIT(ch.ports().size() == 3, kDefaultTimeout);
4721 EXPECT_EQ(ch.ports()[0]->Type(), LOCAL_PORT_TYPE);
4722 EXPECT_EQ(ch.ports()[1]->Type(), RELAY_PORT_TYPE);
4723 EXPECT_EQ(ch.ports()[2]->Type(), RELAY_PORT_TYPE);
4724
4725 // Remote Relay candidate arrives.
4726 ch.AddRemoteCandidate(CreateUdpCandidate(RELAY_PORT_TYPE, "1.1.1.1", 1, 1));
4727 EXPECT_TRUE_WAIT(ch.connections().size() == 3, kDefaultTimeout);
4728
4729 // UDP Relay/Relay should be pinged first.
4730 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE);
4731
4732 // TCP Relay/Relay is the next.
4733 VerifyNextPingableConnection(RELAY_PORT_TYPE, RELAY_PORT_TYPE,
4734 TCP_PROTOCOL_NAME);
4735
4736 // Finally, Local/Relay will be pinged.
4737 VerifyNextPingableConnection(LOCAL_PORT_TYPE, RELAY_PORT_TYPE);
4738 }
4739
4740 // Test that a resolver is created, asked for a result, and destroyed
4741 // when the address is a hostname. The destruction should happen even
4742 // if the channel is not destroyed.
TEST(P2PTransportChannelResolverTest,HostnameCandidateIsResolved)4743 TEST(P2PTransportChannelResolverTest, HostnameCandidateIsResolved) {
4744 rtc::MockAsyncResolver mock_async_resolver;
4745 EXPECT_CALL(mock_async_resolver, GetError()).WillOnce(Return(0));
4746 EXPECT_CALL(mock_async_resolver, GetResolvedAddress(_, _))
4747 .WillOnce(Return(true));
4748 // Destroy is called asynchronously after the address is resolved,
4749 // so we need a variable to wait on.
4750 bool destroy_called = false;
4751 EXPECT_CALL(mock_async_resolver, Destroy(_))
4752 .WillOnce(Assign(&destroy_called, true));
4753 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
4754 EXPECT_CALL(mock_async_resolver_factory, Create())
4755 .WillOnce(Return(&mock_async_resolver));
4756
4757 FakePortAllocator allocator(rtc::Thread::Current(), nullptr);
4758 P2PTransportChannel channel("tn", 0, &allocator,
4759 &mock_async_resolver_factory);
4760 Candidate hostname_candidate;
4761 SocketAddress hostname_address("fake.test", 1000);
4762 hostname_candidate.set_address(hostname_address);
4763 channel.AddRemoteCandidate(hostname_candidate);
4764
4765 ASSERT_EQ_WAIT(1u, channel.remote_candidates().size(), kDefaultTimeout);
4766 const RemoteCandidate& candidate = channel.remote_candidates()[0];
4767 EXPECT_FALSE(candidate.address().IsUnresolvedIP());
4768 WAIT(destroy_called, kShortTimeout);
4769 }
4770
4771 // Test that if we signal a hostname candidate after the remote endpoint
4772 // discovers a prflx remote candidate with the same underlying IP address, the
4773 // prflx candidate is updated to a host candidate after the name resolution is
4774 // done.
TEST_F(P2PTransportChannelTest,PeerReflexiveCandidateBeforeSignalingWithMdnsName)4775 TEST_F(P2PTransportChannelTest,
4776 PeerReflexiveCandidateBeforeSignalingWithMdnsName) {
4777 rtc::MockAsyncResolver mock_async_resolver;
4778 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
4779 EXPECT_CALL(mock_async_resolver_factory, Create())
4780 .WillOnce(Return(&mock_async_resolver));
4781
4782 // ep1 and ep2 will only gather host candidates with addresses
4783 // kPublicAddrs[0] and kPublicAddrs[1], respectively.
4784 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
4785 // ICE parameter will be set up when creating the channels.
4786 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
4787 GetEndpoint(0)->network_manager_.set_mdns_responder(
4788 std::make_unique<webrtc::FakeMdnsResponder>(rtc::Thread::Current()));
4789 GetEndpoint(1)->async_resolver_factory_ = &mock_async_resolver_factory;
4790 CreateChannels();
4791 // Pause sending candidates from both endpoints until we find out what port
4792 // number is assgined to ep1's host candidate.
4793 PauseCandidates(0);
4794 PauseCandidates(1);
4795 ASSERT_EQ_WAIT(1u, GetEndpoint(0)->saved_candidates_.size(), kMediumTimeout);
4796 ASSERT_EQ(1u, GetEndpoint(0)->saved_candidates_[0]->candidates.size());
4797 const auto& local_candidate =
4798 GetEndpoint(0)->saved_candidates_[0]->candidates[0];
4799 // The IP address of ep1's host candidate should be obfuscated.
4800 EXPECT_TRUE(local_candidate.address().IsUnresolvedIP());
4801 // This is the underlying private IP address of the same candidate at ep1.
4802 const auto local_address = rtc::SocketAddress(
4803 kPublicAddrs[0].ipaddr(), local_candidate.address().port());
4804 // Let ep2 signal its candidate to ep1. ep1 should form a candidate
4805 // pair and start to ping. After receiving the ping, ep2 discovers a prflx
4806 // remote candidate and form a candidate pair as well.
4807 ResumeCandidates(1);
4808 ASSERT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr, kMediumTimeout);
4809 // ep2 should have the selected connection connected to the prflx remote
4810 // candidate.
4811 const Connection* selected_connection = nullptr;
4812 ASSERT_TRUE_WAIT(
4813 (selected_connection = ep2_ch1()->selected_connection()) != nullptr,
4814 kMediumTimeout);
4815 EXPECT_EQ(PRFLX_PORT_TYPE, selected_connection->remote_candidate().type());
4816 EXPECT_EQ(kIceUfrag[0], selected_connection->remote_candidate().username());
4817 EXPECT_EQ(kIcePwd[0], selected_connection->remote_candidate().password());
4818 // Set expectation before ep1 signals a hostname candidate.
4819 {
4820 InSequence sequencer;
4821 EXPECT_CALL(mock_async_resolver, Start(_));
4822 EXPECT_CALL(mock_async_resolver, GetError()).WillOnce(Return(0));
4823 // Let the mock resolver of ep2 receives the correct resolution.
4824 EXPECT_CALL(mock_async_resolver, GetResolvedAddress(_, _))
4825 .WillOnce(DoAll(SetArgPointee<1>(local_address), Return(true)));
4826 }
4827 // Destroy is called asynchronously after the address is resolved,
4828 // so we need a variable to wait on.
4829 bool destroy_called = false;
4830 EXPECT_CALL(mock_async_resolver, Destroy(_))
4831 .WillOnce(Assign(&destroy_called, true));
4832 ResumeCandidates(0);
4833 // Verify ep2's selected connection is updated to use the 'local' candidate.
4834 EXPECT_EQ_WAIT(LOCAL_PORT_TYPE,
4835 ep2_ch1()->selected_connection()->remote_candidate().type(),
4836 kMediumTimeout);
4837 EXPECT_EQ(selected_connection, ep2_ch1()->selected_connection());
4838
4839 WAIT(destroy_called, kShortTimeout);
4840 DestroyChannels();
4841 }
4842
4843 // Test that if we discover a prflx candidate during the process of name
4844 // resolution for a remote hostname candidate, we update the prflx candidate to
4845 // a host candidate if the hostname candidate turns out to have the same IP
4846 // address after the resolution completes.
TEST_F(P2PTransportChannelTest,PeerReflexiveCandidateDuringResolvingHostCandidateWithMdnsName)4847 TEST_F(P2PTransportChannelTest,
4848 PeerReflexiveCandidateDuringResolvingHostCandidateWithMdnsName) {
4849 auto mock_async_resolver = new NiceMock<rtc::MockAsyncResolver>();
4850 ON_CALL(*mock_async_resolver, Destroy).WillByDefault([mock_async_resolver] {
4851 delete mock_async_resolver;
4852 });
4853 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
4854 EXPECT_CALL(mock_async_resolver_factory, Create())
4855 .WillOnce(Return(mock_async_resolver));
4856
4857 // ep1 and ep2 will only gather host candidates with addresses
4858 // kPublicAddrs[0] and kPublicAddrs[1], respectively.
4859 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
4860 // ICE parameter will be set up when creating the channels.
4861 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
4862 GetEndpoint(0)->network_manager_.set_mdns_responder(
4863 std::make_unique<webrtc::FakeMdnsResponder>(rtc::Thread::Current()));
4864 GetEndpoint(1)->async_resolver_factory_ = &mock_async_resolver_factory;
4865 CreateChannels();
4866 // Pause sending candidates from both endpoints until we find out what port
4867 // number is assgined to ep1's host candidate.
4868 PauseCandidates(0);
4869 PauseCandidates(1);
4870 ASSERT_EQ_WAIT(1u, GetEndpoint(0)->saved_candidates_.size(), kMediumTimeout);
4871 ASSERT_EQ(1u, GetEndpoint(0)->saved_candidates_[0]->candidates.size());
4872 const auto& local_candidate =
4873 GetEndpoint(0)->saved_candidates_[0]->candidates[0];
4874 // The IP address of ep1's host candidate should be obfuscated.
4875 ASSERT_TRUE(local_candidate.address().IsUnresolvedIP());
4876 // This is the underlying private IP address of the same candidate at ep1.
4877 const auto local_address = rtc::SocketAddress(
4878 kPublicAddrs[0].ipaddr(), local_candidate.address().port());
4879 bool mock_async_resolver_started = false;
4880 // Not signaling done yet, and only make sure we are in the process of
4881 // resolution.
4882 EXPECT_CALL(*mock_async_resolver, Start(_))
4883 .WillOnce(InvokeWithoutArgs([&mock_async_resolver_started]() {
4884 mock_async_resolver_started = true;
4885 }));
4886 // Let ep1 signal its hostname candidate to ep2.
4887 ResumeCandidates(0);
4888 ASSERT_TRUE_WAIT(mock_async_resolver_started, kMediumTimeout);
4889 // Now that ep2 is in the process of resolving the hostname candidate signaled
4890 // by ep1. Let ep2 signal its host candidate with an IP address to ep1, so
4891 // that ep1 can form a candidate pair, select it and start to ping ep2.
4892 ResumeCandidates(1);
4893 ASSERT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr, kMediumTimeout);
4894 // Let the mock resolver of ep2 receives the correct resolution.
4895 EXPECT_CALL(*mock_async_resolver, GetResolvedAddress(_, _))
4896 .WillOnce(DoAll(SetArgPointee<1>(local_address), Return(true)));
4897 // Upon receiving a ping from ep1, ep2 adds a prflx candidate from the
4898 // unknown address and establishes a connection.
4899 //
4900 // There is a caveat in our implementation associated with this expectation.
4901 // See the big comment in P2PTransportChannel::OnUnknownAddress.
4902 ASSERT_TRUE_WAIT(ep2_ch1()->selected_connection() != nullptr, kMediumTimeout);
4903 EXPECT_EQ(PRFLX_PORT_TYPE,
4904 ep2_ch1()->selected_connection()->remote_candidate().type());
4905 // ep2 should also be able resolve the hostname candidate. The resolved remote
4906 // host candidate should be merged with the prflx remote candidate.
4907 mock_async_resolver->SignalDone(mock_async_resolver);
4908 EXPECT_EQ_WAIT(LOCAL_PORT_TYPE,
4909 ep2_ch1()->selected_connection()->remote_candidate().type(),
4910 kMediumTimeout);
4911 EXPECT_EQ(1u, ep2_ch1()->remote_candidates().size());
4912
4913 DestroyChannels();
4914 }
4915
4916 // Test that if we only gather and signal a host candidate, the IP address of
4917 // which is obfuscated by an mDNS name, and if the peer can complete the name
4918 // resolution with the correct IP address, we can have a p2p connection.
TEST_F(P2PTransportChannelTest,CanConnectWithHostCandidateWithMdnsName)4919 TEST_F(P2PTransportChannelTest, CanConnectWithHostCandidateWithMdnsName) {
4920 NiceMock<rtc::MockAsyncResolver> mock_async_resolver;
4921 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
4922 EXPECT_CALL(mock_async_resolver_factory, Create())
4923 .WillOnce(Return(&mock_async_resolver));
4924
4925 // ep1 and ep2 will only gather host candidates with addresses
4926 // kPublicAddrs[0] and kPublicAddrs[1], respectively.
4927 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
4928 // ICE parameter will be set up when creating the channels.
4929 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
4930 GetEndpoint(0)->network_manager_.set_mdns_responder(
4931 std::make_unique<webrtc::FakeMdnsResponder>(rtc::Thread::Current()));
4932 GetEndpoint(1)->async_resolver_factory_ = &mock_async_resolver_factory;
4933 CreateChannels();
4934 // Pause sending candidates from both endpoints until we find out what port
4935 // number is assgined to ep1's host candidate.
4936 PauseCandidates(0);
4937 PauseCandidates(1);
4938 ASSERT_EQ_WAIT(1u, GetEndpoint(0)->saved_candidates_.size(), kMediumTimeout);
4939 ASSERT_EQ(1u, GetEndpoint(0)->saved_candidates_[0]->candidates.size());
4940 const auto& local_candidate_ep1 =
4941 GetEndpoint(0)->saved_candidates_[0]->candidates[0];
4942 // The IP address of ep1's host candidate should be obfuscated.
4943 EXPECT_TRUE(local_candidate_ep1.address().IsUnresolvedIP());
4944 // This is the underlying private IP address of the same candidate at ep1,
4945 // and let the mock resolver of ep2 receive the correct resolution.
4946 rtc::SocketAddress resolved_address_ep1(local_candidate_ep1.address());
4947 resolved_address_ep1.SetResolvedIP(kPublicAddrs[0].ipaddr());
4948
4949 EXPECT_CALL(mock_async_resolver, GetResolvedAddress(_, _))
4950 .WillOnce(DoAll(SetArgPointee<1>(resolved_address_ep1), Return(true)));
4951 // Let ep1 signal its hostname candidate to ep2.
4952 ResumeCandidates(0);
4953
4954 // We should be able to receive a ping from ep2 and establish a connection
4955 // with a peer reflexive candidate from ep2.
4956 ASSERT_TRUE_WAIT((ep1_ch1()->selected_connection()) != nullptr,
4957 kMediumTimeout);
4958 EXPECT_EQ(LOCAL_PORT_TYPE,
4959 ep1_ch1()->selected_connection()->local_candidate().type());
4960 EXPECT_EQ(PRFLX_PORT_TYPE,
4961 ep1_ch1()->selected_connection()->remote_candidate().type());
4962
4963 DestroyChannels();
4964 }
4965
4966 // Test that when the IP of a host candidate is concealed by an mDNS name, the
4967 // stats from the gathering ICE endpoint do not reveal the address of this local
4968 // host candidate or the related address of a local srflx candidate from the
4969 // same endpoint. Also, the remote ICE endpoint that successfully resolves a
4970 // signaled host candidate with an mDNS name should not reveal the address of
4971 // this remote host candidate in stats.
TEST_F(P2PTransportChannelTest,CandidatesSanitizedInStatsWhenMdnsObfuscationEnabled)4972 TEST_F(P2PTransportChannelTest,
4973 CandidatesSanitizedInStatsWhenMdnsObfuscationEnabled) {
4974 NiceMock<rtc::MockAsyncResolver> mock_async_resolver;
4975 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
4976 EXPECT_CALL(mock_async_resolver_factory, Create())
4977 .WillOnce(Return(&mock_async_resolver));
4978
4979 // ep1 and ep2 will gather host candidates with addresses
4980 // kPublicAddrs[0] and kPublicAddrs[1], respectively. ep1 also gathers a srflx
4981 // and a relay candidates.
4982 ConfigureEndpoints(OPEN, OPEN,
4983 kDefaultPortAllocatorFlags | PORTALLOCATOR_DISABLE_TCP,
4984 kOnlyLocalPorts);
4985 // ICE parameter will be set up when creating the channels.
4986 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
4987 GetEndpoint(0)->network_manager_.set_mdns_responder(
4988 std::make_unique<webrtc::FakeMdnsResponder>(rtc::Thread::Current()));
4989 GetEndpoint(1)->async_resolver_factory_ = &mock_async_resolver_factory;
4990 CreateChannels();
4991 // Pause sending candidates from both endpoints until we find out what port
4992 // number is assigned to ep1's host candidate.
4993 PauseCandidates(0);
4994 PauseCandidates(1);
4995 // Ep1 has a UDP host, a srflx and a relay candidates.
4996 ASSERT_EQ_WAIT(3u, GetEndpoint(0)->saved_candidates_.size(), kMediumTimeout);
4997 ASSERT_EQ_WAIT(1u, GetEndpoint(1)->saved_candidates_.size(), kMediumTimeout);
4998
4999 for (const auto& candidates_data : GetEndpoint(0)->saved_candidates_) {
5000 ASSERT_EQ(1u, candidates_data->candidates.size());
5001 const auto& local_candidate_ep1 = candidates_data->candidates[0];
5002 if (local_candidate_ep1.type() == LOCAL_PORT_TYPE) {
5003 // This is the underlying private IP address of the same candidate at ep1,
5004 // and let the mock resolver of ep2 receive the correct resolution.
5005 rtc::SocketAddress resolved_address_ep1(local_candidate_ep1.address());
5006 resolved_address_ep1.SetResolvedIP(kPublicAddrs[0].ipaddr());
5007 EXPECT_CALL(mock_async_resolver, GetResolvedAddress(_, _))
5008 .WillOnce(
5009 DoAll(SetArgPointee<1>(resolved_address_ep1), Return(true)));
5010 break;
5011 }
5012 }
5013 ResumeCandidates(0);
5014 ResumeCandidates(1);
5015
5016 ASSERT_EQ_WAIT(kIceGatheringComplete, ep1_ch1()->gathering_state(),
5017 kMediumTimeout);
5018 // We should have the following candidate pairs on both endpoints:
5019 // ep1_host <-> ep2_host, ep1_srflx <-> ep2_host, ep1_relay <-> ep2_host
5020 ASSERT_EQ_WAIT(3u, ep1_ch1()->connections().size(), kMediumTimeout);
5021 ASSERT_EQ_WAIT(3u, ep2_ch1()->connections().size(), kMediumTimeout);
5022
5023 IceTransportStats ice_transport_stats1;
5024 IceTransportStats ice_transport_stats2;
5025 ep1_ch1()->GetStats(&ice_transport_stats1);
5026 ep2_ch1()->GetStats(&ice_transport_stats2);
5027 EXPECT_EQ(3u, ice_transport_stats1.connection_infos.size());
5028 EXPECT_EQ(3u, ice_transport_stats1.candidate_stats_list.size());
5029 EXPECT_EQ(3u, ice_transport_stats2.connection_infos.size());
5030 // Check the stats of ep1 seen by ep1.
5031 for (const auto& connection_info : ice_transport_stats1.connection_infos) {
5032 const auto& local_candidate = connection_info.local_candidate;
5033 if (local_candidate.type() == LOCAL_PORT_TYPE) {
5034 EXPECT_TRUE(local_candidate.address().IsUnresolvedIP());
5035 } else if (local_candidate.type() == STUN_PORT_TYPE) {
5036 EXPECT_TRUE(local_candidate.related_address().IsAnyIP());
5037 } else if (local_candidate.type() == RELAY_PORT_TYPE) {
5038 // The related address of the relay candidate should be equal to the
5039 // srflx address. Note that NAT is not configured, hence the following
5040 // expectation.
5041 EXPECT_EQ(kPublicAddrs[0].ipaddr(),
5042 local_candidate.related_address().ipaddr());
5043 } else {
5044 FAIL();
5045 }
5046 }
5047 // Check the stats of ep1 seen by ep2.
5048 for (const auto& connection_info : ice_transport_stats2.connection_infos) {
5049 const auto& remote_candidate = connection_info.remote_candidate;
5050 if (remote_candidate.type() == LOCAL_PORT_TYPE) {
5051 EXPECT_TRUE(remote_candidate.address().IsUnresolvedIP());
5052 } else if (remote_candidate.type() == STUN_PORT_TYPE) {
5053 EXPECT_TRUE(remote_candidate.related_address().IsAnyIP());
5054 } else if (remote_candidate.type() == RELAY_PORT_TYPE) {
5055 EXPECT_EQ(kPublicAddrs[0].ipaddr(),
5056 remote_candidate.related_address().ipaddr());
5057 } else {
5058 FAIL();
5059 }
5060 }
5061 DestroyChannels();
5062 }
5063
TEST_F(P2PTransportChannelTest,ConnectingIncreasesSelectedCandidatePairChanges)5064 TEST_F(P2PTransportChannelTest,
5065 ConnectingIncreasesSelectedCandidatePairChanges) {
5066 rtc::ScopedFakeClock clock;
5067 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5068 kDefaultPortAllocatorFlags);
5069 CreateChannels();
5070
5071 IceTransportStats ice_transport_stats;
5072 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5073 EXPECT_EQ(0u, ice_transport_stats.selected_candidate_pair_changes);
5074
5075 // Let the channels connect.
5076 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5077 kMediumTimeout, clock);
5078
5079 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5080 EXPECT_EQ(1u, ice_transport_stats.selected_candidate_pair_changes);
5081
5082 DestroyChannels();
5083 }
5084
TEST_F(P2PTransportChannelTest,DisconnectedIncreasesSelectedCandidatePairChanges)5085 TEST_F(P2PTransportChannelTest,
5086 DisconnectedIncreasesSelectedCandidatePairChanges) {
5087 rtc::ScopedFakeClock clock;
5088 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5089 kDefaultPortAllocatorFlags);
5090 CreateChannels();
5091
5092 IceTransportStats ice_transport_stats;
5093 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5094 EXPECT_EQ(0u, ice_transport_stats.selected_candidate_pair_changes);
5095
5096 // Let the channels connect.
5097 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5098 kMediumTimeout, clock);
5099
5100 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5101 EXPECT_EQ(1u, ice_transport_stats.selected_candidate_pair_changes);
5102
5103 // Prune connections and wait for disconnect.
5104 for (Connection* con : ep1_ch1()->connections()) {
5105 con->Prune();
5106 }
5107 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() == nullptr,
5108 kMediumTimeout, clock);
5109
5110 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5111 EXPECT_EQ(2u, ice_transport_stats.selected_candidate_pair_changes);
5112
5113 DestroyChannels();
5114 }
5115
TEST_F(P2PTransportChannelTest,NewSelectionIncreasesSelectedCandidatePairChanges)5116 TEST_F(P2PTransportChannelTest,
5117 NewSelectionIncreasesSelectedCandidatePairChanges) {
5118 rtc::ScopedFakeClock clock;
5119 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5120 kDefaultPortAllocatorFlags);
5121 CreateChannels();
5122
5123 IceTransportStats ice_transport_stats;
5124 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5125 EXPECT_EQ(0u, ice_transport_stats.selected_candidate_pair_changes);
5126
5127 // Let the channels connect.
5128 EXPECT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5129 kMediumTimeout, clock);
5130
5131 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5132 EXPECT_EQ(1u, ice_transport_stats.selected_candidate_pair_changes);
5133
5134 // Prune the currently selected connection and wait for selection
5135 // of a new one.
5136 const Connection* selected_connection = ep1_ch1()->selected_connection();
5137 for (Connection* con : ep1_ch1()->connections()) {
5138 if (con == selected_connection) {
5139 con->Prune();
5140 }
5141 }
5142 EXPECT_TRUE_SIMULATED_WAIT(
5143 ep1_ch1()->selected_connection() != nullptr &&
5144 (ep1_ch1()->GetStats(&ice_transport_stats),
5145 ice_transport_stats.selected_candidate_pair_changes >= 2u),
5146 kMediumTimeout, clock);
5147
5148 ASSERT_TRUE(ep1_ch1()->GetStats(&ice_transport_stats));
5149 EXPECT_GE(ice_transport_stats.selected_candidate_pair_changes, 2u);
5150
5151 DestroyChannels();
5152 }
5153
5154 // A similar test as above to check the selected candidate pair is sanitized
5155 // when it is queried via GetSelectedCandidatePair.
TEST_F(P2PTransportChannelTest,SelectedCandidatePairSanitizedWhenMdnsObfuscationEnabled)5156 TEST_F(P2PTransportChannelTest,
5157 SelectedCandidatePairSanitizedWhenMdnsObfuscationEnabled) {
5158 NiceMock<rtc::MockAsyncResolver> mock_async_resolver;
5159 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
5160 EXPECT_CALL(mock_async_resolver_factory, Create())
5161 .WillOnce(Return(&mock_async_resolver));
5162
5163 // ep1 and ep2 will gather host candidates with addresses
5164 // kPublicAddrs[0] and kPublicAddrs[1], respectively.
5165 ConfigureEndpoints(OPEN, OPEN, kOnlyLocalPorts, kOnlyLocalPorts);
5166 // ICE parameter will be set up when creating the channels.
5167 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
5168 GetEndpoint(0)->network_manager_.set_mdns_responder(
5169 std::make_unique<webrtc::FakeMdnsResponder>(rtc::Thread::Current()));
5170 GetEndpoint(1)->async_resolver_factory_ = &mock_async_resolver_factory;
5171 CreateChannels();
5172 // Pause sending candidates from both endpoints until we find out what port
5173 // number is assigned to ep1's host candidate.
5174 PauseCandidates(0);
5175 PauseCandidates(1);
5176 ASSERT_EQ_WAIT(1u, GetEndpoint(0)->saved_candidates_.size(), kMediumTimeout);
5177 const auto& candidates_data = GetEndpoint(0)->saved_candidates_[0];
5178 ASSERT_EQ(1u, candidates_data->candidates.size());
5179 const auto& local_candidate_ep1 = candidates_data->candidates[0];
5180 ASSERT_TRUE(local_candidate_ep1.type() == LOCAL_PORT_TYPE);
5181 // This is the underlying private IP address of the same candidate at ep1,
5182 // and let the mock resolver of ep2 receive the correct resolution.
5183 rtc::SocketAddress resolved_address_ep1(local_candidate_ep1.address());
5184 resolved_address_ep1.SetResolvedIP(kPublicAddrs[0].ipaddr());
5185 EXPECT_CALL(mock_async_resolver, GetResolvedAddress(_, _))
5186 .WillOnce(DoAll(SetArgPointee<1>(resolved_address_ep1), Return(true)));
5187 ResumeCandidates(0);
5188 ResumeCandidates(1);
5189
5190 ASSERT_TRUE_WAIT(ep1_ch1()->selected_connection() != nullptr &&
5191 ep2_ch1()->selected_connection() != nullptr,
5192 kMediumTimeout);
5193
5194 const auto pair_ep1 = ep1_ch1()->GetSelectedCandidatePair();
5195 ASSERT_TRUE(pair_ep1.has_value());
5196 EXPECT_EQ(LOCAL_PORT_TYPE, pair_ep1->local_candidate().type());
5197 EXPECT_TRUE(pair_ep1->local_candidate().address().IsUnresolvedIP());
5198
5199 const auto pair_ep2 = ep2_ch1()->GetSelectedCandidatePair();
5200 ASSERT_TRUE(pair_ep2.has_value());
5201 EXPECT_EQ(LOCAL_PORT_TYPE, pair_ep2->remote_candidate().type());
5202 EXPECT_TRUE(pair_ep2->remote_candidate().address().IsUnresolvedIP());
5203
5204 DestroyChannels();
5205 }
5206
TEST_F(P2PTransportChannelTest,NoPairOfLocalRelayCandidateWithRemoteMdnsCandidate)5207 TEST_F(P2PTransportChannelTest,
5208 NoPairOfLocalRelayCandidateWithRemoteMdnsCandidate) {
5209 const int kOnlyRelayPorts = cricket::PORTALLOCATOR_DISABLE_UDP |
5210 cricket::PORTALLOCATOR_DISABLE_STUN |
5211 cricket::PORTALLOCATOR_DISABLE_TCP;
5212 // We use one endpoint to test the behavior of adding remote candidates, and
5213 // this endpoint only gathers relay candidates.
5214 ConfigureEndpoints(OPEN, OPEN, kOnlyRelayPorts, kDefaultPortAllocatorFlags);
5215 GetEndpoint(0)->cd1_.ch_.reset(CreateChannel(
5216 0, ICE_CANDIDATE_COMPONENT_DEFAULT, kIceParams[0], kIceParams[1]));
5217 IceConfig config;
5218 // Start gathering and we should have only a single relay port.
5219 ep1_ch1()->SetIceConfig(config);
5220 ep1_ch1()->MaybeStartGathering();
5221 EXPECT_EQ_WAIT(IceGatheringState::kIceGatheringComplete,
5222 ep1_ch1()->gathering_state(), kDefaultTimeout);
5223 EXPECT_EQ(1u, ep1_ch1()->ports().size());
5224 // Add a plain remote host candidate and three remote mDNS candidates with the
5225 // host, srflx and relay types. Note that the candidates differ in their
5226 // ports.
5227 cricket::Candidate host_candidate = CreateUdpCandidate(
5228 LOCAL_PORT_TYPE, "1.1.1.1", 1 /* port */, 0 /* priority */);
5229 ep1_ch1()->AddRemoteCandidate(host_candidate);
5230
5231 std::vector<cricket::Candidate> mdns_candidates;
5232 mdns_candidates.push_back(CreateUdpCandidate(LOCAL_PORT_TYPE, "example.local",
5233 2 /* port */, 0 /* priority */));
5234 mdns_candidates.push_back(CreateUdpCandidate(STUN_PORT_TYPE, "example.local",
5235 3 /* port */, 0 /* priority */));
5236 mdns_candidates.push_back(CreateUdpCandidate(RELAY_PORT_TYPE, "example.local",
5237 4 /* port */, 0 /* priority */));
5238 // We just resolve the hostname to 1.1.1.1, and add the candidates with this
5239 // address directly to simulate the process of adding remote candidates with
5240 // the name resolution.
5241 for (auto& mdns_candidate : mdns_candidates) {
5242 rtc::SocketAddress resolved_address(mdns_candidate.address());
5243 resolved_address.SetResolvedIP(0x1111); // 1.1.1.1
5244 mdns_candidate.set_address(resolved_address);
5245 EXPECT_FALSE(mdns_candidate.address().IsUnresolvedIP());
5246 ep1_ch1()->AddRemoteCandidate(mdns_candidate);
5247 }
5248
5249 // All remote candidates should have been successfully added.
5250 EXPECT_EQ(4u, ep1_ch1()->remote_candidates().size());
5251
5252 // Expect that there is no connection paired with any mDNS candidate.
5253 ASSERT_EQ(1u, ep1_ch1()->connections().size());
5254 ASSERT_NE(nullptr, ep1_ch1()->connections()[0]);
5255 EXPECT_EQ(
5256 "1.1.1.1:1",
5257 ep1_ch1()->connections()[0]->remote_candidate().address().ToString());
5258 DestroyChannels();
5259 }
5260
5261 class MockMdnsResponder : public webrtc::MdnsResponderInterface {
5262 public:
5263 MOCK_METHOD(void,
5264 CreateNameForAddress,
5265 (const rtc::IPAddress&, NameCreatedCallback),
5266 (override));
5267 MOCK_METHOD(void,
5268 RemoveNameForAddress,
5269 (const rtc::IPAddress&, NameRemovedCallback),
5270 (override));
5271 };
5272
TEST_F(P2PTransportChannelTest,SrflxCandidateCanBeGatheredBeforeMdnsCandidateToCreateConnection)5273 TEST_F(P2PTransportChannelTest,
5274 SrflxCandidateCanBeGatheredBeforeMdnsCandidateToCreateConnection) {
5275 // ep1 and ep2 will only gather host and srflx candidates with base addresses
5276 // kPublicAddrs[0] and kPublicAddrs[1], respectively, and we use a shared
5277 // socket in gathering.
5278 const auto kOnlyLocalAndStunPorts =
5279 cricket::PORTALLOCATOR_DISABLE_RELAY |
5280 cricket::PORTALLOCATOR_DISABLE_TCP |
5281 cricket::PORTALLOCATOR_ENABLE_SHARED_SOCKET;
5282 // ep1 is configured with a NAT so that we do gather a srflx candidate.
5283 ConfigureEndpoints(NAT_FULL_CONE, OPEN, kOnlyLocalAndStunPorts,
5284 kOnlyLocalAndStunPorts);
5285 // ICE parameter will be set up when creating the channels.
5286 set_remote_ice_parameter_source(FROM_SETICEPARAMETERS);
5287 // Use a mock mDNS responder, which does not complete the name registration by
5288 // ignoring the completion callback.
5289 auto mock_mdns_responder = std::make_unique<MockMdnsResponder>();
5290 EXPECT_CALL(*mock_mdns_responder, CreateNameForAddress(_, _))
5291 .Times(1)
5292 .WillOnce(Return());
5293 GetEndpoint(0)->network_manager_.set_mdns_responder(
5294 std::move(mock_mdns_responder));
5295
5296 CreateChannels();
5297
5298 // We should be able to form a srflx-host connection to ep2.
5299 ASSERT_TRUE_WAIT((ep1_ch1()->selected_connection()) != nullptr,
5300 kMediumTimeout);
5301 EXPECT_EQ(STUN_PORT_TYPE,
5302 ep1_ch1()->selected_connection()->local_candidate().type());
5303 EXPECT_EQ(LOCAL_PORT_TYPE,
5304 ep1_ch1()->selected_connection()->remote_candidate().type());
5305
5306 DestroyChannels();
5307 }
5308
5309 // Test that after changing the candidate filter from relay-only to allowing all
5310 // types of candidates when doing continual gathering, we can gather without ICE
5311 // restart the other types of candidates that are now enabled and form candidate
5312 // pairs. Also, we verify that the relay candidates gathered previously are not
5313 // removed and are still usable for necessary route switching.
TEST_F(P2PTransportChannelTest,SurfaceHostCandidateOnCandidateFilterChangeFromRelayToAll)5314 TEST_F(P2PTransportChannelTest,
5315 SurfaceHostCandidateOnCandidateFilterChangeFromRelayToAll) {
5316 rtc::ScopedFakeClock clock;
5317
5318 ConfigureEndpoints(
5319 OPEN, OPEN,
5320 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
5321 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
5322 auto* ep1 = GetEndpoint(0);
5323 auto* ep2 = GetEndpoint(1);
5324 ep1->allocator_->SetCandidateFilter(CF_RELAY);
5325 ep2->allocator_->SetCandidateFilter(CF_RELAY);
5326 // Enable continual gathering and also resurfacing gathered candidates upon
5327 // the candidate filter changed in the ICE configuration.
5328 IceConfig ice_config = CreateIceConfig(1000, GATHER_CONTINUALLY);
5329 ice_config.surface_ice_candidates_on_ice_transport_type_changed = true;
5330 CreateChannels(ice_config, ice_config);
5331 ASSERT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5332 kDefaultTimeout, clock);
5333 ASSERT_TRUE_SIMULATED_WAIT(ep2_ch1()->selected_connection() != nullptr,
5334 kDefaultTimeout, clock);
5335 EXPECT_EQ(RELAY_PORT_TYPE,
5336 ep1_ch1()->selected_connection()->local_candidate().type());
5337 EXPECT_EQ(RELAY_PORT_TYPE,
5338 ep2_ch1()->selected_connection()->local_candidate().type());
5339
5340 // Loosen the candidate filter at ep1.
5341 ep1->allocator_->SetCandidateFilter(CF_ALL);
5342 EXPECT_TRUE_SIMULATED_WAIT(
5343 ep1_ch1()->selected_connection() != nullptr &&
5344 ep1_ch1()->selected_connection()->local_candidate().type() ==
5345 LOCAL_PORT_TYPE,
5346 kDefaultTimeout, clock);
5347 EXPECT_EQ(RELAY_PORT_TYPE,
5348 ep1_ch1()->selected_connection()->remote_candidate().type());
5349
5350 // Loosen the candidate filter at ep2.
5351 ep2->allocator_->SetCandidateFilter(CF_ALL);
5352 EXPECT_TRUE_SIMULATED_WAIT(
5353 ep2_ch1()->selected_connection() != nullptr &&
5354 ep2_ch1()->selected_connection()->local_candidate().type() ==
5355 LOCAL_PORT_TYPE,
5356 kDefaultTimeout, clock);
5357 // We have migrated to a host-host candidate pair.
5358 EXPECT_EQ(LOCAL_PORT_TYPE,
5359 ep2_ch1()->selected_connection()->remote_candidate().type());
5360
5361 // Block the traffic over non-relay-to-relay routes and expect a route change.
5362 fw()->AddRule(false, rtc::FP_ANY, kPublicAddrs[0], kPublicAddrs[1]);
5363 fw()->AddRule(false, rtc::FP_ANY, kPublicAddrs[1], kPublicAddrs[0]);
5364 fw()->AddRule(false, rtc::FP_ANY, kPublicAddrs[0], kTurnUdpExtAddr);
5365 fw()->AddRule(false, rtc::FP_ANY, kPublicAddrs[1], kTurnUdpExtAddr);
5366
5367 // We should be able to reuse the previously gathered relay candidates.
5368 EXPECT_EQ_SIMULATED_WAIT(
5369 RELAY_PORT_TYPE,
5370 ep1_ch1()->selected_connection()->local_candidate().type(),
5371 kDefaultTimeout, clock);
5372 EXPECT_EQ(RELAY_PORT_TYPE,
5373 ep1_ch1()->selected_connection()->remote_candidate().type());
5374 DestroyChannels();
5375 }
5376
5377 // A similar test as SurfaceHostCandidateOnCandidateFilterChangeFromRelayToAll,
5378 // and we should surface server-reflexive candidates that are enabled after
5379 // changing the candidate filter.
TEST_F(P2PTransportChannelTest,SurfaceSrflxCandidateOnCandidateFilterChangeFromRelayToNoHost)5380 TEST_F(P2PTransportChannelTest,
5381 SurfaceSrflxCandidateOnCandidateFilterChangeFromRelayToNoHost) {
5382 rtc::ScopedFakeClock clock;
5383 // We need an actual NAT so that the host candidate is not equivalent to the
5384 // srflx candidate; otherwise, the host candidate would still surface even
5385 // though we disable it via the candidate filter below. This is a result of
5386 // the following limitation in the current implementation:
5387 // 1. We don't generate the srflx candidate when we have public IP.
5388 // 2. We keep the host candidate in this case in CheckCandidateFilter even
5389 // though we intend to filter them.
5390 ConfigureEndpoints(
5391 NAT_FULL_CONE, NAT_FULL_CONE,
5392 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
5393 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
5394 auto* ep1 = GetEndpoint(0);
5395 auto* ep2 = GetEndpoint(1);
5396 ep1->allocator_->SetCandidateFilter(CF_RELAY);
5397 ep2->allocator_->SetCandidateFilter(CF_RELAY);
5398 // Enable continual gathering and also resurfacing gathered candidates upon
5399 // the candidate filter changed in the ICE configuration.
5400 IceConfig ice_config = CreateIceConfig(1000, GATHER_CONTINUALLY);
5401 ice_config.surface_ice_candidates_on_ice_transport_type_changed = true;
5402 CreateChannels(ice_config, ice_config);
5403 ASSERT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5404 kDefaultTimeout, clock);
5405 ASSERT_TRUE_SIMULATED_WAIT(ep2_ch1()->selected_connection() != nullptr,
5406 kDefaultTimeout, clock);
5407 const uint32_t kCandidateFilterNoHost = CF_ALL & ~CF_HOST;
5408 // Loosen the candidate filter at ep1.
5409 ep1->allocator_->SetCandidateFilter(kCandidateFilterNoHost);
5410 EXPECT_TRUE_SIMULATED_WAIT(
5411 ep1_ch1()->selected_connection() != nullptr &&
5412 ep1_ch1()->selected_connection()->local_candidate().type() ==
5413 STUN_PORT_TYPE,
5414 kDefaultTimeout, clock);
5415 EXPECT_EQ(RELAY_PORT_TYPE,
5416 ep1_ch1()->selected_connection()->remote_candidate().type());
5417
5418 // Loosen the candidate filter at ep2.
5419 ep2->allocator_->SetCandidateFilter(kCandidateFilterNoHost);
5420 EXPECT_TRUE_SIMULATED_WAIT(
5421 ep2_ch1()->selected_connection() != nullptr &&
5422 ep2_ch1()->selected_connection()->local_candidate().type() ==
5423 STUN_PORT_TYPE,
5424 kDefaultTimeout, clock);
5425 // We have migrated to a srflx-srflx candidate pair.
5426 EXPECT_EQ(STUN_PORT_TYPE,
5427 ep2_ch1()->selected_connection()->remote_candidate().type());
5428
5429 // Block the traffic over non-relay-to-relay routes and expect a route change.
5430 fw()->AddRule(false, rtc::FP_ANY, kPrivateAddrs[0], kPublicAddrs[1]);
5431 fw()->AddRule(false, rtc::FP_ANY, kPrivateAddrs[1], kPublicAddrs[0]);
5432 fw()->AddRule(false, rtc::FP_ANY, kPrivateAddrs[0], kTurnUdpExtAddr);
5433 fw()->AddRule(false, rtc::FP_ANY, kPrivateAddrs[1], kTurnUdpExtAddr);
5434 // We should be able to reuse the previously gathered relay candidates.
5435 EXPECT_EQ_SIMULATED_WAIT(
5436 RELAY_PORT_TYPE,
5437 ep1_ch1()->selected_connection()->local_candidate().type(),
5438 kDefaultTimeout, clock);
5439 EXPECT_EQ(RELAY_PORT_TYPE,
5440 ep1_ch1()->selected_connection()->remote_candidate().type());
5441 DestroyChannels();
5442 }
5443
5444 // This is the complement to
5445 // SurfaceHostCandidateOnCandidateFilterChangeFromRelayToAll, and instead of
5446 // gathering continually we only gather once, which makes the config
5447 // |surface_ice_candidates_on_ice_transport_type_changed| ineffective after the
5448 // gathering stopped.
TEST_F(P2PTransportChannelTest,CannotSurfaceTheNewlyAllowedOnFilterChangeIfNotGatheringContinually)5449 TEST_F(P2PTransportChannelTest,
5450 CannotSurfaceTheNewlyAllowedOnFilterChangeIfNotGatheringContinually) {
5451 rtc::ScopedFakeClock clock;
5452
5453 ConfigureEndpoints(
5454 OPEN, OPEN,
5455 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
5456 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
5457 auto* ep1 = GetEndpoint(0);
5458 auto* ep2 = GetEndpoint(1);
5459 ep1->allocator_->SetCandidateFilter(CF_RELAY);
5460 ep2->allocator_->SetCandidateFilter(CF_RELAY);
5461 // Only gather once.
5462 IceConfig ice_config = CreateIceConfig(1000, GATHER_ONCE);
5463 ice_config.surface_ice_candidates_on_ice_transport_type_changed = true;
5464 CreateChannels(ice_config, ice_config);
5465 ASSERT_TRUE_SIMULATED_WAIT(ep1_ch1()->selected_connection() != nullptr,
5466 kDefaultTimeout, clock);
5467 ASSERT_TRUE_SIMULATED_WAIT(ep2_ch1()->selected_connection() != nullptr,
5468 kDefaultTimeout, clock);
5469 // Loosen the candidate filter at ep1.
5470 ep1->allocator_->SetCandidateFilter(CF_ALL);
5471 // Wait for a period for any potential surfacing of new candidates.
5472 SIMULATED_WAIT(false, kDefaultTimeout, clock);
5473 EXPECT_EQ(RELAY_PORT_TYPE,
5474 ep1_ch1()->selected_connection()->local_candidate().type());
5475
5476 // Loosen the candidate filter at ep2.
5477 ep2->allocator_->SetCandidateFilter(CF_ALL);
5478 EXPECT_EQ(RELAY_PORT_TYPE,
5479 ep2_ch1()->selected_connection()->local_candidate().type());
5480 DestroyChannels();
5481 }
5482
5483 // Test that when the candidate filter is updated to be more restrictive,
5484 // candidates that 1) have already been gathered and signaled 2) but no longer
5485 // match the filter, are not removed.
TEST_F(P2PTransportChannelTest,RestrictingCandidateFilterDoesNotRemoveRegatheredCandidates)5486 TEST_F(P2PTransportChannelTest,
5487 RestrictingCandidateFilterDoesNotRemoveRegatheredCandidates) {
5488 rtc::ScopedFakeClock clock;
5489
5490 ConfigureEndpoints(
5491 OPEN, OPEN,
5492 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
5493 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
5494 auto* ep1 = GetEndpoint(0);
5495 auto* ep2 = GetEndpoint(1);
5496 ep1->allocator_->SetCandidateFilter(CF_ALL);
5497 ep2->allocator_->SetCandidateFilter(CF_ALL);
5498 // Enable continual gathering and also resurfacing gathered candidates upon
5499 // the candidate filter changed in the ICE configuration.
5500 IceConfig ice_config = CreateIceConfig(1000, GATHER_CONTINUALLY);
5501 ice_config.surface_ice_candidates_on_ice_transport_type_changed = true;
5502 // Pause candidates so we can gather all types of candidates. See
5503 // P2PTransportChannel::OnConnectionStateChange, where we would stop the
5504 // gathering when we have a strongly connected candidate pair.
5505 PauseCandidates(0);
5506 PauseCandidates(1);
5507 CreateChannels(ice_config, ice_config);
5508
5509 // We have gathered host, srflx and relay candidates.
5510 EXPECT_TRUE_SIMULATED_WAIT(ep1->saved_candidates_.size() == 3u,
5511 kDefaultTimeout, clock);
5512 ResumeCandidates(0);
5513 ResumeCandidates(1);
5514 ASSERT_TRUE_SIMULATED_WAIT(
5515 ep1_ch1()->selected_connection() != nullptr &&
5516 LOCAL_PORT_TYPE ==
5517 ep1_ch1()->selected_connection()->local_candidate().type() &&
5518 ep2_ch1()->selected_connection() != nullptr &&
5519 LOCAL_PORT_TYPE ==
5520 ep1_ch1()->selected_connection()->remote_candidate().type(),
5521 kDefaultTimeout, clock);
5522 ASSERT_TRUE_SIMULATED_WAIT(ep2_ch1()->selected_connection() != nullptr,
5523 kDefaultTimeout, clock);
5524 // Test that we have a host-host candidate pair selected and the number of
5525 // candidates signaled to the remote peer stays the same.
5526 auto test_invariants = [this]() {
5527 EXPECT_EQ(LOCAL_PORT_TYPE,
5528 ep1_ch1()->selected_connection()->local_candidate().type());
5529 EXPECT_EQ(LOCAL_PORT_TYPE,
5530 ep1_ch1()->selected_connection()->remote_candidate().type());
5531 EXPECT_THAT(ep2_ch1()->remote_candidates(), SizeIs(3));
5532 };
5533
5534 test_invariants();
5535
5536 // Set a more restrictive candidate filter at ep1.
5537 ep1->allocator_->SetCandidateFilter(CF_HOST | CF_REFLEXIVE);
5538 SIMULATED_WAIT(false, kDefaultTimeout, clock);
5539 test_invariants();
5540
5541 ep1->allocator_->SetCandidateFilter(CF_HOST);
5542 SIMULATED_WAIT(false, kDefaultTimeout, clock);
5543 test_invariants();
5544
5545 ep1->allocator_->SetCandidateFilter(CF_NONE);
5546 SIMULATED_WAIT(false, kDefaultTimeout, clock);
5547 test_invariants();
5548 DestroyChannels();
5549 }
5550
5551 // Verify that things break unless
5552 // - both parties use the surface_ice_candidates_on_ice_transport_type_changed
5553 // - both parties loosen candidate filter at the same time (approx.).
5554 //
5555 // i.e surface_ice_candidates_on_ice_transport_type_changed requires
5556 // coordination outside of webrtc to function properly.
TEST_F(P2PTransportChannelTest,SurfaceRequiresCoordination)5557 TEST_F(P2PTransportChannelTest, SurfaceRequiresCoordination) {
5558 webrtc::test::ScopedFieldTrials field_trials(
5559 "WebRTC-IceFieldTrials/skip_relay_to_non_relay_connections:true/");
5560 rtc::ScopedFakeClock clock;
5561
5562 ConfigureEndpoints(
5563 OPEN, OPEN,
5564 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET,
5565 kDefaultPortAllocatorFlags | PORTALLOCATOR_ENABLE_SHARED_SOCKET);
5566 auto* ep1 = GetEndpoint(0);
5567 auto* ep2 = GetEndpoint(1);
5568 ep1->allocator_->SetCandidateFilter(CF_RELAY);
5569 ep2->allocator_->SetCandidateFilter(CF_ALL);
5570 // Enable continual gathering and also resurfacing gathered candidates upon
5571 // the candidate filter changed in the ICE configuration.
5572 IceConfig ice_config = CreateIceConfig(1000, GATHER_CONTINUALLY);
5573 ice_config.surface_ice_candidates_on_ice_transport_type_changed = true;
5574 // Pause candidates gathering so we can gather all types of candidates. See
5575 // P2PTransportChannel::OnConnectionStateChange, where we would stop the
5576 // gathering when we have a strongly connected candidate pair.
5577 PauseCandidates(0);
5578 PauseCandidates(1);
5579 CreateChannels(ice_config, ice_config);
5580
5581 // On the caller we only have relay,
5582 // on the callee we have host, srflx and relay.
5583 EXPECT_TRUE_SIMULATED_WAIT(ep1->saved_candidates_.size() == 1u,
5584 kDefaultTimeout, clock);
5585 EXPECT_TRUE_SIMULATED_WAIT(ep2->saved_candidates_.size() == 3u,
5586 kDefaultTimeout, clock);
5587
5588 ResumeCandidates(0);
5589 ResumeCandidates(1);
5590 ASSERT_TRUE_SIMULATED_WAIT(
5591 ep1_ch1()->selected_connection() != nullptr &&
5592 RELAY_PORT_TYPE ==
5593 ep1_ch1()->selected_connection()->local_candidate().type() &&
5594 ep2_ch1()->selected_connection() != nullptr &&
5595 RELAY_PORT_TYPE ==
5596 ep1_ch1()->selected_connection()->remote_candidate().type(),
5597 kDefaultTimeout, clock);
5598 ASSERT_TRUE_SIMULATED_WAIT(ep2_ch1()->selected_connection() != nullptr,
5599 kDefaultTimeout, clock);
5600
5601 // Wait until the callee discards it's candidates
5602 // since they don't manage to connect.
5603 SIMULATED_WAIT(false, 300000, clock);
5604
5605 // And then loosen caller candidate filter.
5606 ep1->allocator_->SetCandidateFilter(CF_ALL);
5607
5608 SIMULATED_WAIT(false, kDefaultTimeout, clock);
5609
5610 // No p2p connection will be made, it will remain on relay.
5611 EXPECT_TRUE(ep1_ch1()->selected_connection() != nullptr &&
5612 RELAY_PORT_TYPE ==
5613 ep1_ch1()->selected_connection()->local_candidate().type() &&
5614 ep2_ch1()->selected_connection() != nullptr &&
5615 RELAY_PORT_TYPE ==
5616 ep1_ch1()->selected_connection()->remote_candidate().type());
5617
5618 DestroyChannels();
5619 }
5620
TEST_F(P2PTransportChannelPingTest,TestInitialSelectDampening0)5621 TEST_F(P2PTransportChannelPingTest, TestInitialSelectDampening0) {
5622 webrtc::test::ScopedFieldTrials field_trials(
5623 "WebRTC-IceFieldTrials/initial_select_dampening:0/");
5624
5625 constexpr int kMargin = 10;
5626 rtc::ScopedFakeClock clock;
5627 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
5628
5629 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5630 P2PTransportChannel ch("test channel", 1, &pa);
5631 PrepareChannel(&ch);
5632 ch.SetIceConfig(ch.config());
5633 ch.MaybeStartGathering();
5634
5635 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
5636 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
5637 ASSERT_TRUE(conn1 != nullptr);
5638 EXPECT_EQ(nullptr, ch.selected_connection());
5639 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
5640 // It shall not be selected until 0ms has passed....i.e it should be connected
5641 // directly.
5642 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), kMargin, clock);
5643 }
5644
TEST_F(P2PTransportChannelPingTest,TestInitialSelectDampening)5645 TEST_F(P2PTransportChannelPingTest, TestInitialSelectDampening) {
5646 webrtc::test::ScopedFieldTrials field_trials(
5647 "WebRTC-IceFieldTrials/initial_select_dampening:100/");
5648
5649 constexpr int kMargin = 10;
5650 rtc::ScopedFakeClock clock;
5651 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
5652
5653 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5654 P2PTransportChannel ch("test channel", 1, &pa);
5655 PrepareChannel(&ch);
5656 ch.SetIceConfig(ch.config());
5657 ch.MaybeStartGathering();
5658
5659 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
5660 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
5661 ASSERT_TRUE(conn1 != nullptr);
5662 EXPECT_EQ(nullptr, ch.selected_connection());
5663 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
5664 // It shall not be selected until 100ms has passed.
5665 SIMULATED_WAIT(conn1 == ch.selected_connection(), 100 - kMargin, clock);
5666 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), 2 * kMargin, clock);
5667 }
5668
TEST_F(P2PTransportChannelPingTest,TestInitialSelectDampeningPingReceived)5669 TEST_F(P2PTransportChannelPingTest, TestInitialSelectDampeningPingReceived) {
5670 webrtc::test::ScopedFieldTrials field_trials(
5671 "WebRTC-IceFieldTrials/initial_select_dampening_ping_received:100/");
5672
5673 constexpr int kMargin = 10;
5674 rtc::ScopedFakeClock clock;
5675 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
5676
5677 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5678 P2PTransportChannel ch("test channel", 1, &pa);
5679 PrepareChannel(&ch);
5680 ch.SetIceConfig(ch.config());
5681 ch.MaybeStartGathering();
5682
5683 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
5684 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
5685 ASSERT_TRUE(conn1 != nullptr);
5686 EXPECT_EQ(nullptr, ch.selected_connection());
5687 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
5688 conn1->ReceivedPing("id1"); //
5689 // It shall not be selected until 100ms has passed.
5690 SIMULATED_WAIT(conn1 == ch.selected_connection(), 100 - kMargin, clock);
5691 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), 2 * kMargin, clock);
5692 }
5693
TEST_F(P2PTransportChannelPingTest,TestInitialSelectDampeningBoth)5694 TEST_F(P2PTransportChannelPingTest, TestInitialSelectDampeningBoth) {
5695 webrtc::test::ScopedFieldTrials field_trials(
5696 "WebRTC-IceFieldTrials/"
5697 "initial_select_dampening:100,initial_select_dampening_ping_received:"
5698 "50/");
5699
5700 constexpr int kMargin = 10;
5701 rtc::ScopedFakeClock clock;
5702 clock.AdvanceTime(webrtc::TimeDelta::Seconds(1));
5703
5704 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5705 P2PTransportChannel ch("test channel", 1, &pa);
5706 PrepareChannel(&ch);
5707 ch.SetIceConfig(ch.config());
5708 ch.MaybeStartGathering();
5709
5710 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 100));
5711 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1, &clock);
5712 ASSERT_TRUE(conn1 != nullptr);
5713 EXPECT_EQ(nullptr, ch.selected_connection());
5714 conn1->ReceivedPingResponse(LOW_RTT, "id"); // Becomes writable and receiving
5715 // It shall not be selected until 100ms has passed....but only wait ~50 now.
5716 SIMULATED_WAIT(conn1 == ch.selected_connection(), 50 - kMargin, clock);
5717 // Now receiving ping and new timeout should kick in.
5718 conn1->ReceivedPing("id1"); //
5719 EXPECT_EQ_SIMULATED_WAIT(conn1, ch.selected_connection(), 2 * kMargin, clock);
5720 }
5721
TEST(P2PTransportChannel,InjectIceController)5722 TEST(P2PTransportChannel, InjectIceController) {
5723 MockIceControllerFactory factory;
5724 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5725 EXPECT_CALL(factory, RecordIceControllerCreated()).Times(1);
5726 auto dummy = std::make_unique<cricket::P2PTransportChannel>(
5727 "transport_name",
5728 /* component= */ 77, &pa,
5729 /* async_resolver_factory = */ nullptr,
5730 /* event_log = */ nullptr, &factory);
5731 }
5732
5733 class ForgetLearnedStateController : public cricket::BasicIceController {
5734 public:
ForgetLearnedStateController(const cricket::IceControllerFactoryArgs & args)5735 explicit ForgetLearnedStateController(
5736 const cricket::IceControllerFactoryArgs& args)
5737 : cricket::BasicIceController(args) {}
5738
SortAndSwitchConnection(IceControllerEvent reason)5739 SwitchResult SortAndSwitchConnection(IceControllerEvent reason) override {
5740 auto result = cricket::BasicIceController::SortAndSwitchConnection(reason);
5741 if (forget_connnection_) {
5742 result.connections_to_forget_state_on.push_back(forget_connnection_);
5743 forget_connnection_ = nullptr;
5744 }
5745 result.recheck_event =
5746 IceControllerEvent(IceControllerEvent::ICE_CONTROLLER_RECHECK);
5747 result.recheck_event->recheck_delay_ms = 100;
5748 return result;
5749 }
5750
ForgetThisConnectionNextTimeSortAndSwitchConnectionIsCalled(Connection * con)5751 void ForgetThisConnectionNextTimeSortAndSwitchConnectionIsCalled(
5752 Connection* con) {
5753 forget_connnection_ = con;
5754 }
5755
5756 private:
5757 Connection* forget_connnection_ = nullptr;
5758 };
5759
5760 class ForgetLearnedStateControllerFactory
5761 : public cricket::IceControllerFactoryInterface {
5762 public:
Create(const cricket::IceControllerFactoryArgs & args)5763 std::unique_ptr<cricket::IceControllerInterface> Create(
5764 const cricket::IceControllerFactoryArgs& args) override {
5765 auto controller = std::make_unique<ForgetLearnedStateController>(args);
5766 // Keep a pointer to allow modifying calls.
5767 // Must not be used after the p2ptransportchannel has been destructed.
5768 controller_ = controller.get();
5769 return controller;
5770 }
5771 virtual ~ForgetLearnedStateControllerFactory() = default;
5772
5773 ForgetLearnedStateController* controller_;
5774 };
5775
TEST_F(P2PTransportChannelPingTest,TestForgetLearnedState)5776 TEST_F(P2PTransportChannelPingTest, TestForgetLearnedState) {
5777 ForgetLearnedStateControllerFactory factory;
5778 FakePortAllocator pa(rtc::Thread::Current(), nullptr);
5779 P2PTransportChannel ch("ping sufficiently", 1, &pa, nullptr, nullptr,
5780 &factory);
5781 PrepareChannel(&ch);
5782 ch.MaybeStartGathering();
5783 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "1.1.1.1", 1, 1));
5784 ch.AddRemoteCandidate(CreateUdpCandidate(LOCAL_PORT_TYPE, "2.2.2.2", 2, 2));
5785
5786 Connection* conn1 = WaitForConnectionTo(&ch, "1.1.1.1", 1);
5787 Connection* conn2 = WaitForConnectionTo(&ch, "2.2.2.2", 2);
5788 ASSERT_TRUE(conn1 != nullptr);
5789 ASSERT_TRUE(conn2 != nullptr);
5790
5791 // Wait for conn1 to be selected.
5792 conn1->ReceivedPingResponse(LOW_RTT, "id");
5793 EXPECT_EQ_WAIT(conn1, ch.selected_connection(), kMediumTimeout);
5794
5795 conn2->ReceivedPingResponse(LOW_RTT, "id");
5796 EXPECT_TRUE(conn2->writable());
5797
5798 // Now let the ice controller signal to P2PTransportChannel that it
5799 // should Forget conn2.
5800 factory.controller_
5801 ->ForgetThisConnectionNextTimeSortAndSwitchConnectionIsCalled(conn2);
5802
5803 // We don't have a mock Connection, so verify this by checking that it
5804 // is no longer writable.
5805 EXPECT_EQ_WAIT(false, conn2->writable(), kMediumTimeout);
5806 }
5807
TEST_F(P2PTransportChannelTest,DisableDnsLookupsWithTransportPolicyRelay)5808 TEST_F(P2PTransportChannelTest, DisableDnsLookupsWithTransportPolicyRelay) {
5809 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5810 kDefaultPortAllocatorFlags);
5811 auto* ep1 = GetEndpoint(0);
5812 ep1->allocator_->SetCandidateFilter(CF_RELAY);
5813
5814 rtc::MockAsyncResolver mock_async_resolver;
5815 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
5816 ON_CALL(mock_async_resolver_factory, Create())
5817 .WillByDefault(Return(&mock_async_resolver));
5818 ep1->async_resolver_factory_ = &mock_async_resolver_factory;
5819
5820 bool lookup_started = false;
5821 ON_CALL(mock_async_resolver, Start(_))
5822 .WillByDefault(Assign(&lookup_started, true));
5823
5824 CreateChannels();
5825
5826 ep1_ch1()->AddRemoteCandidate(
5827 CreateUdpCandidate(LOCAL_PORT_TYPE, "hostname.test", 1, 100));
5828
5829 EXPECT_FALSE(lookup_started);
5830
5831 DestroyChannels();
5832 }
5833
TEST_F(P2PTransportChannelTest,DisableDnsLookupsWithTransportPolicyNone)5834 TEST_F(P2PTransportChannelTest, DisableDnsLookupsWithTransportPolicyNone) {
5835 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5836 kDefaultPortAllocatorFlags);
5837 auto* ep1 = GetEndpoint(0);
5838 ep1->allocator_->SetCandidateFilter(CF_NONE);
5839
5840 rtc::MockAsyncResolver mock_async_resolver;
5841 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
5842 ON_CALL(mock_async_resolver_factory, Create())
5843 .WillByDefault(Return(&mock_async_resolver));
5844 ep1->async_resolver_factory_ = &mock_async_resolver_factory;
5845
5846 bool lookup_started = false;
5847 ON_CALL(mock_async_resolver, Start(_))
5848 .WillByDefault(Assign(&lookup_started, true));
5849
5850 CreateChannels();
5851
5852 ep1_ch1()->AddRemoteCandidate(
5853 CreateUdpCandidate(LOCAL_PORT_TYPE, "hostname.test", 1, 100));
5854
5855 EXPECT_FALSE(lookup_started);
5856
5857 DestroyChannels();
5858 }
5859
TEST_F(P2PTransportChannelTest,EnableDnsLookupsWithTransportPolicyNoHost)5860 TEST_F(P2PTransportChannelTest, EnableDnsLookupsWithTransportPolicyNoHost) {
5861 ConfigureEndpoints(OPEN, OPEN, kDefaultPortAllocatorFlags,
5862 kDefaultPortAllocatorFlags);
5863 auto* ep1 = GetEndpoint(0);
5864 ep1->allocator_->SetCandidateFilter(CF_ALL & ~CF_HOST);
5865
5866 rtc::MockAsyncResolver mock_async_resolver;
5867 webrtc::MockAsyncResolverFactory mock_async_resolver_factory;
5868 EXPECT_CALL(mock_async_resolver_factory, Create())
5869 .WillOnce(Return(&mock_async_resolver));
5870 EXPECT_CALL(mock_async_resolver, Destroy(_));
5871
5872 ep1->async_resolver_factory_ = &mock_async_resolver_factory;
5873
5874 bool lookup_started = false;
5875 EXPECT_CALL(mock_async_resolver, Start(_))
5876 .WillOnce(Assign(&lookup_started, true));
5877
5878 CreateChannels();
5879
5880 ep1_ch1()->AddRemoteCandidate(
5881 CreateUdpCandidate(LOCAL_PORT_TYPE, "hostname.test", 1, 100));
5882
5883 EXPECT_TRUE(lookup_started);
5884
5885 DestroyChannels();
5886 }
5887
5888 } // namespace cricket
5889