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/password_manager/password_store_mac.h" | 5 #include "chrome/browser/password_manager/password_store_mac.h" |
| 6 #include "chrome/browser/password_manager/password_store_mac_internal.h" | 6 #include "chrome/browser/password_manager/password_store_mac_internal.h" |
| 7 | 7 |
| 8 #include <CoreServices/CoreServices.h> | 8 #include <CoreServices/CoreServices.h> |
| 9 #include <set> | 9 #include <set> |
| 10 #include <string> | 10 #include <string> |
| 11 #include <utility> | |
| 11 #include <vector> | 12 #include <vector> |
| 12 | 13 |
| 13 #include "base/callback.h" | 14 #include "base/callback.h" |
| 14 #include "base/debug/crash_logging.h" | 15 #include "base/debug/crash_logging.h" |
| 15 #include "base/debug/stack_trace.h" | 16 #include "base/debug/stack_trace.h" |
| 16 #include "base/logging.h" | 17 #include "base/logging.h" |
| 17 #include "base/mac/mac_logging.h" | 18 #include "base/mac/mac_logging.h" |
| 18 #include "base/mac/mac_util.h" | 19 #include "base/mac/mac_util.h" |
| 19 #include "base/message_loop/message_loop.h" | 20 #include "base/message_loop/message_loop.h" |
| 20 #include "base/stl_util.h" | 21 #include "base/stl_util.h" |
| (...skipping 208 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 229 switch (auth_type) { | 230 switch (auth_type) { |
| 230 case kSecAuthenticationTypeHTMLForm: return PasswordForm::SCHEME_HTML; | 231 case kSecAuthenticationTypeHTMLForm: return PasswordForm::SCHEME_HTML; |
| 231 case kSecAuthenticationTypeHTTPBasic: return PasswordForm::SCHEME_BASIC; | 232 case kSecAuthenticationTypeHTTPBasic: return PasswordForm::SCHEME_BASIC; |
| 232 case kSecAuthenticationTypeHTTPDigest: return PasswordForm::SCHEME_DIGEST; | 233 case kSecAuthenticationTypeHTTPDigest: return PasswordForm::SCHEME_DIGEST; |
| 233 default: return PasswordForm::SCHEME_OTHER; | 234 default: return PasswordForm::SCHEME_OTHER; |
| 234 } | 235 } |
| 235 } | 236 } |
| 236 | 237 |
| 237 bool FillPasswordFormFromKeychainItem(const AppleKeychain& keychain, | 238 bool FillPasswordFormFromKeychainItem(const AppleKeychain& keychain, |
| 238 const SecKeychainItemRef& keychain_item, | 239 const SecKeychainItemRef& keychain_item, |
| 239 PasswordForm* form) { | 240 PasswordForm* form, |
| 241 bool extract_password_data) { | |
| 240 DCHECK(form); | 242 DCHECK(form); |
| 241 | 243 |
| 242 SecKeychainAttributeInfo attrInfo; | 244 SecKeychainAttributeInfo attrInfo; |
| 243 UInt32 tags[] = { kSecAccountItemAttr, | 245 UInt32 tags[] = { kSecAccountItemAttr, |
| 244 kSecServerItemAttr, | 246 kSecServerItemAttr, |
| 245 kSecPortItemAttr, | 247 kSecPortItemAttr, |
| 246 kSecPathItemAttr, | 248 kSecPathItemAttr, |
| 247 kSecProtocolItemAttr, | 249 kSecProtocolItemAttr, |
| 248 kSecAuthenticationTypeItemAttr, | 250 kSecAuthenticationTypeItemAttr, |
| 249 kSecSecurityDomainItemAttr, | 251 kSecSecurityDomainItemAttr, |
| 250 kSecCreationDateItemAttr, | 252 kSecCreationDateItemAttr, |
| 251 kSecNegativeItemAttr }; | 253 kSecNegativeItemAttr }; |
| 252 attrInfo.count = arraysize(tags); | 254 attrInfo.count = arraysize(tags); |
| 253 attrInfo.tag = tags; | 255 attrInfo.tag = tags; |
| 254 attrInfo.format = NULL; | 256 attrInfo.format = NULL; |
| 255 | 257 |
| 256 SecKeychainAttributeList *attrList; | 258 SecKeychainAttributeList *attrList; |
| 257 UInt32 password_length; | 259 UInt32 password_length; |
| 258 void* password_data; | 260 |
| 261 // If |extract_password_data| is false, do not pass in a reference to | |
| 262 // |password_data|. ItemCopyAttributesAndData will then extract only the | |
| 263 // attributes of |keychain_item| (doesn't require OS authorization), and not | |
| 264 // attempt to extract its password data (requires OS authorization). | |
| 265 void* password_data = NULL; | |
| 266 void** password_data_ref = extract_password_data ? &password_data : NULL; | |
| 267 | |
| 259 OSStatus result = keychain.ItemCopyAttributesAndData(keychain_item, &attrInfo, | 268 OSStatus result = keychain.ItemCopyAttributesAndData(keychain_item, &attrInfo, |
| 260 NULL, &attrList, | 269 NULL, &attrList, |
| 261 &password_length, | 270 &password_length, |
| 262 &password_data); | 271 password_data_ref); |
| 263 | 272 |
| 264 if (result != noErr) { | 273 if (result != noErr) { |
| 265 // We don't log errSecAuthFailed because that just means that the user | 274 // We don't log errSecAuthFailed because that just means that the user |
| 266 // chose not to allow us access to the item. | 275 // chose not to allow us access to the item. |
| 267 if (result != errSecAuthFailed) { | 276 if (result != errSecAuthFailed) { |
| 268 OSSTATUS_LOG(ERROR, result) << "Keychain data load failed"; | 277 OSSTATUS_LOG(ERROR, result) << "Keychain data load failed"; |
| 269 } | 278 } |
| 270 return false; | 279 return false; |
| 271 } | 280 } |
| 272 | 281 |
| 273 UTF8ToUTF16(static_cast<const char *>(password_data), password_length, | 282 if (extract_password_data) { |
| 274 &(form->password_value)); | 283 UTF8ToUTF16(static_cast<const char *>(password_data), password_length, |
| 284 &(form->password_value)); | |
| 285 } | |
| 275 | 286 |
| 276 int port = kAnyPort; | 287 int port = kAnyPort; |
| 277 std::string server; | 288 std::string server; |
| 278 std::string security_domain; | 289 std::string security_domain; |
| 279 std::string path; | 290 std::string path; |
| 280 for (unsigned int i = 0; i < attrList->count; i++) { | 291 for (unsigned int i = 0; i < attrList->count; i++) { |
| 281 SecKeychainAttribute attr = attrList->attr[i]; | 292 SecKeychainAttribute attr = attrList->attr[i]; |
| 282 if (!attr.data) { | 293 if (!attr.data) { |
| 283 continue; | 294 continue; |
| 284 } | 295 } |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 326 form->blacklisted_by_user = true; | 337 form->blacklisted_by_user = true; |
| 327 } | 338 } |
| 328 break; | 339 break; |
| 329 } | 340 } |
| 330 } | 341 } |
| 331 keychain.ItemFreeAttributesAndData(attrList, password_data); | 342 keychain.ItemFreeAttributesAndData(attrList, password_data); |
| 332 | 343 |
| 333 // kSecNegativeItemAttr doesn't seem to actually be in widespread use. In | 344 // kSecNegativeItemAttr doesn't seem to actually be in widespread use. In |
| 334 // practice, other browsers seem to use a "" or " " password (and a special | 345 // practice, other browsers seem to use a "" or " " password (and a special |
| 335 // user name) to indicated blacklist entries. | 346 // user name) to indicated blacklist entries. |
| 336 if (form->password_value.empty() || EqualsASCII(form->password_value, " ")) { | 347 if (extract_password_data && (form->password_value.empty() || |
| 348 EqualsASCII(form->password_value, " "))) { | |
| 337 form->blacklisted_by_user = true; | 349 form->blacklisted_by_user = true; |
| 338 } | 350 } |
| 339 | 351 |
| 340 form->origin = URLFromComponents(form->ssl_valid, server, port, path); | 352 form->origin = URLFromComponents(form->ssl_valid, server, port, path); |
| 341 // TODO(stuartmorgan): Handle proxies, which need a different signon_realm | 353 // TODO(stuartmorgan): Handle proxies, which need a different signon_realm |
| 342 // format. | 354 // format. |
| 343 form->signon_realm = form->origin.GetOrigin().spec(); | 355 form->signon_realm = form->origin.GetOrigin().spec(); |
| 344 if (form->scheme != PasswordForm::SCHEME_HTML) { | 356 if (form->scheme != PasswordForm::SCHEME_HTML) { |
| 345 form->signon_realm.append(security_domain); | 357 form->signon_realm.append(security_domain); |
| 346 } | 358 } |
| 347 return true; | 359 return true; |
| 348 } | 360 } |
| 349 | 361 |
| 350 bool FormsMatchForMerge(const PasswordForm& form_a, | 362 bool FormsMatchForMerge(const PasswordForm& form_a, |
| 351 const PasswordForm& form_b) { | 363 const PasswordForm& form_b) { |
| 352 // We never merge blacklist entries between our store and the keychain. | 364 // We never merge blacklist entries between our store and the keychain. |
| 353 if (form_a.blacklisted_by_user || form_b.blacklisted_by_user) { | 365 if (form_a.blacklisted_by_user || form_b.blacklisted_by_user) { |
|
stuartmorgan
2013/09/30 22:39:12
As far as I can tell, you are pulling a bunch of p
Raghu Simha
2013/10/02 02:09:50
There is a filtering step for blacklisted password
| |
| 354 return false; | 366 return false; |
| 355 } | 367 } |
| 356 return form_a.scheme == form_b.scheme && | 368 return form_a.scheme == form_b.scheme && |
| 357 form_a.signon_realm == form_b.signon_realm && | 369 form_a.signon_realm == form_b.signon_realm && |
| 358 form_a.username_value == form_b.username_value; | 370 form_a.username_value == form_b.username_value; |
| 359 } | 371 } |
| 360 | 372 |
| 361 // Returns an the best match for |form| from |keychain_forms|, or NULL if there | 373 // Returns an the best match for |form| from |keychain_forms|, or NULL if there |
| 362 // is no suitable match. | 374 // is no suitable match. |
| 363 PasswordForm* BestKeychainFormForForm( | 375 PasswordForm* BestKeychainFormForForm( |
| (...skipping 75 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 439 | 451 |
| 440 // Add in the blacklist entries from the database. | 452 // Add in the blacklist entries from the database. |
| 441 merged_forms->insert(merged_forms->end(), | 453 merged_forms->insert(merged_forms->end(), |
| 442 database_blacklist_forms.begin(), | 454 database_blacklist_forms.begin(), |
| 443 database_blacklist_forms.end()); | 455 database_blacklist_forms.end()); |
| 444 | 456 |
| 445 // Clear out all the Keychain entries we used. | 457 // Clear out all the Keychain entries we used. |
| 446 DeleteVectorElementsInSet(keychain_forms, used_keychain_forms); | 458 DeleteVectorElementsInSet(keychain_forms, used_keychain_forms); |
| 447 } | 459 } |
| 448 | 460 |
| 461 std::vector<MacKeychainPasswordFormAdapter::ItemFormPair> | |
| 462 GetAllKeychainItemAttributesAsPasswordForms( | |
| 463 std::vector<SecKeychainItemRef>* keychain_items, | |
| 464 const AppleKeychain& keychain) { | |
| 465 DCHECK(keychain_items); | |
| 466 MacKeychainPasswordFormAdapter keychain_adapter(&keychain); | |
| 467 *keychain_items = keychain_adapter.GetAllPasswordFormKeychainItems(); | |
| 468 std::vector<MacKeychainPasswordFormAdapter::ItemFormPair> item_form_pairs; | |
| 469 for (std::vector<SecKeychainItemRef>::iterator i = keychain_items->begin(); | |
| 470 i != keychain_items->end(); ++i) { | |
| 471 PasswordForm* form_without_password = new PasswordForm(); | |
| 472 internal_keychain_helpers::FillPasswordFormFromKeychainItem( | |
| 473 keychain, | |
| 474 *i, | |
| 475 form_without_password, | |
| 476 false); // Load password attributes, but not password data. | |
| 477 item_form_pairs.push_back(std::make_pair(&(*i), form_without_password)); | |
| 478 } | |
| 479 return item_form_pairs; | |
| 480 } | |
| 481 | |
| 449 std::vector<PasswordForm*> GetPasswordsForForms( | 482 std::vector<PasswordForm*> GetPasswordsForForms( |
| 450 const AppleKeychain& keychain, | 483 const AppleKeychain& keychain, |
| 451 std::vector<PasswordForm*>* database_forms) { | 484 std::vector<PasswordForm*>* database_forms) { |
| 485 // First load the attributes of all items in the keychain without loading | |
| 486 // their password data, and then match items in |database_forms| against them. | |
| 487 // This avoids individually searching through the keychain for passwords | |
| 488 // matching each form in |database_forms|, and results in a significant | |
| 489 // performance gain, replacing O(N) keychain search operations with a single | |
| 490 // operation that loads all keychain items, and then selective reads of only | |
| 491 // the relevant passwords. See crbug.com/263685. | |
| 492 std::vector<SecKeychainItemRef> keychain_items; | |
| 493 std::vector<MacKeychainPasswordFormAdapter::ItemFormPair> item_form_pairs = | |
| 494 GetAllKeychainItemAttributesAsPasswordForms(&keychain_items, keychain); | |
| 495 | |
| 496 // Next, compare the attributes of the PasswordForms in |database_forms| | |
| 497 // against those in |item_form_pairs|, and extract password data for each | |
| 498 // matching PasswordForm using its corresponding SecKeychainItemRef. | |
| 452 MacKeychainPasswordFormAdapter keychain_adapter(&keychain); | 499 MacKeychainPasswordFormAdapter keychain_adapter(&keychain); |
| 453 | |
| 454 std::vector<PasswordForm*> merged_forms; | 500 std::vector<PasswordForm*> merged_forms; |
| 455 for (std::vector<PasswordForm*>::iterator i = database_forms->begin(); | 501 for (std::vector<PasswordForm*>::iterator i = database_forms->begin(); |
| 456 i != database_forms->end();) { | 502 i != database_forms->end();) { |
| 457 std::vector<PasswordForm*> db_form_container(1, *i); | 503 std::vector<PasswordForm*> db_form_container(1, *i); |
| 458 std::vector<PasswordForm*> keychain_matches = | 504 std::vector<PasswordForm*> keychain_matches = |
| 459 keychain_adapter.PasswordsMergeableWithForm(**i); | 505 keychain_adapter.ExtractPasswordsMergeableWithForm(item_form_pairs, |
| 506 **i); | |
| 460 MergePasswordForms(&keychain_matches, &db_form_container, &merged_forms); | 507 MergePasswordForms(&keychain_matches, &db_form_container, &merged_forms); |
| 461 if (db_form_container.empty()) { | 508 if (db_form_container.empty()) { |
| 462 i = database_forms->erase(i); | 509 i = database_forms->erase(i); |
| 463 } else { | 510 } else { |
| 464 ++i; | 511 ++i; |
| 465 } | 512 } |
| 466 STLDeleteElements(&keychain_matches); | 513 STLDeleteElements(&keychain_matches); |
| 467 } | 514 } |
| 515 | |
| 516 // Clean up temporary PasswordForms and SecKeychainItemRefs. | |
| 517 STLDeleteContainerPairSecondPointers(item_form_pairs.begin(), | |
| 518 item_form_pairs.end()); | |
| 519 for (std::vector<SecKeychainItemRef>::iterator i = keychain_items.begin(); | |
| 520 i != keychain_items.end(); ++i) { | |
| 521 keychain.Free(*i); | |
| 522 } | |
| 468 return merged_forms; | 523 return merged_forms; |
| 469 } | 524 } |
| 470 | 525 |
| 471 class Thread : public base::Thread { | 526 class Thread : public base::Thread { |
| 472 public: | 527 public: |
| 473 Thread(const char* name) : base::Thread(name) {} | 528 Thread(const char* name) : base::Thread(name) {} |
| 474 virtual ~Thread() { | 529 virtual ~Thread() { |
| 475 base::debug::SetCrashKeyToStackTrace( | 530 base::debug::SetCrashKeyToStackTrace( |
| 476 crash_keys::mac::kPasswordThreadDtorTrace, base::debug::StackTrace()); | 531 crash_keys::mac::kPasswordThreadDtorTrace, base::debug::StackTrace()); |
| 477 } | 532 } |
| (...skipping 11 matching lines...) Expand all Loading... | |
| 489 std::vector<PasswordForm*> | 544 std::vector<PasswordForm*> |
| 490 MacKeychainPasswordFormAdapter::PasswordsFillingForm( | 545 MacKeychainPasswordFormAdapter::PasswordsFillingForm( |
| 491 const PasswordForm& query_form) { | 546 const PasswordForm& query_form) { |
| 492 std::vector<SecKeychainItemRef> keychain_items = | 547 std::vector<SecKeychainItemRef> keychain_items = |
| 493 MatchingKeychainItems(query_form.signon_realm, query_form.scheme, | 548 MatchingKeychainItems(query_form.signon_realm, query_form.scheme, |
| 494 NULL, NULL); | 549 NULL, NULL); |
| 495 | 550 |
| 496 return ConvertKeychainItemsToForms(&keychain_items); | 551 return ConvertKeychainItemsToForms(&keychain_items); |
| 497 } | 552 } |
| 498 | 553 |
| 554 bool MacKeychainPasswordFormAdapter::FormIsValidAndMatchesOtherForm( | |
| 555 const PasswordForm& query_form, | |
| 556 const PasswordForm& other_form) { | |
| 557 std::string server; | |
| 558 std::string security_domain; | |
| 559 int port; | |
| 560 bool is_secure; | |
| 561 if (!ExtractSignonRealmComponents(query_form.signon_realm, &server, &port, | |
| 562 &is_secure, &security_domain)) { | |
| 563 return false; | |
| 564 } | |
| 565 return internal_keychain_helpers::FormsMatchForMerge(query_form, other_form); | |
| 566 } | |
| 567 | |
| 499 std::vector<PasswordForm*> | 568 std::vector<PasswordForm*> |
| 500 MacKeychainPasswordFormAdapter::PasswordsMergeableWithForm( | 569 MacKeychainPasswordFormAdapter::ExtractPasswordsMergeableWithForm( |
|
stuartmorgan
2013/09/30 22:39:12
AFAICT this no longer operates on the keychain in
Raghu Simha
2013/10/02 02:09:50
We reference the keychain in line 580, while calli
| |
| 570 const std::vector<ItemFormPair>& item_form_pairs, | |
| 501 const PasswordForm& query_form) { | 571 const PasswordForm& query_form) { |
| 502 std::string username = UTF16ToUTF8(query_form.username_value); | 572 std::vector<PasswordForm*> matches; |
| 503 std::vector<SecKeychainItemRef> keychain_items = | 573 for (std::vector<ItemFormPair>::const_iterator i = item_form_pairs.begin(); |
| 504 MatchingKeychainItems(query_form.signon_realm, query_form.scheme, | 574 i != item_form_pairs.end(); ++i) { |
| 505 NULL, username.c_str()); | 575 if (FormIsValidAndMatchesOtherForm(query_form, *(i->second))) { |
| 506 | 576 // Create a new object, since the caller is responsible for deleting the |
| 507 return ConvertKeychainItemsToForms(&keychain_items); | 577 // returned forms. |
|
stuartmorgan
2013/09/30 22:39:12
Feel free to use ScopedVector anywhere it makes li
Raghu Simha
2013/10/02 02:09:50
I did consider using a ScopedVector here, but ende
| |
| 578 PasswordForm* form_with_password = new PasswordForm(); | |
| 579 internal_keychain_helpers::FillPasswordFormFromKeychainItem( | |
| 580 *keychain_, | |
| 581 *(i->first), | |
| 582 form_with_password, | |
| 583 true); // Load password attributes and data. | |
| 584 matches.push_back(form_with_password); | |
| 585 } | |
| 586 } | |
| 587 return matches; | |
| 508 } | 588 } |
| 509 | 589 |
| 510 PasswordForm* MacKeychainPasswordFormAdapter::PasswordExactlyMatchingForm( | 590 PasswordForm* MacKeychainPasswordFormAdapter::PasswordExactlyMatchingForm( |
| 511 const PasswordForm& query_form) { | 591 const PasswordForm& query_form) { |
| 512 SecKeychainItemRef keychain_item = KeychainItemForForm(query_form); | 592 SecKeychainItemRef keychain_item = KeychainItemForForm(query_form); |
| 513 if (keychain_item) { | 593 if (keychain_item) { |
| 514 PasswordForm* form = new PasswordForm(); | 594 PasswordForm* form = new PasswordForm(); |
| 515 internal_keychain_helpers::FillPasswordFormFromKeychainItem(*keychain_, | 595 internal_keychain_helpers::FillPasswordFormFromKeychainItem(*keychain_, |
| 516 keychain_item, | 596 keychain_item, |
| 517 form); | 597 form, |
| 598 true); | |
| 518 keychain_->Free(keychain_item); | 599 keychain_->Free(keychain_item); |
| 519 return form; | 600 return form; |
| 520 } | 601 } |
| 521 return NULL; | 602 return NULL; |
| 522 } | 603 } |
| 523 | 604 |
| 524 bool MacKeychainPasswordFormAdapter::HasPasswordsMergeableWithForm( | 605 bool MacKeychainPasswordFormAdapter::HasPasswordsMergeableWithForm( |
| 525 const PasswordForm& query_form) { | 606 const PasswordForm& query_form) { |
| 526 std::string username = UTF16ToUTF8(query_form.username_value); | 607 std::string username = UTF16ToUTF8(query_form.username_value); |
| 527 std::vector<SecKeychainItemRef> matches = | 608 std::vector<SecKeychainItemRef> matches = |
| 528 MatchingKeychainItems(query_form.signon_realm, query_form.scheme, | 609 MatchingKeychainItems(query_form.signon_realm, query_form.scheme, |
| 529 NULL, username.c_str()); | 610 NULL, username.c_str()); |
| 530 for (std::vector<SecKeychainItemRef>::iterator i = matches.begin(); | 611 for (std::vector<SecKeychainItemRef>::iterator i = matches.begin(); |
| 531 i != matches.end(); ++i) { | 612 i != matches.end(); ++i) { |
| 532 keychain_->Free(*i); | 613 keychain_->Free(*i); |
| 533 } | 614 } |
| 534 | 615 |
| 535 return !matches.empty(); | 616 return !matches.empty(); |
| 536 } | 617 } |
| 537 | 618 |
| 538 std::vector<PasswordForm*> | 619 std::vector<SecKeychainItemRef> |
| 539 MacKeychainPasswordFormAdapter::GetAllPasswordFormPasswords() { | 620 MacKeychainPasswordFormAdapter::GetAllPasswordFormKeychainItems() { |
| 540 SecAuthenticationType supported_auth_types[] = { | 621 SecAuthenticationType supported_auth_types[] = { |
| 541 kSecAuthenticationTypeHTMLForm, | 622 kSecAuthenticationTypeHTMLForm, |
| 542 kSecAuthenticationTypeHTTPBasic, | 623 kSecAuthenticationTypeHTTPBasic, |
| 543 kSecAuthenticationTypeHTTPDigest, | 624 kSecAuthenticationTypeHTTPDigest, |
| 544 }; | 625 }; |
| 545 | 626 |
| 546 std::vector<SecKeychainItemRef> matches; | 627 std::vector<SecKeychainItemRef> matches; |
| 547 for (unsigned int i = 0; i < arraysize(supported_auth_types); ++i) { | 628 for (unsigned int i = 0; i < arraysize(supported_auth_types); ++i) { |
| 548 KeychainSearch keychain_search(*keychain_); | 629 KeychainSearch keychain_search(*keychain_); |
| 549 keychain_search.Init(NULL, 0, kSecProtocolTypeAny, supported_auth_types[i], | 630 keychain_search.Init(NULL, 0, kSecProtocolTypeAny, supported_auth_types[i], |
| 550 NULL, NULL, NULL, CreatorCodeForSearch()); | 631 NULL, NULL, NULL, CreatorCodeForSearch()); |
| 551 keychain_search.FindMatchingItems(&matches); | 632 keychain_search.FindMatchingItems(&matches); |
| 552 } | 633 } |
| 634 return matches; | |
| 635 } | |
| 553 | 636 |
| 554 return ConvertKeychainItemsToForms(&matches); | 637 std::vector<PasswordForm*> |
| 638 MacKeychainPasswordFormAdapter::GetAllPasswordFormPasswords() { | |
| 639 std::vector<SecKeychainItemRef> items = GetAllPasswordFormKeychainItems(); | |
| 640 return ConvertKeychainItemsToForms(&items); | |
| 555 } | 641 } |
| 556 | 642 |
| 557 bool MacKeychainPasswordFormAdapter::AddPassword(const PasswordForm& form) { | 643 bool MacKeychainPasswordFormAdapter::AddPassword(const PasswordForm& form) { |
| 558 // We should never be trying to store a blacklist in the keychain. | 644 // We should never be trying to store a blacklist in the keychain. |
| 559 DCHECK(!form.blacklisted_by_user); | 645 DCHECK(!form.blacklisted_by_user); |
| 560 | 646 |
| 561 std::string server; | 647 std::string server; |
| 562 std::string security_domain; | 648 std::string security_domain; |
| 563 int port; | 649 int port; |
| 564 bool is_secure; | 650 bool is_secure; |
| (...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 612 finds_only_owned_ = finds_only_owned; | 698 finds_only_owned_ = finds_only_owned; |
| 613 } | 699 } |
| 614 | 700 |
| 615 std::vector<PasswordForm*> | 701 std::vector<PasswordForm*> |
| 616 MacKeychainPasswordFormAdapter::ConvertKeychainItemsToForms( | 702 MacKeychainPasswordFormAdapter::ConvertKeychainItemsToForms( |
| 617 std::vector<SecKeychainItemRef>* items) { | 703 std::vector<SecKeychainItemRef>* items) { |
| 618 std::vector<PasswordForm*> keychain_forms; | 704 std::vector<PasswordForm*> keychain_forms; |
| 619 for (std::vector<SecKeychainItemRef>::const_iterator i = items->begin(); | 705 for (std::vector<SecKeychainItemRef>::const_iterator i = items->begin(); |
| 620 i != items->end(); ++i) { | 706 i != items->end(); ++i) { |
| 621 PasswordForm* form = new PasswordForm(); | 707 PasswordForm* form = new PasswordForm(); |
| 622 if (internal_keychain_helpers::FillPasswordFormFromKeychainItem(*keychain_, | 708 if (internal_keychain_helpers::FillPasswordFormFromKeychainItem( |
| 623 *i, form)) { | 709 *keychain_, *i, form, true)) { |
| 624 keychain_forms.push_back(form); | 710 keychain_forms.push_back(form); |
| 625 } | 711 } |
| 626 keychain_->Free(*i); | 712 keychain_->Free(*i); |
| 627 } | 713 } |
| 628 items->clear(); | 714 items->clear(); |
| 629 return keychain_forms; | 715 return keychain_forms; |
| 630 } | 716 } |
| 631 | 717 |
| 632 SecKeychainItemRef MacKeychainPasswordFormAdapter::KeychainItemForForm( | 718 SecKeychainItemRef MacKeychainPasswordFormAdapter::KeychainItemForForm( |
| 633 const PasswordForm& form) { | 719 const PasswordForm& form) { |
| (...skipping 397 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1031 owned_keychain_adapter.SetFindsOnlyOwnedItems(true); | 1117 owned_keychain_adapter.SetFindsOnlyOwnedItems(true); |
| 1032 for (std::vector<PasswordForm*>::const_iterator i = forms.begin(); | 1118 for (std::vector<PasswordForm*>::const_iterator i = forms.begin(); |
| 1033 i != forms.end(); ++i) { | 1119 i != forms.end(); ++i) { |
| 1034 owned_keychain_adapter.RemovePassword(**i); | 1120 owned_keychain_adapter.RemovePassword(**i); |
| 1035 } | 1121 } |
| 1036 } | 1122 } |
| 1037 | 1123 |
| 1038 void PasswordStoreMac::CreateNotificationService() { | 1124 void PasswordStoreMac::CreateNotificationService() { |
| 1039 notification_service_.reset(content::NotificationService::Create()); | 1125 notification_service_.reset(content::NotificationService::Create()); |
| 1040 } | 1126 } |
| OLD | NEW |