Home | History | Annotate | Download | only in policy
      1 // Copyright 2014 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.
      4 
      5 #include "chrome/browser/chromeos/policy/device_cloud_policy_initializer.h"
      6 
      7 #include "base/bind.h"
      8 #include "base/bind_helpers.h"
      9 #include "base/logging.h"
     10 #include "base/prefs/pref_service.h"
     11 #include "base/sequenced_task_runner.h"
     12 #include "base/values.h"
     13 #include "chrome/browser/browser_process.h"
     14 #include "chrome/browser/chromeos/login/startup_utils.h"
     15 #include "chrome/browser/chromeos/policy/device_cloud_policy_manager_chromeos.h"
     16 #include "chrome/browser/chromeos/policy/device_cloud_policy_store_chromeos.h"
     17 #include "chrome/browser/chromeos/policy/device_status_collector.h"
     18 #include "chrome/browser/chromeos/policy/enrollment_handler_chromeos.h"
     19 #include "chrome/browser/chromeos/policy/enterprise_install_attributes.h"
     20 #include "chrome/browser/chromeos/policy/server_backed_device_state.h"
     21 #include "chrome/browser/chromeos/settings/device_settings_service.h"
     22 #include "chrome/common/chrome_content_client.h"
     23 #include "chrome/common/pref_names.h"
     24 #include "chromeos/system/statistics_provider.h"
     25 #include "components/policy/core/common/cloud/cloud_policy_constants.h"
     26 #include "components/policy/core/common/cloud/cloud_policy_core.h"
     27 #include "components/policy/core/common/cloud/device_management_service.h"
     28 #include "components/policy/core/common/cloud/system_policy_request_context.h"
     29 #include "net/url_request/url_request_context_getter.h"
     30 
     31 namespace em = enterprise_management;
     32 
     33 namespace policy {
     34 
     35 namespace {
     36 
     37 // Gets a machine flag from StatisticsProvider, returning the given
     38 // |default_value| if not present.
     39 bool GetMachineFlag(const std::string& key, bool default_value) {
     40   bool value = default_value;
     41   chromeos::system::StatisticsProvider* provider =
     42       chromeos::system::StatisticsProvider::GetInstance();
     43   if (!provider->GetMachineFlag(key, &value))
     44     return default_value;
     45 
     46   return value;
     47 }
     48 
     49 }  // namespace
     50 
     51 DeviceCloudPolicyInitializer::DeviceCloudPolicyInitializer(
     52     PrefService* local_state,
     53     DeviceManagementService* enterprise_service,
     54     DeviceManagementService* consumer_service,
     55     const scoped_refptr<base::SequencedTaskRunner>& background_task_runner,
     56     EnterpriseInstallAttributes* install_attributes,
     57     ServerBackedStateKeysBroker* state_keys_broker,
     58     DeviceCloudPolicyStoreChromeOS* device_store,
     59     DeviceCloudPolicyManagerChromeOS* manager,
     60     chromeos::DeviceSettingsService* device_settings_service,
     61     const base::Closure& on_connected_callback)
     62     : local_state_(local_state),
     63       enterprise_service_(enterprise_service),
     64       consumer_service_(consumer_service),
     65       background_task_runner_(background_task_runner),
     66       install_attributes_(install_attributes),
     67       state_keys_broker_(state_keys_broker),
     68       device_store_(device_store),
     69       manager_(manager),
     70       device_settings_service_(device_settings_service),
     71       on_connected_callback_(on_connected_callback),
     72       is_initialized_(false) {
     73 }
     74 
     75 DeviceCloudPolicyInitializer::~DeviceCloudPolicyInitializer() {
     76   DCHECK(!is_initialized_);
     77 }
     78 
     79 void DeviceCloudPolicyInitializer::Init() {
     80   DCHECK(!is_initialized_);
     81 
     82   is_initialized_ = true;
     83   device_store_->AddObserver(this);
     84   state_keys_update_subscription_ = state_keys_broker_->RegisterUpdateCallback(
     85       base::Bind(&DeviceCloudPolicyInitializer::TryToCreateClient,
     86                  base::Unretained(this)));
     87 
     88   device_status_provider_.reset(
     89       new DeviceStatusCollector(
     90           local_state_,
     91           chromeos::system::StatisticsProvider::GetInstance(),
     92           NULL));
     93 
     94   TryToCreateClient();
     95 }
     96 
     97 void DeviceCloudPolicyInitializer::Shutdown() {
     98   DCHECK(is_initialized_);
     99 
    100   device_store_->RemoveObserver(this);
    101   device_status_provider_.reset();
    102   enrollment_handler_.reset();
    103   state_keys_update_subscription_.reset();
    104   is_initialized_ = false;
    105 }
    106 
    107 void DeviceCloudPolicyInitializer::StartEnrollment(
    108     em::PolicyData::ManagementMode management_mode,
    109     DeviceManagementService* device_management_service,
    110     const std::string& auth_token,
    111     bool is_auto_enrollment,
    112     const AllowedDeviceModes& allowed_device_modes,
    113     const EnrollmentCallback& enrollment_callback) {
    114   DCHECK(is_initialized_);
    115   DCHECK(!enrollment_handler_);
    116 
    117   manager_->core()->Disconnect();
    118   enrollment_handler_.reset(new EnrollmentHandlerChromeOS(
    119       device_store_,
    120       install_attributes_,
    121       state_keys_broker_,
    122       device_settings_service_,
    123       CreateClient(device_management_service),
    124       background_task_runner_,
    125       auth_token,
    126       install_attributes_->GetDeviceId(),
    127       is_auto_enrollment,
    128       manager_->GetDeviceRequisition(),
    129       allowed_device_modes,
    130       management_mode,
    131       base::Bind(&DeviceCloudPolicyInitializer::EnrollmentCompleted,
    132                  base::Unretained(this),
    133                  enrollment_callback)));
    134   enrollment_handler_->StartEnrollment();
    135 }
    136 
    137 bool DeviceCloudPolicyInitializer::ShouldAutoStartEnrollment() const {
    138   std::string restore_mode = GetRestoreMode();
    139   if (restore_mode == kDeviceStateRestoreModeReEnrollmentRequested ||
    140       restore_mode == kDeviceStateRestoreModeReEnrollmentEnforced) {
    141     return true;
    142   }
    143 
    144   if (local_state_->HasPrefPath(prefs::kDeviceEnrollmentAutoStart))
    145     return local_state_->GetBoolean(prefs::kDeviceEnrollmentAutoStart);
    146 
    147   return GetMachineFlag(chromeos::system::kOemIsEnterpriseManagedKey, false);
    148 }
    149 
    150 bool DeviceCloudPolicyInitializer::ShouldRecoverEnrollment() const {
    151   if (install_attributes_->IsEnterpriseDevice() &&
    152       chromeos::StartupUtils::IsEnrollmentRecoveryRequired()) {
    153     LOG(WARNING) << "Enrollment recovery required according to pref.";
    154     if (!DeviceCloudPolicyManagerChromeOS::GetMachineID().empty())
    155       return true;
    156     LOG(WARNING) << "Postponing recovery because machine id is missing.";
    157   }
    158   return false;
    159 }
    160 
    161 std::string DeviceCloudPolicyInitializer::GetEnrollmentRecoveryDomain() const {
    162   return install_attributes_->GetDomain();
    163 }
    164 
    165 bool DeviceCloudPolicyInitializer::CanExitEnrollment() const {
    166   if (GetRestoreMode() == kDeviceStateRestoreModeReEnrollmentEnforced)
    167     return false;
    168 
    169   if (local_state_->HasPrefPath(prefs::kDeviceEnrollmentCanExit))
    170     return local_state_->GetBoolean(prefs::kDeviceEnrollmentCanExit);
    171 
    172   return GetMachineFlag(chromeos::system::kOemCanExitEnterpriseEnrollmentKey,
    173                         true);
    174 }
    175 
    176 std::string
    177 DeviceCloudPolicyInitializer::GetForcedEnrollmentDomain() const {
    178   const base::DictionaryValue* device_state_dict =
    179       local_state_->GetDictionary(prefs::kServerBackedDeviceState);
    180   std::string management_domain;
    181   device_state_dict->GetString(kDeviceStateManagementDomain,
    182                                &management_domain);
    183   return management_domain;
    184 }
    185 
    186 void DeviceCloudPolicyInitializer::OnStoreLoaded(CloudPolicyStore* store) {
    187   TryToCreateClient();
    188 }
    189 
    190 void DeviceCloudPolicyInitializer::OnStoreError(CloudPolicyStore* store) {
    191   // Do nothing.
    192 }
    193 
    194 void DeviceCloudPolicyInitializer::EnrollmentCompleted(
    195     const EnrollmentCallback& enrollment_callback,
    196     EnrollmentStatus status) {
    197   scoped_ptr<CloudPolicyClient> client = enrollment_handler_->ReleaseClient();
    198   enrollment_handler_.reset();
    199 
    200   if (status.status() == EnrollmentStatus::STATUS_SUCCESS) {
    201     StartConnection(client.Pass());
    202   } else {
    203     // Some attempts to create a client may be blocked because the enrollment
    204     // was in progress. We give it a try again.
    205     TryToCreateClient();
    206   }
    207 
    208   if (!enrollment_callback.is_null())
    209     enrollment_callback.Run(status);
    210 }
    211 
    212 scoped_ptr<CloudPolicyClient> DeviceCloudPolicyInitializer::CreateClient(
    213     DeviceManagementService* device_management_service) {
    214   scoped_refptr<net::URLRequestContextGetter> request_context =
    215       new SystemPolicyRequestContext(
    216           g_browser_process->system_request_context(), GetUserAgent());
    217 
    218   return make_scoped_ptr(
    219       new CloudPolicyClient(DeviceCloudPolicyManagerChromeOS::GetMachineID(),
    220                             DeviceCloudPolicyManagerChromeOS::GetMachineModel(),
    221                             kPolicyVerificationKeyHash,
    222                             USER_AFFILIATION_NONE,
    223                             device_status_provider_.get(),
    224                             device_management_service,
    225                             request_context));
    226 }
    227 
    228 void DeviceCloudPolicyInitializer::TryToCreateClient() {
    229   if (device_store_->is_initialized() &&
    230       device_store_->has_policy() &&
    231       !device_store_->policy()->request_token().empty() &&
    232       !state_keys_broker_->pending() &&
    233       !enrollment_handler_) {
    234     DeviceManagementService* service;
    235     if (device_store_->policy()->management_mode() ==
    236         em::PolicyData::CONSUMER_MANAGED) {
    237       service = consumer_service_;
    238     } else {
    239       service = enterprise_service_;
    240     }
    241     StartConnection(CreateClient(service));
    242   }
    243 }
    244 
    245 void DeviceCloudPolicyInitializer::StartConnection(
    246     scoped_ptr<CloudPolicyClient> client) {
    247   if (!manager_->core()->service())
    248     manager_->StartConnection(client.Pass(), device_status_provider_.Pass());
    249 
    250   if (!on_connected_callback_.is_null()) {
    251     on_connected_callback_.Run();
    252     on_connected_callback_.Reset();
    253   }
    254 }
    255 
    256 std::string DeviceCloudPolicyInitializer::GetRestoreMode() const {
    257   const base::DictionaryValue* device_state_dict =
    258       local_state_->GetDictionary(prefs::kServerBackedDeviceState);
    259   std::string restore_mode;
    260   device_state_dict->GetString(kDeviceStateRestoreMode, &restore_mode);
    261   return restore_mode;
    262 }
    263 
    264 }  // namespace policy
    265