| OLD | NEW |
| (Empty) | |
| 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. |
| 4 |
| 5 #include "chrome/browser/policy/cloud_policy_client.h" |
| 6 |
| 7 #include "base/bind.h" |
| 8 #include "base/logging.h" |
| 9 #include "chrome/browser/policy/device_management_service.h" |
| 10 #include "chrome/browser/policy/proto/device_management_backend.pb.h" |
| 11 #include "chrome/common/guid.h" |
| 12 |
| 13 namespace em = enterprise_management; |
| 14 |
| 15 namespace policy { |
| 16 |
| 17 CloudPolicyClient::Observer::~Observer() {} |
| 18 |
| 19 CloudPolicyClient::StatusProvider::~StatusProvider() {} |
| 20 |
| 21 CloudPolicyClient::CloudPolicyClient(const std::string& machine_id, |
| 22 const std::string& machine_model, |
| 23 UserAffiliation user_affiliation, |
| 24 PolicyScope scope, |
| 25 StatusProvider* status_provider, |
| 26 DeviceManagementService* service) |
| 27 : machine_id_(machine_id), |
| 28 machine_model_(machine_model), |
| 29 user_affiliation_(user_affiliation), |
| 30 scope_(scope), |
| 31 submit_machine_id_(false), |
| 32 public_key_version_(-1), |
| 33 public_key_version_valid_(false), |
| 34 service_(service), |
| 35 status_provider_(status_provider), |
| 36 status_(DM_STATUS_SUCCESS) {} |
| 37 |
| 38 CloudPolicyClient::~CloudPolicyClient() {} |
| 39 |
| 40 void CloudPolicyClient::SetupRegistration(const std::string& dm_token, |
| 41 const std::string& client_id) { |
| 42 DCHECK(!dm_token.empty()); |
| 43 DCHECK(!client_id.empty()); |
| 44 DCHECK(!is_registered()); |
| 45 |
| 46 dm_token_ = dm_token; |
| 47 client_id_ = client_id; |
| 48 request_job_.reset(); |
| 49 policy_.reset(); |
| 50 |
| 51 NotifyRegistrationStateChanged(); |
| 52 } |
| 53 |
| 54 void CloudPolicyClient::Register(const std::string& auth_token) { |
| 55 DCHECK(!auth_token.empty()); |
| 56 DCHECK(!is_registered()); |
| 57 |
| 58 // Generate a new client ID. This is intentionally done on each new |
| 59 // registration request in order to preserve privacy. Reusing IDs would mean |
| 60 // the server could track clients by their registration attempts. |
| 61 client_id_ = guid::GenerateGUID(); |
| 62 |
| 63 request_job_.reset( |
| 64 service_->CreateJob(DeviceManagementRequestJob::TYPE_REGISTRATION)); |
| 65 request_job_->SetOAuthToken(auth_token); |
| 66 request_job_->SetClientID(client_id_); |
| 67 |
| 68 em::DeviceRegisterRequest* request = |
| 69 request_job_->GetRequest()->mutable_register_request(); |
| 70 SetRegistrationType(request); |
| 71 if (!machine_id_.empty()) |
| 72 request->set_machine_id(machine_id_); |
| 73 if (!machine_model_.empty()) |
| 74 request->set_machine_model(machine_model_); |
| 75 |
| 76 request_job_->Start(base::Bind(&CloudPolicyClient::OnRegisterCompleted, |
| 77 base::Unretained(this))); |
| 78 } |
| 79 |
| 80 void CloudPolicyClient::FetchPolicy() { |
| 81 CHECK(is_registered()); |
| 82 |
| 83 request_job_.reset( |
| 84 service_->CreateJob(DeviceManagementRequestJob::TYPE_POLICY_FETCH)); |
| 85 request_job_->SetDMToken(dm_token_); |
| 86 request_job_->SetClientID(client_id_); |
| 87 request_job_->SetUserAffiliation(user_affiliation_); |
| 88 |
| 89 em::DeviceManagementRequest* request = request_job_->GetRequest(); |
| 90 |
| 91 // Build policy fetch request. |
| 92 em::PolicyFetchRequest* policy_request = |
| 93 request->mutable_policy_request()->add_request(); |
| 94 policy_request->set_signature_type(em::PolicyFetchRequest::SHA1_RSA); |
| 95 SetPolicyType(policy_request); |
| 96 if (!last_policy_timestamp_.is_null()) { |
| 97 base::TimeDelta timestamp(last_policy_timestamp_ - base::Time::UnixEpoch()); |
| 98 policy_request->set_timestamp(timestamp.InMilliseconds()); |
| 99 } |
| 100 if (submit_machine_id_ && !machine_id_.empty()) |
| 101 policy_request->set_machine_id(machine_id_); |
| 102 if (public_key_version_valid_) |
| 103 policy_request->set_public_key_version(public_key_version_); |
| 104 |
| 105 // Add status data. |
| 106 if (status_provider_) { |
| 107 if (!status_provider_->GetDeviceStatus( |
| 108 request->mutable_device_status_report_request())) { |
| 109 request->clear_device_status_report_request(); |
| 110 } |
| 111 if (!status_provider_->GetSessionStatus( |
| 112 request->mutable_session_status_report_request())) { |
| 113 request->clear_session_status_report_request(); |
| 114 } |
| 115 } |
| 116 |
| 117 // Fire the job. |
| 118 request_job_->Start(base::Bind(&CloudPolicyClient::OnPolicyFetchCompleted, |
| 119 base::Unretained(this))); |
| 120 } |
| 121 |
| 122 void CloudPolicyClient::Unregister() { |
| 123 request_job_.reset( |
| 124 service_->CreateJob(DeviceManagementRequestJob::TYPE_UNREGISTRATION)); |
| 125 request_job_->SetDMToken(dm_token_); |
| 126 request_job_->SetClientID(client_id_); |
| 127 request_job_->GetRequest()->mutable_unregister_request(); |
| 128 request_job_->Start(base::Bind(&CloudPolicyClient::OnUnregisterCompleted, |
| 129 base::Unretained(this))); |
| 130 } |
| 131 |
| 132 void CloudPolicyClient::AddObserver(Observer* observer) { |
| 133 observers_.AddObserver(observer); |
| 134 } |
| 135 |
| 136 void CloudPolicyClient::RemoveObserver(Observer* observer) { |
| 137 observers_.RemoveObserver(observer); |
| 138 } |
| 139 |
| 140 void CloudPolicyClient::SetRegistrationType( |
| 141 em::DeviceRegisterRequest* request) const { |
| 142 switch (scope_) { |
| 143 case POLICY_SCOPE_USER: |
| 144 request->set_type(em::DeviceRegisterRequest::USER); |
| 145 return; |
| 146 case POLICY_SCOPE_MACHINE: |
| 147 request->set_type(em::DeviceRegisterRequest::DEVICE); |
| 148 return; |
| 149 } |
| 150 NOTREACHED() << "Invalid policy scope " << scope_; |
| 151 } |
| 152 |
| 153 void CloudPolicyClient::SetPolicyType(em::PolicyFetchRequest* request) const { |
| 154 switch (scope_) { |
| 155 case POLICY_SCOPE_USER: |
| 156 request->set_policy_type(dm_protocol::kChromeUserPolicyType); |
| 157 return; |
| 158 case POLICY_SCOPE_MACHINE: |
| 159 request->set_policy_type(dm_protocol::kChromeDevicePolicyType); |
| 160 return; |
| 161 } |
| 162 NOTREACHED() << "Invalid policy scope " << scope_; |
| 163 } |
| 164 |
| 165 void CloudPolicyClient::OnRegisterCompleted( |
| 166 DeviceManagementStatus status, |
| 167 const em::DeviceManagementResponse& response) { |
| 168 if (status == DM_STATUS_SUCCESS && |
| 169 (!response.has_register_response() || |
| 170 !response.register_response().has_device_management_token())) { |
| 171 LOG(WARNING) << "Empty registration response."; |
| 172 status = DM_STATUS_RESPONSE_DECODING_ERROR; |
| 173 } |
| 174 |
| 175 status_ = status; |
| 176 if (status == DM_STATUS_SUCCESS) { |
| 177 dm_token_ = response.register_response().device_management_token(); |
| 178 NotifyRegistrationStateChanged(); |
| 179 } else { |
| 180 NotifyClientError(); |
| 181 } |
| 182 } |
| 183 |
| 184 void CloudPolicyClient::OnPolicyFetchCompleted( |
| 185 DeviceManagementStatus status, |
| 186 const em::DeviceManagementResponse& response) { |
| 187 if (status == DM_STATUS_SUCCESS) { |
| 188 if (!response.has_policy_response() || |
| 189 response.policy_response().response_size() == 0) { |
| 190 LOG(WARNING) << "Empty policy response."; |
| 191 status = DM_STATUS_RESPONSE_DECODING_ERROR; |
| 192 } else if (response.policy_response().response_size() > 1) { |
| 193 LOG(WARNING) << "More than one response entries, ignoring all but first."; |
| 194 } |
| 195 } |
| 196 |
| 197 status_ = status; |
| 198 if (status == DM_STATUS_SUCCESS) { |
| 199 policy_.reset(new enterprise_management::PolicyFetchResponse( |
| 200 response.policy_response().response(0))); |
| 201 if (status_provider_) |
| 202 status_provider_->OnSubmittedSuccessfully(); |
| 203 NotifyPolicyFetched(); |
| 204 } else { |
| 205 NotifyClientError(); |
| 206 } |
| 207 } |
| 208 |
| 209 void CloudPolicyClient::OnUnregisterCompleted( |
| 210 DeviceManagementStatus status, |
| 211 const em::DeviceManagementResponse& response) { |
| 212 if (status == DM_STATUS_SUCCESS && !response.has_unregister_response()) { |
| 213 // Assume unregistration has succeeded either way. |
| 214 LOG(WARNING) << "Empty unregistration response."; |
| 215 } |
| 216 |
| 217 status_ = status; |
| 218 if (status == DM_STATUS_SUCCESS) { |
| 219 dm_token_.clear(); |
| 220 NotifyRegistrationStateChanged(); |
| 221 } else { |
| 222 NotifyClientError(); |
| 223 } |
| 224 } |
| 225 |
| 226 void CloudPolicyClient::NotifyPolicyFetched() { |
| 227 FOR_EACH_OBSERVER(Observer, observers_, OnPolicyFetched(this)); |
| 228 } |
| 229 |
| 230 void CloudPolicyClient::NotifyRegistrationStateChanged() { |
| 231 FOR_EACH_OBSERVER(Observer, observers_, OnRegistrationStateChanged(this)); |
| 232 } |
| 233 |
| 234 void CloudPolicyClient::NotifyClientError() { |
| 235 FOR_EACH_OBSERVER(Observer, observers_, OnClientError(this)); |
| 236 } |
| 237 |
| 238 } // namespace policy |
| OLD | NEW |