1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "chrome/browser/network_time/network_time_service.h"
7 #include "base/command_line.h"
8 #include "base/prefs/pref_service.h"
9 #include "chrome/browser/network_time/network_time_tracker.h"
10 #include "chrome/browser/profiles/profile.h"
11 #include "chrome/common/chrome_switches.h"
12 #include "chrome/common/pref_names.h"
13 #include "components/user_prefs/pref_registry_syncable.h"
16 void NetworkTimeService::RegisterProfilePrefs(
17 user_prefs::PrefRegistrySyncable
* registry
) {
18 registry
->RegisterDictionaryPref(
19 prefs::kNetworkTimeMapping
,
20 new base::DictionaryValue(),
21 user_prefs::PrefRegistrySyncable::UNSYNCABLE_PREF
);
24 NetworkTimeService::NetworkTimeService(Profile
* profile
)
26 if (!CommandLine::ForCurrentProcess()->HasSwitch(
27 switches::kEnableNetworkTime
)) {
31 network_time_tracker_
.reset(new NetworkTimeTracker
);
32 network_time_tracker_
->Start();
34 const base::DictionaryValue
* time_mapping
=
35 profile_
->GetPrefs()->GetDictionary(prefs::kNetworkTimeMapping
);
37 double network_time_js
;
38 if (time_mapping
->GetDouble("local", &local_time_js
) &&
39 time_mapping
->GetDouble("network", &network_time_js
)) {
40 base::Time local_time_saved
= base::Time::FromJsTime(local_time_js
);
41 if (local_time_saved
> base::Time::Now() ||
42 base::Time::Now() - local_time_saved
> base::TimeDelta::FromDays(7)) {
43 // Drop saved mapping if clock skew has changed or the data is too old.
44 profile_
->GetPrefs()->ClearPref(prefs::kNetworkTimeMapping
);
46 network_time_tracker_
->InitFromSavedTime(
47 NetworkTimeTracker::TimeMapping(
48 local_time_saved
, base::Time::FromJsTime(network_time_js
)));
53 NetworkTimeService::~NetworkTimeService() {}
55 void NetworkTimeService::Shutdown() {
56 if (!network_time_tracker_
)
59 if (network_time_tracker_
->received_network_time()) {
60 // Update time mapping if tracker received time update from server, i.e.
61 // mapping is accurate.
62 base::Time local_now
= base::Time::Now();
63 base::Time network_now
= GetNetworkTime(local_now
);
64 base::DictionaryValue time_mapping
;
65 time_mapping
.SetDouble("local", local_now
.ToJsTime());
66 time_mapping
.SetDouble("network", network_now
.ToJsTime());
67 profile_
->GetPrefs()->Set(prefs::kNetworkTimeMapping
, time_mapping
);
71 base::Time
NetworkTimeService::GetNetworkTime(
72 const base::Time
& local_time
) {
73 if (!network_time_tracker_
.get() || local_time
.is_null() ||
77 base::Time network_time_now
;
78 if (!network_time_tracker_
->GetNetworkTime(base::TimeTicks::Now(),
79 &network_time_now
, NULL
)) {
82 return local_time
+ (network_time_now
- base::Time::Now());
85 base::Time
NetworkTimeService::GetNetworkNow() {
86 return GetNetworkTime(base::Time::Now());