| 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/nqe/network_quality_estimator.h" | 5 #include "net/nqe/network_quality_estimator.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 #include <cmath> | 8 #include <cmath> |
| 9 #include <limits> | 9 #include <limits> |
| 10 #include <utility> | 10 #include <utility> |
| (...skipping 258 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 269 static_assert(kMaximumNetworkQualityCacheSize <= 10, | 269 static_assert(kMaximumNetworkQualityCacheSize <= 10, |
| 270 "Size of the network quality cache must <= 10"); | 270 "Size of the network quality cache must <= 10"); |
| 271 | 271 |
| 272 ObtainOperatingParams(variation_params); | 272 ObtainOperatingParams(variation_params); |
| 273 ObtainEffectiveConnectionTypeModelParams(variation_params); | 273 ObtainEffectiveConnectionTypeModelParams(variation_params); |
| 274 NetworkChangeNotifier::AddConnectionTypeObserver(this); | 274 NetworkChangeNotifier::AddConnectionTypeObserver(this); |
| 275 if (external_estimate_provider_) { | 275 if (external_estimate_provider_) { |
| 276 RecordExternalEstimateProviderMetrics( | 276 RecordExternalEstimateProviderMetrics( |
| 277 EXTERNAL_ESTIMATE_PROVIDER_STATUS_AVAILABLE); | 277 EXTERNAL_ESTIMATE_PROVIDER_STATUS_AVAILABLE); |
| 278 external_estimate_provider_->SetUpdatedEstimateDelegate(this); | 278 external_estimate_provider_->SetUpdatedEstimateDelegate(this); |
| 279 QueryExternalEstimateProvider(); | |
| 280 } else { | 279 } else { |
| 281 RecordExternalEstimateProviderMetrics( | 280 RecordExternalEstimateProviderMetrics( |
| 282 EXTERNAL_ESTIMATE_PROVIDER_STATUS_NOT_AVAILABLE); | 281 EXTERNAL_ESTIMATE_PROVIDER_STATUS_NOT_AVAILABLE); |
| 283 } | 282 } |
| 284 current_network_id_ = GetCurrentNetworkID(); | 283 current_network_id_ = GetCurrentNetworkID(); |
| 285 AddDefaultEstimates(); | 284 AddDefaultEstimates(); |
| 286 | 285 |
| 287 throughput_analyzer_.reset(new nqe::internal::ThroughputAnalyzer( | 286 throughput_analyzer_.reset(new nqe::internal::ThroughputAnalyzer( |
| 288 base::ThreadTaskRunnerHandle::Get(), | 287 base::ThreadTaskRunnerHandle::Get(), |
| 289 base::Bind(&NetworkQualityEstimator::OnNewThroughputObservationAvailable, | 288 base::Bind(&NetworkQualityEstimator::OnNewThroughputObservationAvailable, |
| (...skipping 319 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 609 // Write the estimates of the previous network to the cache. | 608 // Write the estimates of the previous network to the cache. |
| 610 CacheNetworkQualityEstimate(); | 609 CacheNetworkQualityEstimate(); |
| 611 | 610 |
| 612 // Clear the local state. | 611 // Clear the local state. |
| 613 last_connection_change_ = base::TimeTicks::Now(); | 612 last_connection_change_ = base::TimeTicks::Now(); |
| 614 peak_network_quality_ = nqe::internal::NetworkQuality(); | 613 peak_network_quality_ = nqe::internal::NetworkQuality(); |
| 615 downstream_throughput_kbps_observations_.Clear(); | 614 downstream_throughput_kbps_observations_.Clear(); |
| 616 rtt_observations_.Clear(); | 615 rtt_observations_.Clear(); |
| 617 current_network_id_ = GetCurrentNetworkID(); | 616 current_network_id_ = GetCurrentNetworkID(); |
| 618 | 617 |
| 619 QueryExternalEstimateProvider(); | 618 // Query the external estimate provider on certain connection types. Once the |
| 619 // updated estimates are available, OnUpdatedEstimateAvailable will be called |
| 620 // by |external_estimate_provider_| with updated estimates. |
| 621 if (external_estimate_provider_ && |
| 622 current_network_id_.type != NetworkChangeNotifier::CONNECTION_NONE && |
| 623 current_network_id_.type != NetworkChangeNotifier::CONNECTION_UNKNOWN && |
| 624 current_network_id_.type != NetworkChangeNotifier::CONNECTION_ETHERNET && |
| 625 current_network_id_.type != NetworkChangeNotifier::CONNECTION_BLUETOOTH) { |
| 626 RecordExternalEstimateProviderMetrics( |
| 627 EXTERNAL_ESTIMATE_PROVIDER_STATUS_QUERIED); |
| 628 external_estimate_provider_->Update(); |
| 629 } |
| 620 | 630 |
| 621 // Read any cached estimates for the new network. If cached estimates are | 631 // Read any cached estimates for the new network. If cached estimates are |
| 622 // unavailable, add the default estimates. | 632 // unavailable, add the default estimates. |
| 623 if (!ReadCachedNetworkQualityEstimate()) | 633 if (!ReadCachedNetworkQualityEstimate()) |
| 624 AddDefaultEstimates(); | 634 AddDefaultEstimates(); |
| 625 estimated_median_network_quality_ = nqe::internal::NetworkQuality(); | 635 estimated_median_network_quality_ = nqe::internal::NetworkQuality(); |
| 626 throughput_analyzer_->OnConnectionTypeChanged(); | 636 throughput_analyzer_->OnConnectionTypeChanged(); |
| 627 } | 637 } |
| 628 | 638 |
| 629 void NetworkQualityEstimator::RecordMetricsOnConnectionTypeChanged() const { | 639 void NetworkQualityEstimator::RecordMetricsOnConnectionTypeChanged() const { |
| (...skipping 311 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 941 RttObservation rtt_observation( | 951 RttObservation rtt_observation( |
| 942 network_quality.http_rtt(), now, | 952 network_quality.http_rtt(), now, |
| 943 NETWORK_QUALITY_OBSERVATION_SOURCE_CACHED_ESTIMATE); | 953 NETWORK_QUALITY_OBSERVATION_SOURCE_CACHED_ESTIMATE); |
| 944 rtt_observations_.AddObservation(rtt_observation); | 954 rtt_observations_.AddObservation(rtt_observation); |
| 945 NotifyObserversOfRTT(rtt_observation); | 955 NotifyObserversOfRTT(rtt_observation); |
| 946 } | 956 } |
| 947 | 957 |
| 948 return read_cached_estimate; | 958 return read_cached_estimate; |
| 949 } | 959 } |
| 950 | 960 |
| 951 void NetworkQualityEstimator::OnUpdatedEstimateAvailable() { | 961 void NetworkQualityEstimator::OnUpdatedEstimateAvailable( |
| 962 const base::TimeDelta& rtt, |
| 963 int32_t downstream_throughput_kbps, |
| 964 int32_t upstream_throughput_kbps) { |
| 952 DCHECK(thread_checker_.CalledOnValidThread()); | 965 DCHECK(thread_checker_.CalledOnValidThread()); |
| 953 DCHECK(external_estimate_provider_); | 966 DCHECK(external_estimate_provider_); |
| 954 | 967 |
| 955 RecordExternalEstimateProviderMetrics( | 968 RecordExternalEstimateProviderMetrics( |
| 956 EXTERNAL_ESTIMATE_PROVIDER_STATUS_CALLBACK); | 969 EXTERNAL_ESTIMATE_PROVIDER_STATUS_CALLBACK); |
| 957 QueryExternalEstimateProvider(); | 970 |
| 971 if (rtt > base::TimeDelta()) { |
| 972 RecordExternalEstimateProviderMetrics( |
| 973 EXTERNAL_ESTIMATE_PROVIDER_STATUS_RTT_AVAILABLE); |
| 974 UMA_HISTOGRAM_TIMES("NQE.ExternalEstimateProvider.RTT", rtt); |
| 975 rtt_observations_.AddObservation( |
| 976 RttObservation(rtt, base::TimeTicks::Now(), |
| 977 NETWORK_QUALITY_OBSERVATION_SOURCE_EXTERNAL_ESTIMATE)); |
| 978 } |
| 979 |
| 980 if (downstream_throughput_kbps > 0) { |
| 981 RecordExternalEstimateProviderMetrics( |
| 982 EXTERNAL_ESTIMATE_PROVIDER_STATUS_DOWNLINK_BANDWIDTH_AVAILABLE); |
| 983 UMA_HISTOGRAM_COUNTS("NQE.ExternalEstimateProvider.DownlinkBandwidth", |
| 984 downstream_throughput_kbps); |
| 985 downstream_throughput_kbps_observations_.AddObservation( |
| 986 ThroughputObservation( |
| 987 downstream_throughput_kbps, base::TimeTicks::Now(), |
| 988 NETWORK_QUALITY_OBSERVATION_SOURCE_EXTERNAL_ESTIMATE)); |
| 989 } |
| 958 } | 990 } |
| 959 | 991 |
| 960 const char* NetworkQualityEstimator::GetNameForEffectiveConnectionType( | 992 const char* NetworkQualityEstimator::GetNameForEffectiveConnectionType( |
| 961 EffectiveConnectionType type) const { | 993 EffectiveConnectionType type) const { |
| 962 switch (type) { | 994 switch (type) { |
| 963 case EFFECTIVE_CONNECTION_TYPE_UNKNOWN: | 995 case EFFECTIVE_CONNECTION_TYPE_UNKNOWN: |
| 964 return "Unknown"; | 996 return "Unknown"; |
| 965 case EFFECTIVE_CONNECTION_TYPE_OFFLINE: | 997 case EFFECTIVE_CONNECTION_TYPE_OFFLINE: |
| 966 return "Offline"; | 998 return "Offline"; |
| 967 case EFFECTIVE_CONNECTION_TYPE_SLOW_2G: | 999 case EFFECTIVE_CONNECTION_TYPE_SLOW_2G: |
| 968 return "Slow2G"; | 1000 return "Slow2G"; |
| 969 case EFFECTIVE_CONNECTION_TYPE_2G: | 1001 case EFFECTIVE_CONNECTION_TYPE_2G: |
| 970 return "2G"; | 1002 return "2G"; |
| 971 case EFFECTIVE_CONNECTION_TYPE_3G: | 1003 case EFFECTIVE_CONNECTION_TYPE_3G: |
| 972 return "3G"; | 1004 return "3G"; |
| 973 case EFFECTIVE_CONNECTION_TYPE_4G: | 1005 case EFFECTIVE_CONNECTION_TYPE_4G: |
| 974 return "4G"; | 1006 return "4G"; |
| 975 case EFFECTIVE_CONNECTION_TYPE_BROADBAND: | 1007 case EFFECTIVE_CONNECTION_TYPE_BROADBAND: |
| 976 return "Broadband"; | 1008 return "Broadband"; |
| 977 default: | 1009 default: |
| 978 NOTREACHED(); | 1010 NOTREACHED(); |
| 979 break; | 1011 break; |
| 980 } | 1012 } |
| 981 return ""; | 1013 return ""; |
| 982 } | 1014 } |
| 983 | 1015 |
| 984 void NetworkQualityEstimator::QueryExternalEstimateProvider() { | |
| 985 DCHECK(thread_checker_.CalledOnValidThread()); | |
| 986 | |
| 987 if (!external_estimate_provider_) | |
| 988 return; | |
| 989 RecordExternalEstimateProviderMetrics( | |
| 990 EXTERNAL_ESTIMATE_PROVIDER_STATUS_QUERIED); | |
| 991 | |
| 992 base::TimeDelta time_since_last_update; | |
| 993 | |
| 994 // Request a new estimate if estimate is not available, or if the available | |
| 995 // estimate is not fresh. | |
| 996 if (!external_estimate_provider_->GetTimeSinceLastUpdate( | |
| 997 &time_since_last_update) || | |
| 998 time_since_last_update > | |
| 999 base::TimeDelta::FromMilliseconds( | |
| 1000 kExternalEstimateProviderFreshnessDurationMsec)) { | |
| 1001 // Request the external estimate provider for updated estimates. When the | |
| 1002 // updates estimates are available, OnUpdatedEstimateAvailable() will be | |
| 1003 // called. | |
| 1004 external_estimate_provider_->Update(); | |
| 1005 return; | |
| 1006 } | |
| 1007 | |
| 1008 RecordExternalEstimateProviderMetrics( | |
| 1009 EXTERNAL_ESTIMATE_PROVIDER_STATUS_QUERY_SUCCESSFUL); | |
| 1010 base::TimeDelta rtt; | |
| 1011 if (external_estimate_provider_->GetRTT(&rtt)) { | |
| 1012 RecordExternalEstimateProviderMetrics( | |
| 1013 EXTERNAL_ESTIMATE_PROVIDER_STATUS_RTT_AVAILABLE); | |
| 1014 UMA_HISTOGRAM_TIMES("NQE.ExternalEstimateProvider.RTT", rtt); | |
| 1015 rtt_observations_.AddObservation( | |
| 1016 RttObservation(rtt, base::TimeTicks::Now(), | |
| 1017 NETWORK_QUALITY_OBSERVATION_SOURCE_EXTERNAL_ESTIMATE)); | |
| 1018 } | |
| 1019 | |
| 1020 int32_t downstream_throughput_kbps; | |
| 1021 if (external_estimate_provider_->GetDownstreamThroughputKbps( | |
| 1022 &downstream_throughput_kbps)) { | |
| 1023 RecordExternalEstimateProviderMetrics( | |
| 1024 EXTERNAL_ESTIMATE_PROVIDER_STATUS_DOWNLINK_BANDWIDTH_AVAILABLE); | |
| 1025 UMA_HISTOGRAM_COUNTS("NQE.ExternalEstimateProvider.DownlinkBandwidth", | |
| 1026 downstream_throughput_kbps); | |
| 1027 downstream_throughput_kbps_observations_.AddObservation( | |
| 1028 ThroughputObservation( | |
| 1029 downstream_throughput_kbps, base::TimeTicks::Now(), | |
| 1030 NETWORK_QUALITY_OBSERVATION_SOURCE_EXTERNAL_ESTIMATE)); | |
| 1031 } | |
| 1032 } | |
| 1033 | |
| 1034 void NetworkQualityEstimator::CacheNetworkQualityEstimate() { | 1016 void NetworkQualityEstimator::CacheNetworkQualityEstimate() { |
| 1035 DCHECK(thread_checker_.CalledOnValidThread()); | 1017 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1036 DCHECK_LE(cached_network_qualities_.size(), | 1018 DCHECK_LE(cached_network_qualities_.size(), |
| 1037 static_cast<size_t>(kMaximumNetworkQualityCacheSize)); | 1019 static_cast<size_t>(kMaximumNetworkQualityCacheSize)); |
| 1038 | 1020 |
| 1039 // If the network name is unavailable, caching should not be performed. | 1021 // If the network name is unavailable, caching should not be performed. |
| 1040 if (current_network_id_.id.empty()) | 1022 if (current_network_id_.id.empty()) |
| 1041 return; | 1023 return; |
| 1042 | 1024 |
| 1043 base::TimeDelta http_rtt = nqe::internal::InvalidRTT(); | 1025 base::TimeDelta http_rtt = nqe::internal::InvalidRTT(); |
| (...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1126 } | 1108 } |
| 1127 ThroughputObservation throughput_observation( | 1109 ThroughputObservation throughput_observation( |
| 1128 downstream_kbps, base::TimeTicks::Now(), | 1110 downstream_kbps, base::TimeTicks::Now(), |
| 1129 NETWORK_QUALITY_OBSERVATION_SOURCE_URL_REQUEST); | 1111 NETWORK_QUALITY_OBSERVATION_SOURCE_URL_REQUEST); |
| 1130 downstream_throughput_kbps_observations_.AddObservation( | 1112 downstream_throughput_kbps_observations_.AddObservation( |
| 1131 throughput_observation); | 1113 throughput_observation); |
| 1132 NotifyObserversOfThroughput(throughput_observation); | 1114 NotifyObserversOfThroughput(throughput_observation); |
| 1133 } | 1115 } |
| 1134 | 1116 |
| 1135 } // namespace net | 1117 } // namespace net |
| OLD | NEW |