| OLD | NEW | 
|     1 // Copyright 2015 The Chromium Authors. All rights reserved. |     1 // Copyright 2015 The Chromium Authors. All rights reserved. | 
|     2 // Use of this source code is governed by a BSD-style license that can be |     2 // Use of this source code is governed by a BSD-style license that can be | 
|     3 // found in the LICENSE file. |     3 // found in the LICENSE file. | 
|     4  |     4  | 
|     5 #include "net/base/network_quality_estimator.h" |     5 #include "net/base/network_quality_estimator.h" | 
|     6  |     6  | 
|     7 #include <float.h> |     7 #include <float.h> | 
|     8 #include <algorithm> |     8 #include <algorithm> | 
|     9 #include <cmath> |     9 #include <cmath> | 
|    10 #include <limits> |    10 #include <limits> | 
| (...skipping 235 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   246         variations_value >= kMinimumThroughputVariationParameterKbps) { |   246         variations_value >= kMinimumThroughputVariationParameterKbps) { | 
|   247       default_observations_[i] = |   247       default_observations_[i] = | 
|   248           NetworkQuality(default_observations_[i].rtt(), variations_value); |   248           NetworkQuality(default_observations_[i].rtt(), variations_value); | 
|   249     } |   249     } | 
|   250   } |   250   } | 
|   251 } |   251 } | 
|   252  |   252  | 
|   253 void NetworkQualityEstimator::AddDefaultEstimates() { |   253 void NetworkQualityEstimator::AddDefaultEstimates() { | 
|   254   DCHECK(thread_checker_.CalledOnValidThread()); |   254   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   255   if (default_observations_[current_network_id_.type].rtt() != InvalidRTT()) { |   255   if (default_observations_[current_network_id_.type].rtt() != InvalidRTT()) { | 
|   256     rtt_msec_observations_.AddObservation(Observation( |   256     Observation rtt_observation( | 
|   257         default_observations_[current_network_id_.type].rtt().InMilliseconds(), |   257         default_observations_[current_network_id_.type].rtt().InMilliseconds(), | 
|   258         base::TimeTicks::Now())); |   258         base::TimeTicks::Now(), DEFAULT_FROM_PLATFORM); | 
 |   259     rtt_msec_observations_.AddObservation(rtt_observation); | 
 |   260     NotifyObserversOfRTT(rtt_observation); | 
|   259   } |   261   } | 
|   260   if (default_observations_[current_network_id_.type] |   262   if (default_observations_[current_network_id_.type] | 
|   261           .downstream_throughput_kbps() != kInvalidThroughput) { |   263           .downstream_throughput_kbps() != kInvalidThroughput) { | 
 |   264     Observation throughput_observation( | 
 |   265         default_observations_[current_network_id_.type] | 
 |   266             .downstream_throughput_kbps(), | 
 |   267         base::TimeTicks::Now(), DEFAULT_FROM_PLATFORM); | 
|   262     downstream_throughput_kbps_observations_.AddObservation( |   268     downstream_throughput_kbps_observations_.AddObservation( | 
|   263         Observation(default_observations_[current_network_id_.type] |   269         throughput_observation); | 
|   264                         .downstream_throughput_kbps(), |   270     NotifyObserversOfThroughput(throughput_observation); | 
|   265                     base::TimeTicks::Now())); |  | 
|   266   } |   271   } | 
|   267 } |   272 } | 
|   268  |   273  | 
|   269 NetworkQualityEstimator::~NetworkQualityEstimator() { |   274 NetworkQualityEstimator::~NetworkQualityEstimator() { | 
|   270   DCHECK(thread_checker_.CalledOnValidThread()); |   275   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   271   NetworkChangeNotifier::RemoveConnectionTypeObserver(this); |   276   NetworkChangeNotifier::RemoveConnectionTypeObserver(this); | 
|   272 } |   277 } | 
|   273  |   278  | 
|   274 void NetworkQualityEstimator::NotifyHeadersReceived(const URLRequest& request) { |   279 void NetworkQualityEstimator::NotifyHeadersReceived(const URLRequest& request) { | 
|   275   DCHECK(thread_checker_.CalledOnValidThread()); |   280   DCHECK(thread_checker_.CalledOnValidThread()); | 
| (...skipping 27 matching lines...) Expand all  Loading... | 
|   303  |   308  | 
|   304   // Duration between when the resource was requested and when response |   309   // Duration between when the resource was requested and when response | 
|   305   // headers were received. |   310   // headers were received. | 
|   306     base::TimeDelta observed_rtt = headers_received_time - request_start_time; |   311     base::TimeDelta observed_rtt = headers_received_time - request_start_time; | 
|   307     DCHECK_GE(observed_rtt, base::TimeDelta()); |   312     DCHECK_GE(observed_rtt, base::TimeDelta()); | 
|   308     if (observed_rtt < peak_network_quality_.rtt()) { |   313     if (observed_rtt < peak_network_quality_.rtt()) { | 
|   309       peak_network_quality_ = NetworkQuality( |   314       peak_network_quality_ = NetworkQuality( | 
|   310           observed_rtt, peak_network_quality_.downstream_throughput_kbps()); |   315           observed_rtt, peak_network_quality_.downstream_throughput_kbps()); | 
|   311     } |   316     } | 
|   312  |   317  | 
|   313     rtt_msec_observations_.AddObservation( |   318     Observation rtt_observation(observed_rtt.InMilliseconds(), now, | 
|   314         Observation(observed_rtt.InMilliseconds(), now)); |   319                                 URL_REQUEST); | 
 |   320     rtt_msec_observations_.AddObservation(rtt_observation); | 
 |   321     NotifyObserversOfRTT(rtt_observation); | 
|   315  |   322  | 
|   316     // Compare the RTT observation with the estimated value and record it. |   323     // Compare the RTT observation with the estimated value and record it. | 
|   317     if (estimated_median_network_quality_.rtt() != InvalidRTT()) { |   324     if (estimated_median_network_quality_.rtt() != InvalidRTT()) { | 
|   318       RecordRTTUMA(estimated_median_network_quality_.rtt().InMilliseconds(), |   325       RecordRTTUMA(estimated_median_network_quality_.rtt().InMilliseconds(), | 
|   319                    observed_rtt.InMilliseconds()); |   326                    observed_rtt.InMilliseconds()); | 
|   320     } |   327     } | 
|   321 } |   328 } | 
|   322  |   329  | 
|   323 void NetworkQualityEstimator::NotifyRequestCompleted( |   330 void NetworkQualityEstimator::NotifyRequestCompleted( | 
|   324     const URLRequest& request) { |   331     const URLRequest& request) { | 
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   371   // connection. |   378   // connection. | 
|   372   if (downstream_kbps - downstream_kbps_as_integer > 0) |   379   if (downstream_kbps - downstream_kbps_as_integer > 0) | 
|   373     downstream_kbps_as_integer++; |   380     downstream_kbps_as_integer++; | 
|   374  |   381  | 
|   375   DCHECK_GT(downstream_kbps_as_integer, 0.0); |   382   DCHECK_GT(downstream_kbps_as_integer, 0.0); | 
|   376   if (downstream_kbps_as_integer > |   383   if (downstream_kbps_as_integer > | 
|   377       peak_network_quality_.downstream_throughput_kbps()) |   384       peak_network_quality_.downstream_throughput_kbps()) | 
|   378     peak_network_quality_ = |   385     peak_network_quality_ = | 
|   379         NetworkQuality(peak_network_quality_.rtt(), downstream_kbps_as_integer); |   386         NetworkQuality(peak_network_quality_.rtt(), downstream_kbps_as_integer); | 
|   380  |   387  | 
 |   388   Observation throughput_observation(downstream_kbps_as_integer, now, | 
 |   389                                      URL_REQUEST); | 
|   381   downstream_throughput_kbps_observations_.AddObservation( |   390   downstream_throughput_kbps_observations_.AddObservation( | 
|   382       Observation(downstream_kbps_as_integer, now)); |   391       throughput_observation); | 
 |   392   NotifyObserversOfThroughput(throughput_observation); | 
 |   393 } | 
 |   394  | 
 |   395 void NetworkQualityEstimator::AddRTTObserver(RTTObserver* rtt_observer) { | 
 |   396   DCHECK(thread_checker_.CalledOnValidThread()); | 
 |   397   rtt_observer_list_.AddObserver(rtt_observer); | 
 |   398 } | 
 |   399  | 
 |   400 void NetworkQualityEstimator::RemoveRTTObserver(RTTObserver* rtt_observer) { | 
 |   401   DCHECK(thread_checker_.CalledOnValidThread()); | 
 |   402   rtt_observer_list_.RemoveObserver(rtt_observer); | 
 |   403 } | 
 |   404  | 
 |   405 void NetworkQualityEstimator::AddThroughputObserver( | 
 |   406     ThroughputObserver* throughput_observer) { | 
 |   407   DCHECK(thread_checker_.CalledOnValidThread()); | 
 |   408   throughput_observer_list_.AddObserver(throughput_observer); | 
 |   409 } | 
 |   410  | 
 |   411 void NetworkQualityEstimator::RemoveThroughputObserver( | 
 |   412     ThroughputObserver* throughput_observer) { | 
 |   413   DCHECK(thread_checker_.CalledOnValidThread()); | 
 |   414   throughput_observer_list_.RemoveObserver(throughput_observer); | 
|   383 } |   415 } | 
|   384  |   416  | 
|   385 void NetworkQualityEstimator::RecordRTTUMA(int32_t estimated_value_msec, |   417 void NetworkQualityEstimator::RecordRTTUMA(int32_t estimated_value_msec, | 
|   386                                            int32_t actual_value_msec) const { |   418                                            int32_t actual_value_msec) const { | 
|   387   DCHECK(thread_checker_.CalledOnValidThread()); |   419   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   388  |   420  | 
|   389   // Record the difference between the actual and the estimated value. |   421   // Record the difference between the actual and the estimated value. | 
|   390   if (estimated_value_msec >= actual_value_msec) { |   422   if (estimated_value_msec >= actual_value_msec) { | 
|   391     base::HistogramBase* difference_rtt = |   423     base::HistogramBase* difference_rtt = | 
|   392         GetHistogram("DifferenceRTTEstimatedAndActual.", |   424         GetHistogram("DifferenceRTTEstimatedAndActual.", | 
| (...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   598 bool NetworkQualityEstimator::GetRecentMedianDownlinkThroughputKbps( |   630 bool NetworkQualityEstimator::GetRecentMedianDownlinkThroughputKbps( | 
|   599     const base::TimeTicks& begin_timestamp, |   631     const base::TimeTicks& begin_timestamp, | 
|   600     int32_t* kbps) const { |   632     int32_t* kbps) const { | 
|   601   DCHECK(thread_checker_.CalledOnValidThread()); |   633   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   602   DCHECK(kbps); |   634   DCHECK(kbps); | 
|   603   *kbps = GetDownlinkThroughputKbpsEstimateInternal(begin_timestamp, 50); |   635   *kbps = GetDownlinkThroughputKbpsEstimateInternal(begin_timestamp, 50); | 
|   604   return (*kbps != kInvalidThroughput); |   636   return (*kbps != kInvalidThroughput); | 
|   605 } |   637 } | 
|   606  |   638  | 
|   607 NetworkQualityEstimator::Observation::Observation(int32_t value, |   639 NetworkQualityEstimator::Observation::Observation(int32_t value, | 
|   608                                                   base::TimeTicks timestamp) |   640                                                   base::TimeTicks timestamp, | 
|   609     : value(value), timestamp(timestamp) { |   641                                                   ObservationSource source) | 
 |   642     : value(value), timestamp(timestamp), source(source) { | 
|   610   DCHECK_GE(value, 0); |   643   DCHECK_GE(value, 0); | 
|   611   DCHECK(!timestamp.is_null()); |   644   DCHECK(!timestamp.is_null()); | 
|   612 } |   645 } | 
|   613  |   646  | 
|   614 NetworkQualityEstimator::Observation::~Observation() { |   647 NetworkQualityEstimator::Observation::~Observation() { | 
|   615 } |   648 } | 
|   616  |   649  | 
|   617 NetworkQualityEstimator::ObservationBuffer::ObservationBuffer( |   650 NetworkQualityEstimator::ObservationBuffer::ObservationBuffer( | 
|   618     double weight_multiplier_per_second) |   651     double weight_multiplier_per_second) | 
|   619     : weight_multiplier_per_second_(weight_multiplier_per_second) { |   652     : weight_multiplier_per_second_(weight_multiplier_per_second) { | 
| (...skipping 194 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   814       cached_network_qualities_.find(current_network_id_); |   847       cached_network_qualities_.find(current_network_id_); | 
|   815  |   848  | 
|   816   if (it == cached_network_qualities_.end()) |   849   if (it == cached_network_qualities_.end()) | 
|   817     return false; |   850     return false; | 
|   818  |   851  | 
|   819   NetworkQuality network_quality(it->second.network_quality()); |   852   NetworkQuality network_quality(it->second.network_quality()); | 
|   820  |   853  | 
|   821   DCHECK_NE(InvalidRTT(), network_quality.rtt()); |   854   DCHECK_NE(InvalidRTT(), network_quality.rtt()); | 
|   822   DCHECK_NE(kInvalidThroughput, network_quality.downstream_throughput_kbps()); |   855   DCHECK_NE(kInvalidThroughput, network_quality.downstream_throughput_kbps()); | 
|   823  |   856  | 
|   824   downstream_throughput_kbps_observations_.AddObservation(Observation( |   857   Observation througphput_observation( | 
|   825       network_quality.downstream_throughput_kbps(), base::TimeTicks::Now())); |   858       network_quality.downstream_throughput_kbps(), base::TimeTicks::Now(), | 
|   826   rtt_msec_observations_.AddObservation(Observation( |   859       CACHED_ESTIMATE); | 
|   827       network_quality.rtt().InMilliseconds(), base::TimeTicks::Now())); |   860   downstream_throughput_kbps_observations_.AddObservation( | 
 |   861       througphput_observation); | 
 |   862   NotifyObserversOfThroughput(througphput_observation); | 
 |   863  | 
 |   864   Observation rtt_observation(network_quality.rtt().InMilliseconds(), | 
 |   865                               base::TimeTicks::Now(), CACHED_ESTIMATE); | 
 |   866   rtt_msec_observations_.AddObservation(rtt_observation); | 
 |   867   NotifyObserversOfRTT(rtt_observation); | 
 |   868  | 
|   828   return true; |   869   return true; | 
|   829 } |   870 } | 
|   830  |   871  | 
|   831 void NetworkQualityEstimator::OnUpdatedEstimateAvailable() { |   872 void NetworkQualityEstimator::OnUpdatedEstimateAvailable() { | 
|   832   DCHECK(thread_checker_.CalledOnValidThread()); |   873   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   833   DCHECK(external_estimate_provider_); |   874   DCHECK(external_estimate_provider_); | 
|   834  |   875  | 
|   835   RecordExternalEstimateProviderMetrics( |   876   RecordExternalEstimateProviderMetrics( | 
|   836       EXTERNAL_ESTIMATE_PROVIDER_STATUS_CALLBACK); |   877       EXTERNAL_ESTIMATE_PROVIDER_STATUS_CALLBACK); | 
|   837   QueryExternalEstimateProvider(); |   878   QueryExternalEstimateProvider(); | 
| (...skipping 20 matching lines...) Expand all  Loading... | 
|   858     // updates estimates are available, OnUpdatedEstimateAvailable() will be |   899     // updates estimates are available, OnUpdatedEstimateAvailable() will be | 
|   859     // called. |   900     // called. | 
|   860     external_estimate_provider_->Update(); |   901     external_estimate_provider_->Update(); | 
|   861     return; |   902     return; | 
|   862   } |   903   } | 
|   863  |   904  | 
|   864   RecordExternalEstimateProviderMetrics( |   905   RecordExternalEstimateProviderMetrics( | 
|   865       EXTERNAL_ESTIMATE_PROVIDER_STATUS_QUERY_SUCCESSFUL); |   906       EXTERNAL_ESTIMATE_PROVIDER_STATUS_QUERY_SUCCESSFUL); | 
|   866   base::TimeDelta rtt; |   907   base::TimeDelta rtt; | 
|   867   if (external_estimate_provider_->GetRTT(&rtt)) { |   908   if (external_estimate_provider_->GetRTT(&rtt)) { | 
|   868     rtt_msec_observations_.AddObservation( |   909     rtt_msec_observations_.AddObservation(Observation( | 
|   869         Observation(rtt.InMilliseconds(), base::TimeTicks::Now())); |   910         rtt.InMilliseconds(), base::TimeTicks::Now(), EXTERNAL_ESTIMATE)); | 
|   870   } |   911   } | 
|   871  |   912  | 
|   872   int32_t downstream_throughput_kbps; |   913   int32_t downstream_throughput_kbps; | 
|   873   if (external_estimate_provider_->GetDownstreamThroughputKbps( |   914   if (external_estimate_provider_->GetDownstreamThroughputKbps( | 
|   874           &downstream_throughput_kbps)) { |   915           &downstream_throughput_kbps)) { | 
|   875     downstream_throughput_kbps_observations_.AddObservation( |   916     downstream_throughput_kbps_observations_.AddObservation(Observation( | 
|   876         Observation(downstream_throughput_kbps, base::TimeTicks::Now())); |   917         downstream_throughput_kbps, base::TimeTicks::Now(), EXTERNAL_ESTIMATE)); | 
|   877   } |   918   } | 
|   878 } |   919 } | 
|   879  |   920  | 
|   880 void NetworkQualityEstimator::CacheNetworkQualityEstimate() { |   921 void NetworkQualityEstimator::CacheNetworkQualityEstimate() { | 
|   881   DCHECK(thread_checker_.CalledOnValidThread()); |   922   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   882   DCHECK_LE(cached_network_qualities_.size(), |   923   DCHECK_LE(cached_network_qualities_.size(), | 
|   883             static_cast<size_t>(kMaximumNetworkQualityCacheSize)); |   924             static_cast<size_t>(kMaximumNetworkQualityCacheSize)); | 
|   884  |   925  | 
|   885   // If the network name is unavailable, caching should not be performed. |   926   // If the network name is unavailable, caching should not be performed. | 
|   886   if (current_network_id_.id.empty()) |   927   if (current_network_id_.id.empty()) | 
| (...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   923       new SocketPerformanceWatcherTCP()); |   964       new SocketPerformanceWatcherTCP()); | 
|   924 } |   965 } | 
|   925  |   966  | 
|   926 scoped_ptr<SocketPerformanceWatcher> |   967 scoped_ptr<SocketPerformanceWatcher> | 
|   927 NetworkQualityEstimator::CreateUDPSocketPerformanceWatcher() const { |   968 NetworkQualityEstimator::CreateUDPSocketPerformanceWatcher() const { | 
|   928   DCHECK(thread_checker_.CalledOnValidThread()); |   969   DCHECK(thread_checker_.CalledOnValidThread()); | 
|   929   return scoped_ptr<SocketPerformanceWatcher>( |   970   return scoped_ptr<SocketPerformanceWatcher>( | 
|   930       new SocketPerformanceWatcherUDP()); |   971       new SocketPerformanceWatcherUDP()); | 
|   931 } |   972 } | 
|   932  |   973  | 
 |   974 void NetworkQualityEstimator::NotifyObserversOfRTT( | 
 |   975     const Observation& observation) { | 
 |   976   FOR_EACH_OBSERVER(RTTObserver, rtt_observer_list_, | 
 |   977                     OnRTTObservation(observation.value, observation.timestamp, | 
 |   978                                      observation.source)); | 
 |   979 } | 
 |   980  | 
 |   981 void NetworkQualityEstimator::NotifyObserversOfThroughput( | 
 |   982     const Observation& observation) { | 
 |   983   FOR_EACH_OBSERVER( | 
 |   984       ThroughputObserver, throughput_observer_list_, | 
 |   985       OnThroughputObservation(observation.value, observation.timestamp, | 
 |   986                               observation.source)); | 
 |   987 } | 
 |   988  | 
|   933 NetworkQualityEstimator::CachedNetworkQuality::CachedNetworkQuality( |   989 NetworkQualityEstimator::CachedNetworkQuality::CachedNetworkQuality( | 
|   934     const NetworkQuality& network_quality) |   990     const NetworkQuality& network_quality) | 
|   935     : last_update_time_(base::TimeTicks::Now()), |   991     : last_update_time_(base::TimeTicks::Now()), | 
|   936       network_quality_(network_quality) { |   992       network_quality_(network_quality) { | 
|   937 } |   993 } | 
|   938  |   994  | 
|   939 NetworkQualityEstimator::CachedNetworkQuality::CachedNetworkQuality( |   995 NetworkQualityEstimator::CachedNetworkQuality::CachedNetworkQuality( | 
|   940     const CachedNetworkQuality& other) |   996     const CachedNetworkQuality& other) | 
|   941     : last_update_time_(other.last_update_time_), |   997     : last_update_time_(other.last_update_time_), | 
|   942       network_quality_(other.network_quality_) { |   998       network_quality_(other.network_quality_) { | 
| (...skipping 27 matching lines...) Expand all  Loading... | 
|   970  |  1026  | 
|   971 NetworkQualityEstimator::NetworkQuality& |  1027 NetworkQualityEstimator::NetworkQuality& | 
|   972     NetworkQualityEstimator::NetworkQuality:: |  1028     NetworkQualityEstimator::NetworkQuality:: | 
|   973     operator=(const NetworkQuality& other) { |  1029     operator=(const NetworkQuality& other) { | 
|   974   rtt_ = other.rtt_; |  1030   rtt_ = other.rtt_; | 
|   975   downstream_throughput_kbps_ = other.downstream_throughput_kbps_; |  1031   downstream_throughput_kbps_ = other.downstream_throughput_kbps_; | 
|   976   return *this; |  1032   return *this; | 
|   977 } |  1033 } | 
|   978  |  1034  | 
|   979 }  // namespace net |  1035 }  // namespace net | 
| OLD | NEW |