| OLD | NEW |
| 1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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 // Portions of this code based on Mozilla: | 5 // Portions of this code based on Mozilla: |
| 6 // (netwerk/cookie/src/nsCookieService.cpp) | 6 // (netwerk/cookie/src/nsCookieService.cpp) |
| 7 /* ***** BEGIN LICENSE BLOCK ***** | 7 /* ***** BEGIN LICENSE BLOCK ***** |
| 8 * Version: MPL 1.1/GPL 2.0/LGPL 2.1 | 8 * Version: MPL 1.1/GPL 2.0/LGPL 2.1 |
| 9 * | 9 * |
| 10 * The contents of this file are subject to the Mozilla Public License Version | 10 * The contents of this file are subject to the Mozilla Public License Version |
| (...skipping 531 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 542 } | 542 } |
| 543 } | 543 } |
| 544 | 544 |
| 545 // The scheme didn't match any in our whitelist. | 545 // The scheme didn't match any in our whitelist. |
| 546 COOKIE_DLOG(WARNING) << "Unsupported cookie scheme: " << url.scheme(); | 546 COOKIE_DLOG(WARNING) << "Unsupported cookie scheme: " << url.scheme(); |
| 547 return false; | 547 return false; |
| 548 } | 548 } |
| 549 | 549 |
| 550 void CookieMonster::SetCookieableSchemes( | 550 void CookieMonster::SetCookieableSchemes( |
| 551 const char* schemes[], size_t num_schemes) { | 551 const char* schemes[], size_t num_schemes) { |
| 552 DCHECK(CalledOnValidThread()); | |
| 553 AutoLock autolock(lock_); | 552 AutoLock autolock(lock_); |
| 554 | 553 |
| 555 // Cookieable Schemes must be set before first use of function. | 554 // Cookieable Schemes must be set before first use of function. |
| 556 DCHECK(!initialized_); | 555 DCHECK(!initialized_); |
| 557 | 556 |
| 558 cookieable_schemes_.clear(); | 557 cookieable_schemes_.clear(); |
| 559 cookieable_schemes_.insert(cookieable_schemes_.end(), | 558 cookieable_schemes_.insert(cookieable_schemes_.end(), |
| 560 schemes, schemes + num_schemes); | 559 schemes, schemes + num_schemes); |
| 561 } | 560 } |
| 562 | 561 |
| 563 bool CookieMonster::SetCookieWithCreationTimeAndOptions( | 562 bool CookieMonster::SetCookieWithCreationTimeAndOptions( |
| 564 const GURL& url, | 563 const GURL& url, |
| 565 const std::string& cookie_line, | 564 const std::string& cookie_line, |
| 566 const Time& creation_time_or_null, | 565 const Time& creation_time_or_null, |
| 567 const CookieOptions& options) { | 566 const CookieOptions& options) { |
| 568 DCHECK(CalledOnValidThread()); | |
| 569 AutoLock autolock(lock_); | 567 AutoLock autolock(lock_); |
| 570 | 568 |
| 571 if (!HasCookieableScheme(url)) { | 569 if (!HasCookieableScheme(url)) { |
| 572 return false; | 570 return false; |
| 573 } | 571 } |
| 574 | 572 |
| 575 InitIfNecessary(); | 573 InitIfNecessary(); |
| 576 | 574 |
| 577 COOKIE_DLOG(INFO) << "SetCookie() line: " << cookie_line; | 575 COOKIE_DLOG(INFO) << "SetCookie() line: " << cookie_line; |
| 578 | 576 |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 614 COOKIE_DLOG(WARNING) << "Failed to allocate CanonicalCookie"; | 612 COOKIE_DLOG(WARNING) << "Failed to allocate CanonicalCookie"; |
| 615 return false; | 613 return false; |
| 616 } | 614 } |
| 617 return SetCanonicalCookie(&cc, cookie_domain, creation_time, options); | 615 return SetCanonicalCookie(&cc, cookie_domain, creation_time, options); |
| 618 } | 616 } |
| 619 | 617 |
| 620 bool CookieMonster::SetCookieWithDetails( | 618 bool CookieMonster::SetCookieWithDetails( |
| 621 const GURL& url, const std::string& name, const std::string& value, | 619 const GURL& url, const std::string& name, const std::string& value, |
| 622 const std::string& domain, const std::string& path, | 620 const std::string& domain, const std::string& path, |
| 623 const base::Time& expiration_time, bool secure, bool http_only) { | 621 const base::Time& expiration_time, bool secure, bool http_only) { |
| 624 DCHECK(CalledOnValidThread()); | |
| 625 | 622 |
| 626 // Expect a valid domain attribute with no illegal characters. | 623 // Expect a valid domain attribute with no illegal characters. |
| 627 std::string parsed_domain = ParsedCookie::ParseValueString(domain); | 624 std::string parsed_domain = ParsedCookie::ParseValueString(domain); |
| 628 if (parsed_domain != domain) | 625 if (parsed_domain != domain) |
| 629 return false; | 626 return false; |
| 630 std::string cookie_domain; | 627 std::string cookie_domain; |
| 631 if (!GetCookieDomainKeyWithString(url, parsed_domain, &cookie_domain)) | 628 if (!GetCookieDomainKeyWithString(url, parsed_domain, &cookie_domain)) |
| 632 return false; | 629 return false; |
| 633 | 630 |
| 634 AutoLock autolock(lock_); | 631 AutoLock autolock(lock_); |
| (...skipping 197 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 832 ++num_deleted; | 829 ++num_deleted; |
| 833 } else if (cookie_its) { | 830 } else if (cookie_its) { |
| 834 cookie_its->push_back(curit); | 831 cookie_its->push_back(curit); |
| 835 } | 832 } |
| 836 } | 833 } |
| 837 | 834 |
| 838 return num_deleted; | 835 return num_deleted; |
| 839 } | 836 } |
| 840 | 837 |
| 841 int CookieMonster::DeleteAll(bool sync_to_store) { | 838 int CookieMonster::DeleteAll(bool sync_to_store) { |
| 842 DCHECK(CalledOnValidThread()); | |
| 843 AutoLock autolock(lock_); | 839 AutoLock autolock(lock_); |
| 844 InitIfNecessary(); | 840 InitIfNecessary(); |
| 845 | 841 |
| 846 int num_deleted = 0; | 842 int num_deleted = 0; |
| 847 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { | 843 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { |
| 848 CookieMap::iterator curit = it; | 844 CookieMap::iterator curit = it; |
| 849 ++it; | 845 ++it; |
| 850 InternalDeleteCookie(curit, sync_to_store); | 846 InternalDeleteCookie(curit, sync_to_store); |
| 851 ++num_deleted; | 847 ++num_deleted; |
| 852 } | 848 } |
| 853 | 849 |
| 854 return num_deleted; | 850 return num_deleted; |
| 855 } | 851 } |
| 856 | 852 |
| 857 int CookieMonster::DeleteAllCreatedBetween(const Time& delete_begin, | 853 int CookieMonster::DeleteAllCreatedBetween(const Time& delete_begin, |
| 858 const Time& delete_end, | 854 const Time& delete_end, |
| 859 bool sync_to_store) { | 855 bool sync_to_store) { |
| 860 DCHECK(CalledOnValidThread()); | |
| 861 AutoLock autolock(lock_); | 856 AutoLock autolock(lock_); |
| 862 InitIfNecessary(); | 857 InitIfNecessary(); |
| 863 | 858 |
| 864 int num_deleted = 0; | 859 int num_deleted = 0; |
| 865 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { | 860 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { |
| 866 CookieMap::iterator curit = it; | 861 CookieMap::iterator curit = it; |
| 867 CanonicalCookie* cc = curit->second; | 862 CanonicalCookie* cc = curit->second; |
| 868 ++it; | 863 ++it; |
| 869 | 864 |
| 870 if (cc->CreationDate() >= delete_begin && | 865 if (cc->CreationDate() >= delete_begin && |
| 871 (delete_end.is_null() || cc->CreationDate() < delete_end)) { | 866 (delete_end.is_null() || cc->CreationDate() < delete_end)) { |
| 872 InternalDeleteCookie(curit, sync_to_store); | 867 InternalDeleteCookie(curit, sync_to_store); |
| 873 ++num_deleted; | 868 ++num_deleted; |
| 874 } | 869 } |
| 875 } | 870 } |
| 876 | 871 |
| 877 return num_deleted; | 872 return num_deleted; |
| 878 } | 873 } |
| 879 | 874 |
| 880 int CookieMonster::DeleteAllCreatedAfter(const Time& delete_begin, | 875 int CookieMonster::DeleteAllCreatedAfter(const Time& delete_begin, |
| 881 bool sync_to_store) { | 876 bool sync_to_store) { |
| 882 DCHECK(CalledOnValidThread()); | |
| 883 return DeleteAllCreatedBetween(delete_begin, Time(), sync_to_store); | 877 return DeleteAllCreatedBetween(delete_begin, Time(), sync_to_store); |
| 884 } | 878 } |
| 885 | 879 |
| 886 int CookieMonster::DeleteAllForURL(const GURL& url, | 880 int CookieMonster::DeleteAllForURL(const GURL& url, |
| 887 bool sync_to_store) { | 881 bool sync_to_store) { |
| 888 DCHECK(CalledOnValidThread()); | |
| 889 AutoLock autolock(lock_); | 882 AutoLock autolock(lock_); |
| 890 InitIfNecessary(); | 883 InitIfNecessary(); |
| 891 | 884 |
| 892 CookieList cookies = InternalGetAllCookiesForURL(url); | 885 CookieList cookies = InternalGetAllCookiesForURL(url); |
| 893 int num_deleted = 0; | 886 int num_deleted = 0; |
| 894 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { | 887 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { |
| 895 CookieMap::iterator curit = it; | 888 CookieMap::iterator curit = it; |
| 896 ++it; | 889 ++it; |
| 897 InternalDeleteCookie(curit, sync_to_store); | 890 InternalDeleteCookie(curit, sync_to_store); |
| 898 } | 891 } |
| 899 return num_deleted; | 892 return num_deleted; |
| 900 } | 893 } |
| 901 | 894 |
| 902 bool CookieMonster::DeleteCookie(const std::string& domain, | 895 bool CookieMonster::DeleteCookie(const std::string& domain, |
| 903 const CanonicalCookie& cookie, | 896 const CanonicalCookie& cookie, |
| 904 bool sync_to_store) { | 897 bool sync_to_store) { |
| 905 DCHECK(CalledOnValidThread()); | |
| 906 AutoLock autolock(lock_); | 898 AutoLock autolock(lock_); |
| 907 InitIfNecessary(); | 899 InitIfNecessary(); |
| 908 | 900 |
| 909 for (CookieMapItPair its = cookies_.equal_range(domain); | 901 for (CookieMapItPair its = cookies_.equal_range(domain); |
| 910 its.first != its.second; ++its.first) { | 902 its.first != its.second; ++its.first) { |
| 911 // The creation date acts as our unique index... | 903 // The creation date acts as our unique index... |
| 912 if (its.first->second->CreationDate() == cookie.CreationDate()) { | 904 if (its.first->second->CreationDate() == cookie.CreationDate()) { |
| 913 InternalDeleteCookie(its.first, sync_to_store); | 905 InternalDeleteCookie(its.first, sync_to_store); |
| 914 return true; | 906 return true; |
| 915 } | 907 } |
| 916 } | 908 } |
| 917 return false; | 909 return false; |
| 918 } | 910 } |
| 919 | 911 |
| 920 // Mozilla sorts on the path length (longest first), and then it | 912 // Mozilla sorts on the path length (longest first), and then it |
| 921 // sorts by creation time (oldest first). | 913 // sorts by creation time (oldest first). |
| 922 // The RFC says the sort order for the domain attribute is undefined. | 914 // The RFC says the sort order for the domain attribute is undefined. |
| 923 static bool CookieSorter(CookieMonster::CanonicalCookie* cc1, | 915 static bool CookieSorter(CookieMonster::CanonicalCookie* cc1, |
| 924 CookieMonster::CanonicalCookie* cc2) { | 916 CookieMonster::CanonicalCookie* cc2) { |
| 925 if (cc1->Path().length() == cc2->Path().length()) | 917 if (cc1->Path().length() == cc2->Path().length()) |
| 926 return cc1->CreationDate() < cc2->CreationDate(); | 918 return cc1->CreationDate() < cc2->CreationDate(); |
| 927 return cc1->Path().length() > cc2->Path().length(); | 919 return cc1->Path().length() > cc2->Path().length(); |
| 928 } | 920 } |
| 929 | 921 |
| 930 bool CookieMonster::SetCookieWithOptions(const GURL& url, | 922 bool CookieMonster::SetCookieWithOptions(const GURL& url, |
| 931 const std::string& cookie_line, | 923 const std::string& cookie_line, |
| 932 const CookieOptions& options) { | 924 const CookieOptions& options) { |
| 933 DCHECK(CalledOnValidThread()); | |
| 934 return SetCookieWithCreationTimeAndOptions(url, cookie_line, Time(), options); | 925 return SetCookieWithCreationTimeAndOptions(url, cookie_line, Time(), options); |
| 935 } | 926 } |
| 936 | 927 |
| 937 // Currently our cookie datastructure is based on Mozilla's approach. We have a | 928 // Currently our cookie datastructure is based on Mozilla's approach. We have a |
| 938 // hash keyed on the cookie's domain, and for any query we walk down the domain | 929 // hash keyed on the cookie's domain, and for any query we walk down the domain |
| 939 // components and probe for cookies until we reach the TLD, where we stop. | 930 // components and probe for cookies until we reach the TLD, where we stop. |
| 940 // For example, a.b.blah.com, we would probe | 931 // For example, a.b.blah.com, we would probe |
| 941 // - a.b.blah.com | 932 // - a.b.blah.com |
| 942 // - .a.b.blah.com (TODO should we check this first or second?) | 933 // - .a.b.blah.com (TODO should we check this first or second?) |
| 943 // - .b.blah.com | 934 // - .b.blah.com |
| 944 // - .blah.com | 935 // - .blah.com |
| 945 // There are some alternative datastructures we could try, like a | 936 // There are some alternative datastructures we could try, like a |
| 946 // search/prefix trie, where we reverse the hostname and query for all | 937 // search/prefix trie, where we reverse the hostname and query for all |
| 947 // keys that are a prefix of our hostname. I think the hash probing | 938 // keys that are a prefix of our hostname. I think the hash probing |
| 948 // should be fast and simple enough for now. | 939 // should be fast and simple enough for now. |
| 949 std::string CookieMonster::GetCookiesWithOptions(const GURL& url, | 940 std::string CookieMonster::GetCookiesWithOptions(const GURL& url, |
| 950 const CookieOptions& options) { | 941 const CookieOptions& options) { |
| 951 DCHECK(CalledOnValidThread()); | |
| 952 AutoLock autolock(lock_); | 942 AutoLock autolock(lock_); |
| 953 InitIfNecessary(); | 943 InitIfNecessary(); |
| 954 | 944 |
| 955 if (!HasCookieableScheme(url)) { | 945 if (!HasCookieableScheme(url)) { |
| 956 return std::string(); | 946 return std::string(); |
| 957 } | 947 } |
| 958 | 948 |
| 959 // Get the cookies for this host and its domain(s). | 949 // Get the cookies for this host and its domain(s). |
| 960 std::vector<CanonicalCookie*> cookies; | 950 std::vector<CanonicalCookie*> cookies; |
| 961 FindCookiesForHostAndDomain(url, options, &cookies); | 951 FindCookiesForHostAndDomain(url, options, &cookies); |
| (...skipping 12 matching lines...) Expand all Loading... |
| 974 cookie_line += (*it)->Value(); | 964 cookie_line += (*it)->Value(); |
| 975 } | 965 } |
| 976 | 966 |
| 977 COOKIE_DLOG(INFO) << "GetCookies() result: " << cookie_line; | 967 COOKIE_DLOG(INFO) << "GetCookies() result: " << cookie_line; |
| 978 | 968 |
| 979 return cookie_line; | 969 return cookie_line; |
| 980 } | 970 } |
| 981 | 971 |
| 982 void CookieMonster::DeleteCookie(const GURL& url, | 972 void CookieMonster::DeleteCookie(const GURL& url, |
| 983 const std::string& cookie_name) { | 973 const std::string& cookie_name) { |
| 984 DCHECK(CalledOnValidThread()); | |
| 985 AutoLock autolock(lock_); | 974 AutoLock autolock(lock_); |
| 986 InitIfNecessary(); | 975 InitIfNecessary(); |
| 987 | 976 |
| 988 if (!HasCookieableScheme(url)) | 977 if (!HasCookieableScheme(url)) |
| 989 return; | 978 return; |
| 990 | 979 |
| 991 CookieOptions options; | 980 CookieOptions options; |
| 992 options.set_include_httponly(); | 981 options.set_include_httponly(); |
| 993 // Get the cookies for this host and its domain(s). | 982 // Get the cookies for this host and its domain(s). |
| 994 std::vector<CanonicalCookie*> cookies; | 983 std::vector<CanonicalCookie*> cookies; |
| (...skipping 11 matching lines...) Expand all Loading... |
| 1006 | 995 |
| 1007 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { | 996 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end();) { |
| 1008 CookieMap::iterator curit = it; | 997 CookieMap::iterator curit = it; |
| 1009 ++it; | 998 ++it; |
| 1010 if (matching_cookies.find(curit->second) != matching_cookies.end()) | 999 if (matching_cookies.find(curit->second) != matching_cookies.end()) |
| 1011 InternalDeleteCookie(curit, true); | 1000 InternalDeleteCookie(curit, true); |
| 1012 } | 1001 } |
| 1013 } | 1002 } |
| 1014 | 1003 |
| 1015 CookieMonster::CookieList CookieMonster::GetAllCookies() { | 1004 CookieMonster::CookieList CookieMonster::GetAllCookies() { |
| 1016 DCHECK(CalledOnValidThread()); | |
| 1017 AutoLock autolock(lock_); | 1005 AutoLock autolock(lock_); |
| 1018 InitIfNecessary(); | 1006 InitIfNecessary(); |
| 1019 | 1007 |
| 1020 // This function is being called to scrape the cookie list for management UI | 1008 // This function is being called to scrape the cookie list for management UI |
| 1021 // or similar. We shouldn't show expired cookies in this list since it will | 1009 // or similar. We shouldn't show expired cookies in this list since it will |
| 1022 // just be confusing to users, and this function is called rarely enough (and | 1010 // just be confusing to users, and this function is called rarely enough (and |
| 1023 // is already slow enough) that it's OK to take the time to garbage collect | 1011 // is already slow enough) that it's OK to take the time to garbage collect |
| 1024 // the expired cookies now. | 1012 // the expired cookies now. |
| 1025 // | 1013 // |
| 1026 // Note that this does not prune cookies to be below our limits (if we've | 1014 // Note that this does not prune cookies to be below our limits (if we've |
| 1027 // exceeded them) the way that calling GarbageCollect() would. | 1015 // exceeded them) the way that calling GarbageCollect() would. |
| 1028 GarbageCollectExpired(Time::Now(), | 1016 GarbageCollectExpired(Time::Now(), |
| 1029 CookieMapItPair(cookies_.begin(), cookies_.end()), | 1017 CookieMapItPair(cookies_.begin(), cookies_.end()), |
| 1030 NULL); | 1018 NULL); |
| 1031 | 1019 |
| 1032 CookieList cookie_list; | 1020 CookieList cookie_list; |
| 1033 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end(); ++it) | 1021 for (CookieMap::iterator it = cookies_.begin(); it != cookies_.end(); ++it) |
| 1034 cookie_list.push_back(CookieListPair(it->first, *it->second)); | 1022 cookie_list.push_back(CookieListPair(it->first, *it->second)); |
| 1035 | 1023 |
| 1036 return cookie_list; | 1024 return cookie_list; |
| 1037 } | 1025 } |
| 1038 | 1026 |
| 1039 CookieMonster::CookieList CookieMonster::GetAllCookiesForURL(const GURL& url) { | 1027 CookieMonster::CookieList CookieMonster::GetAllCookiesForURL(const GURL& url) { |
| 1040 DCHECK(CalledOnValidThread()); | |
| 1041 AutoLock autolock(lock_); | 1028 AutoLock autolock(lock_); |
| 1042 InitIfNecessary(); | 1029 InitIfNecessary(); |
| 1043 | 1030 |
| 1044 return InternalGetAllCookiesForURL(url); | 1031 return InternalGetAllCookiesForURL(url); |
| 1045 } | 1032 } |
| 1046 | 1033 |
| 1047 void CookieMonster::FindCookiesForHostAndDomain( | 1034 void CookieMonster::FindCookiesForHostAndDomain( |
| 1048 const GURL& url, | 1035 const GURL& url, |
| 1049 const CookieOptions& options, | 1036 const CookieOptions& options, |
| 1050 std::vector<CanonicalCookie*>* cookies) { | 1037 std::vector<CanonicalCookie*>* cookies) { |
| (...skipping 477 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1528 return true; | 1515 return true; |
| 1529 } | 1516 } |
| 1530 | 1517 |
| 1531 std::string CookieMonster::CanonicalCookie::DebugString() const { | 1518 std::string CookieMonster::CanonicalCookie::DebugString() const { |
| 1532 return StringPrintf("name: %s value: %s path: %s creation: %" PRId64, | 1519 return StringPrintf("name: %s value: %s path: %s creation: %" PRId64, |
| 1533 name_.c_str(), value_.c_str(), path_.c_str(), | 1520 name_.c_str(), value_.c_str(), path_.c_str(), |
| 1534 static_cast<int64>(creation_date_.ToTimeT())); | 1521 static_cast<int64>(creation_date_.ToTimeT())); |
| 1535 } | 1522 } |
| 1536 | 1523 |
| 1537 } // namespace | 1524 } // namespace |
| OLD | NEW |