Home | History | Annotate | Download | only in base
      1 // Copyright (c) 2006-2008 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 "base/message_pump_default.h"
      6 
      7 #include "base/logging.h"
      8 #include "base/mac/scoped_nsautorelease_pool.h"
      9 
     10 namespace base {
     11 
     12 MessagePumpDefault::MessagePumpDefault()
     13     : keep_running_(true),
     14       event_(false, false) {
     15 }
     16 
     17 void MessagePumpDefault::Run(Delegate* delegate) {
     18   DCHECK(keep_running_) << "Quit must have been called outside of Run!";
     19 
     20   for (;;) {
     21     mac::ScopedNSAutoreleasePool autorelease_pool;
     22 
     23     bool did_work = delegate->DoWork();
     24     if (!keep_running_)
     25       break;
     26 
     27     did_work |= delegate->DoDelayedWork(&delayed_work_time_);
     28     if (!keep_running_)
     29       break;
     30 
     31     if (did_work)
     32       continue;
     33 
     34     did_work = delegate->DoIdleWork();
     35     if (!keep_running_)
     36       break;
     37 
     38     if (did_work)
     39       continue;
     40 
     41     if (delayed_work_time_.is_null()) {
     42       event_.Wait();
     43     } else {
     44       TimeDelta delay = delayed_work_time_ - TimeTicks::Now();
     45       if (delay > TimeDelta()) {
     46         event_.TimedWait(delay);
     47       } else {
     48         // It looks like delayed_work_time_ indicates a time in the past, so we
     49         // need to call DoDelayedWork now.
     50         delayed_work_time_ = TimeTicks();
     51       }
     52     }
     53     // Since event_ is auto-reset, we don't need to do anything special here
     54     // other than service each delegate method.
     55   }
     56 
     57   keep_running_ = true;
     58 }
     59 
     60 void MessagePumpDefault::Quit() {
     61   keep_running_ = false;
     62 }
     63 
     64 void MessagePumpDefault::ScheduleWork() {
     65   // Since this can be called on any thread, we need to ensure that our Run
     66   // loop wakes up.
     67   event_.Signal();
     68 }
     69 
     70 void MessagePumpDefault::ScheduleDelayedWork(
     71     const TimeTicks& delayed_work_time) {
     72   // We know that we can't be blocked on Wait right now since this method can
     73   // only be called on the same thread as Run, so we only need to update our
     74   // record of how long to sleep when we do sleep.
     75   delayed_work_time_ = delayed_work_time;
     76 }
     77 
     78 }  // namespace base
     79