From 895ddf680e1f9fc8a01f40fb569a6f58bc99196a Mon Sep 17 00:00:00 2001 From: Andras Becsi Date: Tue, 9 Jul 2013 11:11:11 +0200 Subject: Refactor process initialization code Move parts of the initialization from the WebEngineContext ctor to ContentMainDelegateQt and BrowserMainPartsQt members so that they are executed in their respective stages of startup. Change-Id: Iefa288c6bf775ac530f183c0dcfebb6a3230d68d Reviewed-by: Simon Hausmann --- lib/content_browser_client_qt.cpp | 116 ++++++++++++++++++++++++++++++++-- lib/web_engine_context.cpp | 127 +++++--------------------------------- 2 files changed, 124 insertions(+), 119 deletions(-) diff --git a/lib/content_browser_client_qt.cpp b/lib/content_browser_client_qt.cpp index e4fcb5acb..d0c5bddce 100644 --- a/lib/content_browser_client_qt.cpp +++ b/lib/content_browser_client_qt.cpp @@ -41,16 +41,111 @@ #include "content_browser_client_qt.h" +#include "base/message_loop/message_loop.h" #include "content/public/browser/browser_main_parts.h" #include "content/public/common/main_function_params.h" #include "browser_context_qt.h" #include "web_contents_view_qt.h" +#include + namespace { ContentBrowserClientQt* gBrowserClient = 0; // Owned by ContentMainDelegateQt. +// Return a timeout suitable for the glib loop, -1 to block forever, +// 0 to return right away, or a timeout in milliseconds from now. +int GetTimeIntervalMilliseconds(const base::TimeTicks& from) { + if (from.is_null()) + return -1; + + // Be careful here. TimeDelta has a precision of microseconds, but we want a + // value in milliseconds. If there are 5.5ms left, should the delay be 5 or + // 6? It should be 6 to avoid executing delayed work too early. + int delay = static_cast( + ceil((from - base::TimeTicks::Now()).InMillisecondsF())); + + // If this value is negative, then we need to run delayed work soon. + return delay < 0 ? 0 : delay; +} + +class MessagePumpForUIQt : public QObject, + public base::MessagePump +{ +public: + MessagePumpForUIQt() + // Usually this gets passed through Run, but since we have + // our own event loop, attach it explicitly ourselves. + : m_delegate(base::MessageLoopForUI::current()) + { + } + + virtual void Run(Delegate *delegate) + { + // FIXME: This could be needed if we want to run Chromium tests. + // We could run a QEventLoop here. + Q_UNREACHABLE(); + } + + virtual void Quit() + { + Q_UNREACHABLE(); + } + + virtual void ScheduleWork() + { + QCoreApplication::postEvent(this, new QEvent(QEvent::User)); + } + + virtual void ScheduleDelayedWork(const base::TimeTicks &delayed_work_time) + { + startTimer(GetTimeIntervalMilliseconds(delayed_work_time)); + } + +protected: + virtual void customEvent(QEvent *ev) + { + if (handleScheduledWork()) + QCoreApplication::postEvent(this, new QEvent(QEvent::User)); + } + + virtual void timerEvent(QTimerEvent *ev) + { + killTimer(ev->timerId()); + + base::TimeTicks next_delayed_work_time; + m_delegate->DoDelayedWork(&next_delayed_work_time); + + if (!next_delayed_work_time.is_null()) + startTimer(GetTimeIntervalMilliseconds(next_delayed_work_time)); + } + +private: + bool handleScheduledWork() { + bool more_work_is_plausible = m_delegate->DoWork(); + + base::TimeTicks delayed_work_time; + more_work_is_plausible |= m_delegate->DoDelayedWork(&delayed_work_time); + + if (more_work_is_plausible) + return true; + + more_work_is_plausible |= m_delegate->DoIdleWork(); + if (!more_work_is_plausible && !delayed_work_time.is_null()) + startTimer(GetTimeIntervalMilliseconds(delayed_work_time)); + + return more_work_is_plausible; + } + + Delegate *m_delegate; +}; + +base::MessagePump* messagePumpFactory() +{ + return new MessagePumpForUIQt; +} + } // namespace class BrowserMainPartsQt : public content::BrowserMainParts @@ -62,12 +157,13 @@ public: , m_runMessageLoop(true) { } - void PreMainMessageLoopStart() { } - void PostMainMessageLoopStart() { } - void PreEarlyInitialization() { } - - void PreMainMessageLoopRun() { + void PreMainMessageLoopStart() Q_DECL_OVERRIDE + { + base::MessageLoop::InitMessagePumpForUIFactory(::messagePumpFactory); + } + void PreMainMessageLoopRun() Q_DECL_OVERRIDE + { m_browserContext.reset(new BrowserContextQt()); if (m_parameters.ui_task) { @@ -81,10 +177,17 @@ public: return !m_runMessageLoop; } - void PostMainMessageLoopRun() { + void PostMainMessageLoopRun() + { m_browserContext.reset(); } + int PreCreateThreads() Q_DECL_OVERRIDE + { + base::ThreadRestrictions::SetIOAllowed(true); + return 0; + } + BrowserContextQt* browser_context() const { return m_browserContext.get(); } @@ -132,6 +235,7 @@ content::BrowserMainParts *ContentBrowserClientQt::CreateBrowserMainParts(const BrowserContextQt* ContentBrowserClientQt::browser_context() { + Q_ASSERT(m_browserMainParts); return static_cast(m_browserMainParts)->browser_context(); } diff --git a/lib/web_engine_context.cpp b/lib/web_engine_context.cpp index 149e580b9..6428165a1 100644 --- a/lib/web_engine_context.cpp +++ b/lib/web_engine_context.cpp @@ -45,7 +45,6 @@ #include "base/command_line.h" #include "base/files/file_path.h" -#include "base/message_loop.h" #include "base/path_service.h" #include "base/run_loop.h" #include "base/threading/thread_restrictions.h" @@ -92,98 +91,6 @@ static QByteArray subProcessPath() { return processPath; } -// Return a timeout suitable for the glib loop, -1 to block forever, -// 0 to return right away, or a timeout in milliseconds from now. -int GetTimeIntervalMilliseconds(const base::TimeTicks& from) { - if (from.is_null()) - return -1; - - // Be careful here. TimeDelta has a precision of microseconds, but we want a - // value in milliseconds. If there are 5.5ms left, should the delay be 5 or - // 6? It should be 6 to avoid executing delayed work too early. - int delay = static_cast( - ceil((from - base::TimeTicks::Now()).InMillisecondsF())); - - // If this value is negative, then we need to run delayed work soon. - return delay < 0 ? 0 : delay; -} - -class MessagePumpForUIQt : public QObject, - public base::MessagePump -{ -public: - MessagePumpForUIQt() - // Usually this gets passed through Run, but since we have - // our own event loop, attach it explicitely ourselves. - : m_delegate(base::MessageLoopForUI::current()) - { - } - - virtual void Run(Delegate *delegate) - { - // FIXME: This could be needed if we want to run Chromium tests. - // We could run a QEventLoop here. - Q_ASSERT(false); - } - - virtual void Quit() - { - Q_ASSERT(false); - } - - virtual void ScheduleWork() - { - QCoreApplication::postEvent(this, new QEvent(QEvent::User)); - } - - virtual void ScheduleDelayedWork(const base::TimeTicks &delayed_work_time) - { - startTimer(GetTimeIntervalMilliseconds(delayed_work_time)); - } - -protected: - virtual void customEvent(QEvent *ev) - { - if (handleScheduledWork()) - QCoreApplication::postEvent(this, new QEvent(QEvent::User)); - } - - virtual void timerEvent(QTimerEvent *ev) - { - killTimer(ev->timerId()); - - base::TimeTicks next_delayed_work_time; - m_delegate->DoDelayedWork(&next_delayed_work_time); - - if (!next_delayed_work_time.is_null()) - startTimer(GetTimeIntervalMilliseconds(next_delayed_work_time)); - } - -private: - bool handleScheduledWork() { - bool more_work_is_plausible = m_delegate->DoWork(); - - base::TimeTicks delayed_work_time; - more_work_is_plausible |= m_delegate->DoDelayedWork(&delayed_work_time); - - if (more_work_is_plausible) - return true; - - more_work_is_plausible |= m_delegate->DoIdleWork(); - if (!more_work_is_plausible && !delayed_work_time.is_null()) - startTimer(GetTimeIntervalMilliseconds(delayed_work_time)); - - return more_work_is_plausible; - } - - Delegate *m_delegate; -}; - -base::MessagePump* messagePumpFactory() -{ - return new MessagePumpForUIQt; -} - class ContentMainDelegateQt : public content::ContentMainDelegate { public: @@ -205,34 +112,29 @@ private: scoped_ptr m_browserClient; }; -} +} // namespace WebEngineContext::WebEngineContext() { Q_ASSERT(!sContext); sContext = this; - { - std::string ua = webkit_glue::BuildUserAgentFromProduct("QtWebEngine/0.1"); - QByteArray userAgentParameter("--user-agent="); - userAgentParameter.append(QString::fromStdString(ua).toUtf8()); + std::string ua = webkit_glue::BuildUserAgentFromProduct("QtWebEngine/0.1"); + QByteArray userAgentParameter("--user-agent="); + userAgentParameter.append(QString::fromStdString(ua).toUtf8()); - QList args; - Q_FOREACH (const QString& arg, QCoreApplication::arguments()) - args << arg.toUtf8(); - args << userAgentParameter; - args << QByteArrayLiteral("--no-sandbox"); - args << QByteArrayLiteral("--disable-plugins"); + QList args; + Q_FOREACH (const QString& arg, QCoreApplication::arguments()) + args << arg.toUtf8(); + args << userAgentParameter; + args << QByteArrayLiteral("--no-sandbox"); + args << QByteArrayLiteral("--disable-plugins"); - const char* argv[args.size()]; - for (int i = 0; i < args.size(); ++i) - argv[i] = args[i].constData(); - - CommandLine::Init(args.size(), argv); - } + const char* argv[args.size()]; + for (int i = 0; i < args.size(); ++i) + argv[i] = args[i].constData(); - // This needs to be set before the MessageLoop is created by BrowserMainRunner. - base::MessageLoop::InitMessagePumpForUIFactory(::messagePumpFactory); + CommandLine::Init(args.size(), argv); static content::ContentMainRunner *runner = 0; if (!runner) { @@ -246,7 +148,6 @@ WebEngineContext::WebEngineContext() browserRunner->Initialize(content::MainFunctionParams(*CommandLine::ForCurrentProcess())); } - base::ThreadRestrictions::SetIOAllowed(true); // Once the MessageLoop has been created, attach a top-level RunLoop. m_runLoop.reset(new base::RunLoop); -- cgit v1.2.3