Componentize HistoryURLProvider/ScoredHistoryMatch.
[chromium-blink-merge.git] / chrome / browser / signin / easy_unlock_auth_attempt.cc
blob5560754a974d7de04eb39e040fec1a8452dc99e2
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.
5 #include "chrome/browser/signin/easy_unlock_auth_attempt.h"
7 #include "base/bind.h"
8 #include "base/logging.h"
9 #include "chrome/browser/signin/easy_unlock_app_manager.h"
10 #include "chrome/browser/signin/proximity_auth_facade.h"
11 #include "components/proximity_auth/screenlock_bridge.h"
12 #include "crypto/encryptor.h"
13 #include "crypto/symmetric_key.h"
15 #if defined(OS_CHROMEOS)
16 #include "chrome/browser/chromeos/login/easy_unlock/easy_unlock_key_manager.h"
17 #endif
19 namespace {
21 // Decrypts the secret that should be used to login from |wrapped_secret| using
22 // raw AES key |raw_key|.
23 // In a case of error, an empty string is returned.
24 std::string UnwrapSecret(const std::string& wrapped_secret,
25 const std::string& raw_key) {
26 if (raw_key.empty())
27 return std::string();
29 // Import the key structure.
30 scoped_ptr<crypto::SymmetricKey> key(
31 crypto::SymmetricKey::Import(crypto::SymmetricKey::AES, raw_key));
33 if (!key)
34 return std::string();
36 std::string iv(raw_key.size(), ' ');
37 crypto::Encryptor encryptor;
38 if (!encryptor.Init(key.get(), crypto::Encryptor::CBC, iv))
39 return std::string();
41 std::string secret;
42 if (!encryptor.Decrypt(wrapped_secret, &secret))
43 return std::string();
45 return secret;
48 void DefaultAuthAttemptFinalizedHandler(
49 EasyUnlockAuthAttempt::Type auth_attempt_type,
50 bool success,
51 const std::string& user_id,
52 const std::string& key_secret,
53 const std::string& key_label) {
54 if (!GetScreenlockBridgeInstance()->IsLocked())
55 return;
57 switch (auth_attempt_type) {
58 case EasyUnlockAuthAttempt::TYPE_UNLOCK:
59 if (success) {
60 GetScreenlockBridgeInstance()->lock_handler()->Unlock(user_id);
61 } else {
62 GetScreenlockBridgeInstance()->lock_handler()->EnableInput();
64 return;
65 case EasyUnlockAuthAttempt::TYPE_SIGNIN:
66 if (success) {
67 GetScreenlockBridgeInstance()->lock_handler()->AttemptEasySignin(
68 user_id, key_secret, key_label);
69 } else {
70 // Attempting signin with an empty secret is equivalent to canceling the
71 // attempt.
72 GetScreenlockBridgeInstance()->lock_handler()->AttemptEasySignin(
73 user_id, std::string(), std::string());
75 return;
79 } // namespace
81 EasyUnlockAuthAttempt::EasyUnlockAuthAttempt(
82 EasyUnlockAppManager* app_manager,
83 const std::string& user_id,
84 Type type,
85 const FinalizedCallback& finalized_callback)
86 : app_manager_(app_manager),
87 state_(STATE_IDLE),
88 user_id_(user_id),
89 type_(type),
90 finalized_callback_(finalized_callback) {
91 if (finalized_callback_.is_null())
92 finalized_callback_ = base::Bind(&DefaultAuthAttemptFinalizedHandler);
95 EasyUnlockAuthAttempt::~EasyUnlockAuthAttempt() {
96 if (state_ == STATE_RUNNING)
97 Cancel(user_id_);
100 bool EasyUnlockAuthAttempt::Start() {
101 DCHECK_EQ(STATE_IDLE, state_);
103 if (!GetScreenlockBridgeInstance()->IsLocked())
104 return false;
106 proximity_auth::ScreenlockBridge::LockHandler::AuthType auth_type =
107 GetScreenlockBridgeInstance()->lock_handler()->GetAuthType(user_id_);
109 if (auth_type != proximity_auth::ScreenlockBridge::LockHandler::USER_CLICK) {
110 Cancel(user_id_);
111 return false;
114 state_ = STATE_RUNNING;
116 if (!app_manager_->SendAuthAttemptEvent()) {
117 Cancel(user_id_);
118 return false;
121 return true;
124 void EasyUnlockAuthAttempt::FinalizeUnlock(const std::string& user_id,
125 bool success) {
126 if (state_ != STATE_RUNNING || user_id != user_id_)
127 return;
129 if (!GetScreenlockBridgeInstance()->IsLocked())
130 return;
132 if (type_ != TYPE_UNLOCK) {
133 Cancel(user_id_);
134 return;
137 finalized_callback_.Run(type_, success, user_id, std::string(),
138 std::string());
139 state_ = STATE_DONE;
142 void EasyUnlockAuthAttempt::FinalizeSignin(const std::string& user_id,
143 const std::string& wrapped_secret,
144 const std::string& raw_session_key) {
145 if (state_ != STATE_RUNNING || user_id != user_id_)
146 return;
148 if (!GetScreenlockBridgeInstance()->IsLocked())
149 return;
151 if (type_ != TYPE_SIGNIN) {
152 Cancel(user_id_);
153 return;
156 if (wrapped_secret.empty()) {
157 Cancel(user_id_);
158 return;
161 std::string unwrapped_secret = UnwrapSecret(wrapped_secret, raw_session_key);
163 std::string key_label;
164 #if defined(OS_CHROMEOS)
165 key_label = chromeos::EasyUnlockKeyManager::GetKeyLabel(0u);
166 #endif // defined(OS_CHROMEOS)
168 const bool kSuccess = true;
169 finalized_callback_.Run(type_, kSuccess, user_id, unwrapped_secret,
170 key_label);
171 state_ = STATE_DONE;
174 void EasyUnlockAuthAttempt::Cancel(const std::string& user_id) {
175 state_ = STATE_DONE;
177 const bool kFailure = false;
178 finalized_callback_.Run(type_, kFailure, user_id, std::string(),
179 std::string());