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

Side by Side Diff: chrome/browser/ui/crypto_module_password_dialog_nss.cc

Issue 6580058: NSS: Unlock crypto devices when populating cert manager. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: review changes Created 9 years, 9 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) 2011 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 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/ui/crypto_module_password_dialog.h" 5 #include "chrome/browser/ui/crypto_module_password_dialog.h"
6 6
7 #include <pk11pub.h> 7 #include <pk11pub.h>
8 8
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "content/browser/browser_thread.h" 10 #include "content/browser/browser_thread.h"
11 #include "net/base/crypto_module.h" 11 #include "net/base/crypto_module.h"
12 #include "net/base/x509_certificate.h" 12 #include "net/base/x509_certificate.h"
13 13
14 namespace { 14 namespace {
15 15
16 bool ShouldShowDialog(const net::CryptoModule* module) {
17 // The wincx arg is unused since we don't call PK11_SetIsLoggedInFunc.
18 return (PK11_NeedLogin(module->os_module_handle()) &&
19 !PK11_IsLoggedIn(module->os_module_handle(), NULL /* wincx */));
20 }
21
16 // Basically an asynchronous implementation of NSS's PK11_DoPassword. 22 // Basically an asynchronous implementation of NSS's PK11_DoPassword.
17 // Note: This currently handles only the simple case. See the TODOs in 23 // Note: This currently handles only the simple case. See the TODOs in
18 // GotPassword for what is yet unimplemented. 24 // GotPassword for what is yet unimplemented.
19 class SlotUnlocker { 25 class SlotUnlocker {
20 public: 26 public:
21 SlotUnlocker(net::CryptoModule* module, 27 SlotUnlocker(const net::CryptoModuleList& modules,
22 browser::CryptoModulePasswordReason reason, 28 browser::CryptoModulePasswordReason reason,
23 const std::string& host, 29 const std::string& host,
24 Callback0::Type* callback); 30 Callback0::Type* callback);
25 31
26 void Start(); 32 void Start();
27 33
28 private: 34 private:
29 void GotPassword(const char* password); 35 void GotPassword(const char* password);
30 void Done(); 36 void Done();
31 37
32 scoped_refptr<net::CryptoModule> module_; 38 size_t current_;
39 net::CryptoModuleList modules_;
33 browser::CryptoModulePasswordReason reason_; 40 browser::CryptoModulePasswordReason reason_;
34 std::string host_; 41 std::string host_;
35 Callback0::Type* callback_; 42 Callback0::Type* callback_;
36 PRBool retry_; 43 PRBool retry_;
37 }; 44 };
38 45
39 SlotUnlocker::SlotUnlocker(net::CryptoModule* module, 46 SlotUnlocker::SlotUnlocker(const net::CryptoModuleList& modules,
40 browser::CryptoModulePasswordReason reason, 47 browser::CryptoModulePasswordReason reason,
41 const std::string& host, 48 const std::string& host,
42 Callback0::Type* callback) 49 Callback0::Type* callback)
43 : module_(module), 50 : current_(0),
51 modules_(modules),
44 reason_(reason), 52 reason_(reason),
45 host_(host), 53 host_(host),
46 callback_(callback), 54 callback_(callback),
47 retry_(PR_FALSE) { 55 retry_(PR_FALSE) {
48 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 56 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
49 } 57 }
50 58
51 void SlotUnlocker::Start() { 59 void SlotUnlocker::Start() {
52 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 60 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
53 61
54 ShowCryptoModulePasswordDialog( 62 for (; current_ < modules_.size(); ++current_) {
55 module_->GetTokenName(), 63 if (ShouldShowDialog(modules_[current_].get())) {
56 retry_, 64 ShowCryptoModulePasswordDialog(
57 reason_, 65 modules_[current_]->GetTokenName(),
58 host_, 66 retry_,
59 NewCallback(this, &SlotUnlocker::GotPassword)); 67 reason_,
68 host_,
69 NewCallback(this, &SlotUnlocker::GotPassword));
70 return;
71 }
72 }
73 Done();
60 } 74 }
61 75
62 void SlotUnlocker::GotPassword(const char* password) { 76 void SlotUnlocker::GotPassword(const char* password) {
63 // TODO(mattm): PK11_DoPassword has something about PK11_Global.verifyPass. 77 // TODO(mattm): PK11_DoPassword has something about PK11_Global.verifyPass.
64 // Do we need it? 78 // Do we need it?
65 // http://mxr.mozilla.org/mozilla/source/security/nss/lib/pk11wrap/pk11auth.c# 577 79 // http://mxr.mozilla.org/mozilla/source/security/nss/lib/pk11wrap/pk11auth.c# 577
66 80
67 if (!password) { 81 if (!password) {
68 // User cancelled entering password. Oh well. 82 // User cancelled entering password. Oh well.
69 Done(); 83 ++current_;
84 Start();
70 return; 85 return;
71 } 86 }
72 87
73 // TODO(mattm): handle protectedAuthPath 88 // TODO(mattm): handle protectedAuthPath
74 SECStatus rv = PK11_CheckUserPassword(module_->os_module_handle(), 89 SECStatus rv = PK11_CheckUserPassword(modules_[current_]->os_module_handle(),
75 password); 90 password);
76 if (rv == SECWouldBlock) { 91 if (rv == SECWouldBlock) {
77 // Incorrect password. Try again. 92 // Incorrect password. Try again.
78 retry_ = PR_TRUE; 93 retry_ = PR_TRUE;
79 Start(); 94 Start();
80 return; 95 return;
81 } 96 }
82 97
83 // TODO(mattm): PK11_DoPassword calls nssTrustDomain_UpdateCachedTokenCerts on 98 // TODO(mattm): PK11_DoPassword calls nssTrustDomain_UpdateCachedTokenCerts on
84 // non-friendly slots. How important is that? 99 // non-friendly slots. How important is that?
85 100
86 // Correct password (SECSuccess) or too many attempts/other failure 101 // Correct password (SECSuccess) or too many attempts/other failure
87 // (SECFailure). Either way we're done. 102 // (SECFailure). Either way we're done with this slot.
88 Done(); 103 ++current_;
104 Start();
89 } 105 }
90 106
91 void SlotUnlocker::Done() { 107 void SlotUnlocker::Done() {
108 DCHECK_EQ(current_, modules_.size());
92 callback_->Run(); 109 callback_->Run();
93 delete this; 110 delete this;
94 } 111 }
95 112
96 } // namespace 113 } // namespace
97 114
98 namespace browser { 115 namespace browser {
99 116
100 void UnlockSlotIfNecessary(net::CryptoModule* module, 117 void UnlockSlotsIfNecessary(const net::CryptoModuleList& modules,
101 browser::CryptoModulePasswordReason reason, 118 browser::CryptoModulePasswordReason reason,
102 const std::string& host, 119 const std::string& host,
103 Callback0::Type* callback) { 120 Callback0::Type* callback) {
104 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 121 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
105 // The wincx arg is unused since we don't call PK11_SetIsLoggedInFunc. 122 for (size_t i = 0; i < modules.size(); ++i) {
106 if (PK11_NeedLogin(module->os_module_handle()) && 123 if (ShouldShowDialog(modules[i].get())) {
107 !PK11_IsLoggedIn(module->os_module_handle(), NULL /* wincx */)) { 124 (new SlotUnlocker(modules, reason, host, callback))->Start();
108 (new SlotUnlocker(module, reason, host, callback))->Start(); 125 return;
109 } else { 126 }
110 callback->Run();
111 } 127 }
128 callback->Run();
112 } 129 }
113 130
114 void UnlockCertSlotIfNecessary(net::X509Certificate* cert, 131 void UnlockCertSlotIfNecessary(net::X509Certificate* cert,
115 browser::CryptoModulePasswordReason reason, 132 browser::CryptoModulePasswordReason reason,
116 const std::string& host, 133 const std::string& host,
117 Callback0::Type* callback) { 134 Callback0::Type* callback) {
118 scoped_refptr<net::CryptoModule> module(net::CryptoModule::CreateFromHandle( 135 net::CryptoModuleList modules;
136 modules.push_back(net::CryptoModule::CreateFromHandle(
119 cert->os_cert_handle()->slot)); 137 cert->os_cert_handle()->slot));
120 UnlockSlotIfNecessary(module.get(), reason, host, callback); 138 UnlockSlotsIfNecessary(modules, reason, host, callback);
121 } 139 }
122 140
123 } // namespace browser 141 } // namespace browser
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698