Home | History | Annotate | Download | only in http
      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
      3 // found in the LICENSE file.
      4 
      5 #include <string>
      6 
      7 #include "base/string16.h"
      8 #include "base/string_util.h"
      9 #include "base/stringprintf.h"
     10 #include "base/utf_string_conversions.h"
     11 #include "net/base/net_errors.h"
     12 #include "net/http/http_auth_cache.h"
     13 #include "net/http/http_auth_handler.h"
     14 #include "testing/gtest/include/gtest/gtest.h"
     15 
     16 namespace net {
     17 
     18 namespace {
     19 
     20 class MockAuthHandler : public HttpAuthHandler {
     21  public:
     22   MockAuthHandler(HttpAuth::Scheme scheme,
     23                   const std::string& realm,
     24                   HttpAuth::Target target) {
     25     // Can't use initializer list since these are members of the base class.
     26     auth_scheme_ = scheme;
     27     realm_ = realm;
     28     score_ = 1;
     29     target_ = target;
     30     properties_ = 0;
     31   }
     32 
     33   virtual HttpAuth::AuthorizationResult HandleAnotherChallenge(
     34       HttpAuth::ChallengeTokenizer* challenge) {
     35     return HttpAuth::AUTHORIZATION_RESULT_REJECT;
     36   }
     37 
     38  protected:
     39   virtual bool Init(HttpAuth::ChallengeTokenizer* challenge) {
     40     return false;  // Unused.
     41   }
     42 
     43   virtual int GenerateAuthTokenImpl(const string16*,
     44                                     const string16*,
     45                                     const HttpRequestInfo*,
     46                                     CompletionCallback* callback,
     47                                     std::string* auth_token) {
     48     *auth_token = "mock-credentials";
     49     return OK;
     50   }
     51 
     52 
     53  private:
     54   ~MockAuthHandler() {}
     55 };
     56 
     57 const char* kRealm1 = "Realm1";
     58 const char* kRealm2 = "Realm2";
     59 const char* kRealm3 = "Realm3";
     60 const char* kRealm4 = "Realm4";
     61 const char* kRealm5 = "Realm5";
     62 const string16 k123(ASCIIToUTF16("123"));
     63 const string16 k1234(ASCIIToUTF16("1234"));
     64 const string16 kAdmin(ASCIIToUTF16("admin"));
     65 const string16 kAlice(ASCIIToUTF16("alice"));
     66 const string16 kAlice2(ASCIIToUTF16("alice2"));
     67 const string16 kPassword(ASCIIToUTF16("password"));
     68 const string16 kRoot(ASCIIToUTF16("root"));
     69 const string16 kUsername(ASCIIToUTF16("username"));
     70 const string16 kWileCoyote(ASCIIToUTF16("wilecoyote"));
     71 
     72 }  // namespace
     73 
     74 // Test adding and looking-up cache entries (both by realm and by path).
     75 TEST(HttpAuthCacheTest, Basic) {
     76   GURL origin("http://www.google.com");
     77   HttpAuthCache cache;
     78   HttpAuthCache::Entry* entry;
     79 
     80   // Add cache entries for 4 realms: "Realm1", "Realm2", "Realm3" and
     81   // "Realm4"
     82 
     83   scoped_ptr<HttpAuthHandler> realm1_handler(
     84       new MockAuthHandler(HttpAuth::AUTH_SCHEME_BASIC,
     85                           kRealm1,
     86                           HttpAuth::AUTH_SERVER));
     87   cache.Add(origin, realm1_handler->realm(), realm1_handler->auth_scheme(),
     88             "Basic realm=Realm1", ASCIIToUTF16("realm1-user"),
     89             ASCIIToUTF16("realm1-password"), "/foo/bar/index.html");
     90 
     91   scoped_ptr<HttpAuthHandler> realm2_handler(
     92       new MockAuthHandler(HttpAuth::AUTH_SCHEME_BASIC,
     93                           kRealm2,
     94                           HttpAuth::AUTH_SERVER));
     95   cache.Add(origin, realm2_handler->realm(), realm2_handler->auth_scheme(),
     96             "Basic realm=Realm2", ASCIIToUTF16("realm2-user"),
     97             ASCIIToUTF16("realm2-password"), "/foo2/index.html");
     98 
     99   scoped_ptr<HttpAuthHandler> realm3_basic_handler(
    100       new MockAuthHandler(HttpAuth::AUTH_SCHEME_BASIC,
    101                           kRealm3,
    102                           HttpAuth::AUTH_PROXY));
    103   cache.Add(origin, realm3_basic_handler->realm(),
    104             realm3_basic_handler->auth_scheme(), "Basic realm=Realm3",
    105             ASCIIToUTF16("realm3-basic-user"),
    106             ASCIIToUTF16("realm3-basic-password"), "");
    107 
    108   scoped_ptr<HttpAuthHandler> realm3_digest_handler(
    109       new MockAuthHandler(HttpAuth::AUTH_SCHEME_DIGEST,
    110                           kRealm3,
    111                           HttpAuth::AUTH_PROXY));
    112   cache.Add(origin, realm3_digest_handler->realm(),
    113             realm3_digest_handler->auth_scheme(), "Digest realm=Realm3",
    114             ASCIIToUTF16("realm3-digest-user"),
    115             ASCIIToUTF16("realm3-digest-password"), "/baz/index.html");
    116 
    117   scoped_ptr<HttpAuthHandler> realm4_basic_handler(
    118       new MockAuthHandler(HttpAuth::AUTH_SCHEME_BASIC,
    119                           kRealm4,
    120                           HttpAuth::AUTH_SERVER));
    121   cache.Add(origin, realm4_basic_handler->realm(),
    122             realm4_basic_handler->auth_scheme(), "Basic realm=Realm4",
    123             ASCIIToUTF16("realm4-basic-user"),
    124             ASCIIToUTF16("realm4-basic-password"), "/");
    125 
    126   // There is no Realm5
    127   entry = cache.Lookup(origin, kRealm5, HttpAuth::AUTH_SCHEME_BASIC);
    128   EXPECT_TRUE(NULL == entry);
    129 
    130   // While Realm3 does exist, the origin scheme is wrong.
    131   entry = cache.Lookup(GURL("https://www.google.com"), kRealm3,
    132                        HttpAuth::AUTH_SCHEME_BASIC);
    133   EXPECT_TRUE(NULL == entry);
    134 
    135   // Realm, origin scheme ok, authentication scheme wrong
    136   entry = cache.Lookup
    137       (GURL("http://www.google.com"), kRealm1, HttpAuth::AUTH_SCHEME_DIGEST);
    138   EXPECT_TRUE(NULL == entry);
    139 
    140   // Valid lookup by origin, realm, scheme.
    141   entry = cache.Lookup(
    142       GURL("http://www.google.com:80"), kRealm3, HttpAuth::AUTH_SCHEME_BASIC);
    143   ASSERT_FALSE(NULL == entry);
    144   EXPECT_EQ(HttpAuth::AUTH_SCHEME_BASIC, entry->scheme());
    145   EXPECT_EQ(kRealm3, entry->realm());
    146   EXPECT_EQ("Basic realm=Realm3", entry->auth_challenge());
    147   EXPECT_EQ(ASCIIToUTF16("realm3-basic-user"), entry->username());
    148   EXPECT_EQ(ASCIIToUTF16("realm3-basic-password"), entry->password());
    149 
    150   // Valid lookup by origin, realm, scheme when there's a duplicate
    151   // origin, realm in the cache
    152   entry = cache.Lookup(
    153       GURL("http://www.google.com:80"), kRealm3, HttpAuth::AUTH_SCHEME_DIGEST);
    154   ASSERT_FALSE(NULL == entry);
    155   EXPECT_EQ(HttpAuth::AUTH_SCHEME_DIGEST, entry->scheme());
    156   EXPECT_EQ(kRealm3, entry->realm());
    157   EXPECT_EQ("Digest realm=Realm3", entry->auth_challenge());
    158   EXPECT_EQ(ASCIIToUTF16("realm3-digest-user"), entry->username());
    159   EXPECT_EQ(ASCIIToUTF16("realm3-digest-password"), entry->password());
    160 
    161   // Valid lookup by realm.
    162   entry = cache.Lookup(origin, kRealm2, HttpAuth::AUTH_SCHEME_BASIC);
    163   ASSERT_FALSE(NULL == entry);
    164   EXPECT_EQ(HttpAuth::AUTH_SCHEME_BASIC, entry->scheme());
    165   EXPECT_EQ(kRealm2, entry->realm());
    166   EXPECT_EQ("Basic realm=Realm2", entry->auth_challenge());
    167   EXPECT_EQ(ASCIIToUTF16("realm2-user"), entry->username());
    168   EXPECT_EQ(ASCIIToUTF16("realm2-password"), entry->password());
    169 
    170   // Check that subpaths are recognized.
    171   HttpAuthCache::Entry* realm2_entry = cache.Lookup(
    172       origin, kRealm2, HttpAuth::AUTH_SCHEME_BASIC);
    173   HttpAuthCache::Entry* realm4_entry = cache.Lookup(
    174       origin, kRealm4, HttpAuth::AUTH_SCHEME_BASIC);
    175   EXPECT_FALSE(NULL == realm2_entry);
    176   EXPECT_FALSE(NULL == realm4_entry);
    177   // Realm4 applies to '/' and Realm2 applies to '/foo2/'.
    178   // LookupByPath() should return the closest enclosing path.
    179   // Positive tests:
    180   entry = cache.LookupByPath(origin, "/foo2/index.html");
    181   EXPECT_TRUE(realm2_entry == entry);
    182   entry = cache.LookupByPath(origin, "/foo2/foobar.html");
    183   EXPECT_TRUE(realm2_entry == entry);
    184   entry = cache.LookupByPath(origin, "/foo2/bar/index.html");
    185   EXPECT_TRUE(realm2_entry == entry);
    186   entry = cache.LookupByPath(origin, "/foo2/");
    187   EXPECT_TRUE(realm2_entry == entry);
    188   entry = cache.LookupByPath(origin, "/foo2");
    189   EXPECT_TRUE(realm4_entry == entry);
    190   entry = cache.LookupByPath(origin, "/");
    191   EXPECT_TRUE(realm4_entry == entry);
    192 
    193   // Negative tests:
    194   entry = cache.LookupByPath(origin, "/foo3/index.html");
    195   EXPECT_FALSE(realm2_entry == entry);
    196   entry = cache.LookupByPath(origin, "");
    197   EXPECT_FALSE(realm2_entry == entry);
    198 
    199   // Confirm we find the same realm, different auth scheme by path lookup
    200   HttpAuthCache::Entry* realm3_digest_entry =
    201       cache.Lookup(origin, kRealm3, HttpAuth::AUTH_SCHEME_DIGEST);
    202   EXPECT_FALSE(NULL == realm3_digest_entry);
    203   entry = cache.LookupByPath(origin, "/baz/index.html");
    204   EXPECT_TRUE(realm3_digest_entry == entry);
    205   entry = cache.LookupByPath(origin, "/baz/");
    206   EXPECT_TRUE(realm3_digest_entry == entry);
    207   entry = cache.LookupByPath(origin, "/baz");
    208   EXPECT_FALSE(realm3_digest_entry == entry);
    209 
    210   // Confirm we find the same realm, different auth scheme by path lookup
    211   HttpAuthCache::Entry* realm3DigestEntry =
    212       cache.Lookup(origin, kRealm3, HttpAuth::AUTH_SCHEME_DIGEST);
    213   EXPECT_FALSE(NULL == realm3DigestEntry);
    214   entry = cache.LookupByPath(origin, "/baz/index.html");
    215   EXPECT_TRUE(realm3DigestEntry == entry);
    216   entry = cache.LookupByPath(origin, "/baz/");
    217   EXPECT_TRUE(realm3DigestEntry == entry);
    218   entry = cache.LookupByPath(origin, "/baz");
    219   EXPECT_FALSE(realm3DigestEntry == entry);
    220 
    221   // Lookup using empty path (may be used for proxy).
    222   entry = cache.LookupByPath(origin, "");
    223   EXPECT_FALSE(NULL == entry);
    224   EXPECT_EQ(HttpAuth::AUTH_SCHEME_BASIC, entry->scheme());
    225   EXPECT_EQ(kRealm3, entry->realm());
    226 }
    227 
    228 TEST(HttpAuthCacheTest, AddPath) {
    229   HttpAuthCache::Entry entry;
    230 
    231   // All of these paths have a common root /1/2/2/4/5/
    232   entry.AddPath("/1/2/3/4/5/x.txt");
    233   entry.AddPath("/1/2/3/4/5/y.txt");
    234   entry.AddPath("/1/2/3/4/5/z.txt");
    235 
    236   EXPECT_EQ(1U, entry.paths_.size());
    237   EXPECT_EQ("/1/2/3/4/5/", entry.paths_.front());
    238 
    239   // Add a new entry (not a subpath).
    240   entry.AddPath("/1/XXX/q");
    241   EXPECT_EQ(2U, entry.paths_.size());
    242   EXPECT_EQ("/1/XXX/", entry.paths_.front());
    243   EXPECT_EQ("/1/2/3/4/5/", entry.paths_.back());
    244 
    245   // Add containing paths of /1/2/3/4/5/ -- should swallow up the deeper paths.
    246   entry.AddPath("/1/2/3/4/x.txt");
    247   EXPECT_EQ(2U, entry.paths_.size());
    248   EXPECT_EQ("/1/2/3/4/", entry.paths_.front());
    249   EXPECT_EQ("/1/XXX/", entry.paths_.back());
    250   entry.AddPath("/1/2/3/x");
    251   EXPECT_EQ(2U, entry.paths_.size());
    252   EXPECT_EQ("/1/2/3/", entry.paths_.front());
    253   EXPECT_EQ("/1/XXX/", entry.paths_.back());
    254 
    255   entry.AddPath("/index.html");
    256   EXPECT_EQ(1U, entry.paths_.size());
    257   EXPECT_EQ("/", entry.paths_.front());
    258 }
    259 
    260 // Calling Add when the realm entry already exists, should append that
    261 // path.
    262 TEST(HttpAuthCacheTest, AddToExistingEntry) {
    263   HttpAuthCache cache;
    264   GURL origin("http://www.foobar.com:70");
    265   const std::string auth_challenge = "Basic realm=MyRealm";
    266 
    267   scoped_ptr<HttpAuthHandler> handler(
    268       new MockAuthHandler(
    269           HttpAuth::AUTH_SCHEME_BASIC, "MyRealm", HttpAuth::AUTH_SERVER));
    270   HttpAuthCache::Entry* orig_entry = cache.Add(
    271       origin, handler->realm(), handler->auth_scheme(), auth_challenge,
    272       ASCIIToUTF16("user1"), ASCIIToUTF16("password1"), "/x/y/z/");
    273   cache.Add(origin, handler->realm(), handler->auth_scheme(), auth_challenge,
    274             ASCIIToUTF16("user2"), ASCIIToUTF16("password2"), "/z/y/x/");
    275   cache.Add(origin, handler->realm(), handler->auth_scheme(), auth_challenge,
    276             ASCIIToUTF16("user3"), ASCIIToUTF16("password3"), "/z/y");
    277 
    278   HttpAuthCache::Entry* entry = cache.Lookup(
    279       origin, "MyRealm", HttpAuth::AUTH_SCHEME_BASIC);
    280 
    281   EXPECT_TRUE(entry == orig_entry);
    282   EXPECT_EQ(ASCIIToUTF16("user3"), entry->username());
    283   EXPECT_EQ(ASCIIToUTF16("password3"), entry->password());
    284 
    285   EXPECT_EQ(2U, entry->paths_.size());
    286   EXPECT_EQ("/z/", entry->paths_.front());
    287   EXPECT_EQ("/x/y/z/", entry->paths_.back());
    288 }
    289 
    290 TEST(HttpAuthCacheTest, Remove) {
    291   GURL origin("http://foobar2.com");
    292 
    293   scoped_ptr<HttpAuthHandler> realm1_handler(
    294       new MockAuthHandler(
    295           HttpAuth::AUTH_SCHEME_BASIC, kRealm1, HttpAuth::AUTH_SERVER));
    296 
    297   scoped_ptr<HttpAuthHandler> realm2_handler(
    298       new MockAuthHandler(
    299           HttpAuth::AUTH_SCHEME_BASIC, kRealm2, HttpAuth::AUTH_SERVER));
    300 
    301   scoped_ptr<HttpAuthHandler> realm3_basic_handler(
    302       new MockAuthHandler(
    303           HttpAuth::AUTH_SCHEME_BASIC, kRealm3, HttpAuth::AUTH_SERVER));
    304 
    305   scoped_ptr<HttpAuthHandler> realm3_digest_handler(
    306       new MockAuthHandler(
    307           HttpAuth::AUTH_SCHEME_DIGEST, kRealm3, HttpAuth::AUTH_SERVER));
    308 
    309   HttpAuthCache cache;
    310   cache.Add(origin, realm1_handler->realm(), realm1_handler->auth_scheme(),
    311             "basic realm=Realm1", kAlice, k123, "/");
    312   cache.Add(origin, realm2_handler->realm(), realm2_handler->auth_scheme(),
    313             "basic realm=Realm2", ASCIIToUTF16("bob"), ASCIIToUTF16("princess"),
    314             "/");
    315   cache.Add(origin, realm3_basic_handler->realm(),
    316             realm3_basic_handler->auth_scheme(), "basic realm=Realm3",
    317             kAdmin, kPassword, "/");
    318   cache.Add(origin, realm3_digest_handler->realm(),
    319             realm3_digest_handler->auth_scheme(), "digest realm=Realm3",
    320             kRoot, kWileCoyote, "/");
    321 
    322   // Fails, because there is no realm "Realm5".
    323   EXPECT_FALSE(cache.Remove(
    324       origin, kRealm5, HttpAuth::AUTH_SCHEME_BASIC, kAlice, k123));
    325 
    326   // Fails because the origin is wrong.
    327   EXPECT_FALSE(cache.Remove(GURL("http://foobar2.com:100"),
    328                             kRealm1,
    329                             HttpAuth::AUTH_SCHEME_BASIC,
    330                             kAlice,
    331                             k123));
    332 
    333   // Fails because the username is wrong.
    334   EXPECT_FALSE(cache.Remove(
    335       origin, kRealm1, HttpAuth::AUTH_SCHEME_BASIC, kAlice2, k123));
    336 
    337   // Fails because the password is wrong.
    338   EXPECT_FALSE(cache.Remove(
    339       origin, kRealm1, HttpAuth::AUTH_SCHEME_BASIC, kAlice, k1234));
    340 
    341   // Fails because the authentication type is wrong.
    342   EXPECT_FALSE(cache.Remove(
    343       origin, kRealm1, HttpAuth::AUTH_SCHEME_DIGEST, kAlice, k123));
    344 
    345   // Succeeds.
    346   EXPECT_TRUE(cache.Remove(
    347       origin, kRealm1, HttpAuth::AUTH_SCHEME_BASIC, kAlice, k123));
    348 
    349   // Fails because we just deleted the entry!
    350   EXPECT_FALSE(cache.Remove(
    351       origin, kRealm1, HttpAuth::AUTH_SCHEME_BASIC, kAlice, k123));
    352 
    353   // Succeed when there are two authentication types for the same origin,realm.
    354   EXPECT_TRUE(cache.Remove(
    355       origin, kRealm3, HttpAuth::AUTH_SCHEME_DIGEST, kRoot, kWileCoyote));
    356 
    357   // Succeed as above, but when entries were added in opposite order
    358   cache.Add(origin, realm3_digest_handler->realm(),
    359             realm3_digest_handler->auth_scheme(), "digest realm=Realm3",
    360             kRoot, kWileCoyote, "/");
    361   EXPECT_TRUE(cache.Remove(
    362       origin, kRealm3, HttpAuth::AUTH_SCHEME_BASIC, kAdmin, kPassword));
    363 
    364   // Make sure that removing one entry still leaves the other available for
    365   // lookup.
    366   HttpAuthCache::Entry* entry = cache.Lookup(
    367       origin, kRealm3, HttpAuth::AUTH_SCHEME_DIGEST);
    368   EXPECT_FALSE(NULL == entry);
    369 }
    370 
    371 TEST(HttpAuthCacheTest, UpdateStaleChallenge) {
    372   HttpAuthCache cache;
    373   GURL origin("http://foobar2.com");
    374   scoped_ptr<HttpAuthHandler> digest_handler(
    375       new MockAuthHandler(
    376           HttpAuth::AUTH_SCHEME_DIGEST, kRealm1, HttpAuth::AUTH_PROXY));
    377   HttpAuthCache::Entry* entry_pre = cache.Add(
    378       origin,
    379       digest_handler->realm(),
    380       digest_handler->auth_scheme(),
    381       "Digest realm=Realm1,"
    382       "nonce=\"s3MzvFhaBAA=4c520af5acd9d8d7ae26947529d18c8eae1e98f4\"",
    383       ASCIIToUTF16("realm-digest-user"),
    384       ASCIIToUTF16("realm-digest-password"),
    385       "/baz/index.html");
    386   ASSERT_TRUE(entry_pre != NULL);
    387 
    388   EXPECT_EQ(2, entry_pre->IncrementNonceCount());
    389   EXPECT_EQ(3, entry_pre->IncrementNonceCount());
    390   EXPECT_EQ(4, entry_pre->IncrementNonceCount());
    391 
    392   bool update_success = cache.UpdateStaleChallenge(
    393       origin,
    394       digest_handler->realm(),
    395       digest_handler->auth_scheme(),
    396       "Digest realm=Realm1,"
    397       "nonce=\"claGgoRXBAA=7583377687842fdb7b56ba0555d175baa0b800e3\","
    398       "stale=\"true\"");
    399   EXPECT_TRUE(update_success);
    400 
    401   // After the stale update, the entry should still exist in the cache and
    402   // the nonce count should be reset to 0.
    403   HttpAuthCache::Entry* entry_post = cache.Lookup(
    404       origin,
    405       digest_handler->realm(),
    406       digest_handler->auth_scheme());
    407   ASSERT_TRUE(entry_post != NULL);
    408   EXPECT_EQ(2, entry_post->IncrementNonceCount());
    409 
    410   // UpdateStaleChallenge will fail if an entry doesn't exist in the cache.
    411   bool update_failure = cache.UpdateStaleChallenge(
    412       origin,
    413       kRealm2,
    414       digest_handler->auth_scheme(),
    415       "Digest realm=Realm2,"
    416       "nonce=\"claGgoRXBAA=7583377687842fdb7b56ba0555d175baa0b800e3\","
    417       "stale=\"true\"");
    418   EXPECT_FALSE(update_failure);
    419 }
    420 
    421 // Test fixture class for eviction tests (contains helpers for bulk
    422 // insertion and existence testing).
    423 class HttpAuthCacheEvictionTest : public testing::Test {
    424  protected:
    425   HttpAuthCacheEvictionTest() : origin_("http://www.google.com") { }
    426 
    427   std::string GenerateRealm(int realm_i) {
    428     return base::StringPrintf("Realm %d", realm_i);
    429   }
    430 
    431   std::string GeneratePath(int realm_i, int path_i) {
    432     return base::StringPrintf("/%d/%d/x/y", realm_i, path_i);
    433   }
    434 
    435   void AddRealm(int realm_i) {
    436     AddPathToRealm(realm_i, 0);
    437   }
    438 
    439   void AddPathToRealm(int realm_i, int path_i) {
    440     cache_.Add(origin_, GenerateRealm(realm_i), HttpAuth::AUTH_SCHEME_BASIC, "",
    441                kUsername, kPassword, GeneratePath(realm_i, path_i));
    442   }
    443 
    444   void CheckRealmExistence(int realm_i, bool exists) {
    445     const HttpAuthCache::Entry* entry =
    446         cache_.Lookup(
    447             origin_, GenerateRealm(realm_i), HttpAuth::AUTH_SCHEME_BASIC);
    448     if (exists) {
    449       EXPECT_FALSE(entry == NULL);
    450       EXPECT_EQ(GenerateRealm(realm_i), entry->realm());
    451     } else {
    452       EXPECT_TRUE(entry == NULL);
    453     }
    454   }
    455 
    456   void CheckPathExistence(int realm_i, int path_i, bool exists) {
    457     const HttpAuthCache::Entry* entry =
    458         cache_.LookupByPath(origin_, GeneratePath(realm_i, path_i));
    459     if (exists) {
    460       EXPECT_FALSE(entry == NULL);
    461       EXPECT_EQ(GenerateRealm(realm_i), entry->realm());
    462     } else {
    463       EXPECT_TRUE(entry == NULL);
    464     }
    465   }
    466 
    467   GURL origin_;
    468   HttpAuthCache cache_;
    469 
    470   static const int kMaxPaths = HttpAuthCache::kMaxNumPathsPerRealmEntry;
    471   static const int kMaxRealms = HttpAuthCache::kMaxNumRealmEntries;
    472 };
    473 
    474 // Add the maxinim number of realm entries to the cache. Each of these entries
    475 // must still be retrievable. Next add three more entries -- since the cache is
    476 // full this causes FIFO eviction of the first three entries.
    477 TEST_F(HttpAuthCacheEvictionTest, RealmEntryEviction) {
    478   for (int i = 0; i < kMaxRealms; ++i)
    479     AddRealm(i);
    480 
    481   for (int i = 0; i < kMaxRealms; ++i)
    482     CheckRealmExistence(i, true);
    483 
    484   for (int i = 0; i < 3; ++i)
    485     AddRealm(i + kMaxRealms);
    486 
    487   for (int i = 0; i < 3; ++i)
    488     CheckRealmExistence(i, false);
    489 
    490   for (int i = 0; i < kMaxRealms; ++i)
    491     CheckRealmExistence(i + 3, true);
    492 }
    493 
    494 // Add the maximum number of paths to a single realm entry. Each of these
    495 // paths should be retrievable. Next add 3 more paths -- since the cache is
    496 // full this causes FIFO eviction of the first three paths.
    497 TEST_F(HttpAuthCacheEvictionTest, RealmPathEviction) {
    498   for (int i = 0; i < kMaxPaths; ++i)
    499     AddPathToRealm(0, i);
    500 
    501   for (int i = 1; i < kMaxRealms; ++i)
    502     AddRealm(i);
    503 
    504   for (int i = 0; i < 3; ++i)
    505     AddPathToRealm(0, i + kMaxPaths);
    506 
    507   for (int i = 0; i < 3; ++i)
    508     CheckPathExistence(0, i, false);
    509 
    510   for (int i = 0; i < kMaxPaths; ++i)
    511     CheckPathExistence(0, i + 3, true);
    512 
    513   for (int i = 0; i < kMaxRealms; ++i)
    514     CheckRealmExistence(i, true);
    515 }
    516 
    517 }  // namespace net
    518