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

Side by Side Diff: chrome/browser/password_manager/native_backend_gnome_x.cc

Issue 906973007: PasswordStore: Clean up expectations about rewriting vectors of forms (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: More comments addressed Created 5 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
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/password_manager/native_backend_gnome_x.h" 5 #include "chrome/browser/password_manager/native_backend_gnome_x.h"
6 6
7 #include <dlfcn.h> 7 #include <dlfcn.h>
8 #include <gnome-keyring.h> 8 #include <gnome-keyring.h>
9 9
10 #include <map> 10 #include <map>
(...skipping 145 matching lines...) Expand 10 before | Expand all | Expand 10 after
156 form->federation_url = GURL(string_attr_map["federation_url"]); 156 form->federation_url = GURL(string_attr_map["federation_url"]);
157 form->skip_zero_click = uint_attr_map["skip_zero_click"]; 157 form->skip_zero_click = uint_attr_map["skip_zero_click"];
158 form->generation_upload_status = 158 form->generation_upload_status =
159 static_cast<PasswordForm::GenerationUploadStatus>( 159 static_cast<PasswordForm::GenerationUploadStatus>(
160 uint_attr_map["generation_upload_status"]); 160 uint_attr_map["generation_upload_status"]);
161 DeserializeFormDataFromBase64String(string_attr_map["form_data"], 161 DeserializeFormDataFromBase64String(string_attr_map["form_data"],
162 &form->form_data); 162 &form->form_data);
163 return form.Pass(); 163 return form.Pass();
164 } 164 }
165 165
166 // Parse all the results from the given GList into a 166 // Converts native credentials in |found| to PasswordForms. If not NULL,
167 // ScopedVector<autofill::PasswordForm>, and free the GList. PasswordForms are
168 // allocated on the heap, and should be deleted by the consumer. If not NULL,
169 // |lookup_form| is used to filter out results -- only credentials with signon 167 // |lookup_form| is used to filter out results -- only credentials with signon
170 // realms passing the PSL matching against |lookup_form->signon_realm| will be 168 // realms passing the PSL matching against |lookup_form->signon_realm| will be
171 // kept. PSL matched results get their signon_realm, origin, and action 169 // kept. PSL matched results get their signon_realm, origin, and action
172 // rewritten to those of |lookup_form_|, with the original signon_realm saved 170 // rewritten to those of |lookup_form_|, with the original signon_realm saved
173 // into the result's original_signon_realm data member. 171 // into the result's original_signon_realm data member.
174 void ConvertFormList(GList* found, 172 ScopedVector<PasswordForm> ConvertFormList(GList* found,
175 const PasswordForm* lookup_form, 173 const PasswordForm* lookup_form) {
176 ScopedVector<autofill::PasswordForm>* forms) { 174 ScopedVector<PasswordForm> forms;
177 password_manager::PSLDomainMatchMetric psl_domain_match_metric = 175 password_manager::PSLDomainMatchMetric psl_domain_match_metric =
178 password_manager::PSL_DOMAIN_MATCH_NONE; 176 password_manager::PSL_DOMAIN_MATCH_NONE;
179 for (GList* element = g_list_first(found); element; 177 for (GList* element = g_list_first(found); element;
180 element = g_list_next(element)) { 178 element = g_list_next(element)) {
181 GnomeKeyringFound* data = static_cast<GnomeKeyringFound*>(element->data); 179 GnomeKeyringFound* data = static_cast<GnomeKeyringFound*>(element->data);
182 GnomeKeyringAttributeList* attrs = data->attributes; 180 GnomeKeyringAttributeList* attrs = data->attributes;
183 181
184 scoped_ptr<PasswordForm> form(FormFromAttributes(attrs)); 182 scoped_ptr<PasswordForm> form(FormFromAttributes(attrs));
185 if (form) { 183 if (form) {
186 if (lookup_form && form->signon_realm != lookup_form->signon_realm) { 184 if (lookup_form && form->signon_realm != lookup_form->signon_realm) {
187 // This is not an exact match, we try PSL matching. 185 // This is not an exact match, we try PSL matching.
188 if (lookup_form->scheme != PasswordForm::SCHEME_HTML || 186 if (lookup_form->scheme != PasswordForm::SCHEME_HTML ||
189 form->scheme != PasswordForm::SCHEME_HTML || 187 form->scheme != PasswordForm::SCHEME_HTML ||
190 !(password_manager::IsPublicSuffixDomainMatch( 188 !(password_manager::IsPublicSuffixDomainMatch(
191 lookup_form->signon_realm, form->signon_realm))) { 189 lookup_form->signon_realm, form->signon_realm))) {
192 continue; 190 continue;
193 } 191 }
194 psl_domain_match_metric = password_manager::PSL_DOMAIN_MATCH_FOUND; 192 psl_domain_match_metric = password_manager::PSL_DOMAIN_MATCH_FOUND;
195 form->original_signon_realm = form->signon_realm; 193 form->original_signon_realm = form->signon_realm;
196 form->signon_realm = lookup_form->signon_realm; 194 form->signon_realm = lookup_form->signon_realm;
197 form->origin = lookup_form->origin; 195 form->origin = lookup_form->origin;
198 form->action = lookup_form->action; 196 form->action = lookup_form->action;
199 } 197 }
200 if (data->secret) { 198 if (data->secret) {
201 form->password_value = UTF8ToUTF16(data->secret); 199 form->password_value = UTF8ToUTF16(data->secret);
202 } else { 200 } else {
203 LOG(WARNING) << "Unable to access password from list element!"; 201 LOG(WARNING) << "Unable to access password from list element!";
204 } 202 }
205 forms->push_back(form.release()); 203 forms.push_back(form.release());
206 } else { 204 } else {
207 LOG(WARNING) << "Could not initialize PasswordForm from attributes!"; 205 LOG(WARNING) << "Could not initialize PasswordForm from attributes!";
208 } 206 }
209 } 207 }
210 if (lookup_form) { 208 if (lookup_form) {
211 const GURL signon_realm(lookup_form->signon_realm); 209 const GURL signon_realm(lookup_form->signon_realm);
212 std::string registered_domain = 210 std::string registered_domain =
213 password_manager::GetRegistryControlledDomain(signon_realm); 211 password_manager::GetRegistryControlledDomain(signon_realm);
214 UMA_HISTOGRAM_ENUMERATION( 212 UMA_HISTOGRAM_ENUMERATION(
215 "PasswordManager.PslDomainMatchTriggering", 213 "PasswordManager.PslDomainMatchTriggering",
216 password_manager::ShouldPSLDomainMatchingApply(registered_domain) 214 password_manager::ShouldPSLDomainMatchingApply(registered_domain)
217 ? psl_domain_match_metric 215 ? psl_domain_match_metric
218 : password_manager::PSL_DOMAIN_MATCH_NOT_USED, 216 : password_manager::PSL_DOMAIN_MATCH_NOT_USED,
219 password_manager::PSL_DOMAIN_MATCH_COUNT); 217 password_manager::PSL_DOMAIN_MATCH_COUNT);
220 } 218 }
219 return forms.Pass();
221 } 220 }
222 221
223 // Schema is analagous to the fields in PasswordForm. 222 // Schema is analagous to the fields in PasswordForm.
224 const GnomeKeyringPasswordSchema kGnomeSchema = { 223 const GnomeKeyringPasswordSchema kGnomeSchema = {
225 GNOME_KEYRING_ITEM_GENERIC_SECRET, { 224 GNOME_KEYRING_ITEM_GENERIC_SECRET, {
226 { "origin_url", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING }, 225 { "origin_url", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING },
227 { "action_url", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING }, 226 { "action_url", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING },
228 { "username_element", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING }, 227 { "username_element", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING },
229 { "username_value", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING }, 228 { "username_value", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING },
230 { "password_element", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING }, 229 { "password_element", GNOME_KEYRING_ATTRIBUTE_TYPE_STRING },
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after
277 void UpdateLoginSearch(const PasswordForm& form, const char* app_string); 276 void UpdateLoginSearch(const PasswordForm& form, const char* app_string);
278 void RemoveLogin(const PasswordForm& form, const char* app_string); 277 void RemoveLogin(const PasswordForm& form, const char* app_string);
279 void GetLogins(const PasswordForm& form, const char* app_string); 278 void GetLogins(const PasswordForm& form, const char* app_string);
280 void GetLoginsList(uint32_t blacklisted_by_user, const char* app_string); 279 void GetLoginsList(uint32_t blacklisted_by_user, const char* app_string);
281 void GetAllLogins(const char* app_string); 280 void GetAllLogins(const char* app_string);
282 281
283 // Use after AddLogin, RemoveLogin. 282 // Use after AddLogin, RemoveLogin.
284 GnomeKeyringResult WaitResult(); 283 GnomeKeyringResult WaitResult();
285 284
286 // Use after AddLoginSearch, UpdateLoginSearch, GetLogins, GetLoginsList, 285 // Use after AddLoginSearch, UpdateLoginSearch, GetLogins, GetLoginsList,
287 // GetAllLogins. 286 // GetAllLogins. Replaces the content of |forms| with found logins.
288 GnomeKeyringResult WaitResult(ScopedVector<autofill::PasswordForm>* forms); 287 GnomeKeyringResult WaitResult(ScopedVector<PasswordForm>* forms);
289 288
290 private: 289 private:
291 struct GnomeKeyringAttributeListFreeDeleter { 290 struct GnomeKeyringAttributeListFreeDeleter {
292 inline void operator()(void* list) const { 291 inline void operator()(void* list) const {
293 gnome_keyring_attribute_list_free( 292 gnome_keyring_attribute_list_free(
294 static_cast<GnomeKeyringAttributeList*>(list)); 293 static_cast<GnomeKeyringAttributeList*>(list));
295 } 294 }
296 }; 295 };
297 296
298 typedef scoped_ptr<GnomeKeyringAttributeList, 297 typedef scoped_ptr<GnomeKeyringAttributeList,
299 GnomeKeyringAttributeListFreeDeleter> ScopedAttributeList; 298 GnomeKeyringAttributeListFreeDeleter> ScopedAttributeList;
300 299
301 // Helper methods to abbreviate Gnome Keyring long API names. 300 // Helper methods to abbreviate Gnome Keyring long API names.
302 static void AppendString(ScopedAttributeList* list, 301 static void AppendString(ScopedAttributeList* list,
303 const char* name, 302 const char* name,
304 const char* value); 303 const char* value);
305 static void AppendString(ScopedAttributeList* list, 304 static void AppendString(ScopedAttributeList* list,
306 const char* name, 305 const char* name,
307 const std::string& value); 306 const std::string& value);
308 static void AppendUint32(ScopedAttributeList* list, 307 static void AppendUint32(ScopedAttributeList* list,
309 const char* name, 308 const char* name,
310 guint32 value); 309 guint32 value);
311 310
312 // All these callbacks are called on UI thread. 311 // All these callbacks are called on UI thread.
313 static void OnOperationDone(GnomeKeyringResult result, gpointer data); 312 static void OnOperationDone(GnomeKeyringResult result, gpointer data);
314 313
314 // This is marked as static, but acts on the GKRMethod instance that |data|
315 // points to. Saves |result| to |result_|. If the result is OK, overwrites
316 // |forms_| with the found credentials.
engedy 2015/03/16 10:35:35 Thanks, looking good! nit: Could you please reins
vabr (Chromium) 2015/03/16 10:58:47 Done.
315 static void OnOperationGetList(GnomeKeyringResult result, GList* list, 317 static void OnOperationGetList(GnomeKeyringResult result, GList* list,
316 gpointer data); 318 gpointer data);
317 319
318 base::WaitableEvent event_; 320 base::WaitableEvent event_;
319 GnomeKeyringResult result_; 321 GnomeKeyringResult result_;
320 ScopedVector<autofill::PasswordForm> forms_; 322 ScopedVector<PasswordForm> forms_;
321 // If the credential search is specified by a single form and needs to use PSL 323 // If the credential search is specified by a single form and needs to use PSL
322 // matching, then the specifying form is stored in |lookup_form_|. If PSL 324 // matching, then the specifying form is stored in |lookup_form_|. If PSL
323 // matching is used to find a result, then the results signon realm, origin 325 // matching is used to find a result, then the results signon realm, origin
324 // and action are stored are replaced by those of |lookup_form_|. 326 // and action are stored are replaced by those of |lookup_form_|.
325 // Additionally, |lookup_form_->signon_realm| is also used to narrow down the 327 // Additionally, |lookup_form_->signon_realm| is also used to narrow down the
326 // found logins to those which indeed PSL-match the look-up. And finally, 328 // found logins to those which indeed PSL-match the look-up. And finally,
327 // |lookup_form_| set to NULL means that PSL matching is not required. 329 // |lookup_form_| set to NULL means that PSL matching is not required.
328 scoped_ptr<PasswordForm> lookup_form_; 330 scoped_ptr<PasswordForm> lookup_form_;
329 }; 331 };
330 332
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after
474 /*data=*/this, 476 /*data=*/this,
475 /*destroy_data=*/nullptr); 477 /*destroy_data=*/nullptr);
476 } 478 }
477 479
478 GnomeKeyringResult GKRMethod::WaitResult() { 480 GnomeKeyringResult GKRMethod::WaitResult() {
479 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 481 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
480 event_.Wait(); 482 event_.Wait();
481 return result_; 483 return result_;
482 } 484 }
483 485
484 GnomeKeyringResult GKRMethod::WaitResult( 486 GnomeKeyringResult GKRMethod::WaitResult(ScopedVector<PasswordForm>* forms) {
485 ScopedVector<autofill::PasswordForm>* forms) {
486 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 487 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
487 event_.Wait(); 488 event_.Wait();
488 if (forms->empty()) { 489 *forms = forms_.Pass();
489 // Normal case. Avoid extra allocation by swapping.
490 forms->swap(forms_);
491 } else {
492 // Rare case. Append forms_ to *forms.
493 forms->insert(forms->end(), forms_.begin(), forms_.end());
494 forms_.weak_clear();
495 }
496 return result_; 490 return result_;
497 } 491 }
498 492
499 // static 493 // static
500 void GKRMethod::AppendString(GKRMethod::ScopedAttributeList* list, 494 void GKRMethod::AppendString(GKRMethod::ScopedAttributeList* list,
501 const char* name, 495 const char* name,
502 const char* value) { 496 const char* value) {
503 gnome_keyring_attribute_list_append_string(list->get(), name, value); 497 gnome_keyring_attribute_list_append_string(list->get(), name, value);
504 } 498 }
505 499
(...skipping 16 matching lines...) Expand all
522 GKRMethod* method = static_cast<GKRMethod*>(data); 516 GKRMethod* method = static_cast<GKRMethod*>(data);
523 method->result_ = result; 517 method->result_ = result;
524 method->event_.Signal(); 518 method->event_.Signal();
525 } 519 }
526 520
527 // static 521 // static
528 void GKRMethod::OnOperationGetList(GnomeKeyringResult result, GList* list, 522 void GKRMethod::OnOperationGetList(GnomeKeyringResult result, GList* list,
529 gpointer data) { 523 gpointer data) {
530 GKRMethod* method = static_cast<GKRMethod*>(data); 524 GKRMethod* method = static_cast<GKRMethod*>(data);
531 method->result_ = result; 525 method->result_ = result;
532 method->forms_.clear();
533 // |list| will be freed after this callback returns, so convert it now. 526 // |list| will be freed after this callback returns, so convert it now.
534 ConvertFormList(list, method->lookup_form_.get(), &method->forms_); 527 if (result == GNOME_KEYRING_RESULT_OK)
528 method->forms_ = ConvertFormList(list, method->lookup_form_.get());
529 else
530 method->forms_.clear();
535 method->lookup_form_.reset(); 531 method->lookup_form_.reset();
536 method->event_.Signal(); 532 method->event_.Signal();
537 } 533 }
538 534
535 // Generates a profile-specific app string based on profile_id.
536 std::string GetProfileSpecificAppString(LocalProfileId profile_id) {
537 // Originally, the application string was always just "chrome" and used only
538 // so that we had *something* to search for since GNOME Keyring won't search
539 // for nothing. Now we use it to distinguish passwords for different profiles.
540 return base::StringPrintf("%s-%d", kGnomeKeyringAppString, profile_id);
541 }
542
539 } // namespace 543 } // namespace
540 544
541 NativeBackendGnome::NativeBackendGnome(LocalProfileId id) 545 NativeBackendGnome::NativeBackendGnome(LocalProfileId id)
542 : profile_id_(id) { 546 : profile_id_(id), app_string_(GetProfileSpecificAppString(id)) {
543 app_string_ = GetProfileSpecificAppString();
544 } 547 }
545 548
546 NativeBackendGnome::~NativeBackendGnome() { 549 NativeBackendGnome::~NativeBackendGnome() {
547 } 550 }
548 551
549 bool NativeBackendGnome::Init() { 552 bool NativeBackendGnome::Init() {
550 return LoadGnomeKeyring() && gnome_keyring_is_available(); 553 return LoadGnomeKeyring() && gnome_keyring_is_available();
551 } 554 }
552 555
553 bool NativeBackendGnome::RawAddLogin(const PasswordForm& form) { 556 bool NativeBackendGnome::RawAddLogin(const PasswordForm& form) {
(...skipping 18 matching lines...) Expand all
572 // on origin_url, username_element, username_value, password_element, submit 575 // on origin_url, username_element, username_value, password_element, submit
573 // element, and signon_realm first, remove that, and then add the new entry. 576 // element, and signon_realm first, remove that, and then add the new entry.
574 // We'd add the new one first, and then delete the original, but then the 577 // We'd add the new one first, and then delete the original, but then the
575 // delete might actually delete the newly-added entry! 578 // delete might actually delete the newly-added entry!
576 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 579 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
577 GKRMethod method; 580 GKRMethod method;
578 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, 581 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
579 base::Bind(&GKRMethod::AddLoginSearch, 582 base::Bind(&GKRMethod::AddLoginSearch,
580 base::Unretained(&method), 583 base::Unretained(&method),
581 form, app_string_.c_str())); 584 form, app_string_.c_str()));
582 ScopedVector<autofill::PasswordForm> forms; 585 ScopedVector<PasswordForm> forms;
583 GnomeKeyringResult result = method.WaitResult(&forms); 586 GnomeKeyringResult result = method.WaitResult(&forms);
584 if (result != GNOME_KEYRING_RESULT_OK && 587 if (result != GNOME_KEYRING_RESULT_OK &&
585 result != GNOME_KEYRING_RESULT_NO_MATCH) { 588 result != GNOME_KEYRING_RESULT_NO_MATCH) {
586 LOG(ERROR) << "Keyring find failed: " 589 LOG(ERROR) << "Keyring find failed: "
587 << gnome_keyring_result_to_message(result); 590 << gnome_keyring_result_to_message(result);
588 return password_manager::PasswordStoreChangeList(); 591 return password_manager::PasswordStoreChangeList();
589 } 592 }
590 password_manager::PasswordStoreChangeList changes; 593 password_manager::PasswordStoreChangeList changes;
591 if (forms.size() > 0) { 594 if (forms.size() > 0) {
592 if (forms.size() > 1) { 595 if (forms.size() > 1) {
(...skipping 23 matching lines...) Expand all
616 // then add the new entry. We'd add the new one first, and then delete the 619 // then add the new entry. We'd add the new one first, and then delete the
617 // original, but then the delete might actually delete the newly-added entry! 620 // original, but then the delete might actually delete the newly-added entry!
618 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 621 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
619 DCHECK(changes); 622 DCHECK(changes);
620 changes->clear(); 623 changes->clear();
621 GKRMethod method; 624 GKRMethod method;
622 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, 625 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
623 base::Bind(&GKRMethod::UpdateLoginSearch, 626 base::Bind(&GKRMethod::UpdateLoginSearch,
624 base::Unretained(&method), 627 base::Unretained(&method),
625 form, app_string_.c_str())); 628 form, app_string_.c_str()));
626 ScopedVector<autofill::PasswordForm> forms; 629 ScopedVector<PasswordForm> forms;
627 GnomeKeyringResult result = method.WaitResult(&forms); 630 GnomeKeyringResult result = method.WaitResult(&forms);
628 if (result != GNOME_KEYRING_RESULT_OK) { 631 if (result != GNOME_KEYRING_RESULT_OK) {
629 LOG(ERROR) << "Keyring find failed: " 632 LOG(ERROR) << "Keyring find failed: "
630 << gnome_keyring_result_to_message(result); 633 << gnome_keyring_result_to_message(result);
631 return false; 634 return false;
632 } 635 }
633 636
634 bool removed = false; 637 bool removed = false;
635 for (size_t i = 0; i < forms.size(); ++i) { 638 for (size_t i = 0; i < forms.size(); ++i) {
636 if (*forms[i] != form) { 639 if (*forms[i] != form) {
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
676 delete_begin, delete_end, CREATION_TIMESTAMP, changes); 679 delete_begin, delete_end, CREATION_TIMESTAMP, changes);
677 } 680 }
678 681
679 bool NativeBackendGnome::RemoveLoginsSyncedBetween( 682 bool NativeBackendGnome::RemoveLoginsSyncedBetween(
680 base::Time delete_begin, 683 base::Time delete_begin,
681 base::Time delete_end, 684 base::Time delete_end,
682 password_manager::PasswordStoreChangeList* changes) { 685 password_manager::PasswordStoreChangeList* changes) {
683 return RemoveLoginsBetween(delete_begin, delete_end, SYNC_TIMESTAMP, changes); 686 return RemoveLoginsBetween(delete_begin, delete_end, SYNC_TIMESTAMP, changes);
684 } 687 }
685 688
686 bool NativeBackendGnome::GetLogins( 689 bool NativeBackendGnome::GetLogins(const PasswordForm& form,
687 const PasswordForm& form, 690 ScopedVector<PasswordForm>* forms) {
688 ScopedVector<autofill::PasswordForm>* forms) {
689 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 691 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
690 GKRMethod method; 692 GKRMethod method;
691 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, 693 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
692 base::Bind(&GKRMethod::GetLogins, 694 base::Bind(&GKRMethod::GetLogins,
693 base::Unretained(&method), 695 base::Unretained(&method),
694 form, app_string_.c_str())); 696 form, app_string_.c_str()));
695 GnomeKeyringResult result = method.WaitResult(forms); 697 GnomeKeyringResult result = method.WaitResult(forms);
696 if (result == GNOME_KEYRING_RESULT_NO_MATCH) 698 if (result == GNOME_KEYRING_RESULT_NO_MATCH)
697 return true; 699 return true;
698 if (result != GNOME_KEYRING_RESULT_OK) { 700 if (result != GNOME_KEYRING_RESULT_OK) {
699 LOG(ERROR) << "Keyring find failed: " 701 LOG(ERROR) << "Keyring find failed: "
700 << gnome_keyring_result_to_message(result); 702 << gnome_keyring_result_to_message(result);
701 return false; 703 return false;
702 } 704 }
703 return true; 705 return true;
704 } 706 }
705 707
706 bool NativeBackendGnome::GetAutofillableLogins( 708 bool NativeBackendGnome::GetAutofillableLogins(
707 ScopedVector<autofill::PasswordForm>* forms) { 709 ScopedVector<PasswordForm>* forms) {
708 return GetLoginsList(true, forms); 710 return GetLoginsList(true, forms);
709 } 711 }
710 712
711 bool NativeBackendGnome::GetBlacklistLogins( 713 bool NativeBackendGnome::GetBlacklistLogins(ScopedVector<PasswordForm>* forms) {
712 ScopedVector<autofill::PasswordForm>* forms) {
713 return GetLoginsList(false, forms); 714 return GetLoginsList(false, forms);
714 } 715 }
715 716
716 bool NativeBackendGnome::GetLoginsList( 717 bool NativeBackendGnome::GetLoginsList(bool autofillable,
717 bool autofillable, 718 ScopedVector<PasswordForm>* forms) {
718 ScopedVector<autofill::PasswordForm>* forms) {
719 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 719 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
720 720
721 uint32_t blacklisted_by_user = !autofillable; 721 uint32_t blacklisted_by_user = !autofillable;
722 722
723 GKRMethod method; 723 GKRMethod method;
724 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, 724 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
725 base::Bind(&GKRMethod::GetLoginsList, 725 base::Bind(&GKRMethod::GetLoginsList,
726 base::Unretained(&method), 726 base::Unretained(&method),
727 blacklisted_by_user, app_string_.c_str())); 727 blacklisted_by_user, app_string_.c_str()));
728 GnomeKeyringResult result = method.WaitResult(forms); 728 GnomeKeyringResult result = method.WaitResult(forms);
729 if (result == GNOME_KEYRING_RESULT_NO_MATCH) 729 if (result == GNOME_KEYRING_RESULT_NO_MATCH)
730 return true; 730 return true;
731 if (result != GNOME_KEYRING_RESULT_OK) { 731 if (result != GNOME_KEYRING_RESULT_OK) {
732 LOG(ERROR) << "Keyring find failed: " 732 LOG(ERROR) << "Keyring find failed: "
733 << gnome_keyring_result_to_message(result); 733 << gnome_keyring_result_to_message(result);
734 return false; 734 return false;
735 } 735 }
736 return true; 736 return true;
737 } 737 }
738 738
739 bool NativeBackendGnome::GetAllLogins( 739 bool NativeBackendGnome::GetAllLogins(ScopedVector<PasswordForm>* forms) {
740 ScopedVector<autofill::PasswordForm>* forms) {
741 GKRMethod method; 740 GKRMethod method;
742 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, 741 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE,
743 base::Bind(&GKRMethod::GetAllLogins, 742 base::Bind(&GKRMethod::GetAllLogins,
744 base::Unretained(&method), 743 base::Unretained(&method),
745 app_string_.c_str())); 744 app_string_.c_str()));
746 GnomeKeyringResult result = method.WaitResult(forms); 745 GnomeKeyringResult result = method.WaitResult(forms);
747 if (result == GNOME_KEYRING_RESULT_NO_MATCH) 746 if (result == GNOME_KEYRING_RESULT_NO_MATCH)
748 return true; 747 return true;
749 if (result != GNOME_KEYRING_RESULT_OK) { 748 if (result != GNOME_KEYRING_RESULT_OK) {
750 LOG(ERROR) << "Keyring find failed: " 749 LOG(ERROR) << "Keyring find failed: "
751 << gnome_keyring_result_to_message(result); 750 << gnome_keyring_result_to_message(result);
752 return false; 751 return false;
753 } 752 }
754 return true; 753 return true;
755 } 754 }
756 755
757 bool NativeBackendGnome::GetLoginsBetween( 756 bool NativeBackendGnome::GetLoginsBetween(base::Time get_begin,
758 base::Time get_begin, 757 base::Time get_end,
759 base::Time get_end, 758 TimestampToCompare date_to_compare,
760 TimestampToCompare date_to_compare, 759 ScopedVector<PasswordForm>* forms) {
761 ScopedVector<autofill::PasswordForm>* forms) {
762 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 760 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
761 forms->clear();
763 // We could walk the list and add items as we find them, but it is much 762 // We could walk the list and add items as we find them, but it is much
764 // easier to build the list and then filter the results. 763 // easier to build the list and then filter the results.
765 ScopedVector<autofill::PasswordForm> all_forms; 764 ScopedVector<PasswordForm> all_forms;
766 if (!GetAllLogins(&all_forms)) 765 if (!GetAllLogins(&all_forms))
767 return false; 766 return false;
768 767
769 base::Time autofill::PasswordForm::*date_member = 768 base::Time PasswordForm::*date_member = date_to_compare == CREATION_TIMESTAMP
770 date_to_compare == CREATION_TIMESTAMP 769 ? &PasswordForm::date_created
771 ? &autofill::PasswordForm::date_created 770 : &PasswordForm::date_synced;
772 : &autofill::PasswordForm::date_synced;
773 for (auto& saved_form : all_forms) { 771 for (auto& saved_form : all_forms) {
774 if (get_begin <= saved_form->*date_member && 772 if (get_begin <= saved_form->*date_member &&
775 (get_end.is_null() || saved_form->*date_member < get_end)) { 773 (get_end.is_null() || saved_form->*date_member < get_end)) {
776 forms->push_back(saved_form); 774 forms->push_back(saved_form);
777 saved_form = nullptr; 775 saved_form = nullptr;
778 } 776 }
779 } 777 }
780 778
781 return true; 779 return true;
782 } 780 }
783 781
784 bool NativeBackendGnome::RemoveLoginsBetween( 782 bool NativeBackendGnome::RemoveLoginsBetween(
785 base::Time get_begin, 783 base::Time get_begin,
786 base::Time get_end, 784 base::Time get_end,
787 TimestampToCompare date_to_compare, 785 TimestampToCompare date_to_compare,
788 password_manager::PasswordStoreChangeList* changes) { 786 password_manager::PasswordStoreChangeList* changes) {
789 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB)); 787 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::DB));
790 DCHECK(changes); 788 DCHECK(changes);
791 changes->clear(); 789 changes->clear();
792 // We could walk the list and delete items as we find them, but it is much 790 // We could walk the list and delete items as we find them, but it is much
793 // easier to build the list and use RemoveLogin() to delete them. 791 // easier to build the list and use RemoveLogin() to delete them.
794 ScopedVector<autofill::PasswordForm> forms; 792 ScopedVector<PasswordForm> forms;
795 if (!GetLoginsBetween(get_begin, get_end, date_to_compare, &forms)) 793 if (!GetLoginsBetween(get_begin, get_end, date_to_compare, &forms))
796 return false; 794 return false;
797 795
798 bool ok = true; 796 bool ok = true;
799 for (size_t i = 0; i < forms.size(); ++i) { 797 for (size_t i = 0; i < forms.size(); ++i) {
800 if (RemoveLogin(*forms[i])) { 798 if (RemoveLogin(*forms[i])) {
801 changes->push_back(password_manager::PasswordStoreChange( 799 changes->push_back(password_manager::PasswordStoreChange(
802 password_manager::PasswordStoreChange::REMOVE, *forms[i])); 800 password_manager::PasswordStoreChange::REMOVE, *forms[i]));
803 } else { 801 } else {
804 ok = false; 802 ok = false;
805 } 803 }
806 } 804 }
807 return ok; 805 return ok;
808 } 806 }
809
810 std::string NativeBackendGnome::GetProfileSpecificAppString() const {
811 // Originally, the application string was always just "chrome" and used only
812 // so that we had *something* to search for since GNOME Keyring won't search
813 // for nothing. Now we use it to distinguish passwords for different profiles.
814 return base::StringPrintf("%s-%d", kGnomeKeyringAppString, profile_id_);
815 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698