Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "chrome/browser/chromeos/policy/user_cloud_policy_store_chromeos.h" | 5 #include "chrome/browser/chromeos/policy/user_cloud_policy_store_chromeos.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/bind_helpers.h" | 8 #include "base/bind_helpers.h" |
| 9 #include "base/callback.h" | 9 #include "base/callback.h" |
| 10 #include "base/file_util.h" | 10 #include "base/file_util.h" |
| 11 #include "base/location.h" | 11 #include "base/location.h" |
| 12 #include "base/logging.h" | 12 #include "base/logging.h" |
| 13 #include "base/metrics/histogram.h" | 13 #include "base/metrics/histogram.h" |
| 14 #include "base/sequenced_task_runner.h" | 14 #include "base/sequenced_task_runner.h" |
| 15 #include "base/stl_util.h" | 15 #include "base/stl_util.h" |
| 16 #include "base/strings/stringprintf.h" | 16 #include "base/strings/stringprintf.h" |
| 17 #include "chrome/browser/chromeos/policy/user_policy_disk_cache.h" | 17 #include "chrome/browser/chromeos/policy/user_policy_disk_cache.h" |
| 18 #include "chrome/browser/chromeos/policy/user_policy_token_loader.h" | 18 #include "chrome/browser/chromeos/policy/user_policy_token_loader.h" |
| 19 #include "chromeos/dbus/cryptohome_client.h" | 19 #include "chromeos/dbus/cryptohome_client.h" |
| 20 #include "chromeos/dbus/session_manager_client.h" | 20 #include "chromeos/dbus/session_manager_client.h" |
| 21 #include "components/policy/core/common/cloud/cloud_policy_constants.h" | |
| 21 #include "google_apis/gaia/gaia_auth_util.h" | 22 #include "google_apis/gaia/gaia_auth_util.h" |
| 22 #include "policy/proto/cloud_policy.pb.h" | 23 #include "policy/proto/cloud_policy.pb.h" |
| 23 #include "policy/proto/device_management_local.pb.h" | 24 #include "policy/proto/device_management_local.pb.h" |
| 24 | 25 |
| 25 namespace em = enterprise_management; | 26 namespace em = enterprise_management; |
| 26 | 27 |
| 27 namespace policy { | 28 namespace policy { |
| 28 | 29 |
| 29 namespace { | 30 namespace { |
| 30 | 31 |
| (...skipping 217 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 248 policy_key_path_ = user_policy_key_dir_.Append( | 249 policy_key_path_ = user_policy_key_dir_.Append( |
| 249 base::StringPrintf(kPolicyKeyFile, sanitized_username.c_str())); | 250 base::StringPrintf(kPolicyKeyFile, sanitized_username.c_str())); |
| 250 LoadPolicyKey(policy_key_path_, &policy_key_); | 251 LoadPolicyKey(policy_key_path_, &policy_key_); |
| 251 policy_key_loaded_ = true; | 252 policy_key_loaded_ = true; |
| 252 | 253 |
| 253 scoped_ptr<UserCloudPolicyValidator> validator = | 254 scoped_ptr<UserCloudPolicyValidator> validator = |
| 254 CreateValidator(policy.Pass(), | 255 CreateValidator(policy.Pass(), |
| 255 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); | 256 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); |
| 256 validator->ValidateUsername(username_); | 257 validator->ValidateUsername(username_); |
| 257 const bool allow_rotation = false; | 258 const bool allow_rotation = false; |
| 258 validator->ValidateSignature(policy_key_, allow_rotation); | 259 validator->ValidateSignature( |
| 260 policy_key_, | |
| 261 GetPolicyVerificationKey(), | |
| 262 std::string(), // No signature verification needed. | |
| 263 allow_rotation); | |
| 259 validator->RunValidation(); | 264 validator->RunValidation(); |
| 260 OnRetrievedPolicyValidated(validator.get()); | 265 OnRetrievedPolicyValidated(validator.get()); |
| 261 } | 266 } |
| 262 | 267 |
| 263 void UserCloudPolicyStoreChromeOS::ValidatePolicyForStore( | 268 void UserCloudPolicyStoreChromeOS::ValidatePolicyForStore( |
| 264 scoped_ptr<em::PolicyFetchResponse> policy) { | 269 scoped_ptr<em::PolicyFetchResponse> policy) { |
| 265 // Create and configure a validator. | 270 // Create and configure a validator. |
| 266 scoped_ptr<UserCloudPolicyValidator> validator = | 271 scoped_ptr<UserCloudPolicyValidator> validator = |
| 267 CreateValidator(policy.Pass(), | 272 CreateValidator(policy.Pass(), |
| 268 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); | 273 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); |
| 269 validator->ValidateUsername(username_); | 274 validator->ValidateUsername(username_); |
| 270 if (policy_key_.empty()) { | 275 if (policy_key_.empty()) { |
| 271 validator->ValidateInitialKey(); | 276 validator->ValidateInitialKey(GetPolicyVerificationKey()); |
| 272 } else { | 277 } else { |
| 273 const bool allow_rotation = true; | 278 const bool allow_rotation = true; |
| 274 validator->ValidateSignature(policy_key_, allow_rotation); | 279 validator->ValidateSignature(policy_key_, |
| 280 GetPolicyVerificationKey(), | |
| 281 std::string(), | |
| 282 allow_rotation); | |
| 275 } | 283 } |
| 276 | 284 |
| 277 // Start validation. The Validator will delete itself once validation is | 285 // Start validation. The Validator will delete itself once validation is |
| 278 // complete. | 286 // complete. |
| 279 validator.release()->StartValidation( | 287 validator.release()->StartValidation( |
| 280 base::Bind(&UserCloudPolicyStoreChromeOS::OnPolicyToStoreValidated, | 288 base::Bind(&UserCloudPolicyStoreChromeOS::OnPolicyToStoreValidated, |
| 281 weak_factory_.GetWeakPtr())); | 289 weak_factory_.GetWeakPtr())); |
| 282 } | 290 } |
| 283 | 291 |
| 284 void UserCloudPolicyStoreChromeOS::OnPolicyToStoreValidated( | 292 void UserCloudPolicyStoreChromeOS::OnPolicyToStoreValidated( |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 360 } | 368 } |
| 361 | 369 |
| 362 void UserCloudPolicyStoreChromeOS::ValidateRetrievedPolicy( | 370 void UserCloudPolicyStoreChromeOS::ValidateRetrievedPolicy( |
| 363 scoped_ptr<em::PolicyFetchResponse> policy) { | 371 scoped_ptr<em::PolicyFetchResponse> policy) { |
| 364 // Create and configure a validator for the loaded policy. | 372 // Create and configure a validator for the loaded policy. |
| 365 scoped_ptr<UserCloudPolicyValidator> validator = | 373 scoped_ptr<UserCloudPolicyValidator> validator = |
| 366 CreateValidator(policy.Pass(), | 374 CreateValidator(policy.Pass(), |
| 367 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); | 375 CloudPolicyValidatorBase::TIMESTAMP_REQUIRED); |
| 368 validator->ValidateUsername(username_); | 376 validator->ValidateUsername(username_); |
| 369 const bool allow_rotation = false; | 377 const bool allow_rotation = false; |
| 370 validator->ValidateSignature(policy_key_, allow_rotation); | 378 validator->ValidateSignature(policy_key_, |
| 379 GetPolicyVerificationKey(), | |
| 380 std::string(), | |
| 381 allow_rotation); | |
| 371 // Start validation. The Validator will delete itself once validation is | 382 // Start validation. The Validator will delete itself once validation is |
| 372 // complete. | 383 // complete. |
| 373 validator.release()->StartValidation( | 384 validator.release()->StartValidation( |
| 374 base::Bind(&UserCloudPolicyStoreChromeOS::OnRetrievedPolicyValidated, | 385 base::Bind(&UserCloudPolicyStoreChromeOS::OnRetrievedPolicyValidated, |
| 375 weak_factory_.GetWeakPtr())); | 386 weak_factory_.GetWeakPtr())); |
| 376 } | 387 } |
| 377 | 388 |
| 378 void UserCloudPolicyStoreChromeOS::OnRetrievedPolicyValidated( | 389 void UserCloudPolicyStoreChromeOS::OnRetrievedPolicyValidated( |
| 379 UserCloudPolicyValidator* validator) { | 390 UserCloudPolicyValidator* validator) { |
| 380 validation_status_ = validator->status(); | 391 validation_status_ = validator->status(); |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 468 | 479 |
| 469 // static | 480 // static |
| 470 void UserCloudPolicyStoreChromeOS::RemoveLegacyCacheDir( | 481 void UserCloudPolicyStoreChromeOS::RemoveLegacyCacheDir( |
| 471 const base::FilePath& dir) { | 482 const base::FilePath& dir) { |
| 472 if (base::PathExists(dir) && !base::DeleteFile(dir, true)) | 483 if (base::PathExists(dir) && !base::DeleteFile(dir, true)) |
| 473 LOG(ERROR) << "Failed to remove cache dir " << dir.value(); | 484 LOG(ERROR) << "Failed to remove cache dir " << dir.value(); |
| 474 } | 485 } |
| 475 | 486 |
| 476 void UserCloudPolicyStoreChromeOS::ReloadPolicyKey( | 487 void UserCloudPolicyStoreChromeOS::ReloadPolicyKey( |
| 477 const base::Closure& callback) { | 488 const base::Closure& callback) { |
| 478 std::vector<uint8>* key = new std::vector<uint8>(); | 489 std::string* key = new std::string(); |
| 479 background_task_runner()->PostTaskAndReply( | 490 background_task_runner()->PostTaskAndReply( |
| 480 FROM_HERE, | 491 FROM_HERE, |
| 481 base::Bind(&UserCloudPolicyStoreChromeOS::LoadPolicyKey, | 492 base::Bind(&UserCloudPolicyStoreChromeOS::LoadPolicyKey, |
| 482 policy_key_path_, | 493 policy_key_path_, |
| 483 key), | 494 key), |
| 484 base::Bind(&UserCloudPolicyStoreChromeOS::OnPolicyKeyReloaded, | 495 base::Bind(&UserCloudPolicyStoreChromeOS::OnPolicyKeyReloaded, |
| 485 weak_factory_.GetWeakPtr(), | 496 weak_factory_.GetWeakPtr(), |
| 486 base::Owned(key), | 497 base::Owned(key), |
| 487 callback)); | 498 callback)); |
| 488 } | 499 } |
| 489 | 500 |
| 490 // static | 501 // static |
| 491 void UserCloudPolicyStoreChromeOS::LoadPolicyKey(const base::FilePath& path, | 502 void UserCloudPolicyStoreChromeOS::LoadPolicyKey(const base::FilePath& path, |
| 492 std::vector<uint8>* key) { | 503 std::string* key) { |
| 493 if (!base::PathExists(path)) { | 504 if (!base::PathExists(path)) { |
| 494 // There is no policy key the first time that a user fetches policy. If | 505 // There is no policy key the first time that a user fetches policy. If |
| 495 // |path| does not exist then that is the most likely scenario, so there's | 506 // |path| does not exist then that is the most likely scenario, so there's |
| 496 // no need to sample a failure. | 507 // no need to sample a failure. |
| 497 VLOG(1) << "No key at " << path.value(); | 508 VLOG(1) << "No key at " << path.value(); |
| 498 return; | 509 return; |
| 499 } | 510 } |
| 500 | 511 |
| 501 int64 size; | 512 int64 size; |
| 502 if (!base::GetFileSize(path, &size)) { | 513 if (!base::GetFileSize(path, &size)) { |
| 503 LOG(ERROR) << "Could not get size of " << path.value(); | 514 LOG(ERROR) << "Could not get size of " << path.value(); |
| 504 } else if (size == 0 || size > kKeySizeLimit) { | 515 } else if (size == 0 || size > kKeySizeLimit) { |
| 505 LOG(ERROR) << "Key at " << path.value() << " has bad size " << size; | 516 LOG(ERROR) << "Key at " << path.value() << " has bad size " << size; |
| 506 } else { | 517 } else { |
| 507 key->resize(size); | 518 if (!base::ReadFileToString(path, key) || |
|
Mattias Nissler (ping if slow)
2014/01/27 13:52:13
nit: I'd prefer ReadFile over ReadFileToString sin
Andrew T Wilson (Slow)
2014/01/30 17:10:31
Done.
| |
| 508 int read_size = base::ReadFile( | 519 key->size() != static_cast<uint64>(size)) { |
| 509 path, reinterpret_cast<char*>(vector_as_array(key)), size); | |
| 510 if (read_size != size) { | |
| 511 LOG(ERROR) << "Failed to read key at " << path.value(); | 520 LOG(ERROR) << "Failed to read key at " << path.value(); |
| 512 key->clear(); | 521 key->clear(); |
| 513 } | 522 } |
| 514 } | 523 } |
| 515 | 524 |
| 516 if (key->empty()) | 525 if (key->empty()) |
| 517 SampleValidationFailure(VALIDATION_FAILURE_LOAD_KEY); | 526 SampleValidationFailure(VALIDATION_FAILURE_LOAD_KEY); |
| 518 } | 527 } |
| 519 | 528 |
| 520 void UserCloudPolicyStoreChromeOS::OnPolicyKeyReloaded( | 529 void UserCloudPolicyStoreChromeOS::OnPolicyKeyReloaded( |
| 521 std::vector<uint8>* key, | 530 std::string* key, |
| 522 const base::Closure& callback) { | 531 const base::Closure& callback) { |
| 523 policy_key_.swap(*key); | 532 policy_key_ = *key; |
| 524 policy_key_loaded_ = true; | 533 policy_key_loaded_ = true; |
| 525 callback.Run(); | 534 callback.Run(); |
| 526 } | 535 } |
| 527 | 536 |
| 528 void UserCloudPolicyStoreChromeOS::EnsurePolicyKeyLoaded( | 537 void UserCloudPolicyStoreChromeOS::EnsurePolicyKeyLoaded( |
| 529 const base::Closure& callback) { | 538 const base::Closure& callback) { |
| 530 if (policy_key_loaded_) { | 539 if (policy_key_loaded_) { |
| 531 callback.Run(); | 540 callback.Run(); |
| 532 } else { | 541 } else { |
| 533 // Get the hashed username that's part of the key's path, to determine | 542 // Get the hashed username that's part of the key's path, to determine |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 548 !sanitized_username.empty()) { | 557 !sanitized_username.empty()) { |
| 549 policy_key_path_ = user_policy_key_dir_.Append( | 558 policy_key_path_ = user_policy_key_dir_.Append( |
| 550 base::StringPrintf(kPolicyKeyFile, sanitized_username.c_str())); | 559 base::StringPrintf(kPolicyKeyFile, sanitized_username.c_str())); |
| 551 } else { | 560 } else { |
| 552 SampleValidationFailure(VALIDATION_FAILURE_DBUS); | 561 SampleValidationFailure(VALIDATION_FAILURE_DBUS); |
| 553 } | 562 } |
| 554 ReloadPolicyKey(callback); | 563 ReloadPolicyKey(callback); |
| 555 } | 564 } |
| 556 | 565 |
| 557 } // namespace policy | 566 } // namespace policy |
| OLD | NEW |