summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjorlow@chromium.org <jorlow@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-26 20:46:06 +0000
committerjorlow@chromium.org <jorlow@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2009-06-26 20:46:06 +0000
commit3bf335afc98d4f9e85bb5a3f72974d53cb77ebeb (patch)
tree876769a0f2b23932c691d25edde4c0074ef87bbe
parent4411c21f13e7da66f3c9d394f40c1f10b6d20782 (diff)
downloadchromium_src-3bf335afc98d4f9e85bb5a3f72974d53cb77ebeb.zip
chromium_src-3bf335afc98d4f9e85bb5a3f72974d53cb77ebeb.tar.gz
chromium_src-3bf335afc98d4f9e85bb5a3f72974d53cb77ebeb.tar.bz2
Create a webkit thread for use within the browser process. This patch also includes some (soon to be fleshed out in another CL) code to demonstrate how it'll be used in DOM Storage.
BUG=None TEST=None Review URL: http://codereview.chromium.org/139003 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@19413 0039d316-1c4b-4281-b951-d872f2087c98
-rw-r--r--chrome/browser/in_process_webkit/browser_webkitclient_impl.cc78
-rw-r--r--chrome/browser/in_process_webkit/browser_webkitclient_impl.h32
-rw-r--r--chrome/browser/in_process_webkit/dom_storage_dispatcher_host.cc70
-rw-r--r--chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h58
-rw-r--r--chrome/browser/in_process_webkit/dom_storage_dispatcher_host_unittest.cc9
-rw-r--r--chrome/browser/in_process_webkit/webkit_context.cc13
-rw-r--r--chrome/browser/in_process_webkit/webkit_context.h30
-rw-r--r--chrome/browser/in_process_webkit/webkit_context_unittest.cc20
-rw-r--r--chrome/browser/in_process_webkit/webkit_thread.cc69
-rw-r--r--chrome/browser/in_process_webkit/webkit_thread.h75
-rw-r--r--chrome/browser/in_process_webkit/webkit_thread_unittest.cc17
-rw-r--r--chrome/browser/profile.cc19
-rw-r--r--chrome/browser/profile.h6
-rw-r--r--chrome/browser/renderer_host/resource_dispatcher_host.cc2
-rw-r--r--chrome/browser/renderer_host/resource_dispatcher_host.h7
-rw-r--r--chrome/browser/renderer_host/resource_message_filter.cc16
-rw-r--r--chrome/browser/renderer_host/resource_message_filter.h6
-rw-r--r--chrome/chrome.gyp11
-rw-r--r--chrome/test/testing_profile.h6
19 files changed, 539 insertions, 5 deletions
diff --git a/chrome/browser/in_process_webkit/browser_webkitclient_impl.cc b/chrome/browser/in_process_webkit/browser_webkitclient_impl.cc
new file mode 100644
index 0000000..58d549a
--- /dev/null
+++ b/chrome/browser/in_process_webkit/browser_webkitclient_impl.cc
@@ -0,0 +1,78 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#include "chrome/browser/in_process_webkit/browser_webkitclient_impl.h"
+
+#include "base/logging.h"
+#include "webkit/api/public/WebData.h"
+#include "webkit/api/public/WebString.h"
+#include "webkit/api/public/WebURL.h"
+
+WebKit::WebClipboard* BrowserWebKitClientImpl::clipboard() {
+ NOTREACHED();
+ return NULL;
+}
+
+WebKit::WebMimeRegistry* BrowserWebKitClientImpl::mimeRegistry() {
+ NOTREACHED();
+ return NULL;
+}
+
+WebKit::WebSandboxSupport* BrowserWebKitClientImpl::sandboxSupport() {
+ NOTREACHED();
+ return NULL;
+}
+
+unsigned long long BrowserWebKitClientImpl::visitedLinkHash(
+ const char* canonical_url,
+ size_t length) {
+ NOTREACHED();
+ return 0;
+}
+
+bool BrowserWebKitClientImpl::isLinkVisited(unsigned long long link_hash) {
+ NOTREACHED();
+ return false;
+}
+
+void BrowserWebKitClientImpl::setCookies(const WebKit::WebURL& url,
+ const WebKit::WebURL& policy_url,
+ const WebKit::WebString& value) {
+ NOTREACHED();
+}
+
+WebKit::WebString BrowserWebKitClientImpl::cookies(
+ const WebKit::WebURL& url, const WebKit::WebURL& policy_url) {
+ NOTREACHED();
+ return WebKit::WebString();
+}
+
+void BrowserWebKitClientImpl::prefetchHostName(const WebKit::WebString&) {
+ NOTREACHED();
+}
+
+WebKit::WebString BrowserWebKitClientImpl::defaultLocale() {
+ NOTREACHED();
+ return WebKit::WebString();
+}
+
+WebKit::WebThemeEngine* BrowserWebKitClientImpl::themeEngine() {
+ NOTREACHED();
+ return NULL;
+}
+
+WebKit::WebURLLoader* BrowserWebKitClientImpl::createURLLoader() {
+ NOTREACHED();
+ return NULL;
+}
+
+void BrowserWebKitClientImpl::getPluginList(bool refresh,
+ WebKit::WebPluginListBuilder* builder) {
+ NOTREACHED();
+}
+
+WebKit::WebData BrowserWebKitClientImpl::loadResource(const char* name) {
+ NOTREACHED();
+ return WebKit::WebData();
+}
diff --git a/chrome/browser/in_process_webkit/browser_webkitclient_impl.h b/chrome/browser/in_process_webkit/browser_webkitclient_impl.h
new file mode 100644
index 0000000..52ee5e2
--- /dev/null
+++ b/chrome/browser/in_process_webkit/browser_webkitclient_impl.h
@@ -0,0 +1,32 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#ifndef CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CLIENT_IMPL_H_
+#define CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CLIENT_IMPL_H_
+
+#include "webkit/glue/webkitclient_impl.h"
+
+class BrowserWebKitClientImpl : public webkit_glue::WebKitClientImpl {
+ public:
+ // WebKitClient methods:
+ virtual WebKit::WebClipboard* clipboard();
+ virtual WebKit::WebMimeRegistry* mimeRegistry();
+ virtual WebKit::WebSandboxSupport* sandboxSupport();
+ virtual unsigned long long visitedLinkHash(const char* canonicalURL,
+ size_t length);
+ virtual bool isLinkVisited(unsigned long long linkHash);
+ virtual void setCookies(const WebKit::WebURL& url,
+ const WebKit::WebURL& policy_url,
+ const WebKit::WebString& value);
+ virtual WebKit::WebString cookies(const WebKit::WebURL& url,
+ const WebKit::WebURL& policy_url);
+ virtual void prefetchHostName(const WebKit::WebString&);
+ virtual WebKit::WebString defaultLocale();
+ virtual WebKit::WebThemeEngine* themeEngine();
+ virtual WebKit::WebURLLoader* createURLLoader();
+ virtual void getPluginList(bool refresh, WebKit::WebPluginListBuilder*);
+ virtual WebKit::WebData loadResource(const char* name);
+};
+
+#endif // CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CLIENT_IMPL_H_
diff --git a/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.cc b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.cc
new file mode 100644
index 0000000..cbbf9ff
--- /dev/null
+++ b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.cc
@@ -0,0 +1,70 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#include "chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h"
+
+#include "chrome/browser/chrome_thread.h"
+#include "chrome/browser/in_process_webkit/webkit_context.h"
+#include "chrome/browser/in_process_webkit/webkit_thread.h"
+
+DOMStorageDispatcherHost::DOMStorageDispatcherHost(
+ IPC::Message::Sender* message_sender,
+ WebKitContext* webkit_context,
+ WebKitThread* webkit_thread)
+ : webkit_context_(webkit_context),
+ webkit_thread_(webkit_thread),
+ message_sender_(message_sender) {
+ DCHECK(webkit_context_.get());
+ DCHECK(webkit_thread_.get());
+ DCHECK(message_sender_);
+}
+
+DOMStorageDispatcherHost::~DOMStorageDispatcherHost() {
+ DCHECK(!message_sender_);
+}
+
+void DOMStorageDispatcherHost::Shutdown() {
+ DCHECK(IsOnIOThread());
+ AutoLock lock(message_sender_lock_);
+ message_sender_ = NULL;
+}
+
+bool DOMStorageDispatcherHost::OnMessageReceived(const IPC::Message& msg) {
+ // TODO(jorlow): Implement DOM Storage's message handler...and the rest
+ // of DOM Storage. :-)
+ return false;
+}
+
+void DOMStorageDispatcherHost::Send(IPC::Message* message) {
+ if (IsOnIOThread()) {
+ if (message_sender_)
+ message_sender_->Send(message);
+ else
+ delete message;
+ }
+
+ // If message_sender_ is NULL, the IO thread has either gone away
+ // or will do so soon. By holding this lock until we finish posting to the
+ // thread, we block the IO thread from completely shutting down benieth us.
+ AutoLock lock(message_sender_lock_);
+ if (!message_sender_) {
+ delete message;
+ return;
+ }
+
+ MessageLoop* io_loop = ChromeThread::GetMessageLoop(ChromeThread::IO);
+ CancelableTask* task = NewRunnableMethod(this,
+ &DOMStorageDispatcherHost::Send,
+ message);
+ io_loop->PostTask(FROM_HERE, task);
+}
+
+bool DOMStorageDispatcherHost::IsOnIOThread() const {
+ MessageLoop* io_loop = ChromeThread::GetMessageLoop(ChromeThread::IO);
+ return MessageLoop::current() == io_loop;
+}
+
+bool DOMStorageDispatcherHost::IsOnWebKitThread() const {
+ return MessageLoop::current() == webkit_thread_->GetMessageLoop();
+}
diff --git a/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h
new file mode 100644
index 0000000..a7b815f
--- /dev/null
+++ b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h
@@ -0,0 +1,58 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#ifndef CHROME_BROWSER_IN_PROCESS_WEBKIT_DOM_STORAGE_DISPATCHER_HOST_H_
+#define CHROME_BROWSER_IN_PROCESS_WEBKIT_DOM_STORAGE_DISPATCHER_HOST_H_
+
+#include "base/ref_counted.h"
+#include "base/thread.h"
+#include "chrome/common/ipc_message.h"
+
+class WebKitContext;
+class WebKitThread;
+
+// This class handles the logistics of DOM Storage within the browser process.
+// It mostly ferries information between IPCs and the WebKit implementations,
+// but it also handles some special cases like when renderer processes die.
+// THIS CLASS MUST NOT BE DESTROYED ON THE WEBKIT THREAD (for now).
+class DOMStorageDispatcherHost :
+ public base::RefCountedThreadSafe<DOMStorageDispatcherHost> {
+ public:
+ // Only call the constructor from the UI thread.
+ DOMStorageDispatcherHost(IPC::Message::Sender* message_sender,
+ WebKitContext*, WebKitThread*);
+
+ // Only call Shutdown from the IO thread. Shutdown warns us that we're going
+ // to go away soon and tells us not to send anything else to the IO thread.
+ void Shutdown();
+
+ // Only call from IO thread.
+ bool OnMessageReceived(const IPC::Message& message);
+
+ // Send a message to the renderer process associated with our
+ // message_sender_ via the IO thread. May be called from any thread.
+ void Send(IPC::Message* message);
+
+ private:
+ friend class base::RefCountedThreadSafe<DOMStorageDispatcherHost>;
+ ~DOMStorageDispatcherHost();
+
+ // Obviously can be called from any thread.
+ bool IsOnIOThread() const;
+ bool IsOnWebKitThread() const;
+
+ // Are immutable and are always valid throughout the lifetime of the object.
+ scoped_refptr<WebKitContext> webkit_context_;
+ scoped_refptr<WebKitThread> webkit_thread_;
+
+ // We keep the message_sender_ pointer for sending messages. All access
+ // to the message_sender_ (and the IO thread in general) should be done under
+ // this lock and only if message_sender_ is non-NULL.
+ Lock message_sender_lock_;
+ IPC::Message::Sender* message_sender_;
+
+ DISALLOW_IMPLICIT_CONSTRUCTORS(DOMStorageDispatcherHost);
+};
+
+#endif // CHROME_BROWSER_IN_PROCESS_WEBKIT_DOM_STORAGE_DISPATCHER_HOST_H_
diff --git a/chrome/browser/in_process_webkit/dom_storage_dispatcher_host_unittest.cc b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host_unittest.cc
new file mode 100644
index 0000000..a277492
--- /dev/null
+++ b/chrome/browser/in_process_webkit/dom_storage_dispatcher_host_unittest.cc
@@ -0,0 +1,9 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+// TODO(jorlow): Write once dom_storage_dispatcher_host is more than just a
+// stub.
diff --git a/chrome/browser/in_process_webkit/webkit_context.cc b/chrome/browser/in_process_webkit/webkit_context.cc
new file mode 100644
index 0000000..e7d7d1a
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_context.cc
@@ -0,0 +1,13 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#include "chrome/browser/in_process_webkit/webkit_context.h"
+
+WebKitContext::WebKitContext(const FilePath& data_path, bool is_incognito)
+ : data_path_(data_path),
+ is_incognito_(is_incognito) {
+}
+
+WebKitContext::~WebKitContext() {
+}
diff --git a/chrome/browser/in_process_webkit/webkit_context.h b/chrome/browser/in_process_webkit/webkit_context.h
new file mode 100644
index 0000000..2b84224
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_context.h
@@ -0,0 +1,30 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#ifndef CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CONTEXT_H_
+#define CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CONTEXT_H_
+
+#include "base/file_path.h"
+#include "base/ref_counted.h"
+
+// There's one WebKitContext per profile. Various DispatcherHost classes
+// have a pointer to the Context to store shared state.
+class WebKitContext : public base::RefCountedThreadSafe<WebKitContext> {
+ public:
+ WebKitContext(const FilePath& data_path, bool is_incognito);
+
+ const FilePath& data_path() const { return data_path_; }
+ bool is_incognito() const { return is_incognito_; }
+
+ private:
+ friend class base::RefCountedThreadSafe<WebKitContext>;
+ ~WebKitContext();
+
+ FilePath data_path_;
+ bool is_incognito_;
+
+ DISALLOW_IMPLICIT_CONSTRUCTORS(WebKitContext);
+};
+
+#endif // CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_CONTEXT_H_
diff --git a/chrome/browser/in_process_webkit/webkit_context_unittest.cc b/chrome/browser/in_process_webkit/webkit_context_unittest.cc
new file mode 100644
index 0000000..e5f446d
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_context_unittest.cc
@@ -0,0 +1,20 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/in_process_webkit/webkit_context.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+TEST(WebKitContextTest, BasicsTest1) {
+ FilePath file_path;
+ scoped_refptr<WebKitContext> context = new WebKitContext(file_path, true);
+ ASSERT_TRUE(file_path == context->data_path());
+ ASSERT_EQ(true, context->is_incognito());
+}
+
+TEST(WebKitContextTest, BasicsTest2) {
+ FilePath file_path;
+ scoped_refptr<WebKitContext> context = new WebKitContext(file_path, false);
+ ASSERT_TRUE(file_path == context->data_path());
+ ASSERT_EQ(false, context->is_incognito());
+}
diff --git a/chrome/browser/in_process_webkit/webkit_thread.cc b/chrome/browser/in_process_webkit/webkit_thread.cc
new file mode 100644
index 0000000..55772c6
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_thread.cc
@@ -0,0 +1,69 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#include "chrome/browser/in_process_webkit/webkit_thread.h"
+
+#include "chrome/browser/in_process_webkit/browser_webkitclient_impl.h"
+#include "webkit/api/public/WebKit.h"
+
+base::LazyInstance<Lock> WebKitThread::global_webkit_lock_(
+ base::LINKER_INITIALIZED);
+int WebKitThread::global_webkit_ref_count_ = 0;
+WebKitThread::InternalWebKitThread* WebKitThread::global_webkit_thread_ = NULL;
+
+WebKitThread::WebKitThread()
+ : cached_webkit_thread_(NULL) {
+ // The thread is started lazily by InitializeThread().
+}
+
+WebKitThread::InternalWebKitThread::InternalWebKitThread()
+ : base::Thread("WebKit"),
+ webkit_client_(NULL) {
+}
+
+void WebKitThread::InternalWebKitThread::Init() {
+ DCHECK(!webkit_client_);
+ webkit_client_ = new BrowserWebKitClientImpl;
+ DCHECK(webkit_client_);
+ WebKit::initialize(webkit_client_);
+ // Don't do anything heavyweight here since this can block the IO thread from
+ // executing (since InitializeThread() is often called on the IO thread).
+}
+
+void WebKitThread::InternalWebKitThread::CleanUp() {
+ DCHECK(webkit_client_);
+ WebKit::shutdown();
+ delete webkit_client_;
+ webkit_client_ = NULL;
+}
+
+WebKitThread::~WebKitThread() {
+ AutoLock lock(global_webkit_lock_.Get());
+ if (cached_webkit_thread_) {
+ DCHECK(global_webkit_ref_count_ > 0);
+ if (--global_webkit_ref_count_ == 0) {
+ // TODO(jorlow): Make this safe.
+ DCHECK(MessageLoop::current() != global_webkit_thread_->message_loop());
+ global_webkit_thread_->Stop();
+ delete global_webkit_thread_;
+ global_webkit_thread_ = NULL;
+ }
+ }
+}
+
+void WebKitThread::InitializeThread() {
+ AutoLock lock(global_webkit_lock_.Get());
+ if (!cached_webkit_thread_) {
+ if (!global_webkit_thread_) {
+ global_webkit_thread_ = new InternalWebKitThread;
+ DCHECK(global_webkit_thread_);
+ bool started = global_webkit_thread_->Start();
+ DCHECK(started);
+ }
+ ++global_webkit_ref_count_;
+ // The cached version can be accessed outside of global_webkit_lock_.
+ cached_webkit_thread_ = global_webkit_thread_;
+ }
+ DCHECK(cached_webkit_thread_->IsRunning());
+}
diff --git a/chrome/browser/in_process_webkit/webkit_thread.h b/chrome/browser/in_process_webkit/webkit_thread.h
new file mode 100644
index 0000000..518fa66
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_thread.h
@@ -0,0 +1,75 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved. Use of this
+// source code is governed by a BSD-style license that can be found in the
+// LICENSE file.
+
+#ifndef CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_THREAD_H_
+#define CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_THREAD_H_
+
+#include "base/lazy_instance.h"
+#include "base/lock.h"
+#include "base/logging.h"
+#include "base/ref_counted.h"
+#include "base/thread.h"
+
+class BrowserWebKitClientImpl;
+
+// This is an object that represents WebKit's "main" thread within the browser
+// process. You can create as many instances of this class as you'd like;
+// they'll all point to the same thread and you're guaranteed they'll
+// initialize in a thread-safe way, though WebKitThread instances should
+// probably be shared when it's easy to do so. The first time you call
+// GetMessageLoop() or EnsureWebKitInitialized() the thread will be created
+// and WebKit initialized. When the last instance of WebKitThread is
+// destroyed, WebKit is shut down and the thread is stopped.
+// THIS CLASS MUST NOT BE DEREFED TO 0 ON THE WEBKIT THREAD (for now).
+class WebKitThread : public base::RefCountedThreadSafe<WebKitThread> {
+ public:
+ WebKitThread();
+
+ MessageLoop* GetMessageLoop() {
+ if (!cached_webkit_thread_)
+ InitializeThread();
+ return cached_webkit_thread_->message_loop();
+ }
+
+ void EnsureWebKitInitialized() {
+ if (!cached_webkit_thread_)
+ InitializeThread();
+ }
+
+ private:
+ // Must be private so that we can carefully control its lifetime.
+ class InternalWebKitThread : public base::Thread {
+ public:
+ InternalWebKitThread();
+ virtual ~InternalWebKitThread() { }
+ // Does the actual initialization and shutdown of WebKit. Called at the
+ // beginning and end of the thread's lifetime.
+ virtual void Init();
+ virtual void CleanUp();
+
+ private:
+ BrowserWebKitClientImpl* webkit_client_;
+ };
+
+ friend class base::RefCountedThreadSafe<WebKitThread>;
+ ~WebKitThread();
+
+ void InitializeThread();
+
+ // If this is set, then this object has incremented the global WebKit ref
+ // count and will shutdown the thread if it sees the ref count go to 0.
+ // It's assumed that once this is non-NULL, the pointer will be valid until
+ // destruction.
+ InternalWebKitThread* cached_webkit_thread_;
+
+ // If there are multiple WebKitThread object (should only be possible in
+ // unittests at the moment), make sure they all share one real thread.
+ static base::LazyInstance<Lock> global_webkit_lock_;
+ static int global_webkit_ref_count_;
+ static InternalWebKitThread* global_webkit_thread_;
+
+ DISALLOW_COPY_AND_ASSIGN(WebKitThread);
+};
+
+#endif // CHROME_BROWSER_IN_PROCESS_WEBKIT_WEBKIT_THREAD_H_
diff --git a/chrome/browser/in_process_webkit/webkit_thread_unittest.cc b/chrome/browser/in_process_webkit/webkit_thread_unittest.cc
new file mode 100644
index 0000000..f66a26c
--- /dev/null
+++ b/chrome/browser/in_process_webkit/webkit_thread_unittest.cc
@@ -0,0 +1,17 @@
+// Copyright (c) 2009 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "chrome/browser/in_process_webkit/webkit_thread.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+// This is important because if there are 2 different message loops, we must
+// have 2 different WebKit threads which would be very bad.
+TEST(WebKitThreadTest, TwoThreadsShareMessageLoopTest) {
+ scoped_refptr<WebKitThread> thread_a = new WebKitThread;
+ scoped_refptr<WebKitThread> thread_b = new WebKitThread;
+ MessageLoop* loop_a = thread_a->GetMessageLoop();
+ MessageLoop* loop_b = thread_b->GetMessageLoop();
+ ASSERT_FALSE(loop_a == NULL);
+ ASSERT_EQ(loop_a, loop_b);
+}
diff --git a/chrome/browser/profile.cc b/chrome/browser/profile.cc
index 35bf8c2..4c776f4 100644
--- a/chrome/browser/profile.cc
+++ b/chrome/browser/profile.cc
@@ -19,6 +19,7 @@
#include "chrome/browser/extensions/extensions_service.h"
#include "chrome/browser/extensions/user_script_master.h"
#include "chrome/browser/history/history.h"
+#include "chrome/browser/in_process_webkit/webkit_context.h"
#include "chrome/browser/net/chrome_url_request_context.h"
#include "chrome/browser/password_manager/password_store_default.h"
#include "chrome/browser/privacy_blacklist/blacklist.h"
@@ -347,6 +348,13 @@ class OffTheRecordProfileImpl : public Profile,
return profile_->GetSpellChecker();
}
+ virtual WebKitContext* GetWebKitContext() {
+ if (!webkit_context_.get())
+ webkit_context_ = new WebKitContext(GetPath(), true);
+ DCHECK(webkit_context_.get());
+ return webkit_context_.get();
+}
+
virtual ThumbnailStore* GetThumbnailStore() {
return NULL;
}
@@ -397,9 +405,11 @@ class OffTheRecordProfileImpl : public Profile,
// The download manager that only stores downloaded items in memory.
scoped_refptr<DownloadManager> download_manager_;
- // The download manager that only stores downloaded items in memory.
scoped_refptr<BrowserThemeProvider> theme_provider_;
+ // Use a special WebKit context for OTR browsing.
+ scoped_refptr<WebKitContext> webkit_context_;
+
// We don't want SSLHostState from the OTR profile to leak back to the main
// profile because then the main profile would learn some of the host names
// the user visited while OTR.
@@ -1069,6 +1079,13 @@ SpellChecker* ProfileImpl::GetSpellChecker() {
return spellchecker_;
}
+WebKitContext* ProfileImpl::GetWebKitContext() {
+ if (!webkit_context_.get())
+ webkit_context_ = new WebKitContext(path_, false);
+ DCHECK(webkit_context_.get());
+ return webkit_context_.get();
+}
+
void ProfileImpl::MarkAsCleanShutdown() {
if (prefs_.get()) {
// The session cleanly exited, set kSessionExitedCleanly appropriately.
diff --git a/chrome/browser/profile.h b/chrome/browser/profile.h
index 1501462..7190cc7 100644
--- a/chrome/browser/profile.h
+++ b/chrome/browser/profile.h
@@ -48,6 +48,7 @@ class URLRequestContext;
class UserScriptMaster;
class VisitedLinkMaster;
class WebDataService;
+class WebKitContext;
class Profile {
public:
@@ -274,6 +275,9 @@ class Profile {
// sent to the I/O thread where it is actually used.
virtual SpellChecker* GetSpellChecker() = 0;
+ // Returns the WebKitContext assigned to this profile.
+ virtual WebKitContext* GetWebKitContext() = 0;
+
// Marks the profile as cleanly shutdown.
//
// NOTE: this is invoked internally on a normal shutdown, but is public so
@@ -359,6 +363,7 @@ class ProfileImpl : public Profile,
virtual void ResetTabRestoreService();
virtual void ReinitializeSpellChecker();
virtual SpellChecker* GetSpellChecker();
+ virtual WebKitContext* GetWebKitContext();
virtual void MarkAsCleanShutdown();
virtual void InitExtensions();
virtual void InitWebResources();
@@ -429,6 +434,7 @@ class ProfileImpl : public Profile,
scoped_refptr<PasswordStore> password_store_;
scoped_refptr<SessionService> session_service_;
scoped_refptr<BrowserThemeProvider> theme_provider_;
+ scoped_refptr<WebKitContext> webkit_context_;
bool history_service_created_;
bool created_web_data_service_;
bool created_password_store_;
diff --git a/chrome/browser/renderer_host/resource_dispatcher_host.cc b/chrome/browser/renderer_host/resource_dispatcher_host.cc
index 75cccfc..36ddf5d 100644
--- a/chrome/browser/renderer_host/resource_dispatcher_host.cc
+++ b/chrome/browser/renderer_host/resource_dispatcher_host.cc
@@ -21,6 +21,7 @@
#include "chrome/browser/download/download_request_manager.h"
#include "chrome/browser/download/save_file_manager.h"
#include "chrome/browser/external_protocol_handler.h"
+#include "chrome/browser/in_process_webkit/webkit_thread.h"
#include "chrome/browser/plugin_service.h"
#include "chrome/browser/privacy_blacklist/blacklist.h"
#include "chrome/browser/profile.h"
@@ -155,6 +156,7 @@ ResourceDispatcherHost::ResourceDispatcherHost(MessageLoop* io_loop)
ALLOW_THIS_IN_INITIALIZER_LIST(
save_file_manager_(new SaveFileManager(ui_loop_, io_loop, this))),
safe_browsing_(new SafeBrowsingService),
+ webkit_thread_(new WebKitThread),
request_id_(-1),
plugin_service_(PluginService::GetInstance()),
ALLOW_THIS_IN_INITIALIZER_LIST(method_runner_(this)),
diff --git a/chrome/browser/renderer_host/resource_dispatcher_host.h b/chrome/browser/renderer_host/resource_dispatcher_host.h
index 685acdd..eaf6323 100644
--- a/chrome/browser/renderer_host/resource_dispatcher_host.h
+++ b/chrome/browser/renderer_host/resource_dispatcher_host.h
@@ -37,6 +37,7 @@ class PluginService;
class SafeBrowsingService;
class SaveFileManager;
class URLRequestContext;
+class WebKitThread;
struct ViewHostMsg_Resource_Request;
class ResourceDispatcherHost : public URLRequest::Delegate {
@@ -285,6 +286,10 @@ class ResourceDispatcherHost : public URLRequest::Delegate {
return safe_browsing_;
}
+ WebKitThread* webkit_thread() const {
+ return webkit_thread_;
+ }
+
MessageLoop* ui_loop() const { return ui_loop_; }
// Called when the onunload handler for a cross-site request has finished.
@@ -523,6 +528,8 @@ class ResourceDispatcherHost : public URLRequest::Delegate {
scoped_refptr<SafeBrowsingService> safe_browsing_;
+ scoped_refptr<WebKitThread> webkit_thread_;
+
// Request ID for browser initiated requests. request_ids generated by
// child processes are counted up from 0, while browser created requests
// start at -2 and go down from there. (We need to start at -2 because -1 is
diff --git a/chrome/browser/renderer_host/resource_message_filter.cc b/chrome/browser/renderer_host/resource_message_filter.cc
index 4728b17..2a745ec 100644
--- a/chrome/browser/renderer_host/resource_message_filter.cc
+++ b/chrome/browser/renderer_host/resource_message_filter.cc
@@ -13,6 +13,7 @@
#include "chrome/browser/chrome_plugin_browsing_context.h"
#include "chrome/browser/chrome_thread.h"
#include "chrome/browser/extensions/extension_message_service.h"
+#include "chrome/browser/in_process_webkit/dom_storage_dispatcher_host.h"
#include "chrome/browser/net/dns_global.h"
#include "chrome/browser/plugin_service.h"
#include "chrome/browser/profile.h"
@@ -136,12 +137,17 @@ ResourceMessageFilter::ResourceMessageFilter(
render_widget_helper_(render_widget_helper),
audio_renderer_host_(audio_renderer_host),
app_cache_dispatcher_host_(new AppCacheDispatcherHost),
+ ALLOW_THIS_IN_INITIALIZER_LIST(dom_storage_dispatcher_host_(
+ new DOMStorageDispatcherHost(this, profile->GetWebKitContext(),
+ resource_dispatcher_host->webkit_thread()))),
off_the_record_(profile->IsOffTheRecord()) {
DCHECK(request_context_.get());
DCHECK(request_context_->cookie_store());
DCHECK(media_request_context_.get());
DCHECK(media_request_context_->cookie_store());
DCHECK(audio_renderer_host_.get());
+ DCHECK(app_cache_dispatcher_host_.get());
+ DCHECK(dom_storage_dispatcher_host_.get());
}
ResourceMessageFilter::~ResourceMessageFilter() {
@@ -149,6 +155,8 @@ ResourceMessageFilter::~ResourceMessageFilter() {
DCHECK(MessageLoop::current() ==
ChromeThread::GetMessageLoop(ChromeThread::IO));
+ dom_storage_dispatcher_host_->Shutdown();
+
// Let interested observers know we are being deleted.
NotificationService::current()->Notify(
NotificationType::RESOURCE_MESSAGE_FILTER_SHUTDOWN,
@@ -223,10 +231,12 @@ bool ResourceMessageFilter::OnMessageReceived(const IPC::Message& message) {
bool handled = resource_dispatcher_host_->OnMessageReceived(
message, this, &msg_is_ok) ||
app_cache_dispatcher_host_->OnMessageReceived(
- message, &msg_is_ok);
- if (!handled && msg_is_ok)
- handled = audio_renderer_host_->OnMessageReceived(message, &msg_is_ok);
+ message, &msg_is_ok) ||
+ dom_storage_dispatcher_host_->OnMessageReceived(message) ||
+ audio_renderer_host_->OnMessageReceived(message, &msg_is_ok);
+
if (!handled) {
+ DCHECK(msg_is_ok); // It should have been marked handled if it wasn't OK.
handled = true;
IPC_BEGIN_MESSAGE_MAP_EX(ResourceMessageFilter, message, msg_is_ok)
// On Linux we need to dispatch these messages to the UI2 thread because
diff --git a/chrome/browser/renderer_host/resource_message_filter.h b/chrome/browser/renderer_host/resource_message_filter.h
index 268b4fb..d5b8057 100644
--- a/chrome/browser/renderer_host/resource_message_filter.h
+++ b/chrome/browser/renderer_host/resource_message_filter.h
@@ -32,6 +32,7 @@
class AppCacheDispatcherHost;
class AudioRendererHost;
class Clipboard;
+class DOMStorageDispatcherHost;
class Profile;
class RenderWidgetHelper;
class SpellChecker;
@@ -286,9 +287,12 @@ class ResourceMessageFilter : public IPC::ChannelProxy::MessageFilter,
// Object that should take care of audio related resource requests.
scoped_refptr<AudioRendererHost> audio_renderer_host_;
- // Handles appcache related messages
+ // Handles AppCache related messages.
scoped_ptr<AppCacheDispatcherHost> app_cache_dispatcher_host_;
+ // Handles DOM Storage related messages.
+ scoped_refptr<DOMStorageDispatcherHost> dom_storage_dispatcher_host_;
+
// Whether this process is used for off the record tabs.
bool off_the_record_;
diff --git a/chrome/chrome.gyp b/chrome/chrome.gyp
index 6f90dac..0a0c614 100644
--- a/chrome/chrome.gyp
+++ b/chrome/chrome.gyp
@@ -1134,6 +1134,14 @@
'browser/importer/mork_reader.h',
'browser/importer/toolbar_importer.cc',
'browser/importer/toolbar_importer.h',
+ 'browser/in_process_webkit/browser_webkitclient_impl.cc',
+ 'browser/in_process_webkit/browser_webkitclient_impl.h',
+ 'browser/in_process_webkit/dom_storage_dispatcher_host.cc',
+ 'browser/in_process_webkit/dom_storage_dispatcher_host.h',
+ 'browser/in_process_webkit/webkit_context.cc',
+ 'browser/in_process_webkit/webkit_context.h',
+ 'browser/in_process_webkit/webkit_thread.cc',
+ 'browser/in_process_webkit/webkit_thread.h',
'browser/input_window_dialog.h',
'browser/input_window_dialog_gtk.cc',
'browser/input_window_dialog_win.cc',
@@ -3453,6 +3461,9 @@
'browser/importer/importer_unittest.cc',
'browser/importer/toolbar_importer_unittest.cc',
'browser/importer/firefox_profile_lock_unittest.cc',
+ 'browser/in_process_webkit/dom_storage_dispatcher_host_unittest.cc',
+ 'browser/in_process_webkit/webkit_context_unittest.cc',
+ 'browser/in_process_webkit/webkit_thread_unittest.cc',
'browser/keychain_mock_mac.cc',
'browser/keychain_mock_mac.h',
'browser/login_prompt_unittest.cc',
diff --git a/chrome/test/testing_profile.h b/chrome/test/testing_profile.h
index b7daf41..d791fdd 100644
--- a/chrome/test/testing_profile.h
+++ b/chrome/test/testing_profile.h
@@ -204,6 +204,12 @@ class TestingProfile : public Profile {
virtual SpellChecker* GetSpellChecker() {
return NULL;
}
+ virtual WebKitContext* GetWebKitContext() {
+ return NULL;
+ }
+ virtual WebKitContext* GetOffTheRecordWebKitContext() {
+ return NULL;
+ }
virtual void MarkAsCleanShutdown() {
}
virtual void InitExtensions() {