1 // Copyright (c) 2012 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/chromeos/policy/device_cloud_policy_manager_chromeos.h"
8 #include "base/bind_helpers.h"
9 #include "base/callback.h"
10 #include "base/command_line.h"
11 #include "base/logging.h"
12 #include "base/prefs/pref_registry_simple.h"
13 #include "base/prefs/pref_service.h"
14 #include "base/strings/string_number_conversions.h"
15 #include "base/time/time.h"
16 #include "chrome/browser/browser_process.h"
17 #include "chrome/browser/chromeos/attestation/attestation_policy_observer.h"
18 #include "chrome/browser/chromeos/login/enrollment/auto_enrollment_controller.h"
19 #include "chrome/browser/chromeos/login/startup_utils.h"
20 #include "chrome/browser/chromeos/policy/device_cloud_policy_store_chromeos.h"
21 #include "chrome/browser/chromeos/policy/device_status_collector.h"
22 #include "chrome/browser/chromeos/policy/enterprise_install_attributes.h"
23 #include "chrome/browser/chromeos/policy/heartbeat_scheduler.h"
24 #include "chrome/browser/chromeos/policy/remote_commands/device_commands_factory_chromeos.h"
25 #include "chrome/browser/chromeos/policy/server_backed_state_keys_broker.h"
26 #include "chrome/browser/chromeos/policy/status_uploader.h"
27 #include "chrome/common/pref_names.h"
28 #include "chromeos/chromeos_constants.h"
29 #include "chromeos/chromeos_switches.h"
30 #include "chromeos/system/statistics_provider.h"
31 #include "components/policy/core/common/cloud/cloud_policy_core.h"
32 #include "components/policy/core/common/cloud/cloud_policy_service.h"
33 #include "components/policy/core/common/cloud/cloud_policy_store.h"
34 #include "components/policy/core/common/remote_commands/remote_commands_factory.h"
35 #include "content/public/browser/browser_thread.h"
36 #include "crypto/sha2.h"
37 #include "policy/proto/device_management_backend.pb.h"
40 using content::BrowserThread
;
42 namespace em
= enterprise_management
;
48 const char kNoRequisition
[] = "none";
49 const char kRemoraRequisition
[] = "remora";
50 const char kSharkRequisition
[] = "shark";
52 // These are the machine serial number keys that we check in order until we
53 // find a non-empty serial number. The VPD spec says the serial number should be
54 // in the "serial_number" key for v2+ VPDs. However, legacy devices used a
55 // different key to report their serial number, which we fall back to if
56 // "serial_number" is not present.
58 // Product_S/N is still special-cased due to inconsistencies with serial
59 // numbers on Lumpy devices: On these devices, serial_number is identical to
60 // Product_S/N with an appended checksum. Unfortunately, the sticker on the
61 // packaging doesn't include that checksum either (the sticker on the device
62 // does though!). The former sticker is the source of the serial number used by
63 // device management service, so we prefer Product_S/N over serial number to
66 // TODO(mnissler): Move serial_number back to the top once the server side uses
67 // the correct serial number.
68 const char* const kMachineInfoSerialNumberKeys
[] = {
69 "Product_S/N", // Lumpy/Alex devices
70 "serial_number", // VPD v2+ devices
71 "Product_SN", // Mario
72 "sn", // old ZGB devices (more recent ones use serial_number)
75 // Fetches a machine statistic value from StatisticsProvider, returns an empty
77 std::string
GetMachineStatistic(const std::string
& key
) {
79 chromeos::system::StatisticsProvider
* provider
=
80 chromeos::system::StatisticsProvider::GetInstance();
81 if (!provider
->GetMachineStatistic(key
, &value
))
87 // Gets a machine flag from StatisticsProvider, returns the given
88 // |default_value| if not present.
89 bool GetMachineFlag(const std::string
& key
, bool default_value
) {
90 bool value
= default_value
;
91 chromeos::system::StatisticsProvider
* provider
=
92 chromeos::system::StatisticsProvider::GetInstance();
93 if (!provider
->GetMachineFlag(key
, &value
))
99 // Checks whether forced re-enrollment is enabled.
100 bool ForcedReEnrollmentEnabled() {
101 return chromeos::AutoEnrollmentController::GetMode() ==
102 chromeos::AutoEnrollmentController::MODE_FORCED_RE_ENROLLMENT
;
107 DeviceCloudPolicyManagerChromeOS::DeviceCloudPolicyManagerChromeOS(
108 scoped_ptr
<DeviceCloudPolicyStoreChromeOS
> store
,
109 const scoped_refptr
<base::SequencedTaskRunner
>& task_runner
,
110 ServerBackedStateKeysBroker
* state_keys_broker
)
111 : CloudPolicyManager(
112 dm_protocol::kChromeDevicePolicyType
,
116 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::FILE),
117 BrowserThread::GetMessageLoopProxyForThread(BrowserThread::IO
)),
118 device_store_(store
.Pass()),
119 state_keys_broker_(state_keys_broker
),
120 task_runner_(task_runner
),
121 local_state_(nullptr) {
124 DeviceCloudPolicyManagerChromeOS::~DeviceCloudPolicyManagerChromeOS() {}
126 void DeviceCloudPolicyManagerChromeOS::Initialize(PrefService
* local_state
) {
129 local_state_
= local_state
;
131 state_keys_update_subscription_
= state_keys_broker_
->RegisterUpdateCallback(
132 base::Bind(&DeviceCloudPolicyManagerChromeOS::OnStateKeysUpdated
,
133 base::Unretained(this)));
135 InitializeRequisition();
138 void DeviceCloudPolicyManagerChromeOS::AddDeviceCloudPolicyManagerObserver(
139 Observer
* observer
) {
140 observers_
.AddObserver(observer
);
143 void DeviceCloudPolicyManagerChromeOS::RemoveDeviceCloudPolicyManagerObserver(
144 Observer
* observer
) {
145 observers_
.RemoveObserver(observer
);
148 std::string
DeviceCloudPolicyManagerChromeOS::GetDeviceRequisition() const {
149 std::string requisition
;
150 const PrefService::Preference
* pref
= local_state_
->FindPreference(
151 prefs::kDeviceEnrollmentRequisition
);
152 if (!pref
->IsDefaultValue())
153 pref
->GetValue()->GetAsString(&requisition
);
155 if (requisition
== kNoRequisition
)
161 void DeviceCloudPolicyManagerChromeOS::SetDeviceRequisition(
162 const std::string
& requisition
) {
163 VLOG(1) << "SetDeviceRequisition " << requisition
;
165 if (requisition
.empty()) {
166 local_state_
->ClearPref(prefs::kDeviceEnrollmentRequisition
);
167 local_state_
->ClearPref(prefs::kDeviceEnrollmentAutoStart
);
168 local_state_
->ClearPref(prefs::kDeviceEnrollmentCanExit
);
170 local_state_
->SetString(prefs::kDeviceEnrollmentRequisition
, requisition
);
171 if (requisition
== kNoRequisition
) {
172 local_state_
->ClearPref(prefs::kDeviceEnrollmentAutoStart
);
173 local_state_
->ClearPref(prefs::kDeviceEnrollmentCanExit
);
175 local_state_
->SetBoolean(prefs::kDeviceEnrollmentAutoStart
, true);
176 local_state_
->SetBoolean(prefs::kDeviceEnrollmentCanExit
, false);
182 bool DeviceCloudPolicyManagerChromeOS::IsRemoraRequisition() const {
183 return GetDeviceRequisition() == kRemoraRequisition
;
186 bool DeviceCloudPolicyManagerChromeOS::IsSharkRequisition() const {
187 return GetDeviceRequisition() == kSharkRequisition
;
190 void DeviceCloudPolicyManagerChromeOS::Shutdown() {
191 status_uploader_
.reset();
192 heartbeat_scheduler_
.reset();
193 state_keys_update_subscription_
.reset();
194 CloudPolicyManager::Shutdown();
198 void DeviceCloudPolicyManagerChromeOS::RegisterPrefs(
199 PrefRegistrySimple
* registry
) {
200 registry
->RegisterStringPref(prefs::kDeviceEnrollmentRequisition
,
202 registry
->RegisterBooleanPref(prefs::kDeviceEnrollmentAutoStart
, false);
203 registry
->RegisterBooleanPref(prefs::kDeviceEnrollmentCanExit
, true);
204 registry
->RegisterDictionaryPref(prefs::kServerBackedDeviceState
);
208 std::string
DeviceCloudPolicyManagerChromeOS::GetMachineID() {
209 std::string machine_id
;
210 chromeos::system::StatisticsProvider
* provider
=
211 chromeos::system::StatisticsProvider::GetInstance();
212 for (size_t i
= 0; i
< arraysize(kMachineInfoSerialNumberKeys
); i
++) {
213 if (provider
->GetMachineStatistic(kMachineInfoSerialNumberKeys
[i
],
215 !machine_id
.empty()) {
220 if (machine_id
.empty())
221 LOG(WARNING
) << "Failed to get machine id.";
227 std::string
DeviceCloudPolicyManagerChromeOS::GetMachineModel() {
228 return GetMachineStatistic(chromeos::system::kHardwareClassKey
);
231 void DeviceCloudPolicyManagerChromeOS::StartConnection(
232 scoped_ptr
<CloudPolicyClient
> client_to_connect
,
233 EnterpriseInstallAttributes
* install_attributes
) {
236 // Set state keys here so the first policy fetch submits them to the server.
237 if (ForcedReEnrollmentEnabled())
238 client_to_connect
->SetStateKeysToUpload(state_keys_broker_
->state_keys());
240 core()->Connect(client_to_connect
.Pass());
241 core()->StartRefreshScheduler();
242 core()->StartRemoteCommandsService(
243 scoped_ptr
<RemoteCommandsFactory
>(new DeviceCommandsFactoryChromeOS()));
244 core()->TrackRefreshDelayPref(local_state_
,
245 prefs::kDevicePolicyRefreshRate
);
246 attestation_policy_observer_
.reset(
247 new chromeos::attestation::AttestationPolicyObserver(client()));
249 // Enable device reporting and status monitoring for enterprise enrolled
250 // devices. We want to create these objects for enrolled devices, even if
251 // monitoring is currently inactive, in case monitoring is turned back on in
252 // a future policy fetch - the classes themselves track the current state of
253 // the monitoring settings and only perform monitoring if it is active.
254 if (install_attributes
->IsEnterpriseDevice()) {
255 CreateStatusUploader();
256 heartbeat_scheduler_
.reset(
257 new HeartbeatScheduler(g_browser_process
->gcm_driver(),
258 install_attributes
->GetDomain(),
259 install_attributes
->GetDeviceId(),
266 void DeviceCloudPolicyManagerChromeOS::Unregister(
267 const UnregisterCallback
& callback
) {
269 LOG(ERROR
) << "Tried to unregister but DeviceCloudPolicyManagerChromeOS is "
275 service()->Unregister(callback
);
278 void DeviceCloudPolicyManagerChromeOS::Disconnect() {
279 status_uploader_
.reset();
280 heartbeat_scheduler_
.reset();
281 core()->Disconnect();
283 NotifyDisconnected();
286 void DeviceCloudPolicyManagerChromeOS::OnStateKeysUpdated() {
287 if (client() && ForcedReEnrollmentEnabled())
288 client()->SetStateKeysToUpload(state_keys_broker_
->state_keys());
291 void DeviceCloudPolicyManagerChromeOS::InitializeRequisition() {
292 // OEM statistics are only loaded when OOBE is not completed.
293 if (chromeos::StartupUtils::IsOobeCompleted())
296 const PrefService::Preference
* pref
= local_state_
->FindPreference(
297 prefs::kDeviceEnrollmentRequisition
);
298 if (pref
->IsDefaultValue()) {
299 std::string requisition
=
300 GetMachineStatistic(chromeos::system::kOemDeviceRequisitionKey
);
302 if (!requisition
.empty()) {
303 local_state_
->SetString(prefs::kDeviceEnrollmentRequisition
,
305 if (requisition
== kRemoraRequisition
||
306 requisition
== kSharkRequisition
) {
307 local_state_
->SetBoolean(prefs::kDeviceEnrollmentAutoStart
, true);
308 local_state_
->SetBoolean(prefs::kDeviceEnrollmentCanExit
, false);
310 local_state_
->SetBoolean(
311 prefs::kDeviceEnrollmentAutoStart
,
312 GetMachineFlag(chromeos::system::kOemIsEnterpriseManagedKey
,
314 local_state_
->SetBoolean(
315 prefs::kDeviceEnrollmentCanExit
,
316 GetMachineFlag(chromeos::system::kOemCanExitEnterpriseEnrollmentKey
,
323 void DeviceCloudPolicyManagerChromeOS::NotifyConnected() {
325 Observer
, observers_
, OnDeviceCloudPolicyManagerConnected());
328 void DeviceCloudPolicyManagerChromeOS::NotifyDisconnected() {
330 Observer
, observers_
, OnDeviceCloudPolicyManagerDisconnected());
333 void DeviceCloudPolicyManagerChromeOS::CreateStatusUploader() {
334 status_uploader_
.reset(new StatusUploader(
336 make_scoped_ptr(new DeviceStatusCollector(
337 local_state_
, chromeos::system::StatisticsProvider::GetInstance(),
338 DeviceStatusCollector::LocationUpdateRequester(),
339 DeviceStatusCollector::VolumeInfoFetcher(),
340 DeviceStatusCollector::CPUStatisticsFetcher(),
341 DeviceStatusCollector::CPUTempFetcher())),
345 } // namespace policy