Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(141)

Side by Side Diff: chrome/browser/chromeos/login/parallel_authenticator.cc

Issue 9466005: Make sure the device recovers from policy loss in the consumer case. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: Created 8 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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/login/parallel_authenticator.h" 5 #include "chrome/browser/chromeos/login/parallel_authenticator.h"
6 6
7 #include <string> 7 #include <string>
8 #include <vector> 8 #include <vector>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
11 #include "base/command_line.h" 11 #include "base/command_line.h"
12 #include "base/file_path.h" 12 #include "base/file_path.h"
13 #include "base/file_util.h" 13 #include "base/file_util.h"
14 #include "base/logging.h" 14 #include "base/logging.h"
15 #include "base/path_service.h" 15 #include "base/path_service.h"
16 #include "base/string_util.h" 16 #include "base/string_util.h"
17 #include "base/synchronization/lock.h" 17 #include "base/synchronization/lock.h"
18 #include "chrome/browser/chromeos/cros/cert_library.h" 18 #include "chrome/browser/chromeos/cros/cert_library.h"
19 #include "chrome/browser/chromeos/cros/cryptohome_library.h" 19 #include "chrome/browser/chromeos/cros/cryptohome_library.h"
20 #include "chrome/browser/chromeos/cros_settings.h"
20 #include "chrome/browser/chromeos/login/auth_response_handler.h" 21 #include "chrome/browser/chromeos/login/auth_response_handler.h"
21 #include "chrome/browser/chromeos/login/authentication_notification_details.h" 22 #include "chrome/browser/chromeos/login/authentication_notification_details.h"
22 #include "chrome/browser/chromeos/login/login_status_consumer.h" 23 #include "chrome/browser/chromeos/login/login_status_consumer.h"
23 #include "chrome/browser/chromeos/login/ownership_service.h" 24 #include "chrome/browser/chromeos/login/ownership_service.h"
24 #include "chrome/browser/chromeos/login/user_manager.h" 25 #include "chrome/browser/chromeos/login/user_manager.h"
25 #include "chrome/browser/profiles/profile.h" 26 #include "chrome/browser/profiles/profile.h"
26 #include "chrome/browser/profiles/profile_manager.h" 27 #include "chrome/browser/profiles/profile_manager.h"
27 #include "chrome/common/chrome_notification_types.h" 28 #include "chrome/common/chrome_notification_types.h"
28 #include "chrome/common/chrome_paths.h" 29 #include "chrome/common/chrome_paths.h"
29 #include "chrome/common/chrome_switches.h" 30 #include "chrome/common/chrome_switches.h"
(...skipping 16 matching lines...) Expand all
46 using file_util::ReadFileToString; 47 using file_util::ReadFileToString;
47 48
48 namespace chromeos { 49 namespace chromeos {
49 50
50 // static 51 // static
51 const int ParallelAuthenticator::kClientLoginTimeoutMs = 10000; 52 const int ParallelAuthenticator::kClientLoginTimeoutMs = 10000;
52 53
53 ParallelAuthenticator::ParallelAuthenticator(LoginStatusConsumer* consumer) 54 ParallelAuthenticator::ParallelAuthenticator(LoginStatusConsumer* consumer)
54 : Authenticator(consumer), 55 : Authenticator(consumer),
55 already_reported_success_(false), 56 already_reported_success_(false),
57 owner_is_verified_(false),
58 user_can_login_(false),
56 using_oauth_( 59 using_oauth_(
57 CommandLine::ForCurrentProcess()->HasSwitch( 60 CommandLine::ForCurrentProcess()->HasSwitch(
58 switches::kWebUILogin) && 61 switches::kWebUILogin) &&
59 !CommandLine::ForCurrentProcess()->HasSwitch( 62 !CommandLine::ForCurrentProcess()->HasSwitch(
60 switches::kSkipOAuthLogin)) { 63 switches::kSkipOAuthLogin)) {
61 // If not already owned, this is a no-op. If it is, this loads the owner's 64 // If not already owned, this is a no-op. If it is, this loads the owner's
62 // public key off of disk. 65 // public key off of disk.
63 OwnershipService::GetSharedInstance()->StartLoadOwnerKeyAttempt(); 66 OwnershipService::GetSharedInstance()->StartLoadOwnerKeyAttempt();
64 } 67 }
65 68
66 ParallelAuthenticator::~ParallelAuthenticator() {} 69 ParallelAuthenticator::~ParallelAuthenticator() {}
67 70
68 void ParallelAuthenticator::AuthenticateToLogin( 71 void ParallelAuthenticator::AuthenticateToLogin(
69 Profile* profile, 72 Profile* profile,
70 const std::string& username, 73 const std::string& username,
71 const std::string& password, 74 const std::string& password,
72 const std::string& login_token, 75 const std::string& login_token,
73 const std::string& login_captcha) { 76 const std::string& login_captcha) {
74 std::string canonicalized = Authenticator::Canonicalize(username); 77 std::string canonicalized = Authenticator::Canonicalize(username);
75 authentication_profile_ = profile; 78 authentication_profile_ = profile;
76 current_state_.reset( 79 current_state_.reset(
77 new AuthAttemptState( 80 new AuthAttemptState(
78 canonicalized, 81 canonicalized,
79 password, 82 password,
80 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password), 83 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password),
81 login_token, 84 login_token,
82 login_captcha, 85 login_captcha,
83 !UserManager::Get()->IsKnownUser(canonicalized))); 86 !UserManager::Get()->IsKnownUser(canonicalized)));
87 {
88 LOG(ERROR) << "@@@ Resetting for " << username;
89 // Reset the verified flag.
90 base::AutoLock for_this_block(owner_verified_lock_);
91 owner_is_verified_ = false;
92 }
84 mounter_ = CryptohomeOp::CreateMountAttempt(current_state_.get(), 93 mounter_ = CryptohomeOp::CreateMountAttempt(current_state_.get(),
85 this, 94 this,
86 false /* don't create */); 95 false /* don't create */);
87 // Sadly, this MUST be on the UI thread due to sending DBus traffic :-/ 96 // Sadly, this MUST be on the UI thread due to sending DBus traffic :-/
88 BrowserThread::PostTask( 97 BrowserThread::PostTask(
89 BrowserThread::UI, FROM_HERE, 98 BrowserThread::UI, FROM_HERE,
90
91 base::Bind(&CryptohomeOp::Initiate, mounter_.get())); 99 base::Bind(&CryptohomeOp::Initiate, mounter_.get()));
92 // ClientLogin authentication check should happen immediately here. 100 // ClientLogin authentication check should happen immediately here.
93 // We should not try OAuthLogin check until the profile loads. 101 // We should not try OAuthLogin check until the profile loads.
94 if (!using_oauth_) { 102 if (!using_oauth_) {
95 // Initiate ClientLogin-based post authentication. 103 // Initiate ClientLogin-based post authentication.
96 current_online_ = new OnlineAttempt(using_oauth_, 104 current_online_ = new OnlineAttempt(using_oauth_,
97 current_state_.get(), 105 current_state_.get(),
98 this); 106 this);
99 current_online_->Initiate(profile); 107 current_online_->Initiate(profile);
100 } 108 }
101 } 109 }
102 110
103 void ParallelAuthenticator::CompleteLogin(Profile* profile, 111 void ParallelAuthenticator::CompleteLogin(Profile* profile,
104 const std::string& username, 112 const std::string& username,
105 const std::string& password) { 113 const std::string& password) {
106 std::string canonicalized = Authenticator::Canonicalize(username); 114 std::string canonicalized = Authenticator::Canonicalize(username);
107 authentication_profile_ = profile; 115 authentication_profile_ = profile;
108 current_state_.reset( 116 current_state_.reset(
109 new AuthAttemptState( 117 new AuthAttemptState(
110 canonicalized, 118 canonicalized,
111 password, 119 password,
112 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password), 120 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password),
113 !UserManager::Get()->IsKnownUser(canonicalized))); 121 !UserManager::Get()->IsKnownUser(canonicalized)));
122 {
123 LOG(ERROR) << "@@@ Resetting for " << username;
124 // Reset the verified flag.
125 base::AutoLock for_this_block(owner_verified_lock_);
126 owner_is_verified_ = false;
127 }
114 mounter_ = CryptohomeOp::CreateMountAttempt(current_state_.get(), 128 mounter_ = CryptohomeOp::CreateMountAttempt(current_state_.get(),
115 this, 129 this,
116 false /* don't create */); 130 false /* don't create */);
117 // Sadly, this MUST be on the UI thread due to sending DBus traffic :-/ 131 // Sadly, this MUST be on the UI thread due to sending DBus traffic :-/
118 BrowserThread::PostTask( 132 BrowserThread::PostTask(
119 BrowserThread::UI, FROM_HERE, 133 BrowserThread::UI, FROM_HERE,
120 base::Bind(&CryptohomeOp::Initiate, mounter_.get())); 134 base::Bind(&CryptohomeOp::Initiate, mounter_.get()));
121 135
122 if (!using_oauth_) { 136 if (!using_oauth_) {
123 // Test automation needs to disable oauth, but that leads to other 137 // Test automation needs to disable oauth, but that leads to other
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
246 } 260 }
247 261
248 void ParallelAuthenticator::ResyncRecoverHelper(CryptohomeOp* to_initiate) { 262 void ParallelAuthenticator::ResyncRecoverHelper(CryptohomeOp* to_initiate) {
249 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 263 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
250 current_state_->ResetCryptohomeStatus(); 264 current_state_->ResetCryptohomeStatus();
251 BrowserThread::PostTask( 265 BrowserThread::PostTask(
252 BrowserThread::UI, FROM_HERE, 266 BrowserThread::UI, FROM_HERE,
253 base::Bind(&CryptohomeOp::Initiate, to_initiate)); 267 base::Bind(&CryptohomeOp::Initiate, to_initiate));
254 } 268 }
255 269
270 void ParallelAuthenticator::VerifyOwnerOnUIThread() {
271 // Check if policy data is fine and continue in safe mode if needed.
272 bool is_safe_mode = false;
273 CrosSettings::Get()->GetBoolean(kPolicyMissingMitigationMode, &is_safe_mode);
274 if (!is_safe_mode) {
275 base::AutoLock for_this_block(owner_verified_lock_);
276 // Now we can continue reading the private key.
277 user_can_login_ = true;
278 owner_is_verified_ = true;
279 BrowserThread::PostTask(
280 BrowserThread::IO, FROM_HERE,
281 base::Bind(&ParallelAuthenticator::Resolve, this));
282 return;
283 }
284 // First we have to make sure the current user's cert store is available.
285 UserManager::Get()->LoadKeyStore();
286 // Now we can continue reading the private key.
287 BrowserThread::PostTask(
288 BrowserThread::FILE, FROM_HERE,
289 base::Bind(&ParallelAuthenticator::FinishVerifyOwnerOnFileThread, this));
290 }
291
292 void ParallelAuthenticator::FinishVerifyOwnerOnFileThread() {
293 base::AutoLock for_this_block(owner_verified_lock_);
294 // Now we can continue reading the private key.
295 user_can_login_ =
296 OwnershipService::GetSharedInstance()->CurrentUserIsOwner();
297 owner_is_verified_ = true;
298 BrowserThread::PostTask(
299 BrowserThread::IO, FROM_HERE,
300 base::Bind(&ParallelAuthenticator::Resolve, this));
301 LOG(ERROR) << "@@@ Check finished: " << user_can_login_;
302 }
303
256 void ParallelAuthenticator::RetryAuth(Profile* profile, 304 void ParallelAuthenticator::RetryAuth(Profile* profile,
257 const std::string& username, 305 const std::string& username,
258 const std::string& password, 306 const std::string& password,
259 const std::string& login_token, 307 const std::string& login_token,
260 const std::string& login_captcha) { 308 const std::string& login_captcha) {
261 reauth_state_.reset( 309 reauth_state_.reset(
262 new AuthAttemptState( 310 new AuthAttemptState(
263 Authenticator::Canonicalize(username), 311 Authenticator::Canonicalize(username),
264 password, 312 password,
265 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password), 313 CrosLibrary::Get()->GetCryptohomeLibrary()->HashPassword(password),
(...skipping 144 matching lines...) Expand 10 before | Expand all | Expand 10 after
410 break; 458 break;
411 case LOGIN_FAILED: 459 case LOGIN_FAILED:
412 current_state_->ResetCryptohomeStatus(); 460 current_state_->ResetCryptohomeStatus();
413 BrowserThread::PostTask(BrowserThread::UI, 461 BrowserThread::PostTask(BrowserThread::UI,
414 FROM_HERE, 462 FROM_HERE,
415 base::Bind( 463 base::Bind(
416 &ParallelAuthenticator::OnLoginFailure, 464 &ParallelAuthenticator::OnLoginFailure,
417 this, 465 this,
418 current_state_->online_outcome())); 466 current_state_->online_outcome()));
419 break; 467 break;
468 case OWNER_REQUIRED:
469 current_state_->ResetCryptohomeStatus();
Chris Masone 2012/02/24 18:49:45 Hm. This doesn't actually unmount the user's cryp
pastarmovj 2012/03/13 15:21:55 Done.
470 BrowserThread::PostTask(BrowserThread::UI,
471 FROM_HERE,
472 base::Bind(
473 &ParallelAuthenticator::OnLoginFailure,
474 this,
475 LoginFailure(LoginFailure::OWNER_REQUIRED)));
476 break;
420 default: 477 default:
421 NOTREACHED(); 478 NOTREACHED();
422 break; 479 break;
423 } 480 }
424 } 481 }
425 482
426 ParallelAuthenticator::AuthState ParallelAuthenticator::ResolveState() { 483 ParallelAuthenticator::AuthState ParallelAuthenticator::ResolveState() {
427 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 484 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
428 // If we haven't mounted the user's home dir yet, we can't be done. 485 // If we haven't mounted the user's home dir yet, we can't be done.
429 // We never get past here if a cryptohome op is still pending. 486 // We never get past here if a cryptohome op is still pending.
(...skipping 95 matching lines...) Expand 10 before | Expand all | Expand 10 after
525 ParallelAuthenticator::ResolveCryptohomeSuccessState() { 582 ParallelAuthenticator::ResolveCryptohomeSuccessState() {
526 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 583 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO));
527 if (data_remover_.get()) 584 if (data_remover_.get())
528 return CREATE_NEW; 585 return CREATE_NEW;
529 if (guest_mounter_.get()) 586 if (guest_mounter_.get())
530 return GUEST_LOGIN; 587 return GUEST_LOGIN;
531 if (key_migrator_.get()) 588 if (key_migrator_.get())
532 return RECOVER_MOUNT; 589 return RECOVER_MOUNT;
533 if (key_checker_.get()) 590 if (key_checker_.get())
534 return UNLOCK; 591 return UNLOCK;
535 return OFFLINE_LOGIN; 592
593 base::AutoLock for_this_block(owner_verified_lock_);
594 LOG(ERROR) << "@@@ cryptohome state " << owner_is_verified_;
595 if (!owner_is_verified_) {
596 BrowserThread::PostTask(
597 BrowserThread::UI, FROM_HERE,
598 base::Bind(&ParallelAuthenticator::VerifyOwnerOnUIThread, this));
599 return CONTINUE;
600 }
601 return user_can_login_ ? OFFLINE_LOGIN : OWNER_REQUIRED;
536 } 602 }
537 603
538 namespace { 604 namespace {
539 bool WasConnectionIssue(const LoginFailure& online_outcome) { 605 bool WasConnectionIssue(const LoginFailure& online_outcome) {
540 return ((online_outcome.reason() == LoginFailure::LOGIN_TIMED_OUT) || 606 return ((online_outcome.reason() == LoginFailure::LOGIN_TIMED_OUT) ||
541 (online_outcome.error().state() == 607 (online_outcome.error().state() ==
542 GoogleServiceAuthError::CONNECTION_FAILED) || 608 GoogleServiceAuthError::CONNECTION_FAILED) ||
543 (online_outcome.error().state() == 609 (online_outcome.error().state() ==
544 GoogleServiceAuthError::REQUEST_CANCELED)); 610 GoogleServiceAuthError::REQUEST_CANCELED));
545 } 611 }
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
582 } 648 }
583 649
584 void ParallelAuthenticator::ResolveLoginCompletionStatus() { 650 void ParallelAuthenticator::ResolveLoginCompletionStatus() {
585 // Shortcut online state resolution process. 651 // Shortcut online state resolution process.
586 current_state_->RecordOnlineLoginStatus(GaiaAuthConsumer::ClientLoginResult(), 652 current_state_->RecordOnlineLoginStatus(GaiaAuthConsumer::ClientLoginResult(),
587 LoginFailure::None()); 653 LoginFailure::None());
588 Resolve(); 654 Resolve();
589 } 655 }
590 656
591 } // namespace chromeos 657 } // namespace chromeos
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698