OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright 2004 The WebRTC Project Authors. All rights reserved. | 2 * Copyright 2004 The WebRTC Project Authors. All rights reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 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 | 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 | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 | 10 |
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
147 connection->SignalReadPacket.connect( | 147 connection->SignalReadPacket.connect( |
148 this, &P2PTransportChannel::OnReadPacket); | 148 this, &P2PTransportChannel::OnReadPacket); |
149 connection->SignalReadyToSend.connect( | 149 connection->SignalReadyToSend.connect( |
150 this, &P2PTransportChannel::OnReadyToSend); | 150 this, &P2PTransportChannel::OnReadyToSend); |
151 connection->SignalStateChange.connect( | 151 connection->SignalStateChange.connect( |
152 this, &P2PTransportChannel::OnConnectionStateChange); | 152 this, &P2PTransportChannel::OnConnectionStateChange); |
153 connection->SignalDestroyed.connect( | 153 connection->SignalDestroyed.connect( |
154 this, &P2PTransportChannel::OnConnectionDestroyed); | 154 this, &P2PTransportChannel::OnConnectionDestroyed); |
155 connection->SignalNominated.connect(this, &P2PTransportChannel::OnNominated); | 155 connection->SignalNominated.connect(this, &P2PTransportChannel::OnNominated); |
156 had_connection_ = true; | 156 had_connection_ = true; |
157 // If this is the first connection and we have remote ICE credentials, we can | |
158 // start pinging. | |
159 MaybeStartPinging(); | |
157 } | 160 } |
158 | 161 |
159 // Determines whether we should switch the selected connection to | 162 // Determines whether we should switch the selected connection to |
160 // |new_connection| based the writable/receiving state, the nomination state, | 163 // |new_connection| based the writable/receiving state, the nomination state, |
161 // and the last data received time. This prevents the controlled side from | 164 // and the last data received time. This prevents the controlled side from |
162 // switching the selected connection too frequently when the controlling side | 165 // switching the selected connection too frequently when the controlling side |
163 // is doing aggressive nominations. The precedence of the connection switching | 166 // is doing aggressive nominations. The precedence of the connection switching |
164 // criteria is as follows: | 167 // criteria is as follows: |
165 // i) write/receiving/connected states | 168 // i) write/receiving/connected states |
166 // ii) For controlled side, | 169 // ii) For controlled side, |
(...skipping 114 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
281 } | 284 } |
282 // We need to update the credentials and generation for any peer reflexive | 285 // We need to update the credentials and generation for any peer reflexive |
283 // candidates. | 286 // candidates. |
284 for (Connection* conn : connections_) { | 287 for (Connection* conn : connections_) { |
285 conn->MaybeSetRemoteIceCredentialsAndGeneration( | 288 conn->MaybeSetRemoteIceCredentialsAndGeneration( |
286 ice_ufrag, ice_pwd, | 289 ice_ufrag, ice_pwd, |
287 static_cast<int>(remote_ice_parameters_.size() - 1)); | 290 static_cast<int>(remote_ice_parameters_.size() - 1)); |
288 } | 291 } |
289 // Updating the remote ICE candidate generation could change the sort order. | 292 // Updating the remote ICE candidate generation could change the sort order. |
290 RequestSort(); | 293 RequestSort(); |
294 // If this is the first time receiving ICE credentials and we already have a | |
295 // connection (for example, to a prflx candidate), we can start pinging. | |
296 MaybeStartPinging(); | |
291 } | 297 } |
292 | 298 |
293 void P2PTransportChannel::SetRemoteIceMode(IceMode mode) { | 299 void P2PTransportChannel::SetRemoteIceMode(IceMode mode) { |
294 remote_ice_mode_ = mode; | 300 remote_ice_mode_ = mode; |
295 } | 301 } |
296 | 302 |
297 void P2PTransportChannel::SetIceConfig(const IceConfig& config) { | 303 void P2PTransportChannel::SetIceConfig(const IceConfig& config) { |
298 config_.gather_continually = config.gather_continually; | 304 config_.gather_continually = config.gather_continually; |
299 LOG(LS_INFO) << "Set gather_continually to " << config_.gather_continually; | 305 LOG(LS_INFO) << "Set gather_continually to " << config_.gather_continually; |
300 | 306 |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
345 LOG(LS_INFO) << "Set presume writable when fully relayed to " | 351 LOG(LS_INFO) << "Set presume writable when fully relayed to " |
346 << config_.presume_writable_when_fully_relayed; | 352 << config_.presume_writable_when_fully_relayed; |
347 } | 353 } |
348 } | 354 } |
349 } | 355 } |
350 | 356 |
351 const IceConfig& P2PTransportChannel::config() const { | 357 const IceConfig& P2PTransportChannel::config() const { |
352 return config_; | 358 return config_; |
353 } | 359 } |
354 | 360 |
355 // Go into the state of processing candidates, and running in general | 361 void P2PTransportChannel::MaybeStartGathering() { |
356 void P2PTransportChannel::Connect() { | |
357 ASSERT(worker_thread_ == rtc::Thread::Current()); | |
358 if (ice_ufrag_.empty() || ice_pwd_.empty()) { | 362 if (ice_ufrag_.empty() || ice_pwd_.empty()) { |
359 ASSERT(false); | |
360 LOG(LS_ERROR) << "P2PTransportChannel::Connect: The ice_ufrag_ and the " | |
361 << "ice_pwd_ are not set."; | |
362 return; | 363 return; |
363 } | 364 } |
364 | |
365 // Start checking and pinging as the ports come in. | |
366 thread()->Post(RTC_FROM_HERE, this, MSG_CHECK_AND_PING); | |
367 } | |
368 | |
369 void P2PTransportChannel::MaybeStartGathering() { | |
370 // Start gathering if we never started before, or if an ICE restart occurred. | 365 // Start gathering if we never started before, or if an ICE restart occurred. |
371 if (allocator_sessions_.empty() || | 366 if (allocator_sessions_.empty() || |
372 IceCredentialsChanged(allocator_sessions_.back()->ice_ufrag(), | 367 IceCredentialsChanged(allocator_sessions_.back()->ice_ufrag(), |
373 allocator_sessions_.back()->ice_pwd(), ice_ufrag_, | 368 allocator_sessions_.back()->ice_pwd(), ice_ufrag_, |
374 ice_pwd_)) { | 369 ice_pwd_)) { |
375 if (gathering_state_ != kIceGatheringGathering) { | 370 if (gathering_state_ != kIceGatheringGathering) { |
376 gathering_state_ = kIceGatheringGathering; | 371 gathering_state_ = kIceGatheringGathering; |
377 SignalGatheringState(this); | 372 SignalGatheringState(this); |
378 } | 373 } |
379 // Time for a new allocator. | 374 // Time for a new allocator. |
(...skipping 565 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
945 } | 940 } |
946 | 941 |
947 // Prepare for best candidate sorting. | 942 // Prepare for best candidate sorting. |
948 void P2PTransportChannel::RequestSort() { | 943 void P2PTransportChannel::RequestSort() { |
949 if (!sort_dirty_) { | 944 if (!sort_dirty_) { |
950 worker_thread_->Post(RTC_FROM_HERE, this, MSG_SORT); | 945 worker_thread_->Post(RTC_FROM_HERE, this, MSG_SORT); |
951 sort_dirty_ = true; | 946 sort_dirty_ = true; |
952 } | 947 } |
953 } | 948 } |
954 | 949 |
950 void P2PTransportChannel::MaybeStartPinging() { | |
951 if (started_pinging_) { | |
952 return; | |
953 } | |
954 | |
955 int64_t now = rtc::TimeMillis(); | |
956 for (const Connection* c : connections_) { | |
957 if (IsPingable(c, now)) { | |
pthatcher1
2016/06/28 01:16:32
Could be slightly more readable with:
if (std::no
Taylor Brandstetter
2016/06/28 02:01:42
Done. Though I think:
if (any_of) {
do_thing();
| |
958 LOG_J(LS_INFO, this) << "Have a pingable connection for the first time; " | |
959 << "starting to ping."; | |
960 thread()->Post(RTC_FROM_HERE, this, MSG_CHECK_AND_PING); | |
961 started_pinging_ = true; | |
962 return; | |
963 } | |
964 } | |
965 } | |
966 | |
955 // Compare two connections based on their writing, receiving, and connected | 967 // Compare two connections based on their writing, receiving, and connected |
956 // states. | 968 // states. |
957 int P2PTransportChannel::CompareConnectionStates(const Connection* a, | 969 int P2PTransportChannel::CompareConnectionStates(const Connection* a, |
958 const Connection* b) const { | 970 const Connection* b) const { |
959 // First, prefer a connection that's writable or presumed writable over | 971 // First, prefer a connection that's writable or presumed writable over |
960 // one that's not writable. | 972 // one that's not writable. |
961 bool a_writable = a->writable() || PresumedWritable(a); | 973 bool a_writable = a->writable() || PresumedWritable(a); |
962 bool b_writable = b->writable() || PresumedWritable(b); | 974 bool b_writable = b->writable() || PresumedWritable(b); |
963 if (a_writable && !b_writable) { | 975 if (a_writable && !b_writable) { |
964 return a_is_better; | 976 return a_is_better; |
(...skipping 454 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1419 PingConnection(conn); | 1431 PingConnection(conn); |
1420 MarkConnectionPinged(conn); | 1432 MarkConnectionPinged(conn); |
1421 } | 1433 } |
1422 } | 1434 } |
1423 int delay = std::min(ping_interval, check_receiving_interval_); | 1435 int delay = std::min(ping_interval, check_receiving_interval_); |
1424 thread()->PostDelayed(RTC_FROM_HERE, delay, this, MSG_CHECK_AND_PING); | 1436 thread()->PostDelayed(RTC_FROM_HERE, delay, this, MSG_CHECK_AND_PING); |
1425 } | 1437 } |
1426 | 1438 |
1427 // A connection is considered a backup connection if the channel state | 1439 // A connection is considered a backup connection if the channel state |
1428 // is completed, the connection is not the selected connection and it is active. | 1440 // is completed, the connection is not the selected connection and it is active. |
1429 bool P2PTransportChannel::IsBackupConnection(Connection* conn) const { | 1441 bool P2PTransportChannel::IsBackupConnection(const Connection* conn) const { |
1430 return state_ == STATE_COMPLETED && conn != selected_connection_ && | 1442 return state_ == STATE_COMPLETED && conn != selected_connection_ && |
1431 conn->active(); | 1443 conn->active(); |
1432 } | 1444 } |
1433 | 1445 |
1434 // Is the connection in a state for us to even consider pinging the other side? | 1446 // Is the connection in a state for us to even consider pinging the other side? |
1435 // We consider a connection pingable even if it's not connected because that's | 1447 // We consider a connection pingable even if it's not connected because that's |
1436 // how a TCP connection is kicked into reconnecting on the active side. | 1448 // how a TCP connection is kicked into reconnecting on the active side. |
1437 bool P2PTransportChannel::IsPingable(Connection* conn, int64_t now) { | 1449 bool P2PTransportChannel::IsPingable(const Connection* conn, |
1450 int64_t now) const { | |
1438 const Candidate& remote = conn->remote_candidate(); | 1451 const Candidate& remote = conn->remote_candidate(); |
1439 // We should never get this far with an empty remote ufrag. | 1452 // We should never get this far with an empty remote ufrag. |
1440 ASSERT(!remote.username().empty()); | 1453 ASSERT(!remote.username().empty()); |
1441 if (remote.username().empty() || remote.password().empty()) { | 1454 if (remote.username().empty() || remote.password().empty()) { |
1442 // If we don't have an ICE ufrag and pwd, there's no way we can ping. | 1455 // If we don't have an ICE ufrag and pwd, there's no way we can ping. |
1443 return false; | 1456 return false; |
1444 } | 1457 } |
1445 | 1458 |
1446 // A failed connection will not be pinged. | 1459 // A failed connection will not be pinged. |
1447 if (conn->state() == Connection::STATE_FAILED) { | 1460 if (conn->state() == Connection::STATE_FAILED) { |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1485 bool P2PTransportChannel::IsSelectedConnectionPingable(int64_t now) { | 1498 bool P2PTransportChannel::IsSelectedConnectionPingable(int64_t now) { |
1486 if (!selected_connection_ || !selected_connection_->connected() || | 1499 if (!selected_connection_ || !selected_connection_->connected() || |
1487 !selected_connection_->writable()) { | 1500 !selected_connection_->writable()) { |
1488 return false; | 1501 return false; |
1489 } | 1502 } |
1490 | 1503 |
1491 int interval = CalculateActiveWritablePingInterval(selected_connection_, now); | 1504 int interval = CalculateActiveWritablePingInterval(selected_connection_, now); |
1492 return selected_connection_->last_ping_sent() + interval <= now; | 1505 return selected_connection_->last_ping_sent() + interval <= now; |
1493 } | 1506 } |
1494 | 1507 |
1495 int P2PTransportChannel::CalculateActiveWritablePingInterval(Connection* conn, | 1508 int P2PTransportChannel::CalculateActiveWritablePingInterval( |
1496 int64_t now) { | 1509 const Connection* conn, |
1510 int64_t now) const { | |
1497 // Ping each connection at a higher rate at least | 1511 // Ping each connection at a higher rate at least |
1498 // MIN_PINGS_AT_WEAK_PING_INTERVAL times. | 1512 // MIN_PINGS_AT_WEAK_PING_INTERVAL times. |
1499 if (conn->num_pings_sent() < MIN_PINGS_AT_WEAK_PING_INTERVAL) { | 1513 if (conn->num_pings_sent() < MIN_PINGS_AT_WEAK_PING_INTERVAL) { |
1500 return weak_ping_interval_; | 1514 return weak_ping_interval_; |
1501 } | 1515 } |
1502 | 1516 |
1503 int stable_interval = config_.stable_writable_connection_ping_interval; | 1517 int stable_interval = config_.stable_writable_connection_ping_interval; |
1504 int stablizing_interval = | 1518 int stablizing_interval = |
1505 std::min(stable_interval, STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL); | 1519 std::min(stable_interval, STABILIZING_WRITABLE_CONNECTION_PING_INTERVAL); |
1506 | 1520 |
(...skipping 292 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1799 | 1813 |
1800 // During the initial state when nothing has been pinged yet, return the first | 1814 // During the initial state when nothing has been pinged yet, return the first |
1801 // one in the ordered |connections_|. | 1815 // one in the ordered |connections_|. |
1802 return *(std::find_if(connections_.begin(), connections_.end(), | 1816 return *(std::find_if(connections_.begin(), connections_.end(), |
1803 [conn1, conn2](Connection* conn) { | 1817 [conn1, conn2](Connection* conn) { |
1804 return conn == conn1 || conn == conn2; | 1818 return conn == conn1 || conn == conn2; |
1805 })); | 1819 })); |
1806 } | 1820 } |
1807 | 1821 |
1808 } // namespace cricket | 1822 } // namespace cricket |
OLD | NEW |