Commit 744eac06 authored by Rohit Rao's avatar Rohit Rao Committed by Commit Bot

[ios] Adds MessagePumpUIApplication::Detach() and calls it on shutdown.

Adds Attach/Detach as virtual methods on MessagePumpCFRunLoopBase
so that they can be called unconditionally from SequenceManagerImpl.

BUG=1002087

Change-Id: I8263188aa388a449c799b7bde17e7dac8b44d3be
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/1826517
Commit-Queue: Rohit Rao <rohitrao@chromium.org>
Reviewed-by: default avatarAlex Clarke <alexclarke@chromium.org>
Reviewed-by: default avatarGabriel Charette <gab@chromium.org>
Cr-Commit-Position: refs/heads/master@{#718316}
parent d21b98cb
...@@ -88,6 +88,15 @@ class BASE_EXPORT MessagePumpCFRunLoopBase : public MessagePump { ...@@ -88,6 +88,15 @@ class BASE_EXPORT MessagePumpCFRunLoopBase : public MessagePump {
void ScheduleDelayedWork(const TimeTicks& delayed_work_time) override; void ScheduleDelayedWork(const TimeTicks& delayed_work_time) override;
void SetTimerSlack(TimerSlack timer_slack) override; void SetTimerSlack(TimerSlack timer_slack) override;
#if defined(OS_IOS)
// Some iOS message pumps do not support calling |Run()| to spin the main
// message loop directly. Instead, call |Attach()| to set up a delegate, then
// |Detach()| before destroying the message pump. These methods do nothing if
// the message pump supports calling |Run()| and |Quit()|.
virtual void Attach(Delegate* delegate);
virtual void Detach();
#endif // OS_IOS
protected: protected:
// Needs access to CreateAutoreleasePool. // Needs access to CreateAutoreleasePool.
friend class MessagePumpScopedAutoreleasePool; friend class MessagePumpScopedAutoreleasePool;
...@@ -332,9 +341,12 @@ class MessagePumpUIApplication : public MessagePumpCFRunLoopBase { ...@@ -332,9 +341,12 @@ class MessagePumpUIApplication : public MessagePumpCFRunLoopBase {
void DoRun(Delegate* delegate) override; void DoRun(Delegate* delegate) override;
bool DoQuit() override; bool DoQuit() override;
// This message pump can not spin the main message loop directly. Instead, // MessagePumpCFRunLoopBase.
// call |Attach()| to set up a delegate. It is an error to call |Run()|. // MessagePumpUIApplication can not spin the main message loop directly.
virtual void Attach(Delegate* delegate); // Instead, call |Attach()| to set up a delegate. It is an error to call
// |Run()|.
void Attach(Delegate* delegate) override;
void Detach() override;
private: private:
RunLoop* run_loop_; RunLoop* run_loop_;
......
...@@ -234,6 +234,12 @@ void MessagePumpCFRunLoopBase::SetTimerSlack(TimerSlack timer_slack) { ...@@ -234,6 +234,12 @@ void MessagePumpCFRunLoopBase::SetTimerSlack(TimerSlack timer_slack) {
timer_slack_ = timer_slack; timer_slack_ = timer_slack;
} }
#if defined(OS_IOS)
void MessagePumpCFRunLoopBase::Attach(Delegate* delegate) {}
void MessagePumpCFRunLoopBase::Detach() {}
#endif // OS_IOS
// Must be called on the run loop thread. // Must be called on the run loop thread.
MessagePumpCFRunLoopBase::MessagePumpCFRunLoopBase(int initial_mode_mask) MessagePumpCFRunLoopBase::MessagePumpCFRunLoopBase(int initial_mode_mask)
: delegate_(NULL), : delegate_(NULL),
...@@ -797,6 +803,13 @@ void MessagePumpUIApplication::Attach(Delegate* delegate) { ...@@ -797,6 +803,13 @@ void MessagePumpUIApplication::Attach(Delegate* delegate) {
SetDelegate(delegate); SetDelegate(delegate);
} }
void MessagePumpUIApplication::Detach() {
DCHECK(run_loop_);
run_loop_->AfterRun();
SetDelegate(nullptr);
run_loop_ = nullptr;
}
#else #else
ScopedPumpMessagesInPrivateModes::ScopedPumpMessagesInPrivateModes() { ScopedPumpMessagesInPrivateModes::ScopedPumpMessagesInPrivateModes() {
......
...@@ -46,9 +46,10 @@ bool PumpTypeUsesDoSomeWork(MessagePumpType type) { ...@@ -46,9 +46,10 @@ bool PumpTypeUsesDoSomeWork(MessagePumpType type) {
case MessagePumpType::UI: case MessagePumpType::UI:
#if defined(OS_IOS) #if defined(OS_IOS)
// iOS uses a MessagePumpDefault for UI in unit tests, ref. // iOS uses a MessagePumpCFRunLoop for UI in unit tests, ref.
// test_support_ios.mm::CreateMessagePumpForUIForTests(). // test_support_ios.mm::CreateMessagePumpForUIForTests(). TODO(gab):
return true; // migrate MessagePumpCFRunLoop too.
return false;
#elif defined(OS_WIN) || defined(OS_ANDROID) || defined(USE_GLIB) #elif defined(OS_WIN) || defined(OS_ANDROID) || defined(USE_GLIB)
return true; return true;
#elif defined(OS_POSIX) && !defined(OS_NACL_SFI) #elif defined(OS_POSIX) && !defined(OS_NACL_SFI)
......
...@@ -215,6 +215,13 @@ SequenceManagerImpl::~SequenceManagerImpl() { ...@@ -215,6 +215,13 @@ SequenceManagerImpl::~SequenceManagerImpl() {
TRACE_EVENT_OBJECT_DELETED_WITH_ID( TRACE_EVENT_OBJECT_DELETED_WITH_ID(
TRACE_DISABLED_BY_DEFAULT("sequence_manager"), "SequenceManager", this); TRACE_DISABLED_BY_DEFAULT("sequence_manager"), "SequenceManager", this);
#if defined(OS_IOS)
if (settings_.message_loop_type == MessagePumpType::UI &&
associated_thread_->IsBound()) {
controller_->DetachFromMessagePump();
}
#endif
// Make sure no Task is running as given that RunLoop does not support the // Make sure no Task is running as given that RunLoop does not support the
// Delegate being destroyed from a Task and // Delegate being destroyed from a Task and
// ThreadControllerWithMessagePumpImpl does not support being destroyed from a // ThreadControllerWithMessagePumpImpl does not support being destroyed from a
...@@ -313,6 +320,13 @@ void SequenceManagerImpl::BindToMessagePump(std::unique_ptr<MessagePump> pump) { ...@@ -313,6 +320,13 @@ void SequenceManagerImpl::BindToMessagePump(std::unique_ptr<MessagePump> pump) {
controller_->AttachToMessagePump(); controller_->AttachToMessagePump();
} }
#endif #endif
// On iOS attach to the native loop when there is one.
#if defined(OS_IOS)
if (settings_.message_loop_type == MessagePumpType::UI) {
controller_->AttachToMessagePump();
}
#endif
} }
void SequenceManagerImpl::BindToCurrentThread() { void SequenceManagerImpl::BindToCurrentThread() {
......
...@@ -96,6 +96,12 @@ class ThreadController { ...@@ -96,6 +96,12 @@ class ThreadController {
virtual void AttachToMessagePump() = 0; virtual void AttachToMessagePump() = 0;
#endif #endif
#if defined(OS_IOS)
// Detaches this ThreadController from the message pump, allowing the
// controller to be shut down cleanly.
virtual void DetachFromMessagePump() = 0;
#endif
// TODO(altimin): Get rid of the methods below. // TODO(altimin): Get rid of the methods below.
// These methods exist due to current integration of SequenceManager // These methods exist due to current integration of SequenceManager
// with MessageLoop. // with MessageLoop.
......
...@@ -322,7 +322,13 @@ MessagePump* ThreadControllerImpl::GetBoundMessagePump() const { ...@@ -322,7 +322,13 @@ MessagePump* ThreadControllerImpl::GetBoundMessagePump() const {
void ThreadControllerImpl::AttachToMessagePump() { void ThreadControllerImpl::AttachToMessagePump() {
NOTREACHED(); NOTREACHED();
} }
#endif #endif // OS_IOS || OS_ANDROID
#if defined(OS_IOS)
void ThreadControllerImpl::DetachFromMessagePump() {
NOTREACHED();
}
#endif // OS_IOS
} // namespace internal } // namespace internal
} // namespace sequence_manager } // namespace sequence_manager
......
...@@ -66,6 +66,9 @@ class BASE_EXPORT ThreadControllerImpl : public ThreadController, ...@@ -66,6 +66,9 @@ class BASE_EXPORT ThreadControllerImpl : public ThreadController,
MessagePump* GetBoundMessagePump() const override; MessagePump* GetBoundMessagePump() const override;
#if defined(OS_IOS) || defined(OS_ANDROID) #if defined(OS_IOS) || defined(OS_ANDROID)
void AttachToMessagePump() override; void AttachToMessagePump() override;
#endif
#if defined(OS_IOS)
void DetachFromMessagePump() override;
#endif #endif
bool ShouldQuitRunLoopWhenIdle() override; bool ShouldQuitRunLoopWhenIdle() override;
......
...@@ -527,7 +527,11 @@ MessagePump* ThreadControllerWithMessagePumpImpl::GetBoundMessagePump() const { ...@@ -527,7 +527,11 @@ MessagePump* ThreadControllerWithMessagePumpImpl::GetBoundMessagePump() const {
#if defined(OS_IOS) #if defined(OS_IOS)
void ThreadControllerWithMessagePumpImpl::AttachToMessagePump() { void ThreadControllerWithMessagePumpImpl::AttachToMessagePump() {
static_cast<MessagePumpUIApplication*>(pump_.get())->Attach(this); static_cast<MessagePumpCFRunLoopBase*>(pump_.get())->Attach(this);
}
void ThreadControllerWithMessagePumpImpl::DetachFromMessagePump() {
static_cast<MessagePumpCFRunLoopBase*>(pump_.get())->Detach();
} }
#elif defined(OS_ANDROID) #elif defined(OS_ANDROID)
void ThreadControllerWithMessagePumpImpl::AttachToMessagePump() { void ThreadControllerWithMessagePumpImpl::AttachToMessagePump() {
......
...@@ -67,6 +67,9 @@ class BASE_EXPORT ThreadControllerWithMessagePumpImpl ...@@ -67,6 +67,9 @@ class BASE_EXPORT ThreadControllerWithMessagePumpImpl
MessagePump* GetBoundMessagePump() const override; MessagePump* GetBoundMessagePump() const override;
#if defined(OS_IOS) || defined(OS_ANDROID) #if defined(OS_IOS) || defined(OS_ANDROID)
void AttachToMessagePump() override; void AttachToMessagePump() override;
#endif
#if defined(OS_IOS)
void DetachFromMessagePump() override;
#endif #endif
bool ShouldQuitRunLoopWhenIdle() override; bool ShouldQuitRunLoopWhenIdle() override;
......
...@@ -21,14 +21,6 @@ SingleThreadTaskExecutor::SingleThreadTaskExecutor(MessagePumpType type) ...@@ -21,14 +21,6 @@ SingleThreadTaskExecutor::SingleThreadTaskExecutor(MessagePumpType type)
simple_task_executor_(sequence_manager_.get(), task_runner()) { simple_task_executor_(sequence_manager_.get(), task_runner()) {
sequence_manager_->SetDefaultTaskRunner(default_task_queue_->task_runner()); sequence_manager_->SetDefaultTaskRunner(default_task_queue_->task_runner());
sequence_manager_->BindToMessagePump(MessagePump::Create(type)); sequence_manager_->BindToMessagePump(MessagePump::Create(type));
#if defined(OS_IOS)
if (type == MessagePumpType::UI) {
static_cast<sequence_manager::internal::SequenceManagerImpl*>(
sequence_manager_.get())
->AttachToMessagePump();
}
#endif
} }
SingleThreadTaskExecutor::~SingleThreadTaskExecutor() = default; SingleThreadTaskExecutor::~SingleThreadTaskExecutor() = default;
......
...@@ -11,7 +11,7 @@ ...@@ -11,7 +11,7 @@
#include "base/logging.h" #include "base/logging.h"
#include "base/mac/scoped_nsobject.h" #include "base/mac/scoped_nsobject.h"
#include "base/message_loop/message_pump.h" #include "base/message_loop/message_pump.h"
#include "base/message_loop/message_pump_default.h" #include "base/message_loop/message_pump_mac.h"
#import "base/test/ios/google_test_runner_delegate.h" #import "base/test/ios/google_test_runner_delegate.h"
#include "base/test/test_suite.h" #include "base/test/test_suite.h"
#include "base/test/test_switches.h" #include "base/test/test_switches.h"
...@@ -199,8 +199,8 @@ static char** g_argv; ...@@ -199,8 +199,8 @@ static char** g_argv;
namespace { namespace {
std::unique_ptr<base::MessagePump> CreateMessagePumpForUIForTests() { std::unique_ptr<base::MessagePump> CreateMessagePumpForUIForTests() {
// A default MessagePump will do quite nicely in tests. // A basic MessagePump will do quite nicely in tests.
return std::unique_ptr<base::MessagePump>(new base::MessagePumpDefault()); return std::unique_ptr<base::MessagePump>(new base::MessagePumpCFRunLoop());
} }
} // namespace } // namespace
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment