15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/network_change_notifier.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/metrics/histogram.h" 85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "base/synchronization/lock.h" 9e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch#include "base/threading/thread_checker.h" 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "build/build_config.h" 115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/net_util.h" 125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/network_change_notifier_factory.h" 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/dns/dns_config_service.h" 142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)#include "net/url_request/url_request.h" 157dbb3d5cf0c15f500944d211057644d6a2f37371Ben Murdoch#include "url/gurl.h" 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 17010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)#if defined(OS_ANDROID) 18010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)#include "base/metrics/sparse_histogram.h" 19010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)#include "base/strings/string_number_conversions.h" 20010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)#include "net/android/network_library.h" 21010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles)#endif 22010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_WIN) 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/network_change_notifier_win.h" 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(OS_LINUX) && !defined(OS_CHROMEOS) 265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/network_change_notifier_linux.h" 275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(OS_MACOSX) 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "net/base/network_change_notifier_mac.h" 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace net { 325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The actual singleton notifier. The class contract forbids usage of the API 365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// in ways that would require us to place locks around access to this object. 375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// (The prohibition on global non-POD objects makes it tricky to do such a thing 385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// anyway.) 395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier* g_network_change_notifier = NULL; 405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Class factory singleton. 425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifierFactory* g_network_change_notifier_factory = NULL; 435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class MockNetworkChangeNotifier : public NetworkChangeNotifier { 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual ConnectionType GetCurrentConnectionType() const OVERRIDE { 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return CONNECTION_UNKNOWN; 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// The main observer class that records UMAs for network events. 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class HistogramWatcher 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : public NetworkChangeNotifier::ConnectionTypeObserver, 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public NetworkChangeNotifier::IPAddressObserver, 572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public NetworkChangeNotifier::DNSObserver, 582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public NetworkChangeNotifier::NetworkChangeObserver { 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) HistogramWatcher() 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : last_ip_address_change_(base::TimeTicks::Now()), 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_connection_change_(base::TimeTicks::Now()), 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_dns_change_(base::TimeTicks::Now()), 642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_network_change_(base::TimeTicks::Now()), 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_connection_type_(NetworkChangeNotifier::CONNECTION_UNKNOWN), 662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) offline_packets_received_(0), 672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bytes_read_since_last_connection_change_(0), 682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_(0) {} 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Registers our three Observer implementations. This is called from the 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // network thread so that our Observer implementations are also called 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // from the network thread. This avoids multi-threaded race conditions 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // because the only other interface, |NotifyDataReceived| is also 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // only called from the network thread. 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void Init() { 76e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 77e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(g_network_change_notifier); 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::AddConnectionTypeObserver(this); 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::AddIPAddressObserver(this); 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::AddDNSObserver(this); 812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeNotifier::AddNetworkChangeObserver(this); 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 84e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch virtual ~HistogramWatcher() { 85e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 86e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(g_network_change_notifier); 87e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch NetworkChangeNotifier::RemoveConnectionTypeObserver(this); 88e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch NetworkChangeNotifier::RemoveIPAddressObserver(this); 89e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch NetworkChangeNotifier::RemoveDNSObserver(this); 90e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch NetworkChangeNotifier::RemoveNetworkChangeObserver(this); 91e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch } 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // NetworkChangeNotifier::IPAddressObserver implementation. 945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnIPAddressChanged() OVERRIDE { 95e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.IPAddressChange", 975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SinceLast(&last_ip_address_change_)); 982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES( 992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) "NCN.ConnectionTypeChangeToIPAddressChange", 1002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_ip_address_change_ - last_connection_change_); 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // NetworkChangeNotifier::ConnectionTypeObserver implementation. 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnConnectionTypeChanged( 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::ConnectionType type) OVERRIDE { 106e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 1072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks now = base::TimeTicks::Now(); 1082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32 kilobytes_read = bytes_read_since_last_connection_change_ / 1000; 1092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta state_duration = SinceLast(&last_connection_change_); 1102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (bytes_read_since_last_connection_change_) { 1112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) switch (last_connection_type_) { 1122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_UNKNOWN: 1132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOnUnknown", 1142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOnUnknown", 1162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_ETHERNET: 1192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOnEthernet", 1202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOnEthernet", 1222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_WIFI: 1252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOnWifi", 1262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOnWifi", 1282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_2G: 1312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOn2G", 1322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOn2G", 1342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_3G: 1372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOn3G", 1382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOn3G", 1402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_4G: 1432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOn4G", 1442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOn4G", 1462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_NONE: 1492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOnNone", 1502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_); 1512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOnNone", 1522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 15446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_BLUETOOTH: 15546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FirstReadOnBluetooth", 15646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) first_byte_after_connection_change_); 15746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) UMA_HISTOGRAM_TIMES("NCN.CM.FastestRTTOnBluetooth", 15846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) fastest_RTT_since_last_connection_change_); 1592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (peak_kbps_since_last_connection_change_) { 1622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) switch (last_connection_type_) { 1632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_UNKNOWN: 1642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOnUnknown", 1652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_ETHERNET: 1682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOnEthernet", 1692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_WIFI: 1722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOnWifi", 1732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_2G: 1762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOn2G", 1772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_3G: 1802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOn3G", 1812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_4G: 1842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOn4G", 1852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 1872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_NONE: 1882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOnNone", 1892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_); 1902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 19146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_BLUETOOTH: 19246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.PeakKbpsOnBluetooth", 19346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) peak_kbps_since_last_connection_change_); 19446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) break; 1952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) switch (last_connection_type_) { 1982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_UNKNOWN: 1992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOnUnknown", state_duration); 2002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOnUnknown", kilobytes_read); 2012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_ETHERNET: 2032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOnEthernet", state_duration); 2042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOnEthernet", kilobytes_read); 2052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_WIFI: 2072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOnWifi", state_duration); 2082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOnWifi", kilobytes_read); 2092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_2G: 2112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOn2G", state_duration); 2122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOn2G", kilobytes_read); 2132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_3G: 2152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOn3G", state_duration); 2162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOn3G", kilobytes_read); 2172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_4G: 2192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOn4G", state_duration); 2202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOn4G", kilobytes_read); 2212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 2222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_NONE: 2232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOnNone", state_duration); 2242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOnNone", kilobytes_read); 2252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 22646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) case NetworkChangeNotifier::CONNECTION_BLUETOOTH: 22746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) UMA_HISTOGRAM_LONG_TIMES("NCN.CM.TimeOnBluetooth", state_duration); 22846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) UMA_HISTOGRAM_COUNTS("NCN.CM.KBTransferedOnBluetooth", kilobytes_read); 22946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) break; 2302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 2312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (type != NetworkChangeNotifier::CONNECTION_NONE) { 2332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.OnlineChange", state_duration); 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (offline_packets_received_) { 2362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if ((now - last_offline_packet_received_) < 2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta::FromSeconds(5)) { 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // We can compare this sum with the sum of NCN.OfflineDataRecv. 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_COUNTS_10000( 2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "NCN.OfflineDataRecvAny5sBeforeOnline", 2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) offline_packets_received_); 2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.OfflineDataRecvUntilOnline", 2452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) now - last_offline_packet_received_); 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 2482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.OfflineChange", state_duration); 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 250010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) 251cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) NetworkChangeNotifier::LogOperatorCodeHistogram(type); 252010d83a9304c5a91596085d917d248abff47903aTorne (Richard Coles) 2532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES( 2542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) "NCN.IPAddressChangeToConnectionTypeChange", 2552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) now - last_ip_address_change_); 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) offline_packets_received_ = 0; 2582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bytes_read_since_last_connection_change_ = 0; 2592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_ = 0; 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_connection_type_ = type; 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) polling_interval_ = base::TimeDelta::FromSeconds(1); 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // NetworkChangeNotifier::DNSObserver implementation. 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) virtual void OnDNSChanged() OVERRIDE { 266e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.DNSConfigChange", 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) SinceLast(&last_dns_change_)); 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // NetworkChangeNotifier::NetworkChangeObserver implementation. 2722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnNetworkChanged( 2732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeNotifier::ConnectionType type) OVERRIDE { 274e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 2752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (type != NetworkChangeNotifier::CONNECTION_NONE) { 2762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.NetworkOnlineChange", 2772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) SinceLast(&last_network_change_)); 2782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } else { 2792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.NetworkOfflineChange", 2802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) SinceLast(&last_network_change_)); 2812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 2822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 2832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 2842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Record histogram data whenever we receive a packet. Should only be called 2852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // from the network thread. 2862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void NotifyDataReceived(const URLRequest& request, int bytes_read) { 287e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 2882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (IsLocalhost(request.url().host()) || 2893551c9c881056c480085172ff9840cab31610854Torne (Richard Coles) !request.url().SchemeIsHTTPOrHTTPS()) { 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 2915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 2925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks now = base::TimeTicks::Now(); 2942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta request_duration = now - request.creation_time(); 2952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (bytes_read_since_last_connection_change_ == 0) { 2962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) first_byte_after_connection_change_ = now - last_connection_change_; 2972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_ = request_duration; 2982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 2992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bytes_read_since_last_connection_change_ += bytes_read; 3002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (request_duration < fastest_RTT_since_last_connection_change_) 3012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) fastest_RTT_since_last_connection_change_ = request_duration; 3022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Ignore tiny transfers which will not produce accurate rates. 3032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Ignore zero duration transfers which might cause divide by zero. 3042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (bytes_read > 10000 && 3052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) request_duration > base::TimeDelta::FromMilliseconds(1) && 3062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) request.creation_time() > last_connection_change_) { 3072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32 kbps = bytes_read * 8 / request_duration.InMilliseconds(); 3082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (kbps > peak_kbps_since_last_connection_change_) 3092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) peak_kbps_since_last_connection_change_ = kbps; 3102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 3112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 3122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (last_connection_type_ != NetworkChangeNotifier::CONNECTION_NONE) 3132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return; 3142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 3155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.OfflineDataRecv", 3162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) now - last_connection_change_); 3175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) offline_packets_received_++; 3182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_offline_packet_received_ = now; 3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if ((now - last_polled_connection_) > polling_interval_) { 3215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) polling_interval_ *= 2; 3222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_polled_connection_ = now; 3235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) last_polled_connection_type_ = 3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::GetConnectionType(); 3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (last_polled_connection_type_ == 3275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::CONNECTION_NONE) { 3285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) UMA_HISTOGRAM_MEDIUM_TIMES("NCN.PollingOfflineDataRecv", 3292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) now - last_connection_change_); 3305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static base::TimeDelta SinceLast(base::TimeTicks *last_time) { 3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks current_time = base::TimeTicks::Now(); 3365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta delta = current_time - *last_time; 3375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *last_time = current_time; 3385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return delta; 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks last_ip_address_change_; 3425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks last_connection_change_; 3435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks last_dns_change_; 3442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeTicks last_network_change_; 3455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks last_offline_packet_received_; 3465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeTicks last_polled_connection_; 3475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |polling_interval_| is initialized by |OnConnectionTypeChanged| on our 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // first transition to offline and on subsequent transitions. Once offline, 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |polling_interval_| doubles as offline data is received and we poll 3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // with |NetworkChangeNotifier::GetConnectionType| to verify the connection 3515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // state. 3525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::TimeDelta polling_interval_; 3535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |last_connection_type_| is the last value passed to 3545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |OnConnectionTypeChanged|. 3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::ConnectionType last_connection_type_; 3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |last_polled_connection_type_| is last result from calling 3575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // |NetworkChangeNotifier::GetConnectionType| in |NotifyDataReceived|. 3585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifier::ConnectionType last_polled_connection_type_; 3592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Count of how many times NotifyDataReceived() has been called while the 3602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // NetworkChangeNotifier thought network connection was offline. 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32 offline_packets_received_; 3622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Number of bytes of network data received since last connectivity change. 3632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32 bytes_read_since_last_connection_change_; 3642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Fastest round-trip-time (RTT) since last connectivity change. RTT measured 3652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // from URLRequest creation until first byte received. 3662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta fastest_RTT_since_last_connection_change_; 3672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Time between connectivity change and first network data byte received. 3682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta first_byte_after_connection_change_; 3692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Rough measurement of peak KB/s witnessed since last connectivity change. 3702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // The accuracy is decreased by ignoring these factors: 3712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // 1) Multiple URLRequests can occur concurrently. 3722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // 2) NotifyDataReceived() may be called repeatedly for one URLRequest. 3732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // 3) The transfer time includes at least one RTT while no bytes are read. 3742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Erring on the conservative side is hopefully offset by taking the maximum. 3752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32 peak_kbps_since_last_connection_change_; 3765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 377e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch base::ThreadChecker thread_checker_; 378e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch 3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DISALLOW_COPY_AND_ASSIGN(HistogramWatcher); 3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// NetworkState is thread safe. 3835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class NetworkChangeNotifier::NetworkState { 3845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public: 3855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkState() {} 3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ~NetworkState() {} 3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void GetDnsConfig(DnsConfig* config) const { 3895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::AutoLock lock(lock_); 3905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *config = dns_config_; 3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) void SetDnsConfig(const DnsConfig& dns_config) { 3945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) base::AutoLock lock(lock_); 3955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) dns_config_ = dns_config; 3965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 3975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private: 3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) mutable base::Lock lock_; 4005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DnsConfig dns_config_; 4015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}; 4025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)NetworkChangeNotifier::NetworkChangeCalculatorParams:: 4042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeCalculatorParams() { 4052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 4062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Calculates NetworkChange signal from IPAddress and ConnectionType signals. 4082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class NetworkChangeNotifier::NetworkChangeCalculator 4092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) : public ConnectionTypeObserver, 4102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public IPAddressObserver { 4112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public: 4122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeCalculator(const NetworkChangeCalculatorParams& params) 4132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) : params_(params), 4142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) have_announced_(false), 4152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_announced_connection_type_(CONNECTION_NONE), 4162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pending_connection_type_(CONNECTION_NONE) {} 4172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void Init() { 419e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 420e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(g_network_change_notifier); 4212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) AddConnectionTypeObserver(this); 4222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) AddIPAddressObserver(this); 4232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4242a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual ~NetworkChangeCalculator() { 426e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 427e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(g_network_change_notifier); 4282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) RemoveConnectionTypeObserver(this); 4292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) RemoveIPAddressObserver(this); 4302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // NetworkChangeNotifier::IPAddressObserver implementation. 4332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnIPAddressChanged() OVERRIDE { 434e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 4352a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta delay = last_announced_connection_type_ == CONNECTION_NONE 4362a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ? params_.ip_address_offline_delay_ : params_.ip_address_online_delay_; 4372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Cancels any previous timer. 4382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) timer_.Start(FROM_HERE, delay, this, &NetworkChangeCalculator::Notify); 4392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // NetworkChangeNotifier::ConnectionTypeObserver implementation. 4422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) virtual void OnConnectionTypeChanged(ConnectionType type) OVERRIDE { 443e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 4442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pending_connection_type_ = type; 4452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::TimeDelta delay = last_announced_connection_type_ == CONNECTION_NONE 4462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ? params_.connection_type_offline_delay_ 4472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) : params_.connection_type_online_delay_; 4482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Cancels any previous timer. 4492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) timer_.Start(FROM_HERE, delay, this, &NetworkChangeCalculator::Notify); 4502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private: 4532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) void Notify() { 454e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DCHECK(thread_checker_.CalledOnValidThread()); 4552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Don't bother signaling about dead connections. 4562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (have_announced_ && 4572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) (last_announced_connection_type_ == CONNECTION_NONE) && 4582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) (pending_connection_type_ == CONNECTION_NONE)) { 4592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return; 4602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) have_announced_ = true; 4622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) last_announced_connection_type_ = pending_connection_type_; 4632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Immediately before sending out an online signal, send out an offline 4642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // signal to perform any destructive actions before constructive actions. 4652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (pending_connection_type_ != CONNECTION_NONE) 4662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeNotifier::NotifyObserversOfNetworkChange(CONNECTION_NONE); 4672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeNotifier::NotifyObserversOfNetworkChange( 4682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pending_connection_type_); 4692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 4702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const NetworkChangeCalculatorParams params_; 4722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Indicates if NotifyObserversOfNetworkChange has been called yet. 4742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bool have_announced_; 4752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Last value passed to NotifyObserversOfNetworkChange. 4762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ConnectionType last_announced_connection_type_; 4772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Value to pass to NotifyObserversOfNetworkChange when Notify is called. 4782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ConnectionType pending_connection_type_; 4792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Used to delay notifications so duplicates can be combined. 4802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) base::OneShotTimer<NetworkChangeCalculator> timer_; 481e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch 482e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch base::ThreadChecker thread_checker_; 483e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch 484e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch DISALLOW_COPY_AND_ASSIGN(NetworkChangeCalculator); 4852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)}; 4862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::~NetworkChangeNotifier() { 488e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch network_change_calculator_.reset(); 4895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK_EQ(this, g_network_change_notifier); 4905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier = NULL; 4915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 4945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::SetFactory( 4955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifierFactory* factory) { 4965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CHECK(!g_network_change_notifier_factory); 4975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier_factory = factory; 4985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier* NetworkChangeNotifier::Create() { 5025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier_factory) 5035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return g_network_change_notifier_factory->CreateInstance(); 5045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_WIN) 5065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NetworkChangeNotifierWin* network_change_notifier = 5075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new NetworkChangeNotifierWin(); 5085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) network_change_notifier->WatchForAddressChange(); 5095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return network_change_notifier; 5105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(OS_CHROMEOS) || defined(OS_ANDROID) 5115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // ChromeOS and Android builds MUST use their own class factory. 5125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if !defined(OS_CHROMEOS) 5135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO(oshima): ash_shell do not have access to chromeos'es 5145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // notifier yet. Re-enable this when chromeos'es notifier moved to 5155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // chromeos root directory. crbug.com/119298. 5165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CHECK(false); 5175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif 5185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return NULL; 5195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(OS_LINUX) 5205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return NetworkChangeNotifierLinux::Create(); 5215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#elif defined(OS_MACOSX) 5225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return new NetworkChangeNotifierMac(); 5235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#else 5245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NOTIMPLEMENTED(); 5255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return NULL; 5265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif 5275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::ConnectionType 5315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::GetConnectionType() { 5325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return g_network_change_notifier ? 5335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->GetCurrentConnectionType() : 5345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CONNECTION_UNKNOWN; 5355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::GetDnsConfig(DnsConfig* config) { 5395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!g_network_change_notifier) { 5405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *config = DnsConfig(); 5415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 5425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->network_state_->GetDnsConfig(config); 5435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)const char* NetworkChangeNotifier::ConnectionTypeToString( 5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConnectionType type) { 5495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static const char* kConnectionTypeNames[] = { 5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_UNKNOWN", 5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_ETHERNET", 5525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_WIFI", 5535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_2G", 5545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_3G", 5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "CONNECTION_4G", 55646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) "CONNECTION_NONE", 55746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) "CONNECTION_BLUETOOTH" 5585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) }; 5595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) COMPILE_ASSERT( 5605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) arraysize(kConnectionTypeNames) == 56146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) NetworkChangeNotifier::CONNECTION_LAST + 1, 5625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConnectionType_name_count_mismatch); 56346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) if (type < CONNECTION_UNKNOWN || type > CONNECTION_LAST) { 5645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NOTREACHED(); 5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return "CONNECTION_INVALID"; 5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 5675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return kConnectionTypeNames[type]; 5685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void NetworkChangeNotifier::NotifyDataReceived(const URLRequest& request, 5722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int bytes_read) { 573e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch if (!g_network_change_notifier || 574e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch !g_network_change_notifier->histogram_watcher_) { 5755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 576e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch } 5772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) g_network_change_notifier->histogram_watcher_->NotifyDataReceived(request, 5782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) bytes_read); 5795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 5825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::InitHistogramWatcher() { 5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!g_network_change_notifier) 5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 585e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch g_network_change_notifier->histogram_watcher_.reset(new HistogramWatcher()); 5865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->histogram_watcher_->Init(); 5875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 589e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch// static 590e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdochvoid NetworkChangeNotifier::ShutdownHistogramWatcher() { 591e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch if (!g_network_change_notifier) 592e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch return; 593e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch g_network_change_notifier->histogram_watcher_.reset(); 594e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch} 595e5d81f57cb97b3b6b7fccc9c5610d21eb81db09dBen Murdoch 596cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)// static 597cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)void NetworkChangeNotifier::LogOperatorCodeHistogram(ConnectionType type) { 598cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#if defined(OS_ANDROID) 599cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) // On a connection type change to 2/3/4G, log the network operator MCC/MNC. 600cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) // Log zero in other cases. 601cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) unsigned mcc_mnc = 0; 602cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (type == NetworkChangeNotifier::CONNECTION_2G || 603cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) type == NetworkChangeNotifier::CONNECTION_3G || 604cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) type == NetworkChangeNotifier::CONNECTION_4G) { 605cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) // Log zero if not perfectly converted. 606cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) if (!base::StringToUint( 607cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) net::android::GetTelephonyNetworkOperator(), &mcc_mnc)) { 608cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) mcc_mnc = 0; 609cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) } 610cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) } 611cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) UMA_HISTOGRAM_SPARSE_SLOWLY("NCN.NetworkOperatorMCCMNC", mcc_mnc); 612cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#endif 613cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)} 614cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles) 6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_LINUX) 6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 6175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)const internal::AddressTrackerLinux* 6185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::GetAddressTracker() { 6195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return g_network_change_notifier ? 6205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->GetAddressTrackerInternal() : NULL; 6215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif 6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 6255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NetworkChangeNotifier::IsOffline() { 6265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return GetConnectionType() == CONNECTION_NONE; 6275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool NetworkChangeNotifier::IsConnectionCellular(ConnectionType type) { 6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool is_cellular = false; 6325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) switch (type) { 6335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_2G: 6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_3G: 6355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_4G: 6365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) is_cellular = true; 6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_UNKNOWN: 6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_ETHERNET: 6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_WIFI: 6415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) case CONNECTION_NONE: 64246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles) case CONNECTION_BLUETOOTH: 6435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) is_cellular = false; 6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return is_cellular; 6475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 6505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier* NetworkChangeNotifier::CreateMock() { 6515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return new MockNetworkChangeNotifier(); 6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::AddIPAddressObserver(IPAddressObserver* observer) { 6555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) 6565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->ip_address_observer_list_->AddObserver(observer); 6575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::AddConnectionTypeObserver( 6605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConnectionTypeObserver* observer) { 6615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) { 6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->connection_type_observer_list_->AddObserver( 6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer); 6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::AddDNSObserver(DNSObserver* observer) { 6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) { 6695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->resolver_state_observer_list_->AddObserver( 6705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer); 6715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void NetworkChangeNotifier::AddNetworkChangeObserver( 6752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeObserver* observer) { 6762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (g_network_change_notifier) { 6772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) g_network_change_notifier->network_change_observer_list_->AddObserver( 6782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) observer); 6792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 6802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 6812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::RemoveIPAddressObserver( 6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) IPAddressObserver* observer) { 6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) { 6855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->ip_address_observer_list_->RemoveObserver( 6865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer); 6875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::RemoveConnectionTypeObserver( 6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ConnectionTypeObserver* observer) { 6925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) { 6935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->connection_type_observer_list_->RemoveObserver( 6945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer); 6955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::RemoveDNSObserver(DNSObserver* observer) { 6995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (g_network_change_notifier) { 7005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->resolver_state_observer_list_->RemoveObserver( 7015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) observer); 7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)void NetworkChangeNotifier::RemoveNetworkChangeObserver( 7062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) NetworkChangeObserver* observer) { 7072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (g_network_change_notifier) { 7082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) g_network_change_notifier->network_change_observer_list_->RemoveObserver( 7092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) observer); 7102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 7112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 7122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 713116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch// static 714116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests() { 715116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier) 716116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfIPAddressChangeImpl(); 717116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 718116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 719116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch// static 720116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfConnectionTypeChangeForTests( 721116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch ConnectionType type) { 722116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier) 723116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfConnectionTypeChangeImpl(type); 724116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 725116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 726116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch// static 7271320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tuccivoid NetworkChangeNotifier::NotifyObserversOfNetworkChangeForTests( 7281320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci ConnectionType type) { 7291320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci if (g_network_change_notifier) 7301320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci g_network_change_notifier->NotifyObserversOfNetworkChangeImpl(type); 7311320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci} 7321320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci 7331320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci// static 734116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::SetTestNotificationsOnly(bool test_only) { 735116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier) 736116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->test_notifications_only_ = test_only; 737116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 738116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 7392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)NetworkChangeNotifier::NetworkChangeNotifier( 7402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) const NetworkChangeCalculatorParams& params 7412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) /*= NetworkChangeCalculatorParams()*/) 7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : ip_address_observer_list_( 7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new ObserverListThreadSafe<IPAddressObserver>( 7445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ObserverListBase<IPAddressObserver>::NOTIFY_EXISTING_ONLY)), 7455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) connection_type_observer_list_( 7465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new ObserverListThreadSafe<ConnectionTypeObserver>( 7475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ObserverListBase<ConnectionTypeObserver>::NOTIFY_EXISTING_ONLY)), 7485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) resolver_state_observer_list_( 7495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) new ObserverListThreadSafe<DNSObserver>( 7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ObserverListBase<DNSObserver>::NOTIFY_EXISTING_ONLY)), 7512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) network_change_observer_list_( 7522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) new ObserverListThreadSafe<NetworkChangeObserver>( 7532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ObserverListBase<NetworkChangeObserver>::NOTIFY_EXISTING_ONLY)), 7545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) network_state_(new NetworkState()), 755116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch network_change_calculator_(new NetworkChangeCalculator(params)), 756116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch test_notifications_only_(false) { 7575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(!g_network_change_notifier); 7585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier = this; 7592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) network_change_calculator_->Init(); 7605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#if defined(OS_LINUX) 7635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)const internal::AddressTrackerLinux* 7645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::GetAddressTrackerInternal() const { 7655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return NULL; 7665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif 7685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 7705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::NotifyObserversOfIPAddressChange() { 771116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier && 772116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch !g_network_change_notifier->test_notifications_only_) { 773116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfIPAddressChangeImpl(); 774116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch } 775116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 776116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 777116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch// static 778116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfConnectionTypeChange() { 779116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier && 780116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch !g_network_change_notifier->test_notifications_only_) { 781116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfConnectionTypeChangeImpl( 782116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch GetConnectionType()); 783116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch } 784116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 785116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 786116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch// static 787116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfNetworkChange( 788116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch ConnectionType type) { 789116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier && 790116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch !g_network_change_notifier->test_notifications_only_) { 791116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfNetworkChangeImpl(type); 7925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 7965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::NotifyObserversOfDNSChange() { 797116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch if (g_network_change_notifier && 798116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch !g_network_change_notifier->test_notifications_only_) { 799116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch g_network_change_notifier->NotifyObserversOfDNSChangeImpl(); 8005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// static 8045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void NetworkChangeNotifier::SetDnsConfig(const DnsConfig& config) { 8055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!g_network_change_notifier) 8065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return; 8075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier->network_state_->SetDnsConfig(config); 8085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) NotifyObserversOfDNSChange(); 8095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 811116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfIPAddressChangeImpl() { 812116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch ip_address_observer_list_->Notify(&IPAddressObserver::OnIPAddressChanged); 8135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 815116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfConnectionTypeChangeImpl( 8162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) ConnectionType type) { 817116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch connection_type_observer_list_->Notify( 818116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch &ConnectionTypeObserver::OnConnectionTypeChanged, type); 819116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 820116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 821116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfNetworkChangeImpl( 822116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch ConnectionType type) { 823116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch network_change_observer_list_->Notify( 824116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch &NetworkChangeObserver::OnNetworkChanged, type); 825116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch} 826116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch 827116680a4aac90f2aa7413d9095a592090648e557Ben Murdochvoid NetworkChangeNotifier::NotifyObserversOfDNSChangeImpl() { 828116680a4aac90f2aa7413d9095a592090648e557Ben Murdoch resolver_state_observer_list_->Notify(&DNSObserver::OnDNSChanged); 8292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 8302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 8315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::DisableForTest::DisableForTest() 8325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) : network_change_notifier_(g_network_change_notifier) { 8335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(g_network_change_notifier); 8345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier = NULL; 8355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)NetworkChangeNotifier::DisableForTest::~DisableForTest() { 8385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DCHECK(!g_network_change_notifier); 8395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) g_network_change_notifier = network_change_notifier_; 8405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace net 843