Home | History | Annotate | Download | only in disk_cache
      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
      3 // found in the LICENSE file.
      4 
      5 #include "net/disk_cache/disk_cache_test_base.h"
      6 
      7 #include "base/file_util.h"
      8 #include "base/path_service.h"
      9 #include "base/run_loop.h"
     10 #include "net/base/io_buffer.h"
     11 #include "net/base/net_errors.h"
     12 #include "net/base/test_completion_callback.h"
     13 #include "net/disk_cache/backend_impl.h"
     14 #include "net/disk_cache/cache_util.h"
     15 #include "net/disk_cache/disk_cache.h"
     16 #include "net/disk_cache/disk_cache_test_util.h"
     17 #include "net/disk_cache/mem_backend_impl.h"
     18 #include "net/disk_cache/simple/simple_backend_impl.h"
     19 #include "net/disk_cache/simple/simple_index.h"
     20 
     21 DiskCacheTest::DiskCacheTest() {
     22   CHECK(temp_dir_.CreateUniqueTempDir());
     23   cache_path_ = temp_dir_.path();
     24   if (!base::MessageLoop::current())
     25     message_loop_.reset(new base::MessageLoopForIO());
     26 }
     27 
     28 DiskCacheTest::~DiskCacheTest() {
     29 }
     30 
     31 bool DiskCacheTest::CopyTestCache(const std::string& name) {
     32   base::FilePath path;
     33   PathService::Get(base::DIR_SOURCE_ROOT, &path);
     34   path = path.AppendASCII("net");
     35   path = path.AppendASCII("data");
     36   path = path.AppendASCII("cache_tests");
     37   path = path.AppendASCII(name);
     38 
     39   if (!CleanupCacheDir())
     40     return false;
     41   return base::CopyDirectory(path, cache_path_, false);
     42 }
     43 
     44 bool DiskCacheTest::CleanupCacheDir() {
     45   return DeleteCache(cache_path_);
     46 }
     47 
     48 void DiskCacheTest::TearDown() {
     49   base::RunLoop().RunUntilIdle();
     50 }
     51 
     52 DiskCacheTestWithCache::DiskCacheTestWithCache()
     53     : cache_impl_(NULL),
     54       simple_cache_impl_(NULL),
     55       mem_cache_(NULL),
     56       mask_(0),
     57       size_(0),
     58       type_(net::DISK_CACHE),
     59       memory_only_(false),
     60       simple_cache_mode_(false),
     61       simple_cache_wait_for_index_(true),
     62       force_creation_(false),
     63       new_eviction_(false),
     64       first_cleanup_(true),
     65       integrity_(true),
     66       use_current_thread_(false),
     67       cache_thread_("CacheThread") {
     68 }
     69 
     70 DiskCacheTestWithCache::~DiskCacheTestWithCache() {}
     71 
     72 void DiskCacheTestWithCache::InitCache() {
     73   if (memory_only_)
     74     InitMemoryCache();
     75   else
     76     InitDiskCache();
     77 
     78   ASSERT_TRUE(NULL != cache_);
     79   if (first_cleanup_)
     80     ASSERT_EQ(0, cache_->GetEntryCount());
     81 }
     82 
     83 // We are expected to leak memory when simulating crashes.
     84 void DiskCacheTestWithCache::SimulateCrash() {
     85   ASSERT_TRUE(!memory_only_);
     86   net::TestCompletionCallback cb;
     87   int rv = cache_impl_->FlushQueueForTest(cb.callback());
     88   ASSERT_EQ(net::OK, cb.GetResult(rv));
     89   cache_impl_->ClearRefCountForTest();
     90 
     91   cache_.reset();
     92   EXPECT_TRUE(CheckCacheIntegrity(cache_path_, new_eviction_, mask_));
     93 
     94   CreateBackend(disk_cache::kNoRandom, &cache_thread_);
     95 }
     96 
     97 void DiskCacheTestWithCache::SetTestMode() {
     98   ASSERT_TRUE(!memory_only_);
     99   cache_impl_->SetUnitTestMode();
    100 }
    101 
    102 void DiskCacheTestWithCache::SetMaxSize(int size) {
    103   size_ = size;
    104   if (simple_cache_impl_)
    105     EXPECT_TRUE(simple_cache_impl_->SetMaxSize(size));
    106 
    107   if (cache_impl_)
    108     EXPECT_TRUE(cache_impl_->SetMaxSize(size));
    109 
    110   if (mem_cache_)
    111     EXPECT_TRUE(mem_cache_->SetMaxSize(size));
    112 }
    113 
    114 int DiskCacheTestWithCache::OpenEntry(const std::string& key,
    115                                       disk_cache::Entry** entry) {
    116   net::TestCompletionCallback cb;
    117   int rv = cache_->OpenEntry(key, entry, cb.callback());
    118   return cb.GetResult(rv);
    119 }
    120 
    121 int DiskCacheTestWithCache::CreateEntry(const std::string& key,
    122                                         disk_cache::Entry** entry) {
    123   net::TestCompletionCallback cb;
    124   int rv = cache_->CreateEntry(key, entry, cb.callback());
    125   return cb.GetResult(rv);
    126 }
    127 
    128 int DiskCacheTestWithCache::DoomEntry(const std::string& key) {
    129   net::TestCompletionCallback cb;
    130   int rv = cache_->DoomEntry(key, cb.callback());
    131   return cb.GetResult(rv);
    132 }
    133 
    134 int DiskCacheTestWithCache::DoomAllEntries() {
    135   net::TestCompletionCallback cb;
    136   int rv = cache_->DoomAllEntries(cb.callback());
    137   return cb.GetResult(rv);
    138 }
    139 
    140 int DiskCacheTestWithCache::DoomEntriesBetween(const base::Time initial_time,
    141                                                const base::Time end_time) {
    142   net::TestCompletionCallback cb;
    143   int rv = cache_->DoomEntriesBetween(initial_time, end_time, cb.callback());
    144   return cb.GetResult(rv);
    145 }
    146 
    147 int DiskCacheTestWithCache::DoomEntriesSince(const base::Time initial_time) {
    148   net::TestCompletionCallback cb;
    149   int rv = cache_->DoomEntriesSince(initial_time, cb.callback());
    150   return cb.GetResult(rv);
    151 }
    152 
    153 int DiskCacheTestWithCache::OpenNextEntry(void** iter,
    154                                           disk_cache::Entry** next_entry) {
    155   net::TestCompletionCallback cb;
    156   int rv = cache_->OpenNextEntry(iter, next_entry, cb.callback());
    157   return cb.GetResult(rv);
    158 }
    159 
    160 void DiskCacheTestWithCache::FlushQueueForTest() {
    161   if (memory_only_ || !cache_impl_)
    162     return;
    163 
    164   net::TestCompletionCallback cb;
    165   int rv = cache_impl_->FlushQueueForTest(cb.callback());
    166   EXPECT_EQ(net::OK, cb.GetResult(rv));
    167 }
    168 
    169 void DiskCacheTestWithCache::RunTaskForTest(const base::Closure& closure) {
    170   if (memory_only_ || !cache_impl_) {
    171     closure.Run();
    172     return;
    173   }
    174 
    175   net::TestCompletionCallback cb;
    176   int rv = cache_impl_->RunTaskForTest(closure, cb.callback());
    177   EXPECT_EQ(net::OK, cb.GetResult(rv));
    178 }
    179 
    180 int DiskCacheTestWithCache::ReadData(disk_cache::Entry* entry, int index,
    181                                      int offset, net::IOBuffer* buf, int len) {
    182   net::TestCompletionCallback cb;
    183   int rv = entry->ReadData(index, offset, buf, len, cb.callback());
    184   return cb.GetResult(rv);
    185 }
    186 
    187 int DiskCacheTestWithCache::WriteData(disk_cache::Entry* entry, int index,
    188                                       int offset, net::IOBuffer* buf, int len,
    189                                       bool truncate) {
    190   net::TestCompletionCallback cb;
    191   int rv = entry->WriteData(index, offset, buf, len, cb.callback(), truncate);
    192   return cb.GetResult(rv);
    193 }
    194 
    195 int DiskCacheTestWithCache::ReadSparseData(disk_cache::Entry* entry,
    196                                            int64 offset, net::IOBuffer* buf,
    197                                            int len) {
    198   net::TestCompletionCallback cb;
    199   int rv = entry->ReadSparseData(offset, buf, len, cb.callback());
    200   return cb.GetResult(rv);
    201 }
    202 
    203 int DiskCacheTestWithCache::WriteSparseData(disk_cache::Entry* entry,
    204                                             int64 offset,
    205                                             net::IOBuffer* buf, int len) {
    206   net::TestCompletionCallback cb;
    207   int rv = entry->WriteSparseData(offset, buf, len, cb.callback());
    208   return cb.GetResult(rv);
    209 }
    210 
    211 void DiskCacheTestWithCache::TrimForTest(bool empty) {
    212   RunTaskForTest(base::Bind(&disk_cache::BackendImpl::TrimForTest,
    213                             base::Unretained(cache_impl_),
    214                             empty));
    215 }
    216 
    217 void DiskCacheTestWithCache::TrimDeletedListForTest(bool empty) {
    218   RunTaskForTest(base::Bind(&disk_cache::BackendImpl::TrimDeletedListForTest,
    219                             base::Unretained(cache_impl_),
    220                             empty));
    221 }
    222 
    223 void DiskCacheTestWithCache::AddDelay() {
    224   base::Time initial = base::Time::Now();
    225   while (base::Time::Now() <= initial) {
    226     base::PlatformThread::Sleep(base::TimeDelta::FromMilliseconds(1));
    227   };
    228 }
    229 
    230 void DiskCacheTestWithCache::TearDown() {
    231   base::RunLoop().RunUntilIdle();
    232   cache_.reset();
    233   if (cache_thread_.IsRunning())
    234     cache_thread_.Stop();
    235 
    236   if (!memory_only_ && !simple_cache_mode_ && integrity_) {
    237     EXPECT_TRUE(CheckCacheIntegrity(cache_path_, new_eviction_, mask_));
    238   }
    239 
    240   PlatformTest::TearDown();
    241 }
    242 
    243 void DiskCacheTestWithCache::InitMemoryCache() {
    244   mem_cache_ = new disk_cache::MemBackendImpl(NULL);
    245   cache_.reset(mem_cache_);
    246   ASSERT_TRUE(cache_);
    247 
    248   if (size_)
    249     EXPECT_TRUE(mem_cache_->SetMaxSize(size_));
    250 
    251   ASSERT_TRUE(mem_cache_->Init());
    252 }
    253 
    254 void DiskCacheTestWithCache::InitDiskCache() {
    255   if (first_cleanup_)
    256     ASSERT_TRUE(CleanupCacheDir());
    257 
    258   if (!cache_thread_.IsRunning()) {
    259     ASSERT_TRUE(cache_thread_.StartWithOptions(
    260         base::Thread::Options(base::MessageLoop::TYPE_IO, 0)));
    261   }
    262   ASSERT_TRUE(cache_thread_.message_loop() != NULL);
    263 
    264   CreateBackend(disk_cache::kNoRandom, &cache_thread_);
    265 }
    266 
    267 void DiskCacheTestWithCache::CreateBackend(uint32 flags, base::Thread* thread) {
    268   base::MessageLoopProxy* runner;
    269   if (use_current_thread_)
    270     runner = base::MessageLoopProxy::current().get();
    271   else
    272     runner = thread->message_loop_proxy().get();
    273 
    274   if (simple_cache_mode_) {
    275     net::TestCompletionCallback cb;
    276     scoped_ptr<disk_cache::SimpleBackendImpl> simple_backend(
    277         new disk_cache::SimpleBackendImpl(
    278             cache_path_, size_, type_, make_scoped_refptr(runner).get(), NULL));
    279     int rv = simple_backend->Init(cb.callback());
    280     ASSERT_EQ(net::OK, cb.GetResult(rv));
    281     simple_cache_impl_ = simple_backend.get();
    282     cache_ = simple_backend.PassAs<disk_cache::Backend>();
    283     if (simple_cache_wait_for_index_) {
    284       net::TestCompletionCallback wait_for_index_cb;
    285       rv = simple_cache_impl_->index()->ExecuteWhenReady(
    286           wait_for_index_cb.callback());
    287       ASSERT_EQ(net::OK, wait_for_index_cb.GetResult(rv));
    288     }
    289     return;
    290   }
    291 
    292   if (mask_)
    293     cache_impl_ = new disk_cache::BackendImpl(cache_path_, mask_, runner, NULL);
    294   else
    295     cache_impl_ = new disk_cache::BackendImpl(cache_path_, runner, NULL);
    296   cache_.reset(cache_impl_);
    297   ASSERT_TRUE(cache_);
    298   if (size_)
    299     EXPECT_TRUE(cache_impl_->SetMaxSize(size_));
    300   if (new_eviction_)
    301     cache_impl_->SetNewEviction();
    302   cache_impl_->SetType(type_);
    303   cache_impl_->SetFlags(flags);
    304   net::TestCompletionCallback cb;
    305   int rv = cache_impl_->Init(cb.callback());
    306   ASSERT_EQ(net::OK, cb.GetResult(rv));
    307 }
    308