Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(997)

Unified Diff: net/disk_cache/simple/simple_entry_impl.cc

Issue 13880016: Make SimpleEntryImpl ref counted. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: remove flaky dchecks Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: net/disk_cache/simple/simple_entry_impl.cc
diff --git a/net/disk_cache/simple/simple_entry_impl.cc b/net/disk_cache/simple/simple_entry_impl.cc
index 1917a88715091ac1a37be9dae3b8fd104b6f4edf..22cbc956972cfc096089ca9021cd23100eb288bb 100644
--- a/net/disk_cache/simple/simple_entry_impl.cc
+++ b/net/disk_cache/simple/simple_entry_impl.cc
@@ -8,6 +8,7 @@
#include "base/bind_helpers.h"
#include "base/callback.h"
#include "base/location.h"
+#include "base/logging.h"
#include "base/message_loop_proxy.h"
#include "base/threading/worker_pool.h"
#include "net/base/io_buffer.h"
@@ -30,11 +31,10 @@ namespace disk_cache {
using base::FilePath;
using base::MessageLoopProxy;
using base::Time;
-using base::WeakPtr;
using base::WorkerPool;
// static
-int SimpleEntryImpl::OpenEntry(WeakPtr<SimpleIndex> index,
+int SimpleEntryImpl::OpenEntry(const scoped_refptr<SimpleIndex>& index,
const FilePath& path,
const std::string& key,
Entry** entry,
@@ -42,9 +42,11 @@ int SimpleEntryImpl::OpenEntry(WeakPtr<SimpleIndex> index,
// TODO(gavinp): More closely unify the last_used_ in the
// SimpleSynchronousEntry and the SimpleIndex.
if (!index || index->UseIfExists(key)) {
+ scoped_refptr<SimpleEntryImpl> new_entry =
+ new SimpleEntryImpl(index, path, key);
SynchronousCreationCallback sync_creation_callback =
base::Bind(&SimpleEntryImpl::CreationOperationComplete,
- index, callback, key, entry);
+ new_entry, entry, callback);
WorkerPool::PostTask(FROM_HERE,
base::Bind(&SimpleSynchronousEntry::OpenEntry, path,
key, MessageLoopProxy::current(),
@@ -56,14 +58,16 @@ int SimpleEntryImpl::OpenEntry(WeakPtr<SimpleIndex> index,
}
// static
-int SimpleEntryImpl::CreateEntry(WeakPtr<SimpleIndex> index,
+int SimpleEntryImpl::CreateEntry(const scoped_refptr<SimpleIndex>& index,
const FilePath& path,
const std::string& key,
Entry** entry,
const CompletionCallback& callback) {
+ scoped_refptr<SimpleEntryImpl> new_entry =
+ new SimpleEntryImpl(index, path, key);
SynchronousCreationCallback sync_creation_callback =
base::Bind(&SimpleEntryImpl::CreationOperationComplete,
- index, callback, key, entry);
+ new_entry, entry, callback);
WorkerPool::PostTask(FROM_HERE,
base::Bind(&SimpleSynchronousEntry::CreateEntry, path,
key, MessageLoopProxy::current(),
@@ -73,12 +77,11 @@ int SimpleEntryImpl::CreateEntry(WeakPtr<SimpleIndex> index,
}
// static
-int SimpleEntryImpl::DoomEntry(WeakPtr<SimpleIndex> index,
+int SimpleEntryImpl::DoomEntry(const scoped_refptr<SimpleIndex>& index,
const FilePath& path,
const std::string& key,
const CompletionCallback& callback) {
- if (index)
- index->Remove(key);
+ index->Remove(key);
WorkerPool::PostTask(FROM_HERE,
base::Bind(&SimpleSynchronousEntry::DoomEntry, path, key,
MessageLoopProxy::current(), callback),
@@ -88,6 +91,7 @@ int SimpleEntryImpl::DoomEntry(WeakPtr<SimpleIndex> index,
void SimpleEntryImpl::Doom() {
DCHECK(io_thread_checker_.CalledOnValidThread());
+ DCHECK(synchronous_entry_);
#if defined(OS_POSIX)
// This call to static SimpleEntryImpl::DoomEntry() will just erase the
// underlying files. On POSIX, this is fine; the files are still open on the
@@ -101,15 +105,7 @@ void SimpleEntryImpl::Doom() {
void SimpleEntryImpl::Close() {
gavinp 2013/04/20 07:28:33 ***THREE*** In response to the callback from ***TW
DCHECK(io_thread_checker_.CalledOnValidThread());
- if (!synchronous_entry_in_use_by_worker_) {
- WorkerPool::PostTask(FROM_HERE,
- base::Bind(&SimpleSynchronousEntry::Close,
- base::Unretained(synchronous_entry_)),
- true);
- }
- // Entry::Close() is expected to release this entry. See disk_cache.h for
- // details.
- delete this;
+ Release(); // Balanced in CreationOperationCompleted().
gavinp 2013/04/20 07:28:33 ***FOUR*** Close releases one ref on SimpleEntryIm
}
std::string SimpleEntryImpl::GetKey() const {
@@ -147,12 +143,10 @@ int SimpleEntryImpl::ReadData(int index,
CHECK(false);
}
synchronous_entry_in_use_by_worker_ = true;
- if (index_)
- index_->UseIfExists(key_);
+ index_->UseIfExists(key_);
SynchronousOperationCallback sync_operation_callback =
base::Bind(&SimpleEntryImpl::EntryOperationComplete,
- index_, callback, weak_ptr_factory_.GetWeakPtr(),
- synchronous_entry_);
+ this, callback);
WorkerPool::PostTask(FROM_HERE,
base::Bind(&SimpleSynchronousEntry::ReadData,
base::Unretained(synchronous_entry_),
@@ -174,12 +168,10 @@ int SimpleEntryImpl::WriteData(int index,
CHECK(false);
}
synchronous_entry_in_use_by_worker_ = true;
- if (index_)
- index_->UseIfExists(key_);
+ index_->UseIfExists(key_);
SynchronousOperationCallback sync_operation_callback =
base::Bind(&SimpleEntryImpl::EntryOperationComplete,
- index_, callback, weak_ptr_factory_.GetWeakPtr(),
- synchronous_entry_);
+ this, callback);
WorkerPool::PostTask(FROM_HERE,
base::Bind(&SimpleSynchronousEntry::WriteData,
base::Unretained(synchronous_entry_),
@@ -238,70 +230,68 @@ int SimpleEntryImpl::ReadyForSparseIO(const CompletionCallback& callback) {
return net::ERR_FAILED;
}
-SimpleEntryImpl::SimpleEntryImpl(
- SimpleSynchronousEntry* synchronous_entry,
- WeakPtr<SimpleIndex> index)
- : ALLOW_THIS_IN_INITIALIZER_LIST(weak_ptr_factory_(this)),
- path_(synchronous_entry->path()),
- key_(synchronous_entry->key()),
- synchronous_entry_(synchronous_entry),
- synchronous_entry_in_use_by_worker_(false),
- index_(index) {
- DCHECK(synchronous_entry);
- SetSynchronousData();
+SimpleEntryImpl::SimpleEntryImpl(const scoped_refptr<SimpleIndex>& index,
+ const base::FilePath& path,
+ const std::string& key)
+ : constructor_thread_(base::MessageLoopProxy::current()),
+ index_(index),
+ path_(path),
+ key_(key),
+ synchronous_entry_(NULL),
+ synchronous_entry_in_use_by_worker_(false) {
}
SimpleEntryImpl::~SimpleEntryImpl() {
- DCHECK(io_thread_checker_.CalledOnValidThread());
+ if (synchronous_entry_) {
+ base::Closure close_sync_entry =
+ base::Bind(&SimpleSynchronousEntry::Close,
+ base::Unretained(synchronous_entry_));
+ // We aren't guaranteed to be able to run IO on our constructor thread, but
+ // we are also not guaranteed to be allowed to run WorkerPool::PostTask on
+ // our other threads.
+ if (constructor_thread_->BelongsToCurrentThread())
+ WorkerPool::PostTask(FROM_HERE, close_sync_entry, true);
+ else
+ close_sync_entry.Run();
+ }
}
-// static
void SimpleEntryImpl::CreationOperationComplete(
- WeakPtr<SimpleIndex> index,
- const CompletionCallback& completion_callback,
- const std::string& key,
Entry** out_entry,
+ const CompletionCallback& completion_callback,
SimpleSynchronousEntry* sync_entry) {
+ DCHECK(io_thread_checker_.CalledOnValidThread());
if (!sync_entry) {
completion_callback.Run(net::ERR_FAILED);
// If OpenEntry failed, we must remove it from our index.
- if (index)
- index->Remove(key);
+ index_->Remove(key_);
+ // The reference held by the Callback calling us will go out of scope and
+ // delete |this| on leaving this scope.
return;
}
- if (index)
- index->Insert(sync_entry->key());
- *out_entry = new SimpleEntryImpl(sync_entry, index);
+ // Adding a reference to self will keep |this| alive after the scope of our
rvargas (doing something else) 2013/04/17 19:56:38 nit: "our callback calling us" -> the callback
gavinp 2013/04/18 09:12:41 Done.
+ // Callback calling us is destroyed.
+ AddRef(); // Balanced in Close().
+ synchronous_entry_ = sync_entry;
+ SetSynchronousData();
+ index_->Insert(key_);
+ *out_entry = this;
rvargas (doing something else) 2013/04/17 19:56:38 nit: I believe the "real" reason for Addref is tha
gavinp 2013/04/18 09:12:41 Done.
completion_callback.Run(net::OK);
}
-// static
void SimpleEntryImpl::EntryOperationComplete(
- base::WeakPtr<SimpleIndex> index,
const CompletionCallback& completion_callback,
- base::WeakPtr<SimpleEntryImpl> entry,
- SimpleSynchronousEntry* sync_entry,
int result) {
- DCHECK(sync_entry);
- if (index) {
- if (result >= 0)
- index->UpdateEntrySize(sync_entry->key(), sync_entry->GetFileSize());
- else
- index->Remove(sync_entry->key());
- }
-
- if (entry) {
- DCHECK(entry->synchronous_entry_in_use_by_worker_);
- entry->synchronous_entry_in_use_by_worker_ = false;
- entry->SetSynchronousData();
+ DCHECK(io_thread_checker_.CalledOnValidThread());
+ DCHECK(synchronous_entry_);
+ DCHECK(synchronous_entry_in_use_by_worker_);
+ synchronous_entry_in_use_by_worker_ = false;
+ SetSynchronousData();
+ if (result >= 0) {
+ index_->UpdateEntrySize(synchronous_entry_->key(),
+ synchronous_entry_->GetFileSize());
} else {
- // |entry| must have had Close() called while this operation was in flight.
- // Since the simple cache now only supports one pending entry operation in
- // flight at a time, it's safe to now call Close() on |sync_entry|.
- WorkerPool::PostTask(FROM_HERE,
- base::Bind(&SimpleSynchronousEntry::Close,
- base::Unretained(sync_entry)),
- true);
+ index_->Remove(synchronous_entry_->key());
}
completion_callback.Run(result);
gavinp 2013/04/20 07:28:33 ***TWO*** The IO thread runs the task posted just
}

Powered by Google App Engine
This is Rietveld 408576698