diff options
author | sergeyu@chromium.org <sergeyu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-09-07 23:10:08 +0000 |
---|---|---|
committer | sergeyu@chromium.org <sergeyu@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-09-07 23:10:08 +0000 |
commit | 693d475a54984430d62272354a0f51183dd9936f (patch) | |
tree | 51222041f3b69060cb60e69512e3d5ed50fede8f /remoting/jingle_glue | |
parent | 68c665ed1c84aa8373ffeb8905d3b61e126490db (diff) | |
download | chromium_src-693d475a54984430d62272354a0f51183dd9936f.zip chromium_src-693d475a54984430d62272354a0f51183dd9936f.tar.gz chromium_src-693d475a54984430d62272354a0f51183dd9936f.tar.bz2 |
Delayed event support in JingleThread.
BUG=54347
TEST=unittests
Review URL: http://codereview.chromium.org/3333014
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@58773 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'remoting/jingle_glue')
-rw-r--r-- | remoting/jingle_glue/jingle_thread.cc | 80 | ||||
-rw-r--r-- | remoting/jingle_glue/jingle_thread_unittest.cc | 29 |
2 files changed, 86 insertions, 23 deletions
diff --git a/remoting/jingle_glue/jingle_thread.cc b/remoting/jingle_glue/jingle_thread.cc index f13477e..450381e 100644 --- a/remoting/jingle_glue/jingle_thread.cc +++ b/remoting/jingle_glue/jingle_thread.cc @@ -15,21 +15,66 @@ namespace remoting { const uint32 kRunTasksMessageId = 1; const uint32 kStopMessageId = 2; -class JingleThread::JingleMessagePump : public base::MessagePump { +class JingleThread::JingleMessagePump : public base::MessagePump, + public talk_base::MessageHandler { public: JingleMessagePump(JingleThread* thread) : thread_(thread) { } - virtual void Run(Delegate* delegate) { NOTIMPLEMENTED() ;} + virtual void Run(Delegate* delegate) { NOTIMPLEMENTED(); } virtual void Quit() { NOTIMPLEMENTED(); } virtual void ScheduleWork() { - thread_->Post(thread_, kRunTasksMessageId); + thread_->Post(this, kRunTasksMessageId); } virtual void ScheduleDelayedWork(const base::Time& time) { - NOTIMPLEMENTED(); + delayed_work_time_ = time; + ScheduleNextDelayedTask(); + } + + void OnMessage(talk_base::Message* msg) { + DCHECK(msg->message_id == kRunTasksMessageId); + + // This code is executed whenever we get new message in |message_loop_|. + // JingleMessagePump posts new tasks in the jingle thread. + // TODO(sergeyu): Remove it when JingleThread moved on Chromium's + // base::Thread. + base::MessagePump::Delegate* delegate = thread_->message_loop(); + // Loop until we run out of work. + while (true) { + if (!delegate->DoWork()) + break; + } + + // Process all pending tasks. + while (true) { + if (delegate->DoWork()) + continue; + if (delegate->DoDelayedWork(&delayed_work_time_)) + continue; + break; + } + + ScheduleNextDelayedTask(); } private: + + void ScheduleNextDelayedTask() { + DCHECK_EQ(thread_->message_loop(), MessageLoop::current()); + + thread_->Clear(this, kRunTasksMessageId); + if (!delayed_work_time_.is_null()) { + base::Time now = base::Time::Now(); + int delay = static_cast<int>((delayed_work_time_ - now).InMilliseconds()); + if (delay > 0) { + thread_->PostDelayed(delay, this, kRunTasksMessageId); + } else { + thread_->Post(this, kRunTasksMessageId); + } + } + } + JingleThread* thread_; + base::Time delayed_work_time_; }; class JingleThread::JingleMessageLoop : public MessageLoop { @@ -107,25 +152,14 @@ TaskPump* JingleThread::task_pump() { } void JingleThread::OnMessage(talk_base::Message* msg) { - if (msg->message_id == kRunTasksMessageId) { - // This code is executed whenever we get new message in |message_loop_|. - // JingleMessagePump posts new tasks in the jingle thread. - // TODO(sergeyu): Remove it when JingleThread moved on Chromium's - // base::Thread. - base::MessagePump::Delegate* delegate = message_loop_; - // Loop until we run out of work. - while (true) { - if (!delegate->DoWork()) - break; - } - } else if (msg->message_id == kStopMessageId) { - // Stop the thread only if there are no more messages left in the queue, - // otherwise post another task to try again later. - if (msgq_.size() > 0 || fPeekKeep_) { - Post(this, kStopMessageId); - } else { - MessageQueue::Quit(); - } + DCHECK(msg->message_id == kStopMessageId); + + // Stop the thread only if there are no more messages left in the queue, + // otherwise post another task to try again later. + if (msgq_.size() > 0 || fPeekKeep_) { + Post(this, kStopMessageId); + } else { + MessageQueue::Quit(); } } diff --git a/remoting/jingle_glue/jingle_thread_unittest.cc b/remoting/jingle_glue/jingle_thread_unittest.cc index a29b69c..bebb16d 100644 --- a/remoting/jingle_glue/jingle_thread_unittest.cc +++ b/remoting/jingle_glue/jingle_thread_unittest.cc @@ -3,6 +3,8 @@ // found in the LICENSE file. #include "base/message_loop.h" +#include "base/time.h" +#include "base/waitable_event.h" #include "remoting/jingle_glue/jingle_thread.h" #include "testing/gmock/include/gmock/gmock.h" #include "testing/gtest/include/gtest/gtest.h" @@ -14,6 +16,13 @@ class MockTask : public Task { MOCK_METHOD0(Run, void()); }; +namespace { +// Delay used to test delayed tasks. Shouldn't be too big, so that we don't +// slow down the test, yet, should be big enough to be measurable. +int kDelayMs = 50; // 0.05 s. +int kDelayTimeoutMs = 10000; // 10 s. +} // namespace + TEST(JingleThreadTest, PostTask) { JingleThread thread; MockTask* task = new MockTask(); @@ -24,4 +33,24 @@ TEST(JingleThreadTest, PostTask) { thread.Stop(); } +ACTION_P(SignalEvent, event) { + event->Signal(); +} + +TEST(JingleThreadTest, PostDelayedTask) { + JingleThread thread; + MockTask* task = new MockTask(); + base::WaitableEvent event(true, false); + EXPECT_CALL(*task, Run()).WillOnce(SignalEvent(&event)); + + thread.Start(); + base::Time start = base::Time::Now(); + thread.message_loop()->PostDelayedTask(FROM_HERE, task, kDelayMs); + event.TimedWait(base::TimeDelta::FromMilliseconds(kDelayTimeoutMs)); + base::Time end = base::Time::Now(); + thread.Stop(); + + EXPECT_GT((end - start).InMillisecondsRoundedUp(), kDelayMs); +} + } // namespace remoting |