| Index: base/message_loop/message_loop.cc
 | 
| diff --git a/base/message_loop/message_loop.cc b/base/message_loop/message_loop.cc
 | 
| index eb0f968849485ea73ef8a1aab9094bb9527af403..4222c774dd58b20354d6b0e4c948efcbbf5abf1b 100644
 | 
| --- a/base/message_loop/message_loop.cc
 | 
| +++ b/base/message_loop/message_loop.cc
 | 
| @@ -100,6 +100,10 @@ MessagePumpForIO* ToPumpIO(MessagePump* pump) {
 | 
|  }
 | 
|  #endif  // !defined(OS_NACL_SFI)
 | 
|  
 | 
| +scoped_ptr<MessagePump> ReturnPump(scoped_ptr<MessagePump> pump) {
 | 
| +  return pump;
 | 
| +}
 | 
| +
 | 
|  }  // namespace
 | 
|  
 | 
|  //------------------------------------------------------------------------------
 | 
| @@ -116,41 +120,19 @@ MessageLoop::DestructionObserver::~DestructionObserver() {
 | 
|  //------------------------------------------------------------------------------
 | 
|  
 | 
|  MessageLoop::MessageLoop(Type type)
 | 
| -    : type_(type),
 | 
| -#if defined(OS_WIN)
 | 
| -      pending_high_res_tasks_(0),
 | 
| -      in_high_res_mode_(false),
 | 
| -#endif
 | 
| -      nestable_tasks_allowed_(true),
 | 
| -#if defined(OS_WIN)
 | 
| -      os_modal_loop_(false),
 | 
| -#endif  // OS_WIN
 | 
| -      message_histogram_(NULL),
 | 
| -      run_loop_(NULL) {
 | 
| -  Init();
 | 
| -
 | 
| -  pump_ = CreateMessagePumpForType(type).Pass();
 | 
| +    : MessageLoop(type, MessagePumpFactoryCallback()) {
 | 
| +  BindToCurrentThread();
 | 
|  }
 | 
|  
 | 
|  MessageLoop::MessageLoop(scoped_ptr<MessagePump> pump)
 | 
| -    : pump_(pump.Pass()),
 | 
| -      type_(TYPE_CUSTOM),
 | 
| -#if defined(OS_WIN)
 | 
| -      pending_high_res_tasks_(0),
 | 
| -      in_high_res_mode_(false),
 | 
| -#endif
 | 
| -      nestable_tasks_allowed_(true),
 | 
| -#if defined(OS_WIN)
 | 
| -      os_modal_loop_(false),
 | 
| -#endif  // OS_WIN
 | 
| -      message_histogram_(NULL),
 | 
| -      run_loop_(NULL) {
 | 
| -  DCHECK(pump_.get());
 | 
| -  Init();
 | 
| +    : MessageLoop(TYPE_CUSTOM, Bind(&ReturnPump, Passed(&pump))) {
 | 
| +  BindToCurrentThread();
 | 
|  }
 | 
|  
 | 
|  MessageLoop::~MessageLoop() {
 | 
| -  DCHECK_EQ(this, current());
 | 
| +  // current() could be NULL if this message loop is destructed before it is
 | 
| +  // bound to a thread.
 | 
| +  DCHECK(current() == this || !current());
 | 
|  
 | 
|    // iOS just attaches to the loop, it doesn't Run it.
 | 
|    // TODO(stuartmorgan): Consider wiring up a Detach().
 | 
| @@ -299,11 +281,13 @@ void MessageLoop::PostNonNestableDelayedTask(
 | 
|  }
 | 
|  
 | 
|  void MessageLoop::Run() {
 | 
| +  DCHECK(pump_);
 | 
|    RunLoop run_loop;
 | 
|    run_loop.Run();
 | 
|  }
 | 
|  
 | 
|  void MessageLoop::RunUntilIdle() {
 | 
| +  DCHECK(pump_);
 | 
|    RunLoop run_loop;
 | 
|    run_loop.RunUntilIdle();
 | 
|  }
 | 
| @@ -383,13 +367,43 @@ bool MessageLoop::IsIdleForTesting() {
 | 
|  
 | 
|  //------------------------------------------------------------------------------
 | 
|  
 | 
| -void MessageLoop::Init() {
 | 
| +scoped_ptr<MessageLoop> MessageLoop::CreateUnbound(
 | 
| +    Type type, MessagePumpFactoryCallback pump_factory) {
 | 
| +  return make_scoped_ptr(new MessageLoop(type, pump_factory));
 | 
| +}
 | 
| +
 | 
| +MessageLoop::MessageLoop(Type type, MessagePumpFactoryCallback pump_factory)
 | 
| +    : type_(type),
 | 
| +#if defined(OS_WIN)
 | 
| +      pending_high_res_tasks_(0),
 | 
| +      in_high_res_mode_(false),
 | 
| +#endif
 | 
| +      nestable_tasks_allowed_(true),
 | 
| +#if defined(OS_WIN)
 | 
| +      os_modal_loop_(false),
 | 
| +#endif  // OS_WIN
 | 
| +      pump_factory_(pump_factory),
 | 
| +      message_histogram_(NULL),
 | 
| +      run_loop_(NULL),
 | 
| +      incoming_task_queue_(new internal::IncomingTaskQueue(this)),
 | 
| +      message_loop_proxy_(
 | 
| +          new internal::MessageLoopProxyImpl(incoming_task_queue_)) {
 | 
| +  // If type is TYPE_CUSTOM non-null pump_factory must be given.
 | 
| +  DCHECK_EQ(type_ == TYPE_CUSTOM, !pump_factory_.is_null());
 | 
| +}
 | 
| +
 | 
| +void MessageLoop::BindToCurrentThread() {
 | 
| +  DCHECK(!pump_);
 | 
| +  if (!pump_factory_.is_null())
 | 
| +    pump_ = pump_factory_.Run();
 | 
| +  else
 | 
| +    pump_ = CreateMessagePumpForType(type_);
 | 
| +
 | 
|    DCHECK(!current()) << "should only have one message loop per thread";
 | 
|    lazy_tls_ptr.Pointer()->Set(this);
 | 
|  
 | 
| -  incoming_task_queue_ = new internal::IncomingTaskQueue(this);
 | 
| -  message_loop_proxy_ =
 | 
| -      new internal::MessageLoopProxyImpl(incoming_task_queue_);
 | 
| +  incoming_task_queue_->StartScheduling();
 | 
| +  message_loop_proxy_->BindToCurrentThread();
 | 
|    thread_task_runner_handle_.reset(
 | 
|        new ThreadTaskRunnerHandle(message_loop_proxy_));
 | 
|  }
 | 
| 
 |