Commit 8ea75ec0 authored by fayang's avatar fayang Committed by Commit bot

Add QuicLRUCache.

Merge internal change 143035999.

BUG=

Review-Url: https://codereview.chromium.org/2603843002
Cr-Commit-Position: refs/heads/master@{#440866}
parent ab0dd766
......@@ -1212,6 +1212,7 @@
'quic/platform/api/quic_ip_address_family.h',
'quic/platform/api/quic_ip_address.cc',
'quic/platform/api/quic_ip_address.h',
'quic/platform/api/quic_lru_cache.h',
'quic/platform/api/quic_mutex.cc',
'quic/platform/api/quic_mutex.h',
'quic/platform/api/quic_reference_counted.h',
......@@ -1224,6 +1225,7 @@
'quic/platform/impl/quic_export_impl.h',
'quic/platform/impl/quic_ip_address_impl.cc',
'quic/platform/impl/quic_ip_address_impl.h',
'quic/platform/impl/quic_lru_cache_impl.h',
'quic/platform/impl/quic_mutex_impl.cc',
'quic/platform/impl/quic_mutex_impl.h',
'quic/platform/impl/quic_reference_counted_impl.h',
......@@ -1963,6 +1965,7 @@
'quic/core/quic_versions_test.cc',
'quic/core/quic_write_blocked_list_test.cc',
'quic/core/spdy_utils_test.cc',
'quic/platform/api/quic_lru_cache_test.cc',
'quic/platform/api/quic_reference_counted_test.cc',
'quic/platform/api/quic_str_cat_test.cc',
'quic/platform/impl/quic_chromium_clock_test.cc',
......
......@@ -76,13 +76,10 @@ const string* QuicCompressedCertsCache::GetCompressedCert(
uint64_t key = ComputeUncompressedCertsHash(uncompressed_certs);
auto cached_it = certs_cache_.Get(key);
if (cached_it != certs_cache_.end()) {
const CachedCerts& cached_value = cached_it->second;
if (cached_value.MatchesUncompressedCerts(uncompressed_certs)) {
return cached_value.compressed_cert();
}
CachedCerts* cached_value = certs_cache_.Lookup(key);
if (cached_value != nullptr &&
cached_value->MatchesUncompressedCerts(uncompressed_certs)) {
return cached_value->compressed_cert();
}
return nullptr;
}
......@@ -98,15 +95,17 @@ void QuicCompressedCertsCache::Insert(
uint64_t key = ComputeUncompressedCertsHash(uncompressed_certs);
// Insert one unit to the cache.
certs_cache_.Put(key, CachedCerts(uncompressed_certs, compressed_cert));
std::unique_ptr<CachedCerts> cached_certs(
new CachedCerts(uncompressed_certs, compressed_cert));
certs_cache_.Insert(key, std::move(cached_certs));
}
size_t QuicCompressedCertsCache::MaxSize() {
return certs_cache_.max_size();
return certs_cache_.MaxSize();
}
size_t QuicCompressedCertsCache::Size() {
return certs_cache_.size();
return certs_cache_.Size();
}
uint64_t QuicCompressedCertsCache::ComputeUncompressedCertsHash(
......
......@@ -8,9 +8,9 @@
#include <string>
#include <vector>
#include "base/containers/mru_cache.h"
#include "net/quic/core/crypto/proof_source.h"
#include "net/quic/platform/api/quic_export.h"
#include "net/quic/platform/api/quic_lru_cache.h"
namespace net {
......@@ -100,7 +100,7 @@ class QUIC_EXPORT_PRIVATE QuicCompressedCertsCache {
// Key is a unit64_t hash for UncompressedCerts. Stored associated value is
// CachedCerts which has both original uncompressed certs data and the
// compressed representation of the certs.
base::MRUCache<uint64_t, CachedCerts> certs_cache_;
QuicLRUCache<uint64_t, CachedCerts> certs_cache_;
};
} // namespace net
......
// Copyright (c) 2016 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.
#ifndef NET_QUIC_PLATFORM_API_QUIC_LRU_CACHE_H_
#define NET_QUIC_PLATFORM_API_QUIC_LRU_CACHE_H_
#include <memory>
#include "net/quic/platform/impl/quic_lru_cache_impl.h"
namespace net {
// A LRU cache that maps from type Key to Value* in QUIC.
// This cache CANNOT be shared by multiple threads (even with locks) because
// Value* returned by Lookup() can be invalid if the entry is evicted by other
// threads.
template <class K, class V>
class QuicLRUCache {
public:
explicit QuicLRUCache(int64_t total_units) : impl_(total_units) {}
// Inserts one unit of |key|, |value| pair to the cache. Cache takes ownership
// of inserted |value|.
void Insert(const K& key, std::unique_ptr<V> value) {
impl_.Insert(key, std::move(value));
}
// If cache contains an entry for |key|, return a pointer to it. This returned
// value is guaranteed to be valid until Insert or Clear.
// Else return nullptr.
V* Lookup(const K& key) { return impl_.Lookup(key); }
// Removes all entries from the cache. This method MUST be called before
// destruction.
void Clear() { impl_.Clear(); }
// Returns maximum size of the cache.
int64_t MaxSize() const { return impl_.MaxSize(); }
// Returns current size of the cache.
int64_t Size() const { return impl_.Size(); }
private:
QuicLRUCacheImpl<K, V> impl_;
DISALLOW_COPY_AND_ASSIGN(QuicLRUCache);
};
} // namespace net
#endif // NET_QUIC_PLATFORM_API_QUIC_LRU_CACHE_H_
// Copyright (c) 2016 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/quic/platform/api/quic_lru_cache.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace net {
namespace test {
namespace {
struct CachedItem {
explicit CachedItem(uint32_t new_value) : value(new_value) {}
uint32_t value;
};
TEST(QuicLRUCacheTest, InsertAndLookup) {
QuicLRUCache<int, CachedItem> cache(5);
EXPECT_EQ(nullptr, cache.Lookup(1));
EXPECT_EQ(0u, cache.Size());
EXPECT_EQ(5u, cache.MaxSize());
// Check that item 1 was properly inserted.
std::unique_ptr<CachedItem> item1(new CachedItem(11));
cache.Insert(1, std::move(item1));
EXPECT_EQ(1u, cache.Size());
EXPECT_EQ(11u, cache.Lookup(1)->value);
// Check that item 2 overrides item 1.
std::unique_ptr<CachedItem> item2(new CachedItem(12));
cache.Insert(1, std::move(item2));
EXPECT_EQ(1u, cache.Size());
EXPECT_EQ(12u, cache.Lookup(1)->value);
std::unique_ptr<CachedItem> item3(new CachedItem(13));
cache.Insert(3, std::move(item3));
EXPECT_EQ(2u, cache.Size());
EXPECT_EQ(13u, cache.Lookup(3)->value);
// No memory leakage.
cache.Clear();
EXPECT_EQ(0u, cache.Size());
}
TEST(QuicLRUCacheTest, Eviction) {
QuicLRUCache<int, CachedItem> cache(3);
for (size_t i = 1; i <= 4; ++i) {
std::unique_ptr<CachedItem> item(new CachedItem(10 + i));
cache.Insert(i, std::move(item));
}
EXPECT_EQ(3u, cache.Size());
EXPECT_EQ(3u, cache.MaxSize());
// Make sure item 1 is evicted.
EXPECT_EQ(nullptr, cache.Lookup(1));
EXPECT_EQ(14u, cache.Lookup(4)->value);
EXPECT_EQ(12u, cache.Lookup(2)->value);
std::unique_ptr<CachedItem> item5(new CachedItem(15));
cache.Insert(5, std::move(item5));
// Make sure item 3 is evicted.
EXPECT_EQ(nullptr, cache.Lookup(3));
EXPECT_EQ(15u, cache.Lookup(5)->value);
// No memory leakage.
cache.Clear();
EXPECT_EQ(0u, cache.Size());
}
} // namespace
} // namespace test
} // namespace net
// Copyright (c) 2016 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.
#ifndef NET_QUIC_PLATFORM_IMPL_QUIC_LRU_CACHE_IMPL_H_
#define NET_QUIC_PLATFORM_IMPL_QUIC_LRU_CACHE_IMPL_H_
#include "base/containers/mru_cache.h"
namespace net {
template <class K, class V>
class QuicLRUCacheImpl {
public:
explicit QuicLRUCacheImpl(int64_t total_units) : mru_cache_(total_units) {}
// Inserts one unit of |key|, |value| pair to the cache.
void Insert(const K& key, std::unique_ptr<V> value) {
mru_cache_.Put(key, std::move(value));
}
// If cache contains an entry for |key|, return a pointer to it. This returned
// value is guaranteed to be valid until Insert or Clear.
// Else return nullptr.
V* Lookup(const K& key) {
auto cached_it = mru_cache_.Get(key);
if (cached_it != mru_cache_.end()) {
return cached_it->second.get();
}
return nullptr;
}
// Removes all entries from the cache.
void Clear() { mru_cache_.Clear(); }
// Returns maximum size of the cache.
int64_t MaxSize() const { return mru_cache_.max_size(); }
// Returns current size of the cache.
int64_t Size() const { return mru_cache_.size(); }
private:
base::MRUCache<K, std::unique_ptr<V>> mru_cache_;
DISALLOW_COPY_AND_ASSIGN(QuicLRUCacheImpl);
};
} // namespace net
#endif // NET_QUIC_PLATFORM_IMPL_QUIC_LRU_CACHE_IMPL_H_
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment