| Index: base/threading/post_task_and_reply_impl.cc
|
| diff --git a/base/threading/post_task_and_reply_impl.cc b/base/threading/post_task_and_reply_impl.cc
|
| index c906866cfb8e61143279a833ed4f5ea04971fb07..d68621c77b008ec9fc766904b34a7a29a5ac483f 100644
|
| --- a/base/threading/post_task_and_reply_impl.cc
|
| +++ b/base/threading/post_task_and_reply_impl.cc
|
| @@ -5,41 +5,42 @@
|
| #include "base/threading/post_task_and_reply_impl.h"
|
|
|
| #include "base/bind.h"
|
| -#include "base/location.h"
|
| -#include "base/single_thread_task_runner.h"
|
| -#include "base/threading/thread_task_runner_handle.h"
|
| +#include "base/callback.h"
|
| +#include "base/logging.h"
|
| +#include "base/memory/ref_counted.h"
|
| +#include "base/sequence_checker.h"
|
| +#include "base/sequenced_task_runner.h"
|
| +#include "base/threading/sequenced_task_runner_handle.h"
|
|
|
| namespace base {
|
|
|
| namespace {
|
|
|
| -// This relay class remembers the MessageLoop that it was created on, and
|
| -// ensures that both the |task| and |reply| Closures are deleted on this same
|
| -// thread. Also, |task| is guaranteed to be deleted before |reply| is run or
|
| -// deleted.
|
| +// This relay class remembers the sequence that it was created on, and ensures
|
| +// that both the |task| and |reply| Closures are deleted on this same sequence.
|
| +// Also, |task| is guaranteed to be deleted before |reply| is run or deleted.
|
| //
|
| -// If this is not possible because the originating MessageLoop is no longer
|
| -// available, the the |task| and |reply| Closures are leaked. Leaking is
|
| -// considered preferable to having a thread-safetey violations caused by
|
| -// invoking the Closure destructor on the wrong thread.
|
| +// If RunReplyAndSelfDestruct() doesn't run because the originating execution
|
| +// context is no longer available, then the |task| and |reply| Closures are
|
| +// leaked. Leaking is considered preferable to having a thread-safetey
|
| +// violations caused by invoking the Closure destructor on the wrong sequence.
|
| class PostTaskAndReplyRelay {
|
| public:
|
| PostTaskAndReplyRelay(const tracked_objects::Location& from_here,
|
| const Closure& task,
|
| const Closure& reply)
|
| : from_here_(from_here),
|
| - origin_task_runner_(ThreadTaskRunnerHandle::Get()) {
|
| - task_ = task;
|
| - reply_ = reply;
|
| - }
|
| + origin_task_runner_(SequencedTaskRunnerHandle::Get()),
|
| + reply_(reply),
|
| + task_(task) {}
|
|
|
| ~PostTaskAndReplyRelay() {
|
| - DCHECK(origin_task_runner_->BelongsToCurrentThread());
|
| + DCHECK(sequence_checker_.CalledOnValidSequence());
|
| task_.Reset();
|
| reply_.Reset();
|
| }
|
|
|
| - void Run() {
|
| + void RunTaskAndPostReply() {
|
| task_.Run();
|
| origin_task_runner_->PostTask(
|
| from_here_, Bind(&PostTaskAndReplyRelay::RunReplyAndSelfDestruct,
|
| @@ -48,7 +49,7 @@ class PostTaskAndReplyRelay {
|
|
|
| private:
|
| void RunReplyAndSelfDestruct() {
|
| - DCHECK(origin_task_runner_->BelongsToCurrentThread());
|
| + DCHECK(sequence_checker_.CalledOnValidSequence());
|
|
|
| // Force |task_| to be released before |reply_| is to ensure that no one
|
| // accidentally depends on |task_| keeping one of its arguments alive while
|
| @@ -61,8 +62,9 @@ class PostTaskAndReplyRelay {
|
| delete this;
|
| }
|
|
|
| - tracked_objects::Location from_here_;
|
| - scoped_refptr<SingleThreadTaskRunner> origin_task_runner_;
|
| + const SequenceChecker sequence_checker_;
|
| + const tracked_objects::Location from_here_;
|
| + const scoped_refptr<SequencedTaskRunner> origin_task_runner_;
|
| Closure reply_;
|
| Closure task_;
|
| };
|
| @@ -75,12 +77,11 @@ bool PostTaskAndReplyImpl::PostTaskAndReply(
|
| const tracked_objects::Location& from_here,
|
| const Closure& task,
|
| const Closure& reply) {
|
| - // TODO(tzik): Use DCHECK here once the crash is gone. http://crbug.com/541319
|
| - CHECK(!task.is_null()) << from_here.ToString();
|
| - CHECK(!reply.is_null()) << from_here.ToString();
|
| + DCHECK(!task.is_null()) << from_here.ToString();
|
| + DCHECK(!reply.is_null()) << from_here.ToString();
|
| PostTaskAndReplyRelay* relay =
|
| new PostTaskAndReplyRelay(from_here, task, reply);
|
| - if (!PostTask(from_here, Bind(&PostTaskAndReplyRelay::Run,
|
| + if (!PostTask(from_here, Bind(&PostTaskAndReplyRelay::RunTaskAndPostReply,
|
| Unretained(relay)))) {
|
| delete relay;
|
| return false;
|
|
|