| // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "net/base/host_cache.h" |
| |
| #include "base/logging.h" |
| #include "base/metrics/field_trial.h" |
| #include "base/metrics/histogram.h" |
| #include "base/string_number_conversions.h" |
| #include "net/base/net_errors.h" |
| |
| namespace net { |
| |
| //----------------------------------------------------------------------------- |
| |
| HostCache::Entry::Entry(int error, const AddressList& addrlist, |
| base::TimeDelta ttl) |
| : error(error), |
| addrlist(addrlist), |
| ttl(ttl) { |
| DCHECK(ttl >= base::TimeDelta()); |
| } |
| |
| HostCache::Entry::Entry(int error, const AddressList& addrlist) |
| : error(error), |
| addrlist(addrlist), |
| ttl(base::TimeDelta::FromSeconds(-1)) { |
| } |
| |
| HostCache::Entry::~Entry() { |
| } |
| |
| //----------------------------------------------------------------------------- |
| |
| HostCache::HostCache(size_t max_entries) |
| : entries_(max_entries) { |
| } |
| |
| HostCache::~HostCache() { |
| } |
| |
| const HostCache::Entry* HostCache::Lookup(const Key& key, |
| base::TimeTicks now) { |
| DCHECK(CalledOnValidThread()); |
| if (caching_is_disabled()) |
| return NULL; |
| |
| return entries_.Get(key, now); |
| } |
| |
| void HostCache::Set(const Key& key, |
| const Entry& entry, |
| base::TimeTicks now, |
| base::TimeDelta ttl) { |
| DCHECK(CalledOnValidThread()); |
| if (caching_is_disabled()) |
| return; |
| |
| entries_.Put(key, entry, now, now + ttl); |
| } |
| |
| void HostCache::clear() { |
| DCHECK(CalledOnValidThread()); |
| entries_.Clear(); |
| } |
| |
| size_t HostCache::size() const { |
| DCHECK(CalledOnValidThread()); |
| return entries_.size(); |
| } |
| |
| size_t HostCache::max_entries() const { |
| DCHECK(CalledOnValidThread()); |
| return entries_.max_entries(); |
| } |
| |
| // Note that this map may contain expired entries. |
| const HostCache::EntryMap& HostCache::entries() const { |
| DCHECK(CalledOnValidThread()); |
| return entries_; |
| } |
| |
| // static |
| scoped_ptr<HostCache> HostCache::CreateDefaultCache() { |
| // Cache capacity is determined by the field trial. |
| #if defined(ENABLE_BUILT_IN_DNS) |
| const size_t kDefaultMaxEntries = 1000; |
| #else |
| const size_t kDefaultMaxEntries = 100; |
| #endif |
| const size_t kSaneMaxEntries = 1 << 20; |
| size_t max_entries = 0; |
| base::StringToSizeT(base::FieldTrialList::FindFullName("HostCacheSize"), |
| &max_entries); |
| if ((max_entries == 0) || (max_entries > kSaneMaxEntries)) |
| max_entries = kDefaultMaxEntries; |
| return make_scoped_ptr(new HostCache(max_entries)); |
| } |
| |
| void HostCache::EvictionHandler::Handle( |
| const Key& key, |
| const Entry& entry, |
| const base::TimeTicks& expiration, |
| const base::TimeTicks& now, |
| bool on_get) const { |
| if (on_get) { |
| DCHECK(now >= expiration); |
| UMA_HISTOGRAM_CUSTOM_TIMES("DNS.CacheExpiredOnGet", now - expiration, |
| base::TimeDelta::FromSeconds(1), base::TimeDelta::FromDays(1), 100); |
| return; |
| } |
| if (expiration > now) { |
| UMA_HISTOGRAM_CUSTOM_TIMES("DNS.CacheEvicted", expiration - now, |
| base::TimeDelta::FromSeconds(1), base::TimeDelta::FromDays(1), 100); |
| } else { |
| UMA_HISTOGRAM_CUSTOM_TIMES("DNS.CacheExpired", now - expiration, |
| base::TimeDelta::FromSeconds(1), base::TimeDelta::FromDays(1), 100); |
| } |
| } |
| |
| } // namespace net |