mirror of
https://bitbucket.org/chromiumembedded/cef
synced 2025-06-05 21:39:12 +02:00
- Update to Chromium revision 138235.
- Move to the new DOM storage backend. Persistent localStorage support will need to be re-implemented (issue #603). - Add CefV8Value::CreateUInt method and indicate that integer types are 32bit via usage of int32 and uint32 types (issue #331). - Add CefV8Context::Eval method for synchronous JavaScript execution that returns a value or exception (issue #444). - Move exception handling from an ExecuteFunction argument to a CefV8Value attribute (issue #546). - Make user data an attribute for all CefV8Value object types and not just CreateObject (issue #547). - Un-fork SQLitePersistentCookieStore by adding stub implementations for sqlite_diagnostics and browser_thread. - Update tools/cef_parser.py to match the CEF3 version. git-svn-id: https://chromiumembedded.googlecode.com/svn/trunk@644 5089003a-bbd8-11dd-ad1f-f1f9622dbc98
This commit is contained in:
291
cef1/libcef/browser_dom_storage_system.cc
Normal file
291
cef1/libcef/browser_dom_storage_system.cc
Normal file
@@ -0,0 +1,291 @@
|
||||
// Copyright (c) 2012 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 "libcef/browser_dom_storage_system.h"
|
||||
|
||||
#include "base/auto_reset.h"
|
||||
#include "googleurl/src/gurl.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebURL.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageArea.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageEventDispatcher.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageNamespace.h"
|
||||
#include "webkit/database/database_util.h"
|
||||
#include "webkit/dom_storage/dom_storage_area.h"
|
||||
#include "webkit/dom_storage/dom_storage_host.h"
|
||||
|
||||
using dom_storage::DomStorageContext;
|
||||
using dom_storage::DomStorageHost;
|
||||
using dom_storage::DomStorageSession;
|
||||
using webkit_database::DatabaseUtil;
|
||||
using WebKit::WebStorageArea;
|
||||
using WebKit::WebStorageNamespace;
|
||||
using WebKit::WebStorageEventDispatcher;
|
||||
using WebKit::WebString;
|
||||
using WebKit::WebURL;
|
||||
|
||||
namespace {
|
||||
const int kInvalidNamespaceId = -1;
|
||||
}
|
||||
|
||||
class BrowserDomStorageSystem::NamespaceImpl : public WebStorageNamespace {
|
||||
public:
|
||||
explicit NamespaceImpl(const base::WeakPtr<BrowserDomStorageSystem>& parent);
|
||||
NamespaceImpl(const base::WeakPtr<BrowserDomStorageSystem>& parent,
|
||||
int session_namespace_id);
|
||||
virtual ~NamespaceImpl();
|
||||
virtual WebStorageArea* createStorageArea(const WebString& origin) OVERRIDE;
|
||||
virtual WebStorageNamespace* copy() OVERRIDE;
|
||||
virtual bool isSameNamespace(const WebStorageNamespace&) const OVERRIDE;
|
||||
|
||||
private:
|
||||
DomStorageContext* Context() {
|
||||
if (!parent_.get())
|
||||
return NULL;
|
||||
return parent_->context_.get();
|
||||
}
|
||||
|
||||
base::WeakPtr<BrowserDomStorageSystem> parent_;
|
||||
int namespace_id_;
|
||||
};
|
||||
|
||||
class BrowserDomStorageSystem::AreaImpl : public WebStorageArea {
|
||||
public:
|
||||
AreaImpl(const base::WeakPtr<BrowserDomStorageSystem>& parent,
|
||||
int namespace_id, const GURL& origin);
|
||||
virtual ~AreaImpl();
|
||||
virtual unsigned length() OVERRIDE;
|
||||
virtual WebString key(unsigned index) OVERRIDE;
|
||||
virtual WebString getItem(const WebString& key) OVERRIDE;
|
||||
virtual void setItem(const WebString& key, const WebString& newValue,
|
||||
const WebURL&, Result&, WebString& oldValue) OVERRIDE;
|
||||
virtual void removeItem(const WebString& key, const WebURL& url,
|
||||
WebString& oldValue) OVERRIDE;
|
||||
virtual void clear(const WebURL& url, bool& somethingCleared) OVERRIDE;
|
||||
|
||||
private:
|
||||
DomStorageHost* Host() {
|
||||
if (!parent_.get())
|
||||
return NULL;
|
||||
return parent_->host_.get();
|
||||
}
|
||||
|
||||
base::WeakPtr<BrowserDomStorageSystem> parent_;
|
||||
int connection_id_;
|
||||
};
|
||||
|
||||
// NamespaceImpl -----------------------------
|
||||
|
||||
BrowserDomStorageSystem::NamespaceImpl::NamespaceImpl(
|
||||
const base::WeakPtr<BrowserDomStorageSystem>& parent)
|
||||
: parent_(parent),
|
||||
namespace_id_(dom_storage::kLocalStorageNamespaceId) {
|
||||
}
|
||||
|
||||
BrowserDomStorageSystem::NamespaceImpl::NamespaceImpl(
|
||||
const base::WeakPtr<BrowserDomStorageSystem>& parent,
|
||||
int session_namespace_id)
|
||||
: parent_(parent),
|
||||
namespace_id_(session_namespace_id) {
|
||||
}
|
||||
|
||||
BrowserDomStorageSystem::NamespaceImpl::~NamespaceImpl() {
|
||||
if (namespace_id_ == dom_storage::kLocalStorageNamespaceId ||
|
||||
namespace_id_ == kInvalidNamespaceId || !Context()) {
|
||||
return;
|
||||
}
|
||||
Context()->DeleteSessionNamespace(namespace_id_);
|
||||
}
|
||||
|
||||
WebStorageArea* BrowserDomStorageSystem::NamespaceImpl::createStorageArea(
|
||||
const WebString& origin) {
|
||||
return new AreaImpl(parent_, namespace_id_, GURL(origin));
|
||||
}
|
||||
|
||||
WebStorageNamespace* BrowserDomStorageSystem::NamespaceImpl::copy() {
|
||||
DCHECK_NE(dom_storage::kLocalStorageNamespaceId, namespace_id_);
|
||||
int new_id = kInvalidNamespaceId;
|
||||
if (Context()) {
|
||||
new_id = Context()->AllocateSessionId();
|
||||
Context()->CloneSessionNamespace(namespace_id_, new_id);
|
||||
}
|
||||
return new NamespaceImpl(parent_, new_id);
|
||||
}
|
||||
|
||||
bool BrowserDomStorageSystem::NamespaceImpl::isSameNamespace(
|
||||
const WebStorageNamespace& other) const {
|
||||
const NamespaceImpl* other_impl = static_cast<const NamespaceImpl*>(&other);
|
||||
return namespace_id_ == other_impl->namespace_id_;
|
||||
}
|
||||
|
||||
// AreaImpl -----------------------------
|
||||
|
||||
BrowserDomStorageSystem::AreaImpl::AreaImpl(
|
||||
const base::WeakPtr<BrowserDomStorageSystem>& parent,
|
||||
int namespace_id, const GURL& origin)
|
||||
: parent_(parent),
|
||||
connection_id_(0) {
|
||||
if (Host()) {
|
||||
connection_id_ = (parent_->next_connection_id_)++;
|
||||
Host()->OpenStorageArea(connection_id_, namespace_id, origin);
|
||||
}
|
||||
}
|
||||
|
||||
BrowserDomStorageSystem::AreaImpl::~AreaImpl() {
|
||||
if (Host())
|
||||
Host()->CloseStorageArea(connection_id_);
|
||||
}
|
||||
|
||||
unsigned BrowserDomStorageSystem::AreaImpl::length() {
|
||||
if (Host())
|
||||
return Host()->GetAreaLength(connection_id_);
|
||||
return 0;
|
||||
}
|
||||
|
||||
WebString BrowserDomStorageSystem::AreaImpl::key(unsigned index) {
|
||||
if (Host())
|
||||
return Host()->GetAreaKey(connection_id_, index);
|
||||
return NullableString16(true);
|
||||
}
|
||||
|
||||
WebString BrowserDomStorageSystem::AreaImpl::getItem(const WebString& key) {
|
||||
if (Host())
|
||||
return Host()->GetAreaItem(connection_id_, key);
|
||||
return NullableString16(true);
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::AreaImpl::setItem(
|
||||
const WebString& key, const WebString& newValue,
|
||||
const WebURL& pageUrl, Result& result, WebString& oldValue) {
|
||||
result = ResultBlockedByQuota;
|
||||
oldValue = NullableString16(true);
|
||||
if (!Host())
|
||||
return;
|
||||
|
||||
AutoReset<AreaImpl*> auto_reset(&parent_->area_being_processed_, this);
|
||||
NullableString16 old_value;
|
||||
if (!Host()->SetAreaItem(connection_id_, key, newValue, pageUrl,
|
||||
&old_value))
|
||||
return;
|
||||
|
||||
result = ResultOK;
|
||||
oldValue = old_value;
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::AreaImpl::removeItem(
|
||||
const WebString& key, const WebURL& pageUrl, WebString& oldValue) {
|
||||
oldValue = NullableString16(true);
|
||||
if (!Host())
|
||||
return;
|
||||
|
||||
AutoReset<AreaImpl*> auto_reset(&parent_->area_being_processed_, this);
|
||||
string16 old_value;
|
||||
if (!Host()->RemoveAreaItem(connection_id_, key, pageUrl, &old_value))
|
||||
return;
|
||||
|
||||
oldValue = old_value;
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::AreaImpl::clear(
|
||||
const WebURL& pageUrl, bool& somethingCleared) {
|
||||
if (Host()) {
|
||||
AutoReset<AreaImpl*> auto_reset(&parent_->area_being_processed_, this);
|
||||
somethingCleared = Host()->ClearArea(connection_id_, pageUrl);
|
||||
return;
|
||||
}
|
||||
somethingCleared = false;
|
||||
}
|
||||
|
||||
// BrowserDomStorageSystem -----------------------------
|
||||
|
||||
BrowserDomStorageSystem* BrowserDomStorageSystem::g_instance_;
|
||||
|
||||
BrowserDomStorageSystem::BrowserDomStorageSystem()
|
||||
: weak_factory_(this),
|
||||
context_(new DomStorageContext(FilePath(), FilePath(), NULL, NULL)),
|
||||
host_(new DomStorageHost(context_)),
|
||||
area_being_processed_(NULL),
|
||||
next_connection_id_(1) {
|
||||
DCHECK(!g_instance_);
|
||||
g_instance_ = this;
|
||||
context_->AddEventObserver(this);
|
||||
}
|
||||
|
||||
BrowserDomStorageSystem::~BrowserDomStorageSystem() {
|
||||
g_instance_ = NULL;
|
||||
host_.reset();
|
||||
context_->RemoveEventObserver(this);
|
||||
}
|
||||
|
||||
WebStorageNamespace* BrowserDomStorageSystem::CreateLocalStorageNamespace() {
|
||||
return new NamespaceImpl(weak_factory_.GetWeakPtr());
|
||||
}
|
||||
|
||||
WebStorageNamespace* BrowserDomStorageSystem::CreateSessionStorageNamespace() {
|
||||
int id = context_->AllocateSessionId();
|
||||
context_->CreateSessionNamespace(id);
|
||||
return new NamespaceImpl(weak_factory_.GetWeakPtr(), id);
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::OnDomStorageItemSet(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const string16& key,
|
||||
const string16& new_value,
|
||||
const NullableString16& old_value,
|
||||
const GURL& page_url) {
|
||||
DispatchDomStorageEvent(area, page_url,
|
||||
NullableString16(key, false),
|
||||
NullableString16(new_value, false),
|
||||
old_value);
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::OnDomStorageItemRemoved(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const string16& key,
|
||||
const string16& old_value,
|
||||
const GURL& page_url) {
|
||||
DispatchDomStorageEvent(area, page_url,
|
||||
NullableString16(key, false),
|
||||
NullableString16(true),
|
||||
NullableString16(old_value, false));
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::OnDomStorageAreaCleared(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const GURL& page_url) {
|
||||
DispatchDomStorageEvent(area, page_url,
|
||||
NullableString16(true),
|
||||
NullableString16(true),
|
||||
NullableString16(true));
|
||||
}
|
||||
|
||||
void BrowserDomStorageSystem::DispatchDomStorageEvent(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const GURL& page_url,
|
||||
const NullableString16& key,
|
||||
const NullableString16& new_value,
|
||||
const NullableString16& old_value) {
|
||||
DCHECK(area_being_processed_);
|
||||
if (area->namespace_id() == dom_storage::kLocalStorageNamespaceId) {
|
||||
WebStorageEventDispatcher::dispatchLocalStorageEvent(
|
||||
key,
|
||||
old_value,
|
||||
new_value,
|
||||
area->origin(),
|
||||
page_url,
|
||||
area_being_processed_,
|
||||
true /* originatedInProcess */);
|
||||
} else {
|
||||
NamespaceImpl session_namespace_for_event_dispatch(
|
||||
base::WeakPtr<BrowserDomStorageSystem>(), area->namespace_id());
|
||||
WebStorageEventDispatcher::dispatchSessionStorageEvent(
|
||||
key,
|
||||
old_value,
|
||||
new_value,
|
||||
area->origin(),
|
||||
page_url,
|
||||
session_namespace_for_event_dispatch,
|
||||
area_being_processed_,
|
||||
true /* originatedInProcess */);
|
||||
}
|
||||
}
|
80
cef1/libcef/browser_dom_storage_system.h
Normal file
80
cef1/libcef/browser_dom_storage_system.h
Normal file
@@ -0,0 +1,80 @@
|
||||
// Copyright (c) 2012 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 CEF_LIBCEF_BROWSER_DOM_STORAGE_SYSTEM_H_
|
||||
#define CEF_LIBCEF_BROWSER_DOM_STORAGE_SYSTEM_H_
|
||||
#pragma once
|
||||
|
||||
#include "base/memory/scoped_ptr.h"
|
||||
#include "base/memory/weak_ptr.h"
|
||||
#include "webkit/dom_storage/dom_storage_context.h"
|
||||
|
||||
namespace dom_storage {
|
||||
class DomStorageHost;
|
||||
}
|
||||
namespace WebKit {
|
||||
class WebStorageNamespace;
|
||||
}
|
||||
|
||||
// Class that composes dom_storage classes together for use
|
||||
// in simple single process environments like test_shell and DRT.
|
||||
class BrowserDomStorageSystem
|
||||
: public dom_storage::DomStorageContext::EventObserver {
|
||||
public:
|
||||
static BrowserDomStorageSystem& instance() { return *g_instance_; }
|
||||
|
||||
BrowserDomStorageSystem();
|
||||
virtual ~BrowserDomStorageSystem();
|
||||
|
||||
// The Create<<>> calls are bound to WebKit api that the embedder
|
||||
// is responsible for implementing. These factories are called strictly
|
||||
// on the 'main' webkit thread. Ditto the methods on the returned
|
||||
// objects. SimplDomStorageSystem manufactures implementations of the
|
||||
// WebStorageNamespace and WebStorageArea interfaces that ultimately
|
||||
// plumb Get, Set, Remove, and Clear javascript calls to the dom_storage
|
||||
// classes. The caller (webkit/webcore) takes ownership of the returned
|
||||
// instances and will delete them when done.
|
||||
WebKit::WebStorageNamespace* CreateLocalStorageNamespace();
|
||||
WebKit::WebStorageNamespace* CreateSessionStorageNamespace();
|
||||
|
||||
private:
|
||||
// Inner classes that implement the WebKit WebStorageNamespace and
|
||||
// WebStorageArea interfaces in terms of dom_storage classes.
|
||||
class NamespaceImpl;
|
||||
class AreaImpl;
|
||||
|
||||
// DomStorageContext::EventObserver implementation which
|
||||
// calls into webkit/webcore to dispatch events.
|
||||
virtual void OnDomStorageItemSet(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const string16& key,
|
||||
const string16& new_value,
|
||||
const NullableString16& old_value,
|
||||
const GURL& page_url) OVERRIDE;
|
||||
virtual void OnDomStorageItemRemoved(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const string16& key,
|
||||
const string16& old_value,
|
||||
const GURL& page_url) OVERRIDE;
|
||||
virtual void OnDomStorageAreaCleared(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const GURL& page_url) OVERRIDE;
|
||||
|
||||
void DispatchDomStorageEvent(
|
||||
const dom_storage::DomStorageArea* area,
|
||||
const GURL& page_url,
|
||||
const NullableString16& key,
|
||||
const NullableString16& new_value,
|
||||
const NullableString16& old_value);
|
||||
|
||||
base::WeakPtrFactory<BrowserDomStorageSystem> weak_factory_;
|
||||
scoped_refptr<dom_storage::DomStorageContext> context_;
|
||||
scoped_ptr<dom_storage::DomStorageHost> host_;
|
||||
AreaImpl* area_being_processed_;
|
||||
int next_connection_id_;
|
||||
|
||||
static BrowserDomStorageSystem* g_instance_;
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_DOM_STORAGE_SYSTEM_H_
|
@@ -210,9 +210,7 @@ void BrowserFileSystem::CleanupOnIOThread() {
|
||||
|
||||
FileSystemOperationInterface* BrowserFileSystem::GetNewOperation(
|
||||
const WebURL& url) {
|
||||
return file_system_context_->CreateFileSystemOperation(
|
||||
GURL(url),
|
||||
base::MessageLoopProxy::current());
|
||||
return file_system_context_->CreateFileSystemOperation(GURL(url));
|
||||
}
|
||||
|
||||
FileSystemOperationInterface::StatusCallback
|
||||
|
@@ -37,9 +37,6 @@ class BrowserFileWriter::IOThreadProxy
|
||||
main_thread_ = base::MessageLoopProxy::current();
|
||||
}
|
||||
|
||||
virtual ~IOThreadProxy() {
|
||||
}
|
||||
|
||||
void Truncate(const GURL& path, int64 offset) {
|
||||
if (!io_thread_->BelongsToCurrentThread()) {
|
||||
io_thread_->PostTask(
|
||||
@@ -82,8 +79,11 @@ class BrowserFileWriter::IOThreadProxy
|
||||
}
|
||||
|
||||
private:
|
||||
friend class base::RefCountedThreadSafe<IOThreadProxy>;
|
||||
virtual ~IOThreadProxy() {}
|
||||
|
||||
FileSystemOperationInterface* GetNewOperation(const GURL& path) {
|
||||
return file_system_context_->CreateFileSystemOperation(path, io_thread_);
|
||||
return file_system_context_->CreateFileSystemOperation(path);
|
||||
}
|
||||
|
||||
void DidSucceedOnMainThread() {
|
||||
|
@@ -180,8 +180,8 @@ CefBrowserImpl::CefBrowserImpl(const CefWindowInfo& windowInfo,
|
||||
popup_delegate_.reset(new BrowserWebViewDelegate(this));
|
||||
nav_controller_.reset(new BrowserNavigationController(this));
|
||||
|
||||
request_context_proxy_ =
|
||||
new BrowserRequestContextProxy(_Context->request_context(), this);
|
||||
request_context_proxy_.reset(
|
||||
new BrowserRequestContextProxy(_Context->request_context(), this));
|
||||
|
||||
if (!file_system_root_.CreateUniqueTempDir()) {
|
||||
LOG(WARNING) << "Failed to create a temp dir for the filesystem."
|
||||
@@ -785,7 +785,7 @@ void CefBrowserImpl::UIT_DestroyBrowser() {
|
||||
UIT_ClearMainWndHandle();
|
||||
|
||||
main_frame_ = NULL;
|
||||
request_context_proxy_ = NULL;
|
||||
request_context_proxy_.reset(NULL);
|
||||
|
||||
// Remove the reference added in UIT_CreateBrowser().
|
||||
Release();
|
||||
|
@@ -357,7 +357,7 @@ class CefBrowserImpl : public CefBrowser {
|
||||
void set_popup_rect(const gfx::Rect& rect) { popup_rect_ = rect; }
|
||||
|
||||
net::URLRequestContext* request_context_proxy() {
|
||||
return request_context_proxy_;
|
||||
return request_context_proxy_.get();
|
||||
}
|
||||
|
||||
static bool ImplementsThreadSafeReferenceCounting() { return true; }
|
||||
@@ -386,7 +386,7 @@ class CefBrowserImpl : public CefBrowser {
|
||||
scoped_ptr<BrowserDevToolsAgent> dev_tools_agent_;
|
||||
scoped_ptr<BrowserDevToolsClient> dev_tools_client_;
|
||||
|
||||
scoped_refptr<BrowserRequestContextProxy> request_context_proxy_;
|
||||
scoped_ptr<BrowserRequestContextProxy> request_context_proxy_;
|
||||
|
||||
CefString title_;
|
||||
|
||||
|
@@ -80,7 +80,7 @@ bool CefBrowserImpl::UIT_CreateBrowser(const CefString& url) {
|
||||
window_info_.m_ParentWidget = parentView;
|
||||
}
|
||||
|
||||
WebPreferences prefs;
|
||||
webkit_glue::WebPreferences prefs;
|
||||
BrowserToWebSettings(settings_, prefs);
|
||||
|
||||
// Create the webview host object
|
||||
|
@@ -93,7 +93,7 @@ bool CefBrowserImpl::UIT_CreateBrowser(const CefString& url) {
|
||||
paint_delegate_.reset(new PaintDelegate(this));
|
||||
}
|
||||
|
||||
WebPreferences prefs;
|
||||
webkit_glue::WebPreferences prefs;
|
||||
BrowserToWebSettings(settings_, prefs);
|
||||
|
||||
// Create the webview host object
|
||||
|
@@ -197,7 +197,7 @@ bool CefBrowserImpl::UIT_CreateBrowser(const CefString& url) {
|
||||
// Add the new browser to the list maintained by the context
|
||||
_Context->AddBrowser(this);
|
||||
|
||||
WebPreferences prefs;
|
||||
webkit_glue::WebPreferences prefs;
|
||||
BrowserToWebSettings(settings_, prefs);
|
||||
|
||||
// Create the webview host object
|
||||
|
@@ -73,8 +73,8 @@ net::NetworkDelegate::AuthRequiredResponse
|
||||
return AUTH_REQUIRED_RESPONSE_NO_ACTION;
|
||||
}
|
||||
|
||||
bool BrowserNetworkDelegate::CanGetCookies(
|
||||
const net::URLRequest* request,
|
||||
bool BrowserNetworkDelegate::OnCanGetCookies(
|
||||
const net::URLRequest& request,
|
||||
const net::CookieList& cookie_list) {
|
||||
net::StaticCookiePolicy::Type policy_type = accept_all_cookies_ ?
|
||||
net::StaticCookiePolicy::ALLOW_ALL_COOKIES :
|
||||
@@ -82,19 +82,25 @@ bool BrowserNetworkDelegate::CanGetCookies(
|
||||
|
||||
net::StaticCookiePolicy policy(policy_type);
|
||||
int rv = policy.CanGetCookies(
|
||||
request->url(), request->first_party_for_cookies());
|
||||
request.url(), request.first_party_for_cookies());
|
||||
return rv == net::OK;
|
||||
}
|
||||
|
||||
bool BrowserNetworkDelegate::CanSetCookie(const net::URLRequest* request,
|
||||
const std::string& cookie_line,
|
||||
net::CookieOptions* options) {
|
||||
bool BrowserNetworkDelegate::OnCanSetCookie(
|
||||
const net::URLRequest& request,
|
||||
const std::string& cookie_line,
|
||||
net::CookieOptions* options) {
|
||||
net::StaticCookiePolicy::Type policy_type = accept_all_cookies_ ?
|
||||
net::StaticCookiePolicy::ALLOW_ALL_COOKIES :
|
||||
net::StaticCookiePolicy::BLOCK_SETTING_THIRD_PARTY_COOKIES;
|
||||
|
||||
net::StaticCookiePolicy policy(policy_type);
|
||||
int rv = policy.CanSetCookie(
|
||||
request->url(), request->first_party_for_cookies());
|
||||
request.url(), request.first_party_for_cookies());
|
||||
return rv == net::OK;
|
||||
}
|
||||
|
||||
bool BrowserNetworkDelegate::OnCanAccessFile(const net::URLRequest& request,
|
||||
const FilePath& path) const {
|
||||
return true;
|
||||
}
|
||||
|
@@ -44,12 +44,13 @@ class BrowserNetworkDelegate : public net::NetworkDelegate {
|
||||
const net::AuthChallengeInfo& auth_info,
|
||||
const AuthCallback& callback,
|
||||
net::AuthCredentials* credentials) OVERRIDE;
|
||||
virtual bool CanGetCookies(
|
||||
const net::URLRequest* request,
|
||||
const net::CookieList& cookie_list) OVERRIDE;
|
||||
virtual bool CanSetCookie(const net::URLRequest* request,
|
||||
const std::string& cookie_line,
|
||||
net::CookieOptions* options) OVERRIDE;
|
||||
virtual bool OnCanGetCookies(const net::URLRequest& request,
|
||||
const net::CookieList& cookie_list) OVERRIDE;
|
||||
virtual bool OnCanSetCookie(const net::URLRequest& request,
|
||||
const std::string& cookie_line,
|
||||
net::CookieOptions* options) OVERRIDE;
|
||||
virtual bool OnCanAccessFile(const net::URLRequest& request,
|
||||
const FilePath& path) const OVERRIDE;
|
||||
|
||||
bool accept_all_cookies_;
|
||||
};
|
||||
|
@@ -1,792 +0,0 @@
|
||||
// Copyright (c) 2012 The Chromium Embedded Framework Authors.
|
||||
// Portions copyright (c) 2011 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 "libcef/browser_persistent_cookie_store.h"
|
||||
|
||||
#include <algorithm>
|
||||
#include <list>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <utility>
|
||||
|
||||
#include "libcef/cef_thread.h"
|
||||
|
||||
#include "base/basictypes.h"
|
||||
#include "base/bind.h"
|
||||
#include "base/callback.h"
|
||||
#include "base/file_path.h"
|
||||
#include "base/file_util.h"
|
||||
#include "base/logging.h"
|
||||
#include "base/memory/ref_counted.h"
|
||||
#include "base/memory/scoped_ptr.h"
|
||||
#include "base/metrics/histogram.h"
|
||||
#include "base/string_util.h"
|
||||
#include "base/synchronization/lock.h"
|
||||
#include "base/threading/thread.h"
|
||||
#include "base/threading/thread_restrictions.h"
|
||||
#include "googleurl/src/gurl.h"
|
||||
#include "net/base/registry_controlled_domain.h"
|
||||
#include "sql/meta_table.h"
|
||||
#include "sql/statement.h"
|
||||
#include "sql/transaction.h"
|
||||
|
||||
using base::Time;
|
||||
|
||||
// This class is designed to be shared between any calling threads and the
|
||||
// database thread. It batches operations and commits them on a timer.
|
||||
//
|
||||
// BrowserPersistentCookieStore::Load is called to load all cookies. It
|
||||
// delegates to Backend::Load, which posts a Backend::LoadAndNotifyOnDBThread
|
||||
// task to the DB thread. This task calls Backend::ChainLoadCookies(), which
|
||||
// repeatedly posts itself to the DB thread to load each eTLD+1's cookies in
|
||||
// separate tasks. When this is complete, Backend::NotifyOnIOThread is posted
|
||||
// to the IO thread, which notifies the caller of BrowserPersistentCookieStore::
|
||||
// Load that the load is complete.
|
||||
//
|
||||
// If a priority load request is invoked via BrowserPersistentCookieStore::
|
||||
// LoadCookiesForKey, it is delegated to Backend::LoadCookiesForKey, which posts
|
||||
// Backend::LoadKeyAndNotifyOnDBThread to the DB thread. That routine loads just
|
||||
// that single domain key (eTLD+1)'s cookies, and posts a Backend::
|
||||
// NotifyOnIOThread to the IO thread to notify the caller of
|
||||
// BrowserPersistentCookieStore::LoadCookiesForKey that that load is complete.
|
||||
//
|
||||
// Subsequent to loading, mutations may be queued by any thread using
|
||||
// AddCookie, UpdateCookieAccessTime, and DeleteCookie. These are flushed to
|
||||
// disk on the DB thread every 30 seconds, 512 operations, or call to Flush(),
|
||||
// whichever occurs first.
|
||||
class BrowserPersistentCookieStore::Backend
|
||||
: public base::RefCountedThreadSafe<BrowserPersistentCookieStore::Backend> {
|
||||
public:
|
||||
Backend(const FilePath& path, bool restore_old_session_cookies)
|
||||
: path_(path),
|
||||
db_(NULL),
|
||||
num_pending_(0),
|
||||
clear_local_state_on_exit_(false),
|
||||
initialized_(false),
|
||||
restore_old_session_cookies_(restore_old_session_cookies) {
|
||||
}
|
||||
|
||||
// Creates or loads the SQLite database.
|
||||
void Load(const LoadedCallback& loaded_callback);
|
||||
|
||||
// Loads cookies for the domain key (eTLD+1).
|
||||
void LoadCookiesForKey(const std::string& domain,
|
||||
const LoadedCallback& loaded_callback);
|
||||
|
||||
// Batch a cookie addition.
|
||||
void AddCookie(const net::CookieMonster::CanonicalCookie& cc);
|
||||
|
||||
// Batch a cookie access time update.
|
||||
void UpdateCookieAccessTime(const net::CookieMonster::CanonicalCookie& cc);
|
||||
|
||||
// Batch a cookie deletion.
|
||||
void DeleteCookie(const net::CookieMonster::CanonicalCookie& cc);
|
||||
|
||||
// Commit pending operations as soon as possible.
|
||||
void Flush(const base::Closure& callback);
|
||||
|
||||
// Commit any pending operations and close the database. This must be called
|
||||
// before the object is destructed.
|
||||
void Close();
|
||||
|
||||
void SetClearLocalStateOnExit(bool clear_local_state);
|
||||
|
||||
private:
|
||||
friend class base::RefCountedThreadSafe<
|
||||
BrowserPersistentCookieStore::Backend>;
|
||||
|
||||
// You should call Close() before destructing this object.
|
||||
~Backend() {
|
||||
DCHECK(!db_.get()) << "Close should have already been called.";
|
||||
DCHECK(num_pending_ == 0 && pending_.empty());
|
||||
}
|
||||
|
||||
// Database upgrade statements.
|
||||
bool EnsureDatabaseVersion();
|
||||
|
||||
class PendingOperation {
|
||||
public:
|
||||
typedef enum {
|
||||
COOKIE_ADD,
|
||||
COOKIE_UPDATEACCESS,
|
||||
COOKIE_DELETE,
|
||||
} OperationType;
|
||||
|
||||
PendingOperation(OperationType op,
|
||||
const net::CookieMonster::CanonicalCookie& cc)
|
||||
: op_(op), cc_(cc) { }
|
||||
|
||||
OperationType op() const { return op_; }
|
||||
const net::CookieMonster::CanonicalCookie& cc() const { return cc_; }
|
||||
|
||||
private:
|
||||
OperationType op_;
|
||||
net::CookieMonster::CanonicalCookie cc_;
|
||||
};
|
||||
|
||||
private:
|
||||
// Creates or loads the SQLite database on DB thread.
|
||||
void LoadAndNotifyOnDBThread(const LoadedCallback& loaded_callback);
|
||||
|
||||
// Loads cookies for the domain key (eTLD+1) on DB thread.
|
||||
void LoadKeyAndNotifyOnDBThread(const std::string& domains,
|
||||
const LoadedCallback& loaded_callback);
|
||||
|
||||
// Notifies the CookieMonster when loading completes for a specific domain key
|
||||
// or for all domain keys. Triggers the callback and passes it all cookies
|
||||
// that have been loaded from DB since last IO notification.
|
||||
void NotifyOnIOThread(
|
||||
const LoadedCallback& loaded_callback,
|
||||
bool load_success);
|
||||
|
||||
// Initialize the data base.
|
||||
bool InitializeDatabase();
|
||||
|
||||
// Loads cookies for the next domain key from the DB, then either reschedules
|
||||
// itself or schedules the provided callback to run on the IO thread (if all
|
||||
// domains are loaded).
|
||||
void ChainLoadCookies(const LoadedCallback& loaded_callback);
|
||||
|
||||
// Load all cookies for a set of domains/hosts
|
||||
bool LoadCookiesForDomains(const std::set<std::string>& key);
|
||||
|
||||
// Batch a cookie operation (add or delete)
|
||||
void BatchOperation(PendingOperation::OperationType op,
|
||||
const net::CookieMonster::CanonicalCookie& cc);
|
||||
// Commit our pending operations to the database.
|
||||
void Commit();
|
||||
// Close() executed on the background thread.
|
||||
void InternalBackgroundClose();
|
||||
|
||||
void DeleteSessionCookies();
|
||||
|
||||
FilePath path_;
|
||||
scoped_ptr<sql::Connection> db_;
|
||||
sql::MetaTable meta_table_;
|
||||
|
||||
typedef std::list<PendingOperation*> PendingOperationsList;
|
||||
PendingOperationsList pending_;
|
||||
PendingOperationsList::size_type num_pending_;
|
||||
// True if the persistent store should be deleted upon destruction.
|
||||
bool clear_local_state_on_exit_;
|
||||
// Guard |cookies_|, |pending_|, |num_pending_|, |clear_local_state_on_exit_|
|
||||
base::Lock lock_;
|
||||
|
||||
// Temporary buffer for cookies loaded from DB. Accumulates cookies to reduce
|
||||
// the number of messages sent to the IO thread. Sent back in response to
|
||||
// individual load requests for domain keys or when all loading completes.
|
||||
std::vector<net::CookieMonster::CanonicalCookie*> cookies_;
|
||||
|
||||
// Map of domain keys(eTLD+1) to domains/hosts that are to be loaded from DB.
|
||||
std::map<std::string, std::set<std::string> > keys_to_load_;
|
||||
|
||||
// Indicates if DB has been initialized.
|
||||
bool initialized_;
|
||||
|
||||
// If false, we should filter out session cookies when reading the DB.
|
||||
bool restore_old_session_cookies_;
|
||||
DISALLOW_COPY_AND_ASSIGN(Backend);
|
||||
};
|
||||
|
||||
// Version number of the database.
|
||||
//
|
||||
// Version 5 adds the columns has_expires and is_persistent, so that the
|
||||
// database can store session cookies as well as persistent cookies. Databases
|
||||
// of version 5 are incompatible with older versions of code. If a database of
|
||||
// version 5 is read by older code, session cookies will be treated as normal
|
||||
// cookies.
|
||||
//
|
||||
// In version 4, we migrated the time epoch. If you open the DB with an older
|
||||
// version on Mac or Linux, the times will look wonky, but the file will likely
|
||||
// be usable. On Windows version 3 and 4 are the same.
|
||||
//
|
||||
// Version 3 updated the database to include the last access time, so we can
|
||||
// expire them in decreasing order of use when we've reached the maximum
|
||||
// number of cookies.
|
||||
static const int kCurrentVersionNumber = 5;
|
||||
static const int kCompatibleVersionNumber = 5;
|
||||
|
||||
namespace {
|
||||
|
||||
// Initializes the cookies table, returning true on success.
|
||||
bool InitTable(sql::Connection* db) {
|
||||
if (!db->DoesTableExist("cookies")) {
|
||||
if (!db->Execute("CREATE TABLE cookies ("
|
||||
"creation_utc INTEGER NOT NULL UNIQUE PRIMARY KEY,"
|
||||
"host_key TEXT NOT NULL,"
|
||||
"name TEXT NOT NULL,"
|
||||
"value TEXT NOT NULL,"
|
||||
"path TEXT NOT NULL,"
|
||||
"expires_utc INTEGER NOT NULL,"
|
||||
"secure INTEGER NOT NULL,"
|
||||
"httponly INTEGER NOT NULL,"
|
||||
"last_access_utc INTEGER NOT NULL, "
|
||||
"has_expires INTEGER NOT NULL DEFAULT 1, "
|
||||
"persistent INTEGER NOT NULL DEFAULT 1)"))
|
||||
return false;
|
||||
}
|
||||
|
||||
// Older code created an index on creation_utc, which is already
|
||||
// primary key for the table.
|
||||
if (!db->Execute("DROP INDEX IF EXISTS cookie_times"))
|
||||
return false;
|
||||
|
||||
if (!db->Execute("CREATE INDEX IF NOT EXISTS domain ON cookies(host_key)"))
|
||||
return false;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::Load(
|
||||
const LoadedCallback& loaded_callback) {
|
||||
// This function should be called only once per instance.
|
||||
DCHECK(!db_.get());
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::LoadAndNotifyOnDBThread, this, loaded_callback));
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::LoadCookiesForKey(
|
||||
const std::string& key,
|
||||
const LoadedCallback& loaded_callback) {
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::LoadKeyAndNotifyOnDBThread, this,
|
||||
key,
|
||||
loaded_callback));
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::LoadAndNotifyOnDBThread(
|
||||
const LoadedCallback& loaded_callback) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
if (!InitializeDatabase()) {
|
||||
CefThread::PostTask(
|
||||
CefThread::IO, FROM_HERE,
|
||||
base::Bind(&BrowserPersistentCookieStore::Backend::NotifyOnIOThread,
|
||||
this, loaded_callback, false));
|
||||
} else {
|
||||
ChainLoadCookies(loaded_callback);
|
||||
}
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::LoadKeyAndNotifyOnDBThread(
|
||||
const std::string& key,
|
||||
const LoadedCallback& loaded_callback) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
bool success = false;
|
||||
if (InitializeDatabase()) {
|
||||
std::map<std::string, std::set<std::string> >::iterator
|
||||
it = keys_to_load_.find(key);
|
||||
if (it != keys_to_load_.end()) {
|
||||
success = LoadCookiesForDomains(it->second);
|
||||
keys_to_load_.erase(it);
|
||||
} else {
|
||||
success = true;
|
||||
}
|
||||
}
|
||||
|
||||
CefThread::PostTask(
|
||||
CefThread::IO, FROM_HERE,
|
||||
base::Bind(&BrowserPersistentCookieStore::Backend::NotifyOnIOThread,
|
||||
this, loaded_callback, success));
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::NotifyOnIOThread(
|
||||
const LoadedCallback& loaded_callback,
|
||||
bool load_success) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::IO));
|
||||
|
||||
std::vector<net::CookieMonster::CanonicalCookie*> cookies;
|
||||
{
|
||||
base::AutoLock locked(lock_);
|
||||
cookies.swap(cookies_);
|
||||
}
|
||||
|
||||
loaded_callback.Run(cookies);
|
||||
}
|
||||
|
||||
bool BrowserPersistentCookieStore::Backend::InitializeDatabase() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
if (initialized_) {
|
||||
// Return false if we were previously initialized but the DB has since been
|
||||
// closed.
|
||||
return db_.get() ? true : false;
|
||||
}
|
||||
|
||||
const FilePath dir = path_.DirName();
|
||||
if (!file_util::PathExists(dir) && !file_util::CreateDirectory(dir)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
db_.reset(new sql::Connection);
|
||||
if (!db_->Open(path_)) {
|
||||
NOTREACHED() << "Unable to open cookie DB.";
|
||||
db_.reset();
|
||||
return false;
|
||||
}
|
||||
|
||||
// db_->set_error_delegate(GetErrorHandlerForCookieDb());
|
||||
|
||||
if (!EnsureDatabaseVersion() || !InitTable(db_.get())) {
|
||||
NOTREACHED() << "Unable to open cookie DB.";
|
||||
db_.reset();
|
||||
return false;
|
||||
}
|
||||
|
||||
// Retrieve all the domains
|
||||
sql::Statement smt(db_->GetUniqueStatement(
|
||||
"SELECT DISTINCT host_key FROM cookies"));
|
||||
|
||||
if (!smt.is_valid()) {
|
||||
smt.Clear(); // Disconnect smt_ref from db_.
|
||||
db_.reset();
|
||||
return false;
|
||||
}
|
||||
|
||||
// Build a map of domain keys (always eTLD+1) to domains.
|
||||
while (smt.Step()) {
|
||||
std::string domain = smt.ColumnString(0);
|
||||
std::string key =
|
||||
net::RegistryControlledDomainService::GetDomainAndRegistry(domain);
|
||||
|
||||
std::map<std::string, std::set<std::string> >::iterator it =
|
||||
keys_to_load_.find(key);
|
||||
if (it == keys_to_load_.end())
|
||||
it = keys_to_load_.insert(std::make_pair
|
||||
(key, std::set<std::string>())).first;
|
||||
it->second.insert(domain);
|
||||
}
|
||||
|
||||
initialized_ = true;
|
||||
return true;
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::ChainLoadCookies(
|
||||
const LoadedCallback& loaded_callback) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
bool load_success = true;
|
||||
|
||||
if (!db_.get()) {
|
||||
// Close() has been called on this store.
|
||||
load_success = false;
|
||||
} else if (keys_to_load_.size() > 0) {
|
||||
// Load cookies for the first domain key.
|
||||
std::map<std::string, std::set<std::string> >::iterator
|
||||
it = keys_to_load_.begin();
|
||||
load_success = LoadCookiesForDomains(it->second);
|
||||
keys_to_load_.erase(it);
|
||||
}
|
||||
|
||||
// If load is successful and there are more domain keys to be loaded,
|
||||
// then post a DB task to continue chain-load;
|
||||
// Otherwise notify on IO thread.
|
||||
if (load_success && keys_to_load_.size() > 0) {
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::ChainLoadCookies, this, loaded_callback));
|
||||
} else {
|
||||
CefThread::PostTask(
|
||||
CefThread::IO, FROM_HERE,
|
||||
base::Bind(&BrowserPersistentCookieStore::Backend::NotifyOnIOThread,
|
||||
this, loaded_callback, load_success));
|
||||
if (load_success && !restore_old_session_cookies_)
|
||||
DeleteSessionCookies();
|
||||
}
|
||||
}
|
||||
|
||||
bool BrowserPersistentCookieStore::Backend::LoadCookiesForDomains(
|
||||
const std::set<std::string>& domains) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
sql::Statement smt;
|
||||
if (restore_old_session_cookies_) {
|
||||
smt.Assign(db_->GetCachedStatement(
|
||||
SQL_FROM_HERE,
|
||||
"SELECT creation_utc, host_key, name, value, path, expires_utc, "
|
||||
"secure, httponly, last_access_utc, has_expires, persistent "
|
||||
"FROM cookies WHERE host_key = ?"));
|
||||
} else {
|
||||
smt.Assign(db_->GetCachedStatement(
|
||||
SQL_FROM_HERE,
|
||||
"SELECT creation_utc, host_key, name, value, path, expires_utc, "
|
||||
"secure, httponly, last_access_utc, has_expires, persistent "
|
||||
"FROM cookies WHERE host_key = ? AND persistent = 1"));
|
||||
}
|
||||
if (!smt.is_valid()) {
|
||||
NOTREACHED() << "select statement prep failed";
|
||||
smt.Clear(); // Disconnect smt_ref from db_.
|
||||
db_.reset();
|
||||
return false;
|
||||
}
|
||||
|
||||
std::vector<net::CookieMonster::CanonicalCookie*> cookies;
|
||||
std::set<std::string>::const_iterator it = domains.begin();
|
||||
for (; it != domains.end(); ++it) {
|
||||
smt.BindString(0, *it);
|
||||
while (smt.Step()) {
|
||||
scoped_ptr<net::CookieMonster::CanonicalCookie> cc(
|
||||
new net::CookieMonster::CanonicalCookie(
|
||||
// The "source" URL is not used with persisted cookies.
|
||||
GURL(), // Source
|
||||
smt.ColumnString(2), // name
|
||||
smt.ColumnString(3), // value
|
||||
smt.ColumnString(1), // domain
|
||||
smt.ColumnString(4), // path
|
||||
std::string(), // TODO(abarth): Persist mac_key
|
||||
std::string(), // TODO(abarth): Persist mac_algorithm
|
||||
Time::FromInternalValue(smt.ColumnInt64(0)), // creation_utc
|
||||
Time::FromInternalValue(smt.ColumnInt64(5)), // expires_utc
|
||||
Time::FromInternalValue(smt.ColumnInt64(8)), // last_access_utc
|
||||
smt.ColumnInt(6) != 0, // secure
|
||||
smt.ColumnInt(7) != 0, // httponly
|
||||
smt.ColumnInt(9) != 0, // has_expires
|
||||
smt.ColumnInt(10) != 0)); // is_persistent
|
||||
DLOG_IF(WARNING,
|
||||
cc->CreationDate() > Time::Now()) << L"CreationDate too recent";
|
||||
cookies.push_back(cc.release());
|
||||
}
|
||||
smt.Reset();
|
||||
}
|
||||
{
|
||||
base::AutoLock locked(lock_);
|
||||
cookies_.insert(cookies_.end(), cookies.begin(), cookies.end());
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool BrowserPersistentCookieStore::Backend::EnsureDatabaseVersion() {
|
||||
// Version check.
|
||||
if (!meta_table_.Init(
|
||||
db_.get(), kCurrentVersionNumber, kCompatibleVersionNumber)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (meta_table_.GetCompatibleVersionNumber() > kCurrentVersionNumber) {
|
||||
LOG(WARNING) << "Cookie database is too new.";
|
||||
return false;
|
||||
}
|
||||
|
||||
int cur_version = meta_table_.GetVersionNumber();
|
||||
if (cur_version == 2) {
|
||||
sql::Transaction transaction(db_.get());
|
||||
if (!transaction.Begin())
|
||||
return false;
|
||||
if (!db_->Execute("ALTER TABLE cookies ADD COLUMN last_access_utc "
|
||||
"INTEGER DEFAULT 0") ||
|
||||
!db_->Execute("UPDATE cookies SET last_access_utc = creation_utc")) {
|
||||
LOG(WARNING) << "Unable to update cookie database to version 3.";
|
||||
return false;
|
||||
}
|
||||
++cur_version;
|
||||
meta_table_.SetVersionNumber(cur_version);
|
||||
meta_table_.SetCompatibleVersionNumber(
|
||||
std::min(cur_version, kCompatibleVersionNumber));
|
||||
transaction.Commit();
|
||||
}
|
||||
|
||||
if (cur_version == 3) {
|
||||
// The time epoch changed for Mac & Linux in this version to match Windows.
|
||||
// This patch came after the main epoch change happened, so some
|
||||
// developers have "good" times for cookies added by the more recent
|
||||
// versions. So we have to be careful to only update times that are under
|
||||
// the old system (which will appear to be from before 1970 in the new
|
||||
// system). The magic number used below is 1970 in our time units.
|
||||
sql::Transaction transaction(db_.get());
|
||||
transaction.Begin();
|
||||
#if !defined(OS_WIN)
|
||||
ignore_result(db_->Execute(
|
||||
"UPDATE cookies "
|
||||
"SET creation_utc = creation_utc + 11644473600000000 "
|
||||
"WHERE rowid IN "
|
||||
"(SELECT rowid FROM cookies WHERE "
|
||||
"creation_utc > 0 AND creation_utc < 11644473600000000)"));
|
||||
ignore_result(db_->Execute(
|
||||
"UPDATE cookies "
|
||||
"SET expires_utc = expires_utc + 11644473600000000 "
|
||||
"WHERE rowid IN "
|
||||
"(SELECT rowid FROM cookies WHERE "
|
||||
"expires_utc > 0 AND expires_utc < 11644473600000000)"));
|
||||
ignore_result(db_->Execute(
|
||||
"UPDATE cookies "
|
||||
"SET last_access_utc = last_access_utc + 11644473600000000 "
|
||||
"WHERE rowid IN "
|
||||
"(SELECT rowid FROM cookies WHERE "
|
||||
"last_access_utc > 0 AND last_access_utc < 11644473600000000)"));
|
||||
#endif
|
||||
++cur_version;
|
||||
meta_table_.SetVersionNumber(cur_version);
|
||||
transaction.Commit();
|
||||
}
|
||||
|
||||
if (cur_version == 4) {
|
||||
sql::Transaction transaction(db_.get());
|
||||
if (!transaction.Begin())
|
||||
return false;
|
||||
if (!db_->Execute("ALTER TABLE cookies "
|
||||
"ADD COLUMN has_expires INTEGER DEFAULT 1") ||
|
||||
!db_->Execute("ALTER TABLE cookies "
|
||||
"ADD COLUMN persistent INTEGER DEFAULT 1")) {
|
||||
LOG(WARNING) << "Unable to update cookie database to version 5.";
|
||||
return false;
|
||||
}
|
||||
++cur_version;
|
||||
meta_table_.SetVersionNumber(cur_version);
|
||||
meta_table_.SetCompatibleVersionNumber(
|
||||
std::min(cur_version, kCompatibleVersionNumber));
|
||||
transaction.Commit();
|
||||
}
|
||||
|
||||
// Put future migration cases here.
|
||||
|
||||
// When the version is too old, we just try to continue anyway, there should
|
||||
// not be a released product that makes a database too old for us to handle.
|
||||
LOG_IF(WARNING, cur_version < kCurrentVersionNumber) <<
|
||||
"Cookie database version " << cur_version << " is too old to handle.";
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::AddCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
BatchOperation(PendingOperation::COOKIE_ADD, cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::UpdateCookieAccessTime(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
BatchOperation(PendingOperation::COOKIE_UPDATEACCESS, cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::DeleteCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
BatchOperation(PendingOperation::COOKIE_DELETE, cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::BatchOperation(
|
||||
PendingOperation::OperationType op,
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
// Commit every 30 seconds.
|
||||
static const int kCommitIntervalMs = 30 * 1000;
|
||||
// Commit right away if we have more than 512 outstanding operations.
|
||||
static const size_t kCommitAfterBatchSize = 512;
|
||||
DCHECK(!CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
// We do a full copy of the cookie here, and hopefully just here.
|
||||
scoped_ptr<PendingOperation> po(new PendingOperation(op, cc));
|
||||
|
||||
PendingOperationsList::size_type num_pending;
|
||||
{
|
||||
base::AutoLock locked(lock_);
|
||||
pending_.push_back(po.release());
|
||||
num_pending = ++num_pending_;
|
||||
}
|
||||
|
||||
if (num_pending == 1) {
|
||||
// We've gotten our first entry for this batch, fire off the timer.
|
||||
CefThread::PostDelayedTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::Commit, this),
|
||||
base::TimeDelta::FromMilliseconds(kCommitIntervalMs));
|
||||
} else if (num_pending == kCommitAfterBatchSize) {
|
||||
// We've reached a big enough batch, fire off a commit now.
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::Commit, this));
|
||||
}
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::Commit() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
|
||||
PendingOperationsList ops;
|
||||
{
|
||||
base::AutoLock locked(lock_);
|
||||
pending_.swap(ops);
|
||||
num_pending_ = 0;
|
||||
}
|
||||
|
||||
// Maybe an old timer fired or we are already Close()'ed.
|
||||
if (!db_.get() || ops.empty())
|
||||
return;
|
||||
|
||||
sql::Statement add_smt(db_->GetCachedStatement(SQL_FROM_HERE,
|
||||
"INSERT INTO cookies (creation_utc, host_key, name, value, path, "
|
||||
"expires_utc, secure, httponly, last_access_utc, has_expires, "
|
||||
"persistent) "
|
||||
"VALUES (?,?,?,?,?,?,?,?,?,?,?)"));
|
||||
if (!add_smt.is_valid())
|
||||
return;
|
||||
|
||||
sql::Statement update_access_smt(db_->GetCachedStatement(SQL_FROM_HERE,
|
||||
"UPDATE cookies SET last_access_utc=? WHERE creation_utc=?"));
|
||||
if (!update_access_smt.is_valid())
|
||||
return;
|
||||
|
||||
sql::Statement del_smt(db_->GetCachedStatement(SQL_FROM_HERE,
|
||||
"DELETE FROM cookies WHERE creation_utc=?"));
|
||||
if (!del_smt.is_valid())
|
||||
return;
|
||||
|
||||
sql::Transaction transaction(db_.get());
|
||||
if (!transaction.Begin())
|
||||
return;
|
||||
|
||||
for (PendingOperationsList::iterator it = ops.begin();
|
||||
it != ops.end(); ++it) {
|
||||
// Free the cookies as we commit them to the database.
|
||||
scoped_ptr<PendingOperation> po(*it);
|
||||
switch (po->op()) {
|
||||
case PendingOperation::COOKIE_ADD:
|
||||
add_smt.Reset();
|
||||
add_smt.BindInt64(0, po->cc().CreationDate().ToInternalValue());
|
||||
add_smt.BindString(1, po->cc().Domain());
|
||||
add_smt.BindString(2, po->cc().Name());
|
||||
add_smt.BindString(3, po->cc().Value());
|
||||
add_smt.BindString(4, po->cc().Path());
|
||||
add_smt.BindInt64(5, po->cc().ExpiryDate().ToInternalValue());
|
||||
add_smt.BindInt(6, po->cc().IsSecure());
|
||||
add_smt.BindInt(7, po->cc().IsHttpOnly());
|
||||
add_smt.BindInt64(8, po->cc().LastAccessDate().ToInternalValue());
|
||||
add_smt.BindInt(9, po->cc().DoesExpire());
|
||||
add_smt.BindInt(10, po->cc().IsPersistent());
|
||||
if (!add_smt.Run())
|
||||
NOTREACHED() << "Could not add a cookie to the DB.";
|
||||
break;
|
||||
|
||||
case PendingOperation::COOKIE_UPDATEACCESS:
|
||||
update_access_smt.Reset();
|
||||
update_access_smt.BindInt64(0,
|
||||
po->cc().LastAccessDate().ToInternalValue());
|
||||
update_access_smt.BindInt64(1,
|
||||
po->cc().CreationDate().ToInternalValue());
|
||||
if (!update_access_smt.Run())
|
||||
NOTREACHED() << "Could not update cookie last access time in the DB.";
|
||||
break;
|
||||
|
||||
case PendingOperation::COOKIE_DELETE:
|
||||
del_smt.Reset();
|
||||
del_smt.BindInt64(0, po->cc().CreationDate().ToInternalValue());
|
||||
if (!del_smt.Run())
|
||||
NOTREACHED() << "Could not delete a cookie from the DB.";
|
||||
break;
|
||||
|
||||
default:
|
||||
NOTREACHED();
|
||||
break;
|
||||
}
|
||||
}
|
||||
transaction.Commit();
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::Flush(
|
||||
const base::Closure& callback) {
|
||||
DCHECK(!CefThread::CurrentlyOn(CefThread::FILE));
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE, base::Bind(&Backend::Commit, this));
|
||||
if (!callback.is_null()) {
|
||||
// We want the completion task to run immediately after Commit() returns.
|
||||
// Posting it from here means there is less chance of another task getting
|
||||
// onto the message queue first, than if we posted it from Commit() itself.
|
||||
CefThread::PostTask(CefThread::FILE, FROM_HERE, callback);
|
||||
}
|
||||
}
|
||||
|
||||
// Fire off a close message to the background thread. We could still have a
|
||||
// pending commit timer or Load operations holding references on us, but if/when
|
||||
// this fires we will already have been cleaned up and it will be ignored.
|
||||
void BrowserPersistentCookieStore::Backend::Close() {
|
||||
if (CefThread::CurrentlyOn(CefThread::FILE)) {
|
||||
InternalBackgroundClose();
|
||||
} else {
|
||||
// Must close the backend on the background thread.
|
||||
CefThread::PostTask(
|
||||
CefThread::FILE, FROM_HERE,
|
||||
base::Bind(&Backend::InternalBackgroundClose, this));
|
||||
}
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::InternalBackgroundClose() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
// Commit any pending operations
|
||||
Commit();
|
||||
|
||||
db_.reset();
|
||||
|
||||
if (clear_local_state_on_exit_)
|
||||
file_util::Delete(path_, false);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::SetClearLocalStateOnExit(
|
||||
bool clear_local_state) {
|
||||
base::AutoLock locked(lock_);
|
||||
clear_local_state_on_exit_ = clear_local_state;
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Backend::DeleteSessionCookies() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::FILE));
|
||||
if (!db_->Execute("DELETE FROM cookies WHERE persistent == 0"))
|
||||
LOG(WARNING) << "Unable to delete session cookies.";
|
||||
}
|
||||
|
||||
BrowserPersistentCookieStore::BrowserPersistentCookieStore(
|
||||
const FilePath& path,
|
||||
bool restore_old_session_cookies)
|
||||
: backend_(new Backend(path, restore_old_session_cookies)) {
|
||||
}
|
||||
|
||||
BrowserPersistentCookieStore::~BrowserPersistentCookieStore() {
|
||||
if (backend_.get()) {
|
||||
backend_->Close();
|
||||
// Release our reference, it will probably still have a reference if the
|
||||
// background thread has not run Close() yet.
|
||||
backend_ = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Load(const LoadedCallback& loaded_callback) {
|
||||
backend_->Load(loaded_callback);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::LoadCookiesForKey(
|
||||
const std::string& key,
|
||||
const LoadedCallback& loaded_callback) {
|
||||
backend_->LoadCookiesForKey(key, loaded_callback);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::AddCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
if (backend_.get())
|
||||
backend_->AddCookie(cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::UpdateCookieAccessTime(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
if (backend_.get())
|
||||
backend_->UpdateCookieAccessTime(cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::DeleteCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) {
|
||||
if (backend_.get())
|
||||
backend_->DeleteCookie(cc);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::SetClearLocalStateOnExit(
|
||||
bool clear_local_state) {
|
||||
if (backend_.get())
|
||||
backend_->SetClearLocalStateOnExit(clear_local_state);
|
||||
}
|
||||
|
||||
void BrowserPersistentCookieStore::Flush(const base::Closure& callback) {
|
||||
if (backend_.get())
|
||||
backend_->Flush(callback);
|
||||
else if (!callback.is_null())
|
||||
MessageLoop::current()->PostTask(FROM_HERE, callback);
|
||||
}
|
@@ -1,63 +0,0 @@
|
||||
// Copyright (c) 2011 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.
|
||||
|
||||
// A sqlite implementation of a cookie monster persistent store.
|
||||
|
||||
// This class is based on src/chrome/browser/net/
|
||||
// sqlite_persistent_cookie_store.h
|
||||
// with the following modifications for use in the cef:
|
||||
// - BrowserThread has been replaced with CefThread
|
||||
// - Performance diagnostic code has been removed (UMA_HISTOGRAM_ENUMERATION)
|
||||
|
||||
#ifndef CEF_LIBCEF_BROWSER_PERSISTENT_COOKIE_STORE_H_
|
||||
#define CEF_LIBCEF_BROWSER_PERSISTENT_COOKIE_STORE_H_
|
||||
#pragma once
|
||||
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/memory/ref_counted.h"
|
||||
#include "net/cookies/cookie_monster.h"
|
||||
|
||||
class FilePath;
|
||||
class Task;
|
||||
|
||||
// Implements the PersistentCookieStore interface in terms of a SQLite database.
|
||||
// For documentation about the actual member functions consult the documentation
|
||||
// of the parent class |net::CookieMonster::PersistentCookieStore|.
|
||||
class BrowserPersistentCookieStore
|
||||
: public net::CookieMonster::PersistentCookieStore {
|
||||
public:
|
||||
BrowserPersistentCookieStore(const FilePath& path,
|
||||
bool restore_old_session_cookies);
|
||||
virtual ~BrowserPersistentCookieStore();
|
||||
|
||||
virtual void Load(const LoadedCallback& loaded_callback) OVERRIDE;
|
||||
|
||||
virtual void LoadCookiesForKey(const std::string& key,
|
||||
const LoadedCallback& callback) OVERRIDE;
|
||||
|
||||
virtual void AddCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) OVERRIDE;
|
||||
|
||||
virtual void UpdateCookieAccessTime(
|
||||
const net::CookieMonster::CanonicalCookie& cc) OVERRIDE;
|
||||
|
||||
virtual void DeleteCookie(
|
||||
const net::CookieMonster::CanonicalCookie& cc) OVERRIDE;
|
||||
|
||||
virtual void SetClearLocalStateOnExit(bool clear_local_state) OVERRIDE;
|
||||
|
||||
virtual void Flush(const base::Closure& callback) OVERRIDE;
|
||||
|
||||
private:
|
||||
class Backend;
|
||||
|
||||
scoped_refptr<Backend> backend_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(BrowserPersistentCookieStore);
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_PERSISTENT_COOKIE_STORE_H_
|
@@ -10,7 +10,6 @@
|
||||
#endif
|
||||
|
||||
#include "libcef/browser_file_system.h"
|
||||
#include "libcef/browser_persistent_cookie_store.h"
|
||||
#include "libcef/browser_resource_loader_bridge.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/cef_thread.h"
|
||||
@@ -18,7 +17,9 @@
|
||||
#include "base/compiler_specific.h"
|
||||
#include "base/file_path.h"
|
||||
#include "base/file_util.h"
|
||||
#include "base/threading/worker_pool.h"
|
||||
#include "build/build_config.h"
|
||||
#include "chrome/browser/net/sqlite_persistent_cookie_store.h"
|
||||
#include "net/base/cert_verifier.h"
|
||||
#include "net/cookies/cookie_monster.h"
|
||||
#include "net/base/default_server_bound_cert_store.h"
|
||||
@@ -157,7 +158,8 @@ void BrowserRequestContext::Init(
|
||||
SetCookieStoragePath(cache_path);
|
||||
|
||||
storage_.set_server_bound_cert_service(new net::ServerBoundCertService(
|
||||
new net::DefaultServerBoundCertStore(NULL)));
|
||||
new net::DefaultServerBoundCertStore(NULL),
|
||||
base::WorkerPool::GetTaskRunner(true)));
|
||||
|
||||
// hard-code A-L and A-C for test shells
|
||||
set_accept_language("en-us,en");
|
||||
@@ -243,15 +245,16 @@ void BrowserRequestContext::Init(
|
||||
new net::HttpCache(host_resolver(),
|
||||
cert_verifier(),
|
||||
server_bound_cert_service(),
|
||||
NULL, // transport_security_state
|
||||
NULL, /* transport_security_state */
|
||||
proxy_service(),
|
||||
"", // ssl_session_cache_shard
|
||||
"", /* ssl_session_cache_shard */
|
||||
ssl_config_service(),
|
||||
http_auth_handler_factory(),
|
||||
NULL, // network_delegate
|
||||
NULL, /* network_delegate */
|
||||
http_server_properties(),
|
||||
NULL, // netlog
|
||||
backend);
|
||||
NULL, /* netlog */
|
||||
backend,
|
||||
"" /* trusted_spdy_proxy */ );
|
||||
|
||||
cache->set_mode(cache_mode);
|
||||
storage_.set_http_transaction_factory(cache);
|
||||
@@ -275,8 +278,7 @@ void BrowserRequestContext::Init(
|
||||
job_factory->SetProtocolHandler(
|
||||
"filesystem",
|
||||
fileapi::CreateFileSystemProtocolHandler(
|
||||
file_system->file_system_context(),
|
||||
CefThread::GetMessageLoopProxyForThread(CefThread::FILE)));
|
||||
file_system->file_system_context()));
|
||||
}
|
||||
|
||||
storage_.set_job_factory(job_factory);
|
||||
@@ -297,11 +299,11 @@ void BrowserRequestContext::SetCookieStoragePath(const FilePath& path) {
|
||||
return;
|
||||
}
|
||||
|
||||
scoped_refptr<BrowserPersistentCookieStore> persistent_store;
|
||||
scoped_refptr<SQLitePersistentCookieStore> persistent_store;
|
||||
if (!path.empty()) {
|
||||
if (file_util::CreateDirectory(path)) {
|
||||
const FilePath& cookie_path = path.AppendASCII("Cookies");
|
||||
persistent_store = new BrowserPersistentCookieStore(cookie_path, false);
|
||||
persistent_store = new SQLitePersistentCookieStore(cookie_path, false);
|
||||
} else {
|
||||
NOTREACHED() << "The cookie storage directory could not be created";
|
||||
}
|
||||
|
@@ -73,6 +73,7 @@
|
||||
#include "webkit/fileapi/file_system_dir_url_request_job.h"
|
||||
#include "webkit/fileapi/file_system_url_request_job.h"
|
||||
#include "webkit/glue/resource_loader_bridge.h"
|
||||
#include "webkit/glue/webkit_glue.h"
|
||||
|
||||
#if defined(OS_MACOSX) || defined(OS_WIN)
|
||||
#include "crypto/nss_util.h"
|
||||
@@ -95,6 +96,7 @@ struct RequestParams {
|
||||
GURL url;
|
||||
GURL first_party_for_cookies;
|
||||
GURL referrer;
|
||||
WebKit::WebReferrerPolicy referrer_policy;
|
||||
std::string headers;
|
||||
int load_flags;
|
||||
ResourceType::Type request_type;
|
||||
@@ -562,6 +564,8 @@ class RequestProxy : public net::URLRequest::Delegate,
|
||||
request_->set_method(params->method);
|
||||
request_->set_first_party_for_cookies(params->first_party_for_cookies);
|
||||
request_->set_referrer(params->referrer.spec());
|
||||
webkit_glue::ConfigureURLRequestForReferrerPolicy(
|
||||
request_.get(), params->referrer_policy);
|
||||
net::HttpRequestHeaders headers;
|
||||
headers.AddHeadersFromString(params->headers);
|
||||
request_->SetExtraRequestHeaders(headers);
|
||||
@@ -982,6 +986,7 @@ class ResourceLoaderBridgeImpl : public ResourceLoaderBridge {
|
||||
params_->url = request_info.url;
|
||||
params_->first_party_for_cookies = request_info.first_party_for_cookies;
|
||||
params_->referrer = request_info.referrer;
|
||||
params_->referrer_policy = request_info.referrer_policy;
|
||||
params_->headers = request_info.headers;
|
||||
params_->load_flags = request_info.load_flags;
|
||||
params_->request_type = request_info.request_type;
|
||||
|
@@ -7,26 +7,40 @@
|
||||
#include "base/utf_string_conversions.h"
|
||||
#include "webkit/glue/webpreferences.h"
|
||||
|
||||
using webkit_glue::WebPreferences;
|
||||
|
||||
void BrowserToWebSettings(const CefBrowserSettings& cef, WebPreferences& web) {
|
||||
if (cef.standard_font_family.length > 0)
|
||||
web.standard_font_family = CefString(&cef.standard_font_family);
|
||||
else
|
||||
web.standard_font_family = ASCIIToUTF16("Times");
|
||||
if (cef.standard_font_family.length > 0) {
|
||||
web.standard_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.standard_font_family);
|
||||
} else {
|
||||
web.standard_font_family_map[WebPreferences::kCommonScript] =
|
||||
ASCIIToUTF16("Times");
|
||||
}
|
||||
|
||||
if (cef.fixed_font_family.length > 0)
|
||||
web.fixed_font_family = CefString(&cef.fixed_font_family);
|
||||
else
|
||||
web.fixed_font_family = ASCIIToUTF16("Courier");
|
||||
if (cef.fixed_font_family.length > 0) {
|
||||
web.fixed_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.fixed_font_family);
|
||||
} else {
|
||||
web.fixed_font_family_map[WebPreferences::kCommonScript] =
|
||||
ASCIIToUTF16("Courier");
|
||||
}
|
||||
|
||||
if (cef.serif_font_family.length > 0)
|
||||
web.serif_font_family = CefString(&cef.serif_font_family);
|
||||
else
|
||||
web.serif_font_family = ASCIIToUTF16("Times");
|
||||
if (cef.serif_font_family.length > 0) {
|
||||
web.serif_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.serif_font_family);
|
||||
} else {
|
||||
web.serif_font_family_map[WebPreferences::kCommonScript] =
|
||||
ASCIIToUTF16("Times");
|
||||
}
|
||||
|
||||
if (cef.sans_serif_font_family.length > 0)
|
||||
web.sans_serif_font_family = CefString(&cef.sans_serif_font_family);
|
||||
else
|
||||
web.sans_serif_font_family = ASCIIToUTF16("Helvetica");
|
||||
if (cef.sans_serif_font_family.length > 0) {
|
||||
web.sans_serif_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.sans_serif_font_family);
|
||||
} else {
|
||||
web.sans_serif_font_family_map[WebPreferences::kCommonScript] =
|
||||
ASCIIToUTF16("Helvetica");
|
||||
}
|
||||
|
||||
// These two fonts below are picked from the intersection of
|
||||
// Win XP font list and Vista font list :
|
||||
@@ -40,22 +54,26 @@ void BrowserToWebSettings(const CefBrowserSettings& cef, WebPreferences& web) {
|
||||
// as long as they're available.
|
||||
|
||||
if (cef.cursive_font_family.length > 0) {
|
||||
web.cursive_font_family = CefString(&cef.cursive_font_family);
|
||||
web.cursive_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.cursive_font_family);
|
||||
} else {
|
||||
web.cursive_font_family_map[WebPreferences::kCommonScript] =
|
||||
#if defined(OS_MACOSX)
|
||||
web.cursive_font_family = ASCIIToUTF16("Apple Chancery");
|
||||
ASCIIToUTF16("Apple Chancery");
|
||||
#else
|
||||
web.cursive_font_family = ASCIIToUTF16("Comic Sans MS");
|
||||
ASCIIToUTF16("Comic Sans MS");
|
||||
#endif
|
||||
}
|
||||
|
||||
if (cef.fantasy_font_family.length > 0) {
|
||||
web.fantasy_font_family = CefString(&cef.fantasy_font_family);
|
||||
web.fantasy_font_family_map[WebPreferences::kCommonScript] =
|
||||
CefString(&cef.fantasy_font_family);
|
||||
} else {
|
||||
web.fantasy_font_family_map[WebPreferences::kCommonScript] =
|
||||
#if defined(OS_MACOSX)
|
||||
web.fantasy_font_family = ASCIIToUTF16("Papyrus");
|
||||
ASCIIToUTF16("Papyrus");
|
||||
#else
|
||||
web.fantasy_font_family = ASCIIToUTF16("Impact");
|
||||
ASCIIToUTF16("Impact");
|
||||
#endif
|
||||
}
|
||||
|
||||
|
@@ -7,8 +7,12 @@
|
||||
#pragma once
|
||||
|
||||
#include "include/internal/cef_types_wrappers.h"
|
||||
struct WebPreferences;
|
||||
|
||||
void BrowserToWebSettings(const CefBrowserSettings& cef, WebPreferences& web);
|
||||
namespace webkit_glue {
|
||||
struct WebPreferences;
|
||||
}
|
||||
|
||||
void BrowserToWebSettings(const CefBrowserSettings& cef,
|
||||
webkit_glue::WebPreferences& web);
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_SETTINGS_H_
|
||||
|
@@ -223,14 +223,11 @@ void WebSocketStreamHandleBridgeImpl::DoOnClose() {
|
||||
void BrowserSocketStreamBridge::InitializeOnIOThread(
|
||||
net::URLRequestContext* request_context) {
|
||||
g_io_thread = MessageLoop::current();
|
||||
if ((g_request_context = request_context))
|
||||
g_request_context->AddRef();
|
||||
g_request_context = request_context;
|
||||
}
|
||||
|
||||
void BrowserSocketStreamBridge::Cleanup() {
|
||||
g_io_thread = NULL;
|
||||
if (g_request_context)
|
||||
g_request_context->Release();
|
||||
g_request_context = NULL;
|
||||
}
|
||||
|
||||
|
68
cef1/libcef/browser_thread_stub.cc
Normal file
68
cef1/libcef/browser_thread_stub.cc
Normal file
@@ -0,0 +1,68 @@
|
||||
// Copyright (c) 2012 The Chromium Embedded Framework 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 "content/public/browser/browser_thread.h"
|
||||
#include "libcef/cef_thread.h"
|
||||
|
||||
// Stub implementations to convert BrowserThread calls to CefThread.
|
||||
|
||||
namespace content {
|
||||
|
||||
namespace {
|
||||
|
||||
int GetCefId(BrowserThread::ID browser_id) {
|
||||
switch (browser_id) {
|
||||
case BrowserThread::UI:
|
||||
return CefThread::UI;
|
||||
case BrowserThread::IO:
|
||||
return CefThread::IO;
|
||||
case BrowserThread::DB:
|
||||
case BrowserThread::FILE:
|
||||
return CefThread::FILE;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
// The specified BrowserThread ID is not supported.
|
||||
NOTREACHED();
|
||||
return -1;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
// static
|
||||
bool BrowserThread::PostTask(ID identifier,
|
||||
const tracked_objects::Location& from_here,
|
||||
const base::Closure& task) {
|
||||
int cef_id = GetCefId(identifier);
|
||||
if (cef_id < 0)
|
||||
return false;
|
||||
|
||||
return CefThread::PostTask(static_cast<CefThread::ID>(cef_id), from_here,
|
||||
task);
|
||||
}
|
||||
|
||||
// static
|
||||
bool BrowserThread::PostDelayedTask(ID identifier,
|
||||
const tracked_objects::Location& from_here,
|
||||
const base::Closure& task,
|
||||
base::TimeDelta delay) {
|
||||
int cef_id = GetCefId(identifier);
|
||||
if (cef_id < 0)
|
||||
return false;
|
||||
|
||||
return CefThread::PostDelayedTask(static_cast<CefThread::ID>(cef_id),
|
||||
from_here, task, delay);
|
||||
}
|
||||
|
||||
// static
|
||||
bool BrowserThread::CurrentlyOn(ID identifier) {
|
||||
int cef_id = GetCefId(identifier);
|
||||
if (cef_id < 0)
|
||||
return false;
|
||||
|
||||
return CefThread::CurrentlyOn(static_cast<CefThread::ID>(cef_id));
|
||||
}
|
||||
|
||||
} // namespace content
|
@@ -66,6 +66,9 @@ void BrowserWebBlobRegistryImpl::unregisterBlobURL(const WebURL& url) {
|
||||
thread_safe_url));
|
||||
}
|
||||
|
||||
BrowserWebBlobRegistryImpl::~BrowserWebBlobRegistryImpl() {
|
||||
}
|
||||
|
||||
void BrowserWebBlobRegistryImpl::AddFinishedBlob(
|
||||
const GURL& url, BlobData* blob_data) {
|
||||
DCHECK(g_blob_storage_controller);
|
||||
|
@@ -33,6 +33,9 @@ class BrowserWebBlobRegistryImpl
|
||||
const WebKit::WebURL& src_url);
|
||||
virtual void unregisterBlobURL(const WebKit::WebURL& url);
|
||||
|
||||
protected:
|
||||
virtual ~BrowserWebBlobRegistryImpl();
|
||||
|
||||
private:
|
||||
friend class base::RefCountedThreadSafe<BrowserWebBlobRegistryImpl>;
|
||||
|
||||
|
@@ -7,7 +7,6 @@
|
||||
#include "libcef/browser_resource_loader_bridge.h"
|
||||
#include "libcef/browser_socket_stream_bridge.h"
|
||||
#include "libcef/browser_webkit_glue.h"
|
||||
#include "libcef/browser_webstoragenamespace_impl.h"
|
||||
#include "libcef/cef_context.h"
|
||||
|
||||
#include "base/metrics/stats_counters.h"
|
||||
@@ -198,22 +197,7 @@ WebKit::WebString BrowserWebKitInit::defaultLocale() {
|
||||
|
||||
WebKit::WebStorageNamespace* BrowserWebKitInit::createLocalStorageNamespace(
|
||||
const WebKit::WebString& path, unsigned quota) {
|
||||
#ifdef ENABLE_NEW_DOM_STORAGE_BACKEND
|
||||
NOTREACHED();
|
||||
#else
|
||||
return new BrowserWebStorageNamespaceImpl(DOM_STORAGE_LOCAL);
|
||||
#endif
|
||||
}
|
||||
|
||||
void BrowserWebKitInit::dispatchStorageEvent(const WebKit::WebString& key,
|
||||
const WebKit::WebString& old_value, const WebKit::WebString& new_value,
|
||||
const WebKit::WebString& origin, const WebKit::WebURL& url,
|
||||
bool is_local_storage) {
|
||||
// All events are dispatched by the WebCore::StorageAreaProxy in the
|
||||
// simple single process case.
|
||||
#ifdef ENABLE_NEW_DOM_STORAGE_BACKEND
|
||||
NOTREACHED();
|
||||
#endif
|
||||
return dom_storage_system_.CreateLocalStorageNamespace();
|
||||
}
|
||||
|
||||
WebKit::WebIDBFactory* BrowserWebKitInit::idbFactory() {
|
||||
@@ -222,13 +206,11 @@ WebKit::WebIDBFactory* BrowserWebKitInit::idbFactory() {
|
||||
|
||||
void BrowserWebKitInit::createIDBKeysFromSerializedValuesAndKeyPath(
|
||||
const WebKit::WebVector<WebKit::WebSerializedScriptValue>& values,
|
||||
const WebKit::WebString& keyPath,
|
||||
const WebKit::WebIDBKeyPath& keyPath,
|
||||
WebKit::WebVector<WebKit::WebIDBKey>& keys_out) {
|
||||
WebKit::WebVector<WebKit::WebIDBKey> keys(values.size());
|
||||
for (size_t i = 0; i < values.size(); ++i) {
|
||||
keys[i] = WebKit::WebIDBKey::createFromValueAndKeyPath(
|
||||
values[i], WebKit::WebIDBKeyPath::create(keyPath));
|
||||
}
|
||||
for (size_t i = 0; i < values.size(); ++i)
|
||||
keys[i] = WebKit::WebIDBKey::createFromValueAndKeyPath(values[i], keyPath);
|
||||
keys_out.swap(keys);
|
||||
}
|
||||
|
||||
@@ -236,9 +218,9 @@ WebKit::WebSerializedScriptValue
|
||||
BrowserWebKitInit::injectIDBKeyIntoSerializedValue(
|
||||
const WebKit::WebIDBKey& key,
|
||||
const WebKit::WebSerializedScriptValue& value,
|
||||
const WebKit::WebString& keyPath) {
|
||||
const WebKit::WebIDBKeyPath& keyPath) {
|
||||
return WebKit::WebIDBKey::injectIDBKeyIntoSerializedValue(
|
||||
key, value, WebKit::WebIDBKeyPath::create(keyPath));
|
||||
key, value, keyPath);
|
||||
}
|
||||
|
||||
WebKit::WebGraphicsContext3D*
|
||||
@@ -264,6 +246,11 @@ base::StringPiece BrowserWebKitInit::GetDataResource(int resource_id) {
|
||||
return _Context->GetDataResource(resource_id);
|
||||
}
|
||||
|
||||
base::StringPiece BrowserWebKitInit::GetImageResource(int resource_id,
|
||||
float scale_factor) {
|
||||
return GetDataResource(resource_id);
|
||||
}
|
||||
|
||||
webkit_glue::ResourceLoaderBridge* BrowserWebKitInit::CreateResourceLoader(
|
||||
const webkit_glue::ResourceLoaderBridge::RequestInfo& request_info) {
|
||||
return BrowserResourceLoaderBridge::Create(request_info);
|
||||
|
@@ -11,6 +11,7 @@
|
||||
|
||||
#include "libcef/browser_appcache_system.h"
|
||||
#include "libcef/browser_database_system.h"
|
||||
#include "libcef/browser_dom_storage_system.h"
|
||||
#include "libcef/browser_file_system.h"
|
||||
#include "libcef/browser_webblobregistry_impl.h"
|
||||
#include "libcef/browser_webcookiejar_impl.h"
|
||||
@@ -63,23 +64,21 @@ class BrowserWebKitInit : public webkit_glue::WebKitPlatformSupportImpl {
|
||||
virtual WebKit::WebString defaultLocale() OVERRIDE;
|
||||
virtual WebKit::WebStorageNamespace* createLocalStorageNamespace(
|
||||
const WebKit::WebString& path, unsigned quota) OVERRIDE;
|
||||
void dispatchStorageEvent(const WebKit::WebString& key,
|
||||
const WebKit::WebString& old_value, const WebKit::WebString& new_value,
|
||||
const WebKit::WebString& origin, const WebKit::WebURL& url,
|
||||
bool is_local_storage) OVERRIDE;
|
||||
virtual WebKit::WebIDBFactory* idbFactory() OVERRIDE;
|
||||
virtual void createIDBKeysFromSerializedValuesAndKeyPath(
|
||||
const WebKit::WebVector<WebKit::WebSerializedScriptValue>& values,
|
||||
const WebKit::WebString& keyPath,
|
||||
const WebKit::WebIDBKeyPath& keyPath,
|
||||
WebKit::WebVector<WebKit::WebIDBKey>& keys_out) OVERRIDE;
|
||||
virtual WebKit::WebSerializedScriptValue injectIDBKeyIntoSerializedValue(
|
||||
const WebKit::WebIDBKey& key,
|
||||
const WebKit::WebSerializedScriptValue& value,
|
||||
const WebKit::WebString& keyPath) OVERRIDE;
|
||||
const WebKit::WebIDBKeyPath& keyPath) OVERRIDE;
|
||||
virtual WebKit::WebGraphicsContext3D* createOffscreenGraphicsContext3D(
|
||||
const WebKit::WebGraphicsContext3D::Attributes& attributes) OVERRIDE;
|
||||
virtual string16 GetLocalizedString(int message_id) OVERRIDE;
|
||||
virtual base::StringPiece GetDataResource(int resource_id) OVERRIDE;
|
||||
virtual base::StringPiece GetImageResource(int resource_id,
|
||||
float scale_factor) OVERRIDE;
|
||||
virtual void GetPlugins(bool refresh,
|
||||
std::vector<webkit::WebPluginInfo>* plugins) OVERRIDE;
|
||||
virtual webkit_glue::ResourceLoaderBridge* CreateResourceLoader(
|
||||
@@ -106,6 +105,7 @@ class BrowserWebKitInit : public webkit_glue::WebKitPlatformSupportImpl {
|
||||
ScopedTempDir appcache_dir_;
|
||||
BrowserAppCacheSystem appcache_system_;
|
||||
BrowserDatabaseSystem database_system_;
|
||||
BrowserDomStorageSystem dom_storage_system_;
|
||||
BrowserWebCookieJarImpl cookie_jar_;
|
||||
scoped_refptr<BrowserWebBlobRegistryImpl> blob_registry_;
|
||||
};
|
||||
|
@@ -1,55 +0,0 @@
|
||||
// Copyright (c) 2010 The Chromium Embedded Framework 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 "libcef/browser_webstoragearea_impl.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/dom_storage_area.h"
|
||||
#include "libcef/dom_storage_namespace.h"
|
||||
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebFrame.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebURL.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebView.h"
|
||||
|
||||
using WebKit::WebFrame;
|
||||
using WebKit::WebString;
|
||||
using WebKit::WebURL;
|
||||
using WebKit::WebView;
|
||||
|
||||
BrowserWebStorageAreaImpl::BrowserWebStorageAreaImpl(
|
||||
int64 namespace_id, const WebString& origin) {
|
||||
area_ =
|
||||
_Context->storage_context()->GetStorageArea(namespace_id, origin, true);
|
||||
DCHECK(area_ != NULL);
|
||||
}
|
||||
|
||||
BrowserWebStorageAreaImpl::~BrowserWebStorageAreaImpl() {
|
||||
}
|
||||
|
||||
unsigned BrowserWebStorageAreaImpl::length() {
|
||||
return area_->Length();
|
||||
}
|
||||
|
||||
WebString BrowserWebStorageAreaImpl::key(unsigned index) {
|
||||
return area_->Key(index);
|
||||
}
|
||||
|
||||
WebString BrowserWebStorageAreaImpl::getItem(const WebString& key) {
|
||||
return area_->GetItem(key);
|
||||
}
|
||||
|
||||
void BrowserWebStorageAreaImpl::setItem(
|
||||
const WebString& key, const WebString& value, const WebURL& url,
|
||||
WebStorageArea::Result& result, WebString& old_value_webkit) {
|
||||
old_value_webkit = area_->SetItem(key, value, &result);
|
||||
}
|
||||
|
||||
void BrowserWebStorageAreaImpl::removeItem(
|
||||
const WebString& key, const WebURL& url, WebString& old_value_webkit) {
|
||||
old_value_webkit = area_->RemoveItem(key);
|
||||
}
|
||||
|
||||
void BrowserWebStorageAreaImpl::clear(
|
||||
const WebURL& url, bool& cleared_something) {
|
||||
cleared_something = area_->Clear();
|
||||
}
|
@@ -1,39 +0,0 @@
|
||||
// Copyright (c) 2010 The Chromium Embedded Framework 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 CEF_LIBCEF_BROWSER_WEBSTORAGEAREA_IMPL_H_
|
||||
#define CEF_LIBCEF_BROWSER_WEBSTORAGEAREA_IMPL_H_
|
||||
#pragma once
|
||||
|
||||
#include "base/basictypes.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageArea.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
|
||||
|
||||
class DOMStorageArea;
|
||||
|
||||
class BrowserWebStorageAreaImpl : public WebKit::WebStorageArea {
|
||||
public:
|
||||
BrowserWebStorageAreaImpl(int64 namespace_id,
|
||||
const WebKit::WebString& origin);
|
||||
virtual ~BrowserWebStorageAreaImpl();
|
||||
|
||||
// See WebStorageArea.h for documentation on these functions.
|
||||
virtual unsigned length();
|
||||
virtual WebKit::WebString key(unsigned index);
|
||||
virtual WebKit::WebString getItem(const WebKit::WebString& key);
|
||||
virtual void setItem(
|
||||
const WebKit::WebString& key, const WebKit::WebString& value,
|
||||
const WebKit::WebURL& url, WebStorageArea::Result& result,
|
||||
WebKit::WebString& old_value);
|
||||
virtual void removeItem(
|
||||
const WebKit::WebString& key, const WebKit::WebURL& url,
|
||||
WebKit::WebString& old_value);
|
||||
virtual void clear(const WebKit::WebURL& url, bool& cleared_something);
|
||||
|
||||
private:
|
||||
// The object is owned by DOMStorageNamespace.
|
||||
DOMStorageArea* area_;
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_WEBSTORAGEAREA_IMPL_H_
|
@@ -1,50 +0,0 @@
|
||||
// Copyright (c) 2010 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 "libcef/browser_webstoragenamespace_impl.h"
|
||||
#include "libcef/browser_webstoragearea_impl.h"
|
||||
#include "libcef/cef_context.h"
|
||||
|
||||
#include "base/logging.h"
|
||||
|
||||
using WebKit::WebStorageArea;
|
||||
using WebKit::WebStorageNamespace;
|
||||
using WebKit::WebString;
|
||||
|
||||
BrowserWebStorageNamespaceImpl::BrowserWebStorageNamespaceImpl(
|
||||
DOMStorageType storage_type)
|
||||
: storage_type_(storage_type),
|
||||
namespace_id_(kLocalStorageNamespaceId) {
|
||||
}
|
||||
|
||||
BrowserWebStorageNamespaceImpl::BrowserWebStorageNamespaceImpl(
|
||||
DOMStorageType storage_type, int64 namespace_id)
|
||||
: storage_type_(storage_type),
|
||||
namespace_id_(namespace_id) {
|
||||
}
|
||||
|
||||
BrowserWebStorageNamespaceImpl::~BrowserWebStorageNamespaceImpl() {
|
||||
}
|
||||
|
||||
WebStorageArea* BrowserWebStorageNamespaceImpl::createStorageArea(
|
||||
const WebString& origin) {
|
||||
// Ideally, we'd keep a hash map of origin to these objects. Unfortunately
|
||||
// this doesn't seem practical because there's no good way to ref-count these
|
||||
// objects, and it'd be unclear who owned them. So, instead, we'll pay the
|
||||
// price in terms of wasted memory.
|
||||
return new BrowserWebStorageAreaImpl(namespace_id_, origin);
|
||||
}
|
||||
|
||||
WebStorageNamespace* BrowserWebStorageNamespaceImpl::copy() {
|
||||
// By returning NULL, we're telling WebKit to lazily fetch it the next time
|
||||
// session storage is used. In the WebViewClient::createView, we do the
|
||||
// book-keeping necessary to make it a true copy-on-write despite not doing
|
||||
// anything here, now.
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void BrowserWebStorageNamespaceImpl::close() {
|
||||
// This is called only on LocalStorage namespaces when WebKit thinks its
|
||||
// shutting down. This has no impact on Chromium.
|
||||
}
|
@@ -1,35 +0,0 @@
|
||||
// Copyright (c) 2010 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 CEF_LIBCEF_BROWSER_WEBSTORAGENAMESPACE_IMPL_H_
|
||||
#define CEF_LIBCEF_BROWSER_WEBSTORAGENAMESPACE_IMPL_H_
|
||||
#pragma once
|
||||
|
||||
#include "libcef/dom_storage_common.h"
|
||||
|
||||
#include "base/basictypes.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageNamespace.h"
|
||||
|
||||
class BrowserWebStorageNamespaceImpl : public WebKit::WebStorageNamespace {
|
||||
public:
|
||||
explicit BrowserWebStorageNamespaceImpl(DOMStorageType storage_type);
|
||||
BrowserWebStorageNamespaceImpl(DOMStorageType storage_type,
|
||||
int64 namespace_id);
|
||||
|
||||
// See WebStorageNamespace.h for documentation on these functions.
|
||||
virtual ~BrowserWebStorageNamespaceImpl();
|
||||
virtual WebKit::WebStorageArea* createStorageArea(
|
||||
const WebKit::WebString& origin);
|
||||
virtual WebKit::WebStorageNamespace* copy();
|
||||
virtual void close();
|
||||
|
||||
private:
|
||||
// Used during lazy initialization of namespace_id_.
|
||||
const DOMStorageType storage_type_;
|
||||
|
||||
// Our namespace ID.
|
||||
int64 namespace_id_;
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_BROWSER_WEBSTORAGENAMESPACE_IMPL_H_
|
@@ -12,11 +12,11 @@
|
||||
#include <algorithm>
|
||||
|
||||
#include "libcef/browser_appcache_system.h"
|
||||
#include "libcef/browser_dom_storage_system.h"
|
||||
#include "libcef/browser_file_system.h"
|
||||
#include "libcef/browser_impl.h"
|
||||
#include "libcef/browser_navigation_controller.h"
|
||||
#include "libcef/browser_webkit_glue.h"
|
||||
#include "libcef/browser_webstoragenamespace_impl.h"
|
||||
#include "libcef/browser_zoom_map.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/cef_process_ui_thread.h"
|
||||
@@ -188,13 +188,7 @@ WebWidget* BrowserWebViewDelegate::createPopupMenu(WebPopupType popup_type) {
|
||||
|
||||
WebStorageNamespace* BrowserWebViewDelegate::createSessionStorageNamespace(
|
||||
unsigned quota) {
|
||||
#ifdef ENABLE_NEW_DOM_STORAGE_BACKEND
|
||||
NOTREACHED();
|
||||
#else
|
||||
// Ignore the quota parameter from WebCore as in Chrome.
|
||||
return new BrowserWebStorageNamespaceImpl(DOM_STORAGE_SESSION,
|
||||
kLocalStorageNamespaceId + 1);
|
||||
#endif
|
||||
return BrowserDomStorageSystem::instance().CreateSessionStorageNamespace();
|
||||
}
|
||||
|
||||
WebKit::WebGraphicsContext3D* BrowserWebViewDelegate::createGraphicsContext3D(
|
||||
@@ -517,6 +511,11 @@ bool BrowserWebViewDelegate::allowScriptExtension(
|
||||
|
||||
// WebPluginPageDelegate -----------------------------------------------------
|
||||
|
||||
WebKit::WebPlugin* BrowserWebViewDelegate::CreatePluginReplacement(
|
||||
const FilePath& file_path) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
WebCookieJar* BrowserWebViewDelegate::GetCookieJar() {
|
||||
return &cookie_jar_;
|
||||
}
|
||||
|
@@ -119,8 +119,9 @@ class BrowserWebViewDelegate : public WebKit::WebViewClient,
|
||||
virtual void setToolTipText(
|
||||
const WebKit::WebString& text, WebKit::WebTextDirection hint) OVERRIDE;
|
||||
virtual void startDragging(
|
||||
WebKit::WebFrame* frame,
|
||||
const WebKit::WebDragData& data,
|
||||
WebKit::WebDragOperationsMask mask,
|
||||
WebKit::WebDragOperationsMask mask,
|
||||
const WebKit::WebImage& image,
|
||||
const WebKit::WebPoint& image_offset) OVERRIDE;
|
||||
virtual bool acceptsLoadDrops() OVERRIDE;
|
||||
@@ -221,6 +222,8 @@ class BrowserWebViewDelegate : public WebKit::WebViewClient,
|
||||
virtual webkit::npapi::WebPluginDelegate* CreatePluginDelegate(
|
||||
const FilePath& file_path,
|
||||
const std::string& mime_type) OVERRIDE;
|
||||
virtual WebKit::WebPlugin* CreatePluginReplacement(
|
||||
const FilePath& file_path) OVERRIDE;
|
||||
virtual void CreatedPluginWindow(
|
||||
gfx::PluginWindowHandle handle) OVERRIDE;
|
||||
virtual void WillDestroyPluginWindow(
|
||||
|
@@ -291,11 +291,11 @@ WebRect BrowserWebViewDelegate::windowResizerRect() {
|
||||
}
|
||||
|
||||
void BrowserWebViewDelegate::startDragging(
|
||||
WebFrame* frame,
|
||||
const WebDragData& data,
|
||||
WebDragOperationsMask mask,
|
||||
const WebImage& image,
|
||||
const WebPoint& image_offset) {
|
||||
|
||||
if (browser_->settings().drag_drop_disabled) {
|
||||
browser_->UIT_GetWebView()->dragSourceSystemDragEnded();
|
||||
return;
|
||||
|
@@ -348,10 +348,12 @@ WebRect BrowserWebViewDelegate::windowResizerRect() {
|
||||
return gfx::Rect(NSRectToCGRect(resize_rect));
|
||||
}
|
||||
|
||||
void BrowserWebViewDelegate::startDragging(const WebDragData& data,
|
||||
WebDragOperationsMask mask,
|
||||
const WebImage& image,
|
||||
const WebPoint& image_offset) {
|
||||
void BrowserWebViewDelegate::startDragging(
|
||||
WebFrame* frame,
|
||||
const WebDragData& data,
|
||||
WebDragOperationsMask mask,
|
||||
const WebImage& image,
|
||||
const WebPoint& image_offset) {
|
||||
if (browser_->settings().drag_drop_disabled ||
|
||||
browser_->IsWindowRenderingDisabled()) {
|
||||
browser_->UIT_GetWebView()->dragSourceSystemDragEnded();
|
||||
|
@@ -224,6 +224,7 @@ WebRect BrowserWebViewDelegate::windowResizerRect() {
|
||||
}
|
||||
|
||||
void BrowserWebViewDelegate::startDragging(
|
||||
WebFrame* frame,
|
||||
const WebDragData& data,
|
||||
WebDragOperationsMask mask,
|
||||
const WebImage& image,
|
||||
|
@@ -12,6 +12,7 @@
|
||||
#include "base/path_service.h"
|
||||
#include "base/synchronization/waitable_event.h"
|
||||
#include "ui/base/resource/resource_bundle.h"
|
||||
#include "ui/base/resource/resource_handle.h"
|
||||
#include "ui/base/ui_base_paths.h"
|
||||
|
||||
#if defined(OS_MACOSX) || defined(OS_WIN)
|
||||
@@ -19,6 +20,7 @@
|
||||
#endif
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
#include "base/mac/foundation_util.h"
|
||||
#include "base/mac/mac_util.h"
|
||||
#include "grit/webkit_resources.h"
|
||||
#endif
|
||||
@@ -27,15 +29,33 @@
|
||||
#include "base/win/resource_util.h"
|
||||
#endif
|
||||
|
||||
// Both the CefContext constuctor and the CefContext::RemoveBrowser method need
|
||||
// to initialize or reset to the same value.
|
||||
const int kNextBrowserIdReset = 1;
|
||||
|
||||
// Global CefContext pointer
|
||||
CefRefPtr<CefContext> _Context;
|
||||
|
||||
namespace {
|
||||
|
||||
// Both the CefContext constuctor and the CefContext::RemoveBrowser method need
|
||||
// to initialize or reset to the same value.
|
||||
const int kNextBrowserIdReset = 1;
|
||||
|
||||
#if defined(OS_MACOSX)
|
||||
|
||||
FilePath GetDefaultPackPath() {
|
||||
FilePath bundlePath = base::mac::GetAppBundlePath(execPath);
|
||||
return bundlePath.Append(FILE_PATH_LITERAL("Contents"))
|
||||
.Append(FILE_PATH_LITERAL("Resources"));
|
||||
}
|
||||
|
||||
#else // !defined(OS_MACOSX)
|
||||
|
||||
FilePath GetDefaultPackPath() {
|
||||
FilePath pak_dir;
|
||||
PathService::Get(base::DIR_MODULE, &pak_dir);
|
||||
return pak_dir;
|
||||
}
|
||||
|
||||
#endif // !defined(OS_MACOSX)
|
||||
|
||||
// Used in multi-threaded message loop mode to observe shutdown of the UI
|
||||
// thread.
|
||||
class DestructionObserver : public MessageLoop::DestructionObserver {
|
||||
@@ -66,6 +86,69 @@ base::StringPiece GetRawDataResource(HMODULE module, int resource_id) {
|
||||
|
||||
} // namespace
|
||||
|
||||
|
||||
class CefResourceBundleDelegate : public ui::ResourceBundle::Delegate {
|
||||
public:
|
||||
CefResourceBundleDelegate(CefContext* context)
|
||||
: context_(context),
|
||||
allow_pack_file_load_(false) {
|
||||
}
|
||||
|
||||
void set_allow_pack_file_load(bool val) { allow_pack_file_load_ = val; }
|
||||
|
||||
private:
|
||||
virtual FilePath GetPathForResourcePack(const FilePath& pack_path,
|
||||
float scale_factor) OVERRIDE {
|
||||
// Only allow the cef pack file to load.
|
||||
if (!context_->settings().pack_loading_disabled && allow_pack_file_load_)
|
||||
return pack_path;
|
||||
return FilePath();
|
||||
}
|
||||
|
||||
virtual FilePath GetPathForLocalePack(const FilePath& pack_path,
|
||||
const std::string& locale) OVERRIDE {
|
||||
if (!context_->settings().pack_loading_disabled)
|
||||
return pack_path;
|
||||
return FilePath();
|
||||
}
|
||||
|
||||
virtual gfx::Image GetImageNamed(int resource_id) OVERRIDE {
|
||||
return gfx::Image();
|
||||
}
|
||||
|
||||
virtual gfx::Image GetNativeImageNamed(
|
||||
int resource_id,
|
||||
ui::ResourceBundle::ImageRTL rtl) OVERRIDE {
|
||||
return gfx::Image();
|
||||
}
|
||||
|
||||
virtual base::RefCountedStaticMemory* LoadDataResourceBytes(
|
||||
int resource_id) OVERRIDE {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
virtual bool GetRawDataResource(int resource_id,
|
||||
base::StringPiece* value) OVERRIDE {
|
||||
return false;
|
||||
}
|
||||
|
||||
virtual bool GetLocalizedString(int message_id, string16* value) OVERRIDE {
|
||||
return false;
|
||||
}
|
||||
|
||||
virtual scoped_ptr<gfx::Font> GetFont(
|
||||
ui::ResourceBundle::FontStyle style) OVERRIDE {
|
||||
return scoped_ptr<gfx::Font>();
|
||||
}
|
||||
|
||||
// CefContext pointer is guaranteed to outlive this object.
|
||||
CefContext* context_;
|
||||
bool allow_pack_file_load_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefResourceBundleDelegate);
|
||||
};
|
||||
|
||||
|
||||
bool CefInitialize(const CefSettings& settings, CefRefPtr<CefApp> application) {
|
||||
// Return true if the global context already exists.
|
||||
if (_Context.get())
|
||||
@@ -157,6 +240,7 @@ void CefQuitMessageLoop() {
|
||||
CefContext::CefContext()
|
||||
: initialized_(false),
|
||||
shutting_down_(false),
|
||||
request_context_(NULL),
|
||||
next_browser_id_(kNextBrowserIdReset),
|
||||
current_webviewhost_(NULL) {
|
||||
}
|
||||
@@ -293,47 +377,48 @@ CefRefPtr<CefBrowserImpl> CefContext::GetBrowserByID(int id) {
|
||||
}
|
||||
|
||||
void CefContext::InitializeResourceBundle() {
|
||||
if (settings_.pack_loading_disabled)
|
||||
return;
|
||||
|
||||
FilePath pak_file, locales_dir;
|
||||
|
||||
if (settings_.pack_file_path.length > 0)
|
||||
pak_file = FilePath(CefString(&settings_.pack_file_path));
|
||||
if (!settings_.pack_loading_disabled) {
|
||||
if (settings_.pack_file_path.length > 0)
|
||||
pak_file = FilePath(CefString(&settings_.pack_file_path));
|
||||
|
||||
if (pak_file.empty()) {
|
||||
FilePath pak_dir;
|
||||
PathService::Get(base::DIR_MODULE, &pak_dir);
|
||||
pak_file = pak_dir.Append(FILE_PATH_LITERAL("chrome.pak"));
|
||||
if (pak_file.empty())
|
||||
pak_file = GetDefaultPackPath().Append(FILE_PATH_LITERAL("chrome.pak"));
|
||||
|
||||
if (settings_.locales_dir_path.length > 0)
|
||||
locales_dir = FilePath(CefString(&settings_.locales_dir_path));
|
||||
|
||||
if (!locales_dir.empty())
|
||||
PathService::Override(ui::DIR_LOCALES, locales_dir);
|
||||
}
|
||||
|
||||
if (!pak_file.empty())
|
||||
PathService::Override(ui::FILE_RESOURCES_PAK, pak_file);
|
||||
|
||||
if (settings_.locales_dir_path.length > 0)
|
||||
locales_dir = FilePath(CefString(&settings_.locales_dir_path));
|
||||
|
||||
if (!locales_dir.empty())
|
||||
PathService::Override(ui::DIR_LOCALES, locales_dir);
|
||||
|
||||
std::string locale_str = locale();
|
||||
const std::string loaded_locale =
|
||||
ui::ResourceBundle::InitSharedInstanceWithLocale(locale_str);
|
||||
CHECK(!loaded_locale.empty()) << "Locale could not be found for " <<
|
||||
locale_str;
|
||||
if (locale_str.empty())
|
||||
locale_str = "en-US";
|
||||
|
||||
#if defined(OS_WIN)
|
||||
// Explicitly load chrome.pak on Windows.
|
||||
if (file_util::PathExists(pak_file))
|
||||
ResourceBundle::AddDataPackToSharedInstance(pak_file);
|
||||
else
|
||||
NOTREACHED() << "Could not load chrome.pak";
|
||||
#endif
|
||||
resource_bundle_delegate_.reset(new CefResourceBundleDelegate(this));
|
||||
const std::string loaded_locale =
|
||||
ui::ResourceBundle::InitSharedInstanceWithLocale(
|
||||
locale_str, resource_bundle_delegate_.get());
|
||||
if (!settings_.pack_loading_disabled) {
|
||||
CHECK(!loaded_locale.empty()) << "Locale could not be found for "
|
||||
<< locale_str;
|
||||
|
||||
if (file_util::PathExists(pak_file)) {
|
||||
resource_bundle_delegate_->set_allow_pack_file_load(true);
|
||||
ResourceBundle::GetSharedInstance().AddDataPack(
|
||||
pak_file, ui::ResourceHandle::kScaleFactor100x);
|
||||
resource_bundle_delegate_->set_allow_pack_file_load(false);
|
||||
} else {
|
||||
NOTREACHED() << "Could not load chrome.pak";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void CefContext::CleanupResourceBundle() {
|
||||
if (!settings_.pack_loading_disabled)
|
||||
ResourceBundle::CleanupSharedInstance();
|
||||
ResourceBundle::CleanupSharedInstance();
|
||||
resource_bundle_delegate_.reset(NULL);
|
||||
}
|
||||
|
||||
string16 CefContext::GetLocalizedString(int message_id) const {
|
||||
@@ -382,7 +467,7 @@ base::StringPiece CefContext::GetDataResource(int resource_id) const {
|
||||
hModule = ::GetModuleHandle(file_path.value().c_str());
|
||||
if (!hModule)
|
||||
hModule = ::GetModuleHandle(NULL);
|
||||
value = GetRawDataResource(hModule, resource_id);
|
||||
value = ::GetRawDataResource(hModule, resource_id);
|
||||
}
|
||||
#elif defined(OS_MACOSX)
|
||||
if (value.empty()) {
|
||||
|
@@ -15,13 +15,13 @@
|
||||
#include "libcef/browser_file_system.h"
|
||||
#include "libcef/browser_request_context.h"
|
||||
#include "libcef/cef_process.h"
|
||||
#include "libcef/dom_storage_context.h"
|
||||
|
||||
#include "base/at_exit.h"
|
||||
#include "base/file_path.h"
|
||||
#include "base/memory/ref_counted.h"
|
||||
|
||||
class CefBrowserImpl;
|
||||
class CefResourceBundleDelegate;
|
||||
class WebViewHost;
|
||||
|
||||
namespace base {
|
||||
@@ -78,12 +78,6 @@ class CefContext : public CefBase {
|
||||
}
|
||||
BrowserRequestContext* request_context() { return request_context_; }
|
||||
|
||||
// The DOMStorageContext object is managed by CefProcessUIThread.
|
||||
void set_storage_context(DOMStorageContext* storage_context) {
|
||||
storage_context_.reset(storage_context);
|
||||
}
|
||||
DOMStorageContext* storage_context() { return storage_context_.get(); }
|
||||
|
||||
BrowserFileSystem* file_system() { return &file_system_; }
|
||||
|
||||
// Used to keep track of the web view host we're dragging over. WARNING:
|
||||
@@ -116,9 +110,9 @@ class CefContext : public CefBase {
|
||||
CefSettings settings_;
|
||||
CefRefPtr<CefApp> application_;
|
||||
FilePath cache_path_;
|
||||
scoped_refptr<BrowserRequestContext> request_context_;
|
||||
scoped_ptr<DOMStorageContext> storage_context_;
|
||||
BrowserRequestContext* request_context_;
|
||||
BrowserFileSystem file_system_;
|
||||
scoped_ptr<CefResourceBundleDelegate> resource_bundle_delegate_;
|
||||
|
||||
// Map of browsers that currently exist.
|
||||
BrowserList browserlist_;
|
||||
|
@@ -37,18 +37,18 @@ void CefProcessIOThread::Init() {
|
||||
CefThread::Init();
|
||||
|
||||
FilePath cache_path(_Context->cache_path());
|
||||
request_context_ = new BrowserRequestContext(cache_path,
|
||||
net::HttpCache::NORMAL, false);
|
||||
_Context->set_request_context(request_context_);
|
||||
request_context_.reset(new BrowserRequestContext(cache_path,
|
||||
net::HttpCache::NORMAL, false));
|
||||
_Context->set_request_context(request_context_.get());
|
||||
|
||||
network_delegate_.reset(new BrowserNetworkDelegate());
|
||||
request_context_->set_network_delegate(network_delegate_.get());
|
||||
|
||||
BrowserAppCacheSystem::InitializeOnIOThread(request_context_);
|
||||
BrowserFileWriter::InitializeOnIOThread(request_context_);
|
||||
BrowserAppCacheSystem::InitializeOnIOThread(request_context_.get());
|
||||
BrowserFileWriter::InitializeOnIOThread(request_context_.get());
|
||||
BrowserFileSystem::InitializeOnIOThread(
|
||||
request_context_->blob_storage_controller());
|
||||
BrowserSocketStreamBridge::InitializeOnIOThread(request_context_);
|
||||
BrowserSocketStreamBridge::InitializeOnIOThread(request_context_.get());
|
||||
BrowserWebBlobRegistryImpl::InitializeOnIOThread(
|
||||
request_context_->blob_storage_controller());
|
||||
}
|
||||
@@ -71,7 +71,8 @@ void CefProcessIOThread::CleanUp() {
|
||||
request_context_->set_network_delegate(NULL);
|
||||
network_delegate_.reset(NULL);
|
||||
|
||||
request_context_ = NULL;
|
||||
_Context->set_request_context(NULL);
|
||||
request_context_.reset(NULL);
|
||||
|
||||
CefThread::Cleanup();
|
||||
}
|
||||
|
@@ -31,15 +31,13 @@ class CefProcessIOThread : public CefThread {
|
||||
explicit CefProcessIOThread(MessageLoop* message_loop);
|
||||
virtual ~CefProcessIOThread();
|
||||
|
||||
scoped_refptr<BrowserRequestContext> request_context() {
|
||||
return request_context_;
|
||||
}
|
||||
BrowserRequestContext* request_context() { return request_context_.get(); }
|
||||
|
||||
protected:
|
||||
virtual void Init();
|
||||
virtual void CleanUp();
|
||||
|
||||
scoped_refptr<BrowserRequestContext> request_context_;
|
||||
scoped_ptr<BrowserRequestContext> request_context_;
|
||||
scoped_ptr<net::NetworkDelegate> network_delegate_;
|
||||
|
||||
DISALLOW_COPY_AND_ASSIGN(CefProcessIOThread);
|
||||
|
@@ -24,7 +24,7 @@
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebNetworkStateNotifier.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebScriptController.h"
|
||||
#include "ui/base/ui_base_paths.h"
|
||||
#include "ui/gfx/gl/gl_implementation.h"
|
||||
#include "ui/gl/gl_implementation.h"
|
||||
#include "webkit/glue/user_agent.h"
|
||||
#include "webkit/glue/webkit_glue.h"
|
||||
#include "webkit/plugins/npapi/plugin_list.h"
|
||||
@@ -133,17 +133,6 @@ void CefProcessUIThread::Init() {
|
||||
gfx::InitializeGLBindings(gfx::kGLImplementationDesktopGL);
|
||||
#endif
|
||||
|
||||
// Set storage quota limits.
|
||||
if (settings.local_storage_quota != 0)
|
||||
DOMStorageContext::set_local_storage_quota(settings.local_storage_quota);
|
||||
if (settings.session_storage_quota != 0) {
|
||||
DOMStorageContext::set_session_storage_quota(
|
||||
settings.session_storage_quota);
|
||||
}
|
||||
|
||||
// Create the storage context object.
|
||||
_Context->set_storage_context(new DOMStorageContext(_Context->cache_path()));
|
||||
|
||||
if (settings.user_agent.length > 0) {
|
||||
webkit_glue::SetUserAgent(CefString(&settings.user_agent), false);
|
||||
} else {
|
||||
@@ -192,9 +181,6 @@ void CefProcessUIThread::CleanUp() {
|
||||
// purify leak-test results.
|
||||
MessageLoop::current()->RunAllPending();
|
||||
|
||||
// Destroy the storage context object.
|
||||
_Context->set_storage_context(NULL);
|
||||
|
||||
// Tear down the shared StatsTable.
|
||||
base::StatsTable::set_current(NULL);
|
||||
delete statstable_;
|
||||
|
@@ -6,13 +6,13 @@
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "libcef/browser_persistent_cookie_store.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/cef_thread.h"
|
||||
#include "libcef/cef_time_util.h"
|
||||
|
||||
#include "base/bind.h"
|
||||
#include "base/logging.h"
|
||||
#include "chrome/browser/net/sqlite_persistent_cookie_store.h"
|
||||
|
||||
namespace {
|
||||
|
||||
@@ -225,11 +225,11 @@ bool CefCookieManagerImpl::SetStoragePath(const CefString& path) {
|
||||
return true;
|
||||
}
|
||||
|
||||
scoped_refptr<BrowserPersistentCookieStore> persistent_store;
|
||||
scoped_refptr<SQLitePersistentCookieStore> persistent_store;
|
||||
if (!new_path.empty()) {
|
||||
if (file_util::CreateDirectory(new_path)) {
|
||||
const FilePath& cookie_path = new_path.AppendASCII("Cookies");
|
||||
persistent_store = new BrowserPersistentCookieStore(cookie_path, false);
|
||||
persistent_store = new SQLitePersistentCookieStore(cookie_path, false);
|
||||
} else {
|
||||
NOTREACHED() << "The cookie storage directory could not be created";
|
||||
storage_path_.clear();
|
||||
|
@@ -59,6 +59,12 @@ void CefCookieStoreProxy::DeleteAllCreatedBetweenAsync(
|
||||
callback);
|
||||
}
|
||||
|
||||
void CefCookieStoreProxy::DeleteSessionCookiesAsync(
|
||||
const DeleteCallback& callback) {
|
||||
scoped_refptr<net::CookieStore> cookie_store = GetCookieStore();
|
||||
cookie_store->DeleteSessionCookiesAsync(callback);
|
||||
}
|
||||
|
||||
net::CookieMonster* CefCookieStoreProxy::GetCookieMonster() {
|
||||
scoped_refptr<net::CookieStore> cookie_store = GetCookieStore();
|
||||
return cookie_store->GetCookieMonster();
|
||||
|
@@ -35,6 +35,8 @@ class CefCookieStoreProxy : public net::CookieStore {
|
||||
const base::Time& delete_end,
|
||||
const DeleteCallback& callback)
|
||||
OVERRIDE;
|
||||
virtual void DeleteSessionCookiesAsync(const DeleteCallback& callback)
|
||||
OVERRIDE;
|
||||
virtual net::CookieMonster* GetCookieMonster() OVERRIDE;
|
||||
|
||||
private:
|
||||
|
@@ -12,7 +12,6 @@
|
||||
#include "base/logging.h"
|
||||
#include "base/string_util.h"
|
||||
#include "base/utf_string_conversions.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebAttribute.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebDocument.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebDOMEvent.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebDOMEventListener.h"
|
||||
@@ -20,12 +19,10 @@
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebFrame.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebFormControlElement.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebInputElement.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebNamedNodeMap.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebNode.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebSelectElement.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
|
||||
|
||||
using WebKit::WebAttribute;
|
||||
using WebKit::WebDocument;
|
||||
using WebKit::WebDOMEvent;
|
||||
using WebKit::WebDOMEventListener;
|
||||
@@ -33,7 +30,6 @@ using WebKit::WebElement;
|
||||
using WebKit::WebFrame;
|
||||
using WebKit::WebFormControlElement;
|
||||
using WebKit::WebInputElement;
|
||||
using WebKit::WebNamedNodeMap;
|
||||
using WebKit::WebNode;
|
||||
using WebKit::WebSelectElement;
|
||||
using WebKit::WebString;
|
||||
@@ -356,7 +352,7 @@ bool CefDOMNodeImpl::HasElementAttributes() {
|
||||
}
|
||||
|
||||
const WebElement& element = node_.toConst<WebKit::WebElement>();
|
||||
return (element.attributes().length() > 0);
|
||||
return (element.attributeCount() > 0);
|
||||
}
|
||||
|
||||
bool CefDOMNodeImpl::HasElementAttribute(const CefString& attrName) {
|
||||
@@ -400,24 +396,14 @@ void CefDOMNodeImpl::GetElementAttributes(AttributeMap& attrMap) {
|
||||
}
|
||||
|
||||
const WebElement& element = node_.toConst<WebKit::WebElement>();
|
||||
const WebNamedNodeMap& map = element.attributes();
|
||||
unsigned int len = map.length();
|
||||
unsigned int len = element.attributeCount();
|
||||
if (len == 0)
|
||||
return;
|
||||
|
||||
string16 nameStr, valueStr;
|
||||
|
||||
for (unsigned int i = 0; i < len; ++i) {
|
||||
const WebAttribute& attrib = map.attributeItem(i);
|
||||
string16 nameStr, valueStr;
|
||||
const WebString& name = attrib.localName();
|
||||
if (!name.isNull())
|
||||
nameStr = name;
|
||||
const WebString& value = attrib.value();
|
||||
if (!value.isNull())
|
||||
valueStr = value;
|
||||
|
||||
attrMap.insert(std::make_pair(nameStr, valueStr));
|
||||
string16 name = element.attributeLocalName(i);
|
||||
string16 value = element.attributeValue(i);
|
||||
attrMap.insert(std::make_pair(name, value));
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -1,80 +0,0 @@
|
||||
// Copyright (c) 2011 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 "libcef/dom_storage_area.h"
|
||||
#include "libcef/dom_storage_context.h"
|
||||
#include "libcef/dom_storage_namespace.h"
|
||||
|
||||
#include "base/logging.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebSecurityOrigin.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageArea.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebURL.h"
|
||||
#include "webkit/glue/webkit_glue.h"
|
||||
|
||||
using WebKit::WebSecurityOrigin;
|
||||
using WebKit::WebStorageArea;
|
||||
using WebKit::WebString;
|
||||
using WebKit::WebURL;
|
||||
|
||||
DOMStorageArea::DOMStorageArea(
|
||||
const string16& origin,
|
||||
int64 id,
|
||||
DOMStorageNamespace* owner)
|
||||
: origin_(origin),
|
||||
origin_url_(origin),
|
||||
id_(id),
|
||||
owner_(owner) {
|
||||
DCHECK(owner_);
|
||||
}
|
||||
|
||||
DOMStorageArea::~DOMStorageArea() {
|
||||
}
|
||||
|
||||
unsigned DOMStorageArea::Length() {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
return storage_area_->length();
|
||||
}
|
||||
|
||||
NullableString16 DOMStorageArea::Key(unsigned index) {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
return storage_area_->key(index);
|
||||
}
|
||||
|
||||
NullableString16 DOMStorageArea::GetItem(const string16& key) {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
return storage_area_->getItem(key);
|
||||
}
|
||||
|
||||
NullableString16 DOMStorageArea::SetItem(
|
||||
const string16& key, const string16& value,
|
||||
WebStorageArea::Result* result) {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
WebString old_value;
|
||||
storage_area_->setItem(key, value, WebURL(), *result, old_value);
|
||||
return old_value;
|
||||
}
|
||||
|
||||
NullableString16 DOMStorageArea::RemoveItem(const string16& key) {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
WebString old_value;
|
||||
storage_area_->removeItem(key, WebURL(), old_value);
|
||||
return old_value;
|
||||
}
|
||||
|
||||
bool DOMStorageArea::Clear() {
|
||||
CreateWebStorageAreaIfNecessary();
|
||||
bool somethingCleared;
|
||||
storage_area_->clear(WebURL(), somethingCleared);
|
||||
return somethingCleared;
|
||||
}
|
||||
|
||||
void DOMStorageArea::PurgeMemory() {
|
||||
storage_area_.reset();
|
||||
}
|
||||
|
||||
void DOMStorageArea::CreateWebStorageAreaIfNecessary() {
|
||||
if (!storage_area_.get())
|
||||
storage_area_.reset(owner_->CreateWebStorageArea(origin_));
|
||||
}
|
@@ -1,80 +0,0 @@
|
||||
// Copyright (c) 2011 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 CEF_LIBCEF_DOM_STORAGE_AREA_H_
|
||||
#define CEF_LIBCEF_DOM_STORAGE_AREA_H_
|
||||
#pragma once
|
||||
|
||||
#include "base/hash_tables.h"
|
||||
#include "base/memory/ref_counted.h"
|
||||
#include "base/memory/scoped_ptr.h"
|
||||
#include "base/nullable_string16.h"
|
||||
#include "base/string16.h"
|
||||
#include "googleurl/src/gurl.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageArea.h"
|
||||
|
||||
class DOMStorageNamespace;
|
||||
// Only use on the WebKit thread. DOMStorageNamespace manages our registration
|
||||
// with DOMStorageContext.
|
||||
class DOMStorageArea {
|
||||
public:
|
||||
DOMStorageArea(const string16& origin,
|
||||
int64 id,
|
||||
DOMStorageNamespace* owner);
|
||||
~DOMStorageArea();
|
||||
|
||||
unsigned Length();
|
||||
NullableString16 Key(unsigned index);
|
||||
NullableString16 GetItem(const string16& key);
|
||||
NullableString16 SetItem(
|
||||
const string16& key, const string16& value,
|
||||
WebKit::WebStorageArea::Result* result);
|
||||
NullableString16 RemoveItem(const string16& key);
|
||||
bool Clear();
|
||||
void PurgeMemory();
|
||||
|
||||
int64 id() const { return id_; }
|
||||
|
||||
DOMStorageNamespace* owner() const { return owner_; }
|
||||
const string16& origin() const { return origin_; }
|
||||
|
||||
private:
|
||||
// Creates the underlying WebStorageArea on demand.
|
||||
void CreateWebStorageAreaIfNecessary();
|
||||
|
||||
// The origin this storage area represents.
|
||||
string16 origin_;
|
||||
GURL origin_url_;
|
||||
|
||||
// The storage area we wrap.
|
||||
scoped_ptr<WebKit::WebStorageArea> storage_area_;
|
||||
|
||||
// Our storage area id. Unique to our parent context.
|
||||
int64 id_;
|
||||
|
||||
// The DOMStorageNamespace that owns us.
|
||||
DOMStorageNamespace* owner_;
|
||||
|
||||
DISALLOW_IMPLICIT_CONSTRUCTORS(DOMStorageArea);
|
||||
};
|
||||
|
||||
#if defined(COMPILER_GCC)
|
||||
#if defined(OS_ANDROID)
|
||||
// Android stlport uses std namespace
|
||||
namespace std {
|
||||
#else
|
||||
namespace __gnu_cxx {
|
||||
#endif
|
||||
|
||||
template<>
|
||||
struct hash<DOMStorageArea*> {
|
||||
std::size_t operator()(DOMStorageArea* const& p) const {
|
||||
return reinterpret_cast<std::size_t>(p);
|
||||
}
|
||||
};
|
||||
|
||||
} // namespace __gnu_cxx
|
||||
#endif
|
||||
|
||||
#endif // CEF_LIBCEF_DOM_STORAGE_AREA_H_
|
@@ -1,19 +0,0 @@
|
||||
// Copyright (c) 2010 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 CEF_LIBCEF_DOM_STORAGE_COMMON_H_
|
||||
#define CEF_LIBCEF_DOM_STORAGE_COMMON_H_
|
||||
#pragma once
|
||||
|
||||
#include "base/basictypes.h"
|
||||
|
||||
const int64 kLocalStorageNamespaceId = 0;
|
||||
const int64 kInvalidSessionStorageNamespaceId = kLocalStorageNamespaceId;
|
||||
|
||||
enum DOMStorageType {
|
||||
DOM_STORAGE_LOCAL = 0,
|
||||
DOM_STORAGE_SESSION
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_DOM_STORAGE_COMMON_H_
|
@@ -1,305 +0,0 @@
|
||||
// Copyright (c) 2010 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 "libcef/dom_storage_context.h"
|
||||
|
||||
#include <algorithm>
|
||||
|
||||
#include "libcef/cef_thread.h"
|
||||
#include "libcef/dom_storage_area.h"
|
||||
#include "libcef/dom_storage_namespace.h"
|
||||
|
||||
#include "base/bind.h"
|
||||
#include "base/file_path.h"
|
||||
#include "base/file_util.h"
|
||||
#include "base/string_util.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebSecurityOrigin.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageNamespace.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
|
||||
#include "webkit/database/database_util.h"
|
||||
#include "webkit/glue/webkit_glue.h"
|
||||
|
||||
const FilePath::CharType DOMStorageContext::kLocalStorageDirectory[] =
|
||||
FILE_PATH_LITERAL("Local Storage");
|
||||
|
||||
const FilePath::CharType DOMStorageContext::kLocalStorageExtension[] =
|
||||
FILE_PATH_LITERAL(".localstorage");
|
||||
|
||||
// Use WebStorageNamespace quota sizes as the default.
|
||||
unsigned int DOMStorageContext::local_storage_quota_ =
|
||||
WebKit::WebStorageNamespace::m_localStorageQuota;
|
||||
unsigned int DOMStorageContext::session_storage_quota_ =
|
||||
WebKit::WebStorageNamespace::m_sessionStorageQuota;
|
||||
|
||||
DOMStorageContext::DOMStorageContext(const FilePath& local_storage_path)
|
||||
: local_storage_path_(local_storage_path),
|
||||
last_storage_area_id_(0),
|
||||
last_session_storage_namespace_id_on_ui_thread_(kLocalStorageNamespaceId),
|
||||
last_session_storage_namespace_id_on_io_thread_(
|
||||
kLocalStorageNamespaceId) {
|
||||
}
|
||||
|
||||
DOMStorageContext::~DOMStorageContext() {
|
||||
for (StorageNamespaceMap::iterator iter(storage_namespace_map_.begin());
|
||||
iter != storage_namespace_map_.end(); ++iter) {
|
||||
delete iter->second;
|
||||
}
|
||||
}
|
||||
|
||||
int64 DOMStorageContext::AllocateStorageAreaId() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
return ++last_storage_area_id_;
|
||||
}
|
||||
|
||||
int64 DOMStorageContext::AllocateSessionStorageNamespaceId() {
|
||||
if (CefThread::CurrentlyOn(CefThread::UI))
|
||||
return ++last_session_storage_namespace_id_on_ui_thread_;
|
||||
return --last_session_storage_namespace_id_on_io_thread_;
|
||||
}
|
||||
|
||||
int64 DOMStorageContext::CloneSessionStorage(int64 original_id) {
|
||||
DCHECK(!CefThread::CurrentlyOn(CefThread::UI));
|
||||
int64 clone_id = AllocateSessionStorageNamespaceId();
|
||||
CefThread::PostTask(
|
||||
CefThread::UI, FROM_HERE,
|
||||
base::Bind(&DOMStorageContext::CompleteCloningSessionStorage, this,
|
||||
original_id, clone_id));
|
||||
return clone_id;
|
||||
}
|
||||
|
||||
void DOMStorageContext::RegisterStorageArea(DOMStorageArea* storage_area) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
int64 id = storage_area->id();
|
||||
DCHECK(!GetStorageArea(id));
|
||||
storage_area_map_[id] = storage_area;
|
||||
}
|
||||
|
||||
void DOMStorageContext::UnregisterStorageArea(DOMStorageArea* storage_area) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
int64 id = storage_area->id();
|
||||
DCHECK(GetStorageArea(id));
|
||||
storage_area_map_.erase(id);
|
||||
}
|
||||
|
||||
DOMStorageArea* DOMStorageContext::GetStorageArea(int64 id) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
StorageAreaMap::iterator iter = storage_area_map_.find(id);
|
||||
if (iter == storage_area_map_.end())
|
||||
return NULL;
|
||||
return iter->second;
|
||||
}
|
||||
|
||||
void DOMStorageContext::DeleteSessionStorageNamespace(int64 namespace_id) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
StorageNamespaceMap::iterator iter =
|
||||
storage_namespace_map_.find(namespace_id);
|
||||
if (iter == storage_namespace_map_.end())
|
||||
return;
|
||||
DCHECK(iter->second->dom_storage_type() == DOM_STORAGE_SESSION);
|
||||
delete iter->second;
|
||||
storage_namespace_map_.erase(iter);
|
||||
}
|
||||
|
||||
void DOMStorageContext::DeleteLocalStorageNamespace() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
StorageNamespaceMap::iterator iter =
|
||||
storage_namespace_map_.find(kLocalStorageNamespaceId);
|
||||
if (iter == storage_namespace_map_.end())
|
||||
return;
|
||||
DCHECK(iter->second->dom_storage_type() == DOM_STORAGE_LOCAL);
|
||||
delete iter->second;
|
||||
storage_namespace_map_.erase(iter);
|
||||
}
|
||||
|
||||
DOMStorageNamespace* DOMStorageContext::GetStorageNamespace(
|
||||
int64 id, bool allocation_allowed) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
StorageNamespaceMap::iterator iter = storage_namespace_map_.find(id);
|
||||
if (iter != storage_namespace_map_.end())
|
||||
return iter->second;
|
||||
if (!allocation_allowed)
|
||||
return NULL;
|
||||
if (id == kLocalStorageNamespaceId)
|
||||
return CreateLocalStorage();
|
||||
return CreateSessionStorage(id);
|
||||
}
|
||||
|
||||
DOMStorageArea* DOMStorageContext::GetStorageArea(int64 namespace_id,
|
||||
const string16& origin, bool allocation_allowed) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
DOMStorageNamespace* ns =
|
||||
GetStorageNamespace(namespace_id, allocation_allowed);
|
||||
if (ns)
|
||||
return ns->GetStorageArea(origin, allocation_allowed);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void DOMStorageContext::PurgeMemory(int64 namespace_id) {
|
||||
DOMStorageNamespace* ns = GetStorageNamespace(namespace_id, false);
|
||||
if (ns)
|
||||
ns->PurgeMemory();
|
||||
}
|
||||
|
||||
void DOMStorageContext::DeleteDataModifiedSince(
|
||||
const base::Time& cutoff,
|
||||
const char* url_scheme_to_be_skipped,
|
||||
const std::vector<string16>& protected_origins) {
|
||||
// Make sure that we don't delete a database that's currently being accessed
|
||||
// by unloading all of the databases temporarily.
|
||||
PurgeMemory(kLocalStorageNamespaceId);
|
||||
|
||||
if (local_storage_path_.empty())
|
||||
return;
|
||||
|
||||
file_util::FileEnumerator file_enumerator(
|
||||
local_storage_path_.Append(kLocalStorageDirectory), false,
|
||||
file_util::FileEnumerator::FILES);
|
||||
for (FilePath path = file_enumerator.Next(); !path.value().empty();
|
||||
path = file_enumerator.Next()) {
|
||||
WebKit::WebSecurityOrigin web_security_origin =
|
||||
WebKit::WebSecurityOrigin::createFromDatabaseIdentifier(
|
||||
webkit_glue::FilePathToWebString(path.BaseName()));
|
||||
if (EqualsASCII(web_security_origin.protocol(), url_scheme_to_be_skipped))
|
||||
continue;
|
||||
|
||||
std::vector<string16>::const_iterator find_iter =
|
||||
std::find(protected_origins.begin(), protected_origins.end(),
|
||||
web_security_origin.databaseIdentifier());
|
||||
if (find_iter != protected_origins.end())
|
||||
continue;
|
||||
|
||||
file_util::FileEnumerator::FindInfo find_info;
|
||||
file_enumerator.GetFindInfo(&find_info);
|
||||
if (file_util::HasFileBeenModifiedSince(find_info, cutoff))
|
||||
file_util::Delete(path, false);
|
||||
}
|
||||
}
|
||||
|
||||
void DOMStorageContext::DeleteLocalStorageForOrigin(const string16& origin) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
|
||||
DOMStorageArea* area =
|
||||
GetStorageArea(kLocalStorageNamespaceId, origin, false);
|
||||
if (!area)
|
||||
return;
|
||||
|
||||
// Calling Clear() is necessary to remove the data from the namespace.
|
||||
area->Clear();
|
||||
area->PurgeMemory();
|
||||
|
||||
if (local_storage_path_.empty())
|
||||
return;
|
||||
|
||||
FilePath file_path = GetLocalStorageFilePath(origin);
|
||||
if (!file_path.empty())
|
||||
file_util::Delete(file_path, false);
|
||||
}
|
||||
|
||||
void DOMStorageContext::DeleteAllLocalStorageFiles() {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
|
||||
// Make sure that we don't delete a database that's currently being accessed
|
||||
// by unloading all of the databases temporarily.
|
||||
PurgeMemory(kLocalStorageNamespaceId);
|
||||
|
||||
if (local_storage_path_.empty())
|
||||
return;
|
||||
|
||||
file_util::FileEnumerator file_enumerator(
|
||||
local_storage_path_.Append(kLocalStorageDirectory), false,
|
||||
file_util::FileEnumerator::FILES);
|
||||
for (FilePath file_path = file_enumerator.Next(); !file_path.empty();
|
||||
file_path = file_enumerator.Next()) {
|
||||
if (file_path.Extension() == kLocalStorageExtension)
|
||||
file_util::Delete(file_path, false);
|
||||
}
|
||||
}
|
||||
|
||||
void DOMStorageContext::SetLocalStoragePath(
|
||||
const FilePath& local_storage_path) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
|
||||
if ((local_storage_path.empty() && local_storage_path_.empty()) ||
|
||||
local_storage_path == local_storage_path_)
|
||||
return;
|
||||
|
||||
// Make sure that we don't swap out a database that's currently being accessed
|
||||
// by unloading all of the databases temporarily.
|
||||
PurgeMemory(kLocalStorageNamespaceId);
|
||||
|
||||
// Delete the current namespace, if any. It will be recreated using the new
|
||||
// path when needed.
|
||||
DeleteLocalStorageNamespace();
|
||||
|
||||
local_storage_path_ = local_storage_path;
|
||||
}
|
||||
|
||||
DOMStorageNamespace* DOMStorageContext::CreateLocalStorage() {
|
||||
FilePath dir_path;
|
||||
if (!local_storage_path_.empty())
|
||||
dir_path = local_storage_path_.Append(kLocalStorageDirectory);
|
||||
DOMStorageNamespace* new_namespace =
|
||||
DOMStorageNamespace::CreateLocalStorageNamespace(this, dir_path);
|
||||
RegisterStorageNamespace(new_namespace);
|
||||
return new_namespace;
|
||||
}
|
||||
|
||||
DOMStorageNamespace* DOMStorageContext::CreateSessionStorage(
|
||||
int64 namespace_id) {
|
||||
DOMStorageNamespace* new_namespace =
|
||||
DOMStorageNamespace::CreateSessionStorageNamespace(this, namespace_id);
|
||||
RegisterStorageNamespace(new_namespace);
|
||||
return new_namespace;
|
||||
}
|
||||
|
||||
void DOMStorageContext::RegisterStorageNamespace(
|
||||
DOMStorageNamespace* storage_namespace) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
int64 id = storage_namespace->id();
|
||||
DCHECK(!GetStorageNamespace(id, false));
|
||||
storage_namespace_map_[id] = storage_namespace;
|
||||
}
|
||||
|
||||
/* static */
|
||||
void DOMStorageContext::CompleteCloningSessionStorage(
|
||||
DOMStorageContext* context, int64 existing_id, int64 clone_id) {
|
||||
DCHECK(CefThread::CurrentlyOn(CefThread::UI));
|
||||
DOMStorageNamespace* existing_namespace =
|
||||
context->GetStorageNamespace(existing_id, false);
|
||||
// If nothing exists, then there's nothing to clone.
|
||||
if (existing_namespace)
|
||||
context->RegisterStorageNamespace(existing_namespace->Copy(clone_id));
|
||||
}
|
||||
|
||||
// static
|
||||
void DOMStorageContext::ClearLocalState(const FilePath& profile_path,
|
||||
const char* url_scheme_to_be_skipped) {
|
||||
file_util::FileEnumerator file_enumerator(profile_path.Append(
|
||||
kLocalStorageDirectory), false, file_util::FileEnumerator::FILES);
|
||||
for (FilePath file_path = file_enumerator.Next(); !file_path.empty();
|
||||
file_path = file_enumerator.Next()) {
|
||||
if (file_path.Extension() == kLocalStorageExtension) {
|
||||
WebKit::WebSecurityOrigin web_security_origin =
|
||||
WebKit::WebSecurityOrigin::createFromDatabaseIdentifier(
|
||||
webkit_glue::FilePathToWebString(file_path.BaseName()));
|
||||
if (!EqualsASCII(web_security_origin.protocol(),
|
||||
url_scheme_to_be_skipped))
|
||||
file_util::Delete(file_path, false);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
FilePath DOMStorageContext::GetLocalStorageFilePath(
|
||||
const string16& origin) const {
|
||||
DCHECK(!local_storage_path_.empty());
|
||||
|
||||
string16 origin_id =
|
||||
webkit_database::DatabaseUtil::GetOriginIdentifier(GURL(origin));
|
||||
|
||||
FilePath storageDir = local_storage_path_.Append(
|
||||
DOMStorageContext::kLocalStorageDirectory);
|
||||
FilePath::StringType id =
|
||||
webkit_glue::WebStringToFilePathString(origin_id);
|
||||
return storageDir.Append(id.append(kLocalStorageExtension));
|
||||
}
|
@@ -1,150 +0,0 @@
|
||||
// Copyright (c) 2010 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 CEF_LIBCEF_DOM_STORAGE_CONTEXT_H_
|
||||
#define CEF_LIBCEF_DOM_STORAGE_CONTEXT_H_
|
||||
#pragma once
|
||||
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <vector>
|
||||
|
||||
#include "base/file_path.h"
|
||||
#include "base/string16.h"
|
||||
#include "base/time.h"
|
||||
|
||||
class DOMStorageArea;
|
||||
class DOMStorageNamespace;
|
||||
|
||||
// This is owned by CefContext and is all the dom storage information that's
|
||||
// shared by all of the browser windows. The specifics of responsibilities are
|
||||
// fairly well documented here and in StorageNamespace and StorageArea.
|
||||
// Everything is only to be accessed on the WebKit thread unless noted
|
||||
// otherwise.
|
||||
//
|
||||
// NOTE: Virtual methods facilitate mocking functions for testing.
|
||||
class DOMStorageContext {
|
||||
public:
|
||||
explicit DOMStorageContext(const FilePath& local_storage_path);
|
||||
virtual ~DOMStorageContext();
|
||||
|
||||
// Allocate a new storage area id. Only call on the WebKit thread.
|
||||
int64 AllocateStorageAreaId();
|
||||
|
||||
// Allocate a new session storage id. Only call on the UI or IO thread.
|
||||
int64 AllocateSessionStorageNamespaceId();
|
||||
|
||||
// Clones a session storage namespace and returns the cloned namespaces' id.
|
||||
// Only call on the IO thread.
|
||||
int64 CloneSessionStorage(int64 original_id);
|
||||
|
||||
// Various storage area methods. The storage area is owned by one of the
|
||||
// namespaces that's owned by this class.
|
||||
void RegisterStorageArea(DOMStorageArea* storage_area);
|
||||
void UnregisterStorageArea(DOMStorageArea* storage_area);
|
||||
DOMStorageArea* GetStorageArea(int64 id);
|
||||
|
||||
// Called on WebKit thread when a session storage namespace can be deleted.
|
||||
void DeleteSessionStorageNamespace(int64 namespace_id);
|
||||
|
||||
// Called on WebKit thread when the local storage namespace can be deleted.
|
||||
void DeleteLocalStorageNamespace();
|
||||
|
||||
// Get a namespace from an id. What's returned is owned by this class. If
|
||||
// allocation_allowed is true, then this function will create the storage
|
||||
// namespace if it hasn't been already.
|
||||
DOMStorageNamespace* GetStorageNamespace(int64 id, bool allocation_allowed);
|
||||
|
||||
// Get a storage area with the specified namespace_id and origin. If
|
||||
// allocation_allowed is true this function will create a new namespace and/or
|
||||
// storage area if it doesn't already exist.
|
||||
DOMStorageArea* GetStorageArea(int64 namespace_id, const string16& origin,
|
||||
bool allocation_allowed);
|
||||
|
||||
// Tells storage namespaces to purge any memory they do not need.
|
||||
virtual void PurgeMemory(int64 namespace_id);
|
||||
|
||||
// Delete any local storage files that have been touched since the cutoff
|
||||
// date that's supplied.
|
||||
void DeleteDataModifiedSince(const base::Time& cutoff,
|
||||
const char* url_scheme_to_be_skipped,
|
||||
const std::vector<string16>& protected_origins);
|
||||
|
||||
// Deletes the local storage file for the given origin.
|
||||
void DeleteLocalStorageForOrigin(const string16& origin);
|
||||
|
||||
// Deletes all local storage files.
|
||||
void DeleteAllLocalStorageFiles();
|
||||
|
||||
// Sets the path that will be used for local storage. If |local_storage_path|
|
||||
// is empty in-memory storage will be used.
|
||||
void SetLocalStoragePath(const FilePath& local_storage_path);
|
||||
|
||||
// The local storage directory.
|
||||
static const FilePath::CharType kLocalStorageDirectory[];
|
||||
|
||||
// The local storage file extension.
|
||||
static const FilePath::CharType kLocalStorageExtension[];
|
||||
|
||||
// Delete all non-extension local storage files.
|
||||
static void ClearLocalState(const FilePath& profile_path,
|
||||
const char* url_scheme_to_be_skipped);
|
||||
|
||||
// Get the file name of the local storage file for the given origin.
|
||||
FilePath GetLocalStorageFilePath(const string16& origin) const;
|
||||
|
||||
// Set the quota limits for localStorage and sessionStorage respectively.
|
||||
// Changes will only take affect if made before creation of the namespaces.
|
||||
static void set_local_storage_quota(unsigned int quota)
|
||||
{ local_storage_quota_ = quota; }
|
||||
static void set_session_storage_quota(unsigned int quota)
|
||||
{ session_storage_quota_ = quota; }
|
||||
static unsigned int local_storage_quota() { return local_storage_quota_; }
|
||||
static unsigned int session_storage_quota() { return session_storage_quota_; }
|
||||
|
||||
private:
|
||||
// Get the local storage instance. The object is owned by this class.
|
||||
DOMStorageNamespace* CreateLocalStorage();
|
||||
|
||||
// Get a new session storage namespace. The object is owned by this class.
|
||||
DOMStorageNamespace* CreateSessionStorage(int64 namespace_id);
|
||||
|
||||
// Used internally to register storage namespaces we create.
|
||||
void RegisterStorageNamespace(DOMStorageNamespace* storage_namespace);
|
||||
|
||||
// The WebKit thread half of CloneSessionStorage above. Static because
|
||||
// DOMStorageContext isn't ref counted thus we can't use a runnable method.
|
||||
// That said, we know this is safe because this class is destroyed on the
|
||||
// WebKit thread, so there's no way it could be destroyed before this is run.
|
||||
static void CompleteCloningSessionStorage(DOMStorageContext* context,
|
||||
int64 existing_id, int64 clone_id);
|
||||
|
||||
// Location where localStorage files will be stored on disk. This may be empty
|
||||
// in which case localStorage data will be stored in-memory only.
|
||||
FilePath local_storage_path_;
|
||||
|
||||
// The last used storage_area_id and storage_namespace_id's. For the storage
|
||||
// namespaces, IDs allocated on the UI thread are positive and count up while
|
||||
// IDs allocated on the IO thread are negative and count down. This allows us
|
||||
// to allocate unique IDs on both without any locking. All storage area ids
|
||||
// are allocated on the WebKit thread.
|
||||
int64 last_storage_area_id_;
|
||||
int64 last_session_storage_namespace_id_on_ui_thread_;
|
||||
int64 last_session_storage_namespace_id_on_io_thread_;
|
||||
|
||||
// Maps ids to StorageAreas. We do NOT own these objects. StorageNamespace
|
||||
// (which does own them) will notify us when we should remove the entries.
|
||||
typedef std::map<int64, DOMStorageArea*> StorageAreaMap;
|
||||
StorageAreaMap storage_area_map_;
|
||||
|
||||
// Maps ids to StorageNamespaces. We own these objects.
|
||||
typedef std::map<int64, DOMStorageNamespace*> StorageNamespaceMap;
|
||||
StorageNamespaceMap storage_namespace_map_;
|
||||
|
||||
// Quota limits for localStorage and sessionStorage respectively.
|
||||
static unsigned int local_storage_quota_;
|
||||
static unsigned int session_storage_quota_;
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_DOM_STORAGE_CONTEXT_H_
|
@@ -1,124 +0,0 @@
|
||||
// Copyright (c) 2010 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 "libcef/dom_storage_namespace.h"
|
||||
#include "libcef/dom_storage_area.h"
|
||||
#include "libcef/dom_storage_context.h"
|
||||
|
||||
#include "base/file_path.h"
|
||||
#include "base/logging.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageArea.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/WebStorageNamespace.h"
|
||||
#include "webkit/glue/webkit_glue.h"
|
||||
|
||||
using WebKit::WebStorageArea;
|
||||
using WebKit::WebStorageNamespace;
|
||||
using WebKit::WebString;
|
||||
|
||||
/* static */
|
||||
DOMStorageNamespace* DOMStorageNamespace::CreateLocalStorageNamespace(
|
||||
DOMStorageContext* dom_storage_context, const FilePath& data_dir_path) {
|
||||
int64 id = kLocalStorageNamespaceId;
|
||||
DCHECK(!dom_storage_context->GetStorageNamespace(id, false));
|
||||
WebString path;
|
||||
if (!data_dir_path.empty())
|
||||
path = webkit_glue::FilePathToWebString(data_dir_path);
|
||||
return new DOMStorageNamespace(dom_storage_context, id, path,
|
||||
DOM_STORAGE_LOCAL);
|
||||
}
|
||||
|
||||
/* static */
|
||||
DOMStorageNamespace* DOMStorageNamespace::CreateSessionStorageNamespace(
|
||||
DOMStorageContext* dom_storage_context, int64 id) {
|
||||
DCHECK(!dom_storage_context->GetStorageNamespace(id, false));
|
||||
return new DOMStorageNamespace(dom_storage_context, id, WebString(),
|
||||
DOM_STORAGE_SESSION);
|
||||
}
|
||||
|
||||
DOMStorageNamespace::DOMStorageNamespace(DOMStorageContext* dom_storage_context,
|
||||
int64 id,
|
||||
const WebString& data_dir_path,
|
||||
DOMStorageType dom_storage_type)
|
||||
: dom_storage_context_(dom_storage_context),
|
||||
id_(id),
|
||||
data_dir_path_(data_dir_path),
|
||||
dom_storage_type_(dom_storage_type) {
|
||||
DCHECK(dom_storage_context_);
|
||||
}
|
||||
|
||||
DOMStorageNamespace::~DOMStorageNamespace() {
|
||||
// TODO(jorlow): If the DOMStorageContext is being destructed, there's no need
|
||||
// to do these calls. Maybe we should add a fast path?
|
||||
for (OriginToStorageAreaMap::iterator iter(origin_to_storage_area_.begin());
|
||||
iter != origin_to_storage_area_.end(); ++iter) {
|
||||
dom_storage_context_->UnregisterStorageArea(iter->second);
|
||||
delete iter->second;
|
||||
}
|
||||
}
|
||||
|
||||
DOMStorageArea* DOMStorageNamespace::GetStorageArea(
|
||||
const string16& origin, bool allocation_allowed) {
|
||||
// We may have already created it for another dispatcher host.
|
||||
OriginToStorageAreaMap::iterator iter = origin_to_storage_area_.find(origin);
|
||||
if (iter != origin_to_storage_area_.end())
|
||||
return iter->second;
|
||||
|
||||
if (!allocation_allowed)
|
||||
return NULL;
|
||||
|
||||
// We need to create a new one.
|
||||
int64 id = dom_storage_context_->AllocateStorageAreaId();
|
||||
DCHECK(!dom_storage_context_->GetStorageArea(id));
|
||||
DOMStorageArea* storage_area = new DOMStorageArea(origin, id, this);
|
||||
origin_to_storage_area_[origin] = storage_area;
|
||||
dom_storage_context_->RegisterStorageArea(storage_area);
|
||||
return storage_area;
|
||||
}
|
||||
|
||||
DOMStorageNamespace* DOMStorageNamespace::Copy(int64 id) {
|
||||
DCHECK(dom_storage_type_ == DOM_STORAGE_SESSION);
|
||||
DCHECK(!dom_storage_context_->GetStorageNamespace(id, false));
|
||||
DOMStorageNamespace* new_storage_namespace = new DOMStorageNamespace(
|
||||
dom_storage_context_, id, data_dir_path_, dom_storage_type_);
|
||||
// If we haven't used the namespace yet, there's nothing to copy.
|
||||
if (storage_namespace_.get())
|
||||
new_storage_namespace->storage_namespace_.reset(storage_namespace_->copy());
|
||||
return new_storage_namespace;
|
||||
}
|
||||
|
||||
void DOMStorageNamespace::GetStorageAreas(std::vector<DOMStorageArea*>& areas,
|
||||
bool skip_empty) const {
|
||||
OriginToStorageAreaMap::const_iterator iter = origin_to_storage_area_.begin();
|
||||
for (; iter != origin_to_storage_area_.end(); ++iter) {
|
||||
if (!skip_empty || iter->second->Length() > 0)
|
||||
areas.push_back(iter->second);
|
||||
}
|
||||
}
|
||||
|
||||
void DOMStorageNamespace::PurgeMemory() {
|
||||
for (OriginToStorageAreaMap::iterator iter(origin_to_storage_area_.begin());
|
||||
iter != origin_to_storage_area_.end(); ++iter)
|
||||
iter->second->PurgeMemory();
|
||||
storage_namespace_.reset();
|
||||
}
|
||||
|
||||
WebStorageArea* DOMStorageNamespace::CreateWebStorageArea(
|
||||
const string16& origin) {
|
||||
CreateWebStorageNamespaceIfNecessary();
|
||||
return storage_namespace_->createStorageArea(origin);
|
||||
}
|
||||
|
||||
void DOMStorageNamespace::CreateWebStorageNamespaceIfNecessary() {
|
||||
if (storage_namespace_.get())
|
||||
return;
|
||||
|
||||
if (dom_storage_type_ == DOM_STORAGE_LOCAL) {
|
||||
storage_namespace_.reset(
|
||||
WebStorageNamespace::createLocalStorageNamespace(data_dir_path_,
|
||||
DOMStorageContext::local_storage_quota()));
|
||||
} else {
|
||||
storage_namespace_.reset(WebStorageNamespace::createSessionStorageNamespace(
|
||||
DOMStorageContext::session_storage_quota()));
|
||||
}
|
||||
}
|
@@ -1,91 +0,0 @@
|
||||
// Copyright (c) 2010 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 CEF_LIBCEF_DOM_STORAGE_NAMESPACE_H_
|
||||
#define CEF_LIBCEF_DOM_STORAGE_NAMESPACE_H_
|
||||
#pragma once
|
||||
|
||||
#include "libcef/dom_storage_common.h"
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include "base/hash_tables.h"
|
||||
#include "base/memory/scoped_ptr.h"
|
||||
#include "base/string16.h"
|
||||
#include "third_party/WebKit/Source/WebKit/chromium/public/platform/WebString.h"
|
||||
|
||||
class DOMStorageArea;
|
||||
class DOMStorageContext;
|
||||
class FilePath;
|
||||
|
||||
namespace WebKit {
|
||||
class WebStorageArea;
|
||||
class WebStorageNamespace;
|
||||
}
|
||||
|
||||
// Only to be used on the WebKit thread.
|
||||
class DOMStorageNamespace {
|
||||
public:
|
||||
static DOMStorageNamespace* CreateLocalStorageNamespace(
|
||||
DOMStorageContext* dom_storage_context, const FilePath& data_dir_path);
|
||||
static DOMStorageNamespace* CreateSessionStorageNamespace(
|
||||
DOMStorageContext* dom_storage_context, int64 namespace_id);
|
||||
|
||||
~DOMStorageNamespace();
|
||||
|
||||
DOMStorageArea* GetStorageArea(const string16& origin,
|
||||
bool allocation_allowed);
|
||||
DOMStorageNamespace* Copy(int64 clone_namespace_id);
|
||||
|
||||
void GetStorageAreas(std::vector<DOMStorageArea*>& areas,
|
||||
bool skip_empty) const;
|
||||
|
||||
void PurgeMemory();
|
||||
|
||||
const DOMStorageContext* dom_storage_context() const {
|
||||
return dom_storage_context_;
|
||||
}
|
||||
int64 id() const { return id_; }
|
||||
const WebKit::WebString& data_dir_path() const { return data_dir_path_; }
|
||||
DOMStorageType dom_storage_type() const { return dom_storage_type_; }
|
||||
|
||||
// Creates a WebStorageArea for the given origin. This should only be called
|
||||
// by an owned DOMStorageArea.
|
||||
WebKit::WebStorageArea* CreateWebStorageArea(const string16& origin);
|
||||
|
||||
private:
|
||||
// Called by the static factory methods above.
|
||||
DOMStorageNamespace(DOMStorageContext* dom_storage_context,
|
||||
int64 id,
|
||||
const WebKit::WebString& data_dir_path,
|
||||
DOMStorageType storage_type);
|
||||
|
||||
// Creates the underlying WebStorageNamespace on demand.
|
||||
void CreateWebStorageNamespaceIfNecessary();
|
||||
|
||||
// All the storage areas we own.
|
||||
typedef base::hash_map<string16, // NOLINT(build/include_what_you_use)
|
||||
DOMStorageArea*> OriginToStorageAreaMap;
|
||||
OriginToStorageAreaMap origin_to_storage_area_;
|
||||
|
||||
// The DOMStorageContext that owns us.
|
||||
DOMStorageContext* dom_storage_context_;
|
||||
|
||||
// The WebKit storage namespace we manage.
|
||||
scoped_ptr<WebKit::WebStorageNamespace> storage_namespace_;
|
||||
|
||||
// Our id. Unique to our parent context class.
|
||||
int64 id_;
|
||||
|
||||
// The path used to create us, so we can recreate our WebStorageNamespace on
|
||||
// demand.
|
||||
WebKit::WebString data_dir_path_;
|
||||
|
||||
// SessionStorage vs. LocalStorage.
|
||||
const DOMStorageType dom_storage_type_;
|
||||
|
||||
DISALLOW_IMPLICIT_CONSTRUCTORS(DOMStorageNamespace);
|
||||
};
|
||||
|
||||
#endif // CEF_LIBCEF_DOM_STORAGE_NAMESPACE_H_
|
@@ -54,9 +54,10 @@ bool CefDragDataImpl::GetFileNames(std::vector<CefString>& names) {
|
||||
if (data_.filenames.empty())
|
||||
return false;
|
||||
|
||||
std::vector<string16>::const_iterator it = data_.filenames.begin();
|
||||
std::vector<WebDropData::FileInfo>::const_iterator it =
|
||||
data_.filenames.begin();
|
||||
for (; it != data_.filenames.end(); ++it)
|
||||
names.push_back(*it);
|
||||
names.push_back(it->path);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
10
cef1/libcef/sqlite_diagnostics_stub.cc
Normal file
10
cef1/libcef/sqlite_diagnostics_stub.cc
Normal file
@@ -0,0 +1,10 @@
|
||||
// Copyright (c) 2012 The Chromium Embedded Framework 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/diagnostics/sqlite_diagnostics.h"
|
||||
|
||||
// Used by SQLitePersistentCookieStore
|
||||
sql::ErrorDelegate* GetErrorHandlerForCookieDb() {
|
||||
return NULL;
|
||||
}
|
@@ -1,304 +0,0 @@
|
||||
// Copyright (c) 2011 The Chromium Embedded Framework 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 "include/cef_storage.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/cef_thread.h"
|
||||
#include "libcef/dom_storage_common.h"
|
||||
#include "libcef/dom_storage_namespace.h"
|
||||
#include "libcef/dom_storage_area.h"
|
||||
|
||||
namespace {
|
||||
|
||||
void UIT_VisitStorage(int64 namespace_id, const CefString& origin,
|
||||
const CefString& key,
|
||||
CefRefPtr<CefStorageVisitor> visitor) {
|
||||
REQUIRE_UIT();
|
||||
|
||||
DOMStorageContext* context = _Context->storage_context();
|
||||
|
||||
// Allow storage to be allocated for localStorage so that on-disk data, if
|
||||
// any, will be available.
|
||||
bool allocation_allowed = (namespace_id == kLocalStorageNamespaceId);
|
||||
|
||||
DOMStorageNamespace* ns =
|
||||
context->GetStorageNamespace(namespace_id, allocation_allowed);
|
||||
if (!ns)
|
||||
return;
|
||||
|
||||
typedef std::vector<DOMStorageArea*> AreaList;
|
||||
AreaList areas;
|
||||
|
||||
if (!origin.empty()) {
|
||||
// Visit only the area with the specified origin.
|
||||
DOMStorageArea* area = ns->GetStorageArea(origin, allocation_allowed);
|
||||
if (area)
|
||||
areas.push_back(area);
|
||||
} else {
|
||||
// Visit all areas.
|
||||
ns->GetStorageAreas(areas, true);
|
||||
}
|
||||
|
||||
if (areas.empty())
|
||||
return;
|
||||
|
||||
// Count the total number of matching keys.
|
||||
unsigned int total = 0;
|
||||
{
|
||||
NullableString16 value;
|
||||
AreaList::iterator it = areas.begin();
|
||||
for (; it != areas.end(); ) {
|
||||
DOMStorageArea* area = (*it);
|
||||
if (!key.empty()) {
|
||||
value = area->GetItem(key);
|
||||
if (value.is_null()) {
|
||||
it = areas.erase(it);
|
||||
// Don't increment the iterator.
|
||||
continue;
|
||||
} else {
|
||||
total++;
|
||||
}
|
||||
} else {
|
||||
total += area->Length();
|
||||
}
|
||||
++it;
|
||||
}
|
||||
}
|
||||
|
||||
if (total == 0)
|
||||
return;
|
||||
|
||||
DOMStorageArea* area;
|
||||
bool stop = false, deleteData;
|
||||
unsigned int count = 0, i, len;
|
||||
NullableString16 keyVal, valueVal;
|
||||
string16 keyStr, valueStr;
|
||||
typedef std::vector<string16> String16List;
|
||||
String16List delete_keys;
|
||||
|
||||
// Visit all matching pairs.
|
||||
AreaList::iterator it = areas.begin();
|
||||
for (; it != areas.end() && !stop; ++it) {
|
||||
// Each area.
|
||||
area = *(it);
|
||||
if (!key.empty()) {
|
||||
// Visit only the matching key.
|
||||
valueVal = area->GetItem(key);
|
||||
if (valueVal.is_null())
|
||||
valueStr.clear();
|
||||
else
|
||||
valueStr = valueVal.string();
|
||||
|
||||
deleteData = false;
|
||||
stop = !visitor->Visit(static_cast<CefStorageType>(namespace_id),
|
||||
area->origin(), key, valueStr, count, total, deleteData);
|
||||
if (deleteData)
|
||||
area->RemoveItem(key);
|
||||
count++;
|
||||
} else {
|
||||
// Visit all keys.
|
||||
len = area->Length();
|
||||
for (i = 0; i < len && !stop; ++i) {
|
||||
keyVal = area->Key(i);
|
||||
if (keyVal.is_null()) {
|
||||
keyStr.clear();
|
||||
valueStr.clear();
|
||||
} else {
|
||||
keyStr = keyVal.string();
|
||||
valueVal = area->GetItem(keyStr);
|
||||
if (valueVal.is_null())
|
||||
valueStr.clear();
|
||||
else
|
||||
valueStr = valueVal.string();
|
||||
}
|
||||
|
||||
deleteData = false;
|
||||
stop = !visitor->Visit(static_cast<CefStorageType>(namespace_id),
|
||||
area->origin(), keyStr, valueStr, count, total, deleteData);
|
||||
if (deleteData)
|
||||
delete_keys.push_back(keyStr);
|
||||
count++;
|
||||
}
|
||||
|
||||
// Delete the requested keys.
|
||||
if (!delete_keys.empty()) {
|
||||
String16List::const_iterator it = delete_keys.begin();
|
||||
for (; it != delete_keys.end(); ++it)
|
||||
area->RemoveItem(*it);
|
||||
delete_keys.clear();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void UIT_SetStoragePath(int64 namespace_id, const CefString& path) {
|
||||
REQUIRE_UIT();
|
||||
|
||||
if (namespace_id != kLocalStorageNamespaceId)
|
||||
return;
|
||||
|
||||
FilePath file_path;
|
||||
if (!path.empty())
|
||||
file_path = FilePath(path);
|
||||
|
||||
DOMStorageContext* context = _Context->storage_context();
|
||||
DCHECK(context);
|
||||
if (context)
|
||||
context->SetLocalStoragePath(file_path);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
bool CefVisitStorage(CefStorageType type, const CefString& origin,
|
||||
const CefString& key,
|
||||
CefRefPtr<CefStorageVisitor> visitor) {
|
||||
// Verify that the context is in a valid state.
|
||||
if (!CONTEXT_STATE_VALID()) {
|
||||
NOTREACHED() << "context not valid";
|
||||
return false;
|
||||
}
|
||||
|
||||
int64 namespace_id;
|
||||
if (type == ST_LOCALSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId;
|
||||
} else if (type == ST_SESSIONSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId + 1;
|
||||
} else {
|
||||
NOTREACHED() << "invalid type";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (CefThread::CurrentlyOn(CefThread::UI)) {
|
||||
UIT_VisitStorage(namespace_id, origin, key, visitor);
|
||||
} else {
|
||||
CefThread::PostTask(CefThread::UI, FROM_HERE,
|
||||
base::Bind(&UIT_VisitStorage, namespace_id, origin, key, visitor));
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CefSetStorage(CefStorageType type, const CefString& origin,
|
||||
const CefString& key, const CefString& value) {
|
||||
// Verify that the context is in a valid state.
|
||||
if (!CONTEXT_STATE_VALID()) {
|
||||
NOTREACHED() << "context not valid";
|
||||
return false;
|
||||
}
|
||||
|
||||
// Verify that this function is being called on the UI thread.
|
||||
if (!CefThread::CurrentlyOn(CefThread::UI)) {
|
||||
NOTREACHED() << "called on invalid thread";
|
||||
return false;
|
||||
}
|
||||
|
||||
int64 namespace_id;
|
||||
if (type == ST_LOCALSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId;
|
||||
} else if (type == ST_SESSIONSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId + 1;
|
||||
} else {
|
||||
NOTREACHED() << "invalid type";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (origin.empty()) {
|
||||
NOTREACHED() << "invalid origin";
|
||||
return false;
|
||||
}
|
||||
|
||||
DOMStorageArea* area =
|
||||
_Context->storage_context()->GetStorageArea(namespace_id, origin, true);
|
||||
if (!area)
|
||||
return false;
|
||||
|
||||
WebKit::WebStorageArea::Result result;
|
||||
area->SetItem(key, value, &result);
|
||||
return (result == WebKit::WebStorageArea::ResultOK);
|
||||
}
|
||||
|
||||
bool CefDeleteStorage(CefStorageType type, const CefString& origin,
|
||||
const CefString& key) {
|
||||
// Verify that the context is in a valid state.
|
||||
if (!CONTEXT_STATE_VALID()) {
|
||||
NOTREACHED() << "context not valid";
|
||||
return false;
|
||||
}
|
||||
|
||||
// Verify that this function is being called on the UI thread.
|
||||
if (!CefThread::CurrentlyOn(CefThread::UI)) {
|
||||
NOTREACHED() << "called on invalid thread";
|
||||
return false;
|
||||
}
|
||||
|
||||
int64 namespace_id;
|
||||
if (type == ST_LOCALSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId;
|
||||
} else if (type == ST_SESSIONSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId + 1;
|
||||
} else {
|
||||
NOTREACHED() << "invalid type";
|
||||
return false;
|
||||
}
|
||||
|
||||
DOMStorageContext* context = _Context->storage_context();
|
||||
|
||||
// Allow storage to be allocated for localStorage so that on-disk data, if
|
||||
// any, will be available.
|
||||
bool allocation_allowed = (namespace_id == kLocalStorageNamespaceId);
|
||||
|
||||
if (origin.empty()) {
|
||||
// Delete all storage for the namespace.
|
||||
if (namespace_id == kLocalStorageNamespaceId)
|
||||
context->DeleteAllLocalStorageFiles();
|
||||
else
|
||||
context->PurgeMemory(namespace_id);
|
||||
} else if (key.empty()) {
|
||||
// Clear the storage area for the specified origin.
|
||||
if (namespace_id == kLocalStorageNamespaceId) {
|
||||
context->DeleteLocalStorageForOrigin(origin);
|
||||
} else {
|
||||
DOMStorageArea* area =
|
||||
context->GetStorageArea(namespace_id, origin, allocation_allowed);
|
||||
if (area) {
|
||||
// Calling Clear() is necessary to remove the data from the namespace.
|
||||
area->Clear();
|
||||
area->PurgeMemory();
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// Delete the specified key.
|
||||
DOMStorageArea* area =
|
||||
context->GetStorageArea(namespace_id, origin, allocation_allowed);
|
||||
if (area)
|
||||
area->RemoveItem(key);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CefSetStoragePath(CefStorageType type, const CefString& path) {
|
||||
// Verify that the context is in a valid state.
|
||||
if (!CONTEXT_STATE_VALID()) {
|
||||
NOTREACHED() << "context not valid";
|
||||
return false;
|
||||
}
|
||||
|
||||
int64 namespace_id;
|
||||
if (type == ST_LOCALSTORAGE) {
|
||||
namespace_id = kLocalStorageNamespaceId;
|
||||
} else {
|
||||
NOTREACHED() << "invalid type";
|
||||
return false;
|
||||
}
|
||||
|
||||
if (CefThread::CurrentlyOn(CefThread::UI)) {
|
||||
UIT_SetStoragePath(namespace_id, path);
|
||||
} else {
|
||||
CefThread::PostTask(CefThread::UI, FROM_HERE,
|
||||
base::Bind(&UIT_SetStoragePath, namespace_id, path));
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
@@ -2,10 +2,19 @@
|
||||
// reserved. Use of this source code is governed by a BSD-style license that
|
||||
// can be found in the LICENSE file.
|
||||
|
||||
#include "libcef/v8_impl.h"
|
||||
|
||||
#include <string>
|
||||
|
||||
#include "base/compiler_specific.h"
|
||||
|
||||
#include "third_party/WebKit/Source/WebCore/config.h"
|
||||
MSVC_PUSH_WARNING_LEVEL(0);
|
||||
#include "V8Proxy.h" // NOLINT(build/include)
|
||||
#include "V8RecursionScope.h" // NOLINT(build/include)
|
||||
MSVC_POP_WARNING();
|
||||
#undef LOG
|
||||
|
||||
#include "libcef/v8_impl.h"
|
||||
|
||||
#include "libcef/browser_impl.h"
|
||||
#include "libcef/cef_context.h"
|
||||
#include "libcef/tracker.h"
|
||||
@@ -30,10 +39,7 @@
|
||||
|
||||
namespace {
|
||||
|
||||
static const char kCefAccessor[] = "Cef::Accessor";
|
||||
static const char kCefHandler[] = "Cef::Handler";
|
||||
static const char kCefUserData[] = "Cef::UserData";
|
||||
static const char kCefExternalMemory[] = "Cef::ExternalMemory";
|
||||
static const char kCefTrackObject[] = "Cef::TrackObject";
|
||||
|
||||
// Memory manager.
|
||||
|
||||
@@ -41,20 +47,78 @@ base::LazyInstance<CefTrackManager> g_v8_tracker = LAZY_INSTANCE_INITIALIZER;
|
||||
|
||||
class V8TrackObject : public CefTrackNode {
|
||||
public:
|
||||
V8TrackObject(CefBase* object = NULL, CefBase* user_data = NULL)
|
||||
: object_(object),
|
||||
user_data_(user_data),
|
||||
external_memory_counter_(0) {
|
||||
V8TrackObject()
|
||||
: external_memory_(0) {
|
||||
}
|
||||
~V8TrackObject() {
|
||||
if (external_memory_ != 0)
|
||||
v8::V8::AdjustAmountOfExternalAllocatedMemory(-external_memory_);
|
||||
}
|
||||
|
||||
int* GetMemoryCounter() {
|
||||
return &external_memory_counter_;
|
||||
inline int GetExternallyAllocatedMemory() {
|
||||
return external_memory_;
|
||||
}
|
||||
|
||||
int AdjustExternallyAllocatedMemory(int change_in_bytes) {
|
||||
int new_value = external_memory_ + change_in_bytes;
|
||||
if (new_value < 0) {
|
||||
NOTREACHED() << "External memory usage cannot be less than 0 bytes";
|
||||
change_in_bytes = -(external_memory_);
|
||||
new_value = 0;
|
||||
}
|
||||
|
||||
if (change_in_bytes != 0)
|
||||
v8::V8::AdjustAmountOfExternalAllocatedMemory(change_in_bytes);
|
||||
external_memory_ = new_value;
|
||||
|
||||
return new_value;
|
||||
}
|
||||
|
||||
inline void SetAccessor(CefRefPtr<CefV8Accessor> accessor) {
|
||||
accessor_ = accessor;
|
||||
}
|
||||
|
||||
inline CefRefPtr<CefV8Accessor> GetAccessor() {
|
||||
return accessor_;
|
||||
}
|
||||
|
||||
inline void SetHandler(CefRefPtr<CefV8Handler> handler) {
|
||||
handler_ = handler;
|
||||
}
|
||||
|
||||
inline CefRefPtr<CefV8Handler> GetHandler() {
|
||||
return handler_;
|
||||
}
|
||||
|
||||
inline void SetUserData(CefRefPtr<CefBase> user_data) {
|
||||
user_data_ = user_data;
|
||||
}
|
||||
|
||||
inline CefRefPtr<CefBase> GetUserData() {
|
||||
return user_data_;
|
||||
}
|
||||
|
||||
// Attach this track object to the specified V8 object.
|
||||
void AttachTo(v8::Handle<v8::Object> object) {
|
||||
object->SetHiddenValue(v8::String::New(kCefTrackObject),
|
||||
v8::External::Wrap(this));
|
||||
}
|
||||
|
||||
// Retrieve the track object for the specified V8 object.
|
||||
static V8TrackObject* Unwrap(v8::Handle<v8::Object> object) {
|
||||
v8::Local<v8::Value> value =
|
||||
object->GetHiddenValue(v8::String::New(kCefTrackObject));
|
||||
if (!value.IsEmpty())
|
||||
return static_cast<V8TrackObject*>(v8::External::Unwrap(value));
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
private:
|
||||
CefRefPtr<CefBase> object_;
|
||||
CefRefPtr<CefV8Accessor> accessor_;
|
||||
CefRefPtr<CefV8Handler> handler_;
|
||||
CefRefPtr<CefBase> user_data_;
|
||||
int external_memory_counter_;
|
||||
int external_memory_;
|
||||
};
|
||||
|
||||
class V8TrackString : public CefTrackNode {
|
||||
@@ -76,16 +140,9 @@ void TrackDelete(CefTrackNode* object) {
|
||||
|
||||
// Callback for weak persistent reference destruction.
|
||||
void TrackDestructor(v8::Persistent<v8::Value> object, void* parameter) {
|
||||
if (parameter) {
|
||||
if (object->IsObject()) {
|
||||
V8TrackObject* tracker = static_cast<V8TrackObject*>(parameter);
|
||||
DCHECK(tracker);
|
||||
int adjustment = -(*tracker->GetMemoryCounter());
|
||||
if (adjustment != 0)
|
||||
v8::V8::AdjustAmountOfExternalAllocatedMemory(adjustment);
|
||||
}
|
||||
if (parameter)
|
||||
TrackDelete(static_cast<CefTrackNode*>(parameter));
|
||||
}
|
||||
|
||||
object.Dispose();
|
||||
object.Clear();
|
||||
}
|
||||
@@ -213,8 +270,13 @@ v8::Handle<v8::Value> AccessorGetterCallbackImpl(v8::Local<v8::String> property,
|
||||
|
||||
v8::Handle<v8::Object> obj = info.This();
|
||||
|
||||
CefV8Accessor* accessorPtr = CefV8ValueImpl::GetAccessor(obj);
|
||||
if (accessorPtr) {
|
||||
CefRefPtr<CefV8Accessor> accessorPtr;
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
accessorPtr = tracker->GetAccessor();
|
||||
|
||||
if (accessorPtr.get()) {
|
||||
CefRefPtr<CefV8Value> retval;
|
||||
CefRefPtr<CefV8Value> object = new CefV8ValueImpl(obj);
|
||||
CefString name, exception;
|
||||
@@ -241,8 +303,13 @@ void AccessorSetterCallbackImpl(v8::Local<v8::String> property,
|
||||
|
||||
v8::Handle<v8::Object> obj = info.This();
|
||||
|
||||
CefV8Accessor* accessorPtr = CefV8ValueImpl::GetAccessor(obj);
|
||||
if (accessorPtr) {
|
||||
CefRefPtr<CefV8Accessor> accessorPtr;
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
accessorPtr = tracker->GetAccessor();
|
||||
|
||||
if (accessorPtr.get()) {
|
||||
CefRefPtr<CefV8Value> object = new CefV8ValueImpl(obj);
|
||||
CefRefPtr<CefV8Value> cefValue = new CefV8ValueImpl(value);
|
||||
CefString name, exception;
|
||||
@@ -264,8 +331,10 @@ class ExtensionWrapper : public v8::Extension {
|
||||
CefV8Handler* handler)
|
||||
: v8::Extension(extension_name, javascript_code), handler_(handler) {
|
||||
if (handler) {
|
||||
// The reference will be released when the application exits.
|
||||
TrackAdd(new V8TrackObject(handler));
|
||||
// The reference will be released when the process exits.
|
||||
V8TrackObject* object = new V8TrackObject;
|
||||
object->SetHandler(handler);
|
||||
TrackAdd(object);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -339,6 +408,9 @@ class CefV8ExceptionImpl : public CefV8Exception {
|
||||
|
||||
} // namespace
|
||||
|
||||
|
||||
// Global functions.
|
||||
|
||||
bool CefRegisterExtension(const CefString& extension_name,
|
||||
const CefString& javascript_code,
|
||||
CefRefPtr<CefV8Handler> handler) {
|
||||
@@ -359,7 +431,7 @@ bool CefRegisterExtension(const CefString& extension_name,
|
||||
}
|
||||
|
||||
|
||||
// CefV8Context
|
||||
// CefV8Context implementation.
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Context> CefV8Context::GetCurrentContext() {
|
||||
@@ -393,7 +465,25 @@ bool CefV8Context::InContext() {
|
||||
}
|
||||
|
||||
|
||||
// CefV8ContextImpl
|
||||
// CefV8ContextImpl implementation.
|
||||
|
||||
#define CEF_V8_REQUIRE_OBJECT_RETURN(ret) \
|
||||
if (!GetHandle()->IsObject()) { \
|
||||
NOTREACHED() << "V8 value is not an object"; \
|
||||
return ret; \
|
||||
}
|
||||
|
||||
#define CEF_V8_REQUIRE_ARRAY_RETURN(ret) \
|
||||
if (!GetHandle()->IsArray()) { \
|
||||
NOTREACHED() << "V8 value is not an array"; \
|
||||
return ret; \
|
||||
}
|
||||
|
||||
#define CEF_V8_REQUIRE_FUNCTION_RETURN(ret) \
|
||||
if (!GetHandle()->IsFunction()) { \
|
||||
NOTREACHED() << "V8 value is not a function"; \
|
||||
return ret; \
|
||||
}
|
||||
|
||||
CefV8ContextImpl::CefV8ContextImpl(v8::Handle<v8::Context> context)
|
||||
#ifndef NDEBUG
|
||||
@@ -475,6 +565,51 @@ bool CefV8ContextImpl::IsSame(CefRefPtr<CefV8Context> that) {
|
||||
return (thisHandle == thatHandle);
|
||||
}
|
||||
|
||||
bool CefV8ContextImpl::Eval(const CefString& code,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception) {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
|
||||
if (code.empty()) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
}
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Context::Scope context_scope(v8_context_->GetHandle());
|
||||
v8::Local<v8::Object> obj = v8_context_->GetHandle()->Global();
|
||||
|
||||
// Retrieve the eval function.
|
||||
v8::Local<v8::Value> val = obj->Get(v8::String::New("eval"));
|
||||
if (val.IsEmpty() || !val->IsFunction())
|
||||
return false;
|
||||
|
||||
v8::Local<v8::Function> func = v8::Local<v8::Function>::Cast(val);
|
||||
v8::Handle<v8::Value> code_val = GetV8String(code);
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
v8::Local<v8::Value> func_rv;
|
||||
|
||||
retval = NULL;
|
||||
exception = NULL;
|
||||
|
||||
// Execute the function call using the V8Proxy so that inspector
|
||||
// instrumentation works.
|
||||
WebCore::V8Proxy* proxy = WebCore::V8Proxy::retrieve();
|
||||
DCHECK(proxy);
|
||||
if (proxy)
|
||||
func_rv = proxy->callFunction(func, obj, 1, &code_val);
|
||||
|
||||
if (try_catch.HasCaught()) {
|
||||
exception = new CefV8ExceptionImpl(try_catch.Message());
|
||||
return false;
|
||||
} else if (!func_rv.IsEmpty()) {
|
||||
retval = new CefV8ValueImpl(func_rv);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
v8::Local<v8::Context> CefV8ContextImpl::GetContext() {
|
||||
return v8::Local<v8::Context>::New(v8_context_->GetHandle());
|
||||
}
|
||||
@@ -530,13 +665,21 @@ CefRefPtr<CefV8Value> CefV8Value::CreateBool(bool value) {
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateInt(int value) {
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateInt(int32 value) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
v8::HandleScope handle_scope;
|
||||
return new CefV8ValueImpl(v8::Int32::New(value));
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateUInt(uint32 value) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
v8::HandleScope handle_scope;
|
||||
return new CefV8ValueImpl(v8::Int32::NewFromUnsigned(value));
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateDouble(double value) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
@@ -564,7 +707,7 @@ CefRefPtr<CefV8Value> CefV8Value::CreateString(const CefString& value) {
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateObject(
|
||||
CefRefPtr<CefBase> user_data, CefRefPtr<CefV8Accessor> accessor) {
|
||||
CefRefPtr<CefV8Accessor> accessor) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
|
||||
@@ -579,39 +722,19 @@ CefRefPtr<CefV8Value> CefV8Value::CreateObject(
|
||||
// Create the new V8 object.
|
||||
v8::Local<v8::Object> obj = v8::Object::New();
|
||||
|
||||
// Provide a tracker object that will cause the user data and/or accessor
|
||||
// Create a tracker object that will cause the user data and/or accessor
|
||||
// reference to be released when the V8 object is destroyed.
|
||||
V8TrackObject* tracker = NULL;
|
||||
if (user_data.get() && accessor.get()) {
|
||||
tracker = new V8TrackObject(accessor, user_data);
|
||||
} else if (user_data.get() || accessor.get()) {
|
||||
CefBase* object = user_data.get() ? user_data.get() : accessor.get();
|
||||
tracker = new V8TrackObject(object);
|
||||
} else {
|
||||
tracker = new V8TrackObject();
|
||||
}
|
||||
V8TrackObject* tracker = new V8TrackObject;
|
||||
tracker->SetAccessor(accessor);
|
||||
|
||||
// Attach the memory counter.
|
||||
obj->SetHiddenValue(v8::String::New(kCefExternalMemory),
|
||||
v8::External::Wrap(tracker->GetMemoryCounter()));
|
||||
|
||||
// Attach the user data to the V8 object.
|
||||
if (user_data.get()) {
|
||||
v8::Local<v8::Value> data = v8::External::Wrap(user_data.get());
|
||||
obj->SetHiddenValue(v8::String::New(kCefUserData), data);
|
||||
}
|
||||
|
||||
// Attach the accessor to the V8 object.
|
||||
if (accessor.get()) {
|
||||
v8::Local<v8::Value> data = v8::External::Wrap(accessor.get());
|
||||
obj->SetHiddenValue(v8::String::New(kCefAccessor), data);
|
||||
}
|
||||
// Attach the tracker object.
|
||||
tracker->AttachTo(obj);
|
||||
|
||||
return new CefV8ValueImpl(obj, tracker);
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateArray() {
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateArray(int length) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
|
||||
@@ -623,12 +746,23 @@ CefRefPtr<CefV8Value> CefV8Value::CreateArray() {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
return new CefV8ValueImpl(v8::Array::New());
|
||||
// Create a tracker object that will cause the user data reference to be
|
||||
// released when the V8 object is destroyed.
|
||||
V8TrackObject* tracker = new V8TrackObject;
|
||||
|
||||
// Create the new V8 array.
|
||||
v8::Local<v8::Array> arr = v8::Array::New(length);
|
||||
|
||||
// Attach the tracker object.
|
||||
tracker->AttachTo(arr);
|
||||
|
||||
return new CefV8ValueImpl(arr, tracker);
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefV8Value> CefV8Value::CreateFunction(
|
||||
const CefString& name, CefRefPtr<CefV8Handler> handler) {
|
||||
const CefString& name,
|
||||
CefRefPtr<CefV8Handler> handler) {
|
||||
CEF_REQUIRE_VALID_CONTEXT(NULL);
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
|
||||
@@ -645,7 +779,7 @@ CefRefPtr<CefV8Value> CefV8Value::CreateFunction(
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// Create a new V8 function template with one internal field.
|
||||
// Create a new V8 function template.
|
||||
v8::Local<v8::FunctionTemplate> tmpl = v8::FunctionTemplate::New();
|
||||
|
||||
v8::Local<v8::Value> data = v8::External::Wrap(handler.get());
|
||||
@@ -662,14 +796,13 @@ CefRefPtr<CefV8Value> CefV8Value::CreateFunction(
|
||||
|
||||
func->SetName(GetV8String(name));
|
||||
|
||||
V8TrackObject* tracker = new V8TrackObject(handler.get());
|
||||
// Create a tracker object that will cause the user data and/or handler
|
||||
// reference to be released when the V8 object is destroyed.
|
||||
V8TrackObject* tracker = new V8TrackObject;
|
||||
tracker->SetHandler(handler);
|
||||
|
||||
// Attach the memory counter.
|
||||
func->SetHiddenValue(v8::String::New(kCefExternalMemory),
|
||||
v8::External::Wrap(tracker->GetMemoryCounter()));
|
||||
|
||||
// Attach the handler instance to the V8 object.
|
||||
func->SetHiddenValue(v8::String::New(kCefHandler), data);
|
||||
// Attach the tracker object.
|
||||
tracker->AttachTo(func);
|
||||
|
||||
// Create the CefV8ValueImpl and provide a tracker object that will cause
|
||||
// the handler reference to be released when the V8 object is destroyed.
|
||||
@@ -680,7 +813,8 @@ CefRefPtr<CefV8Value> CefV8Value::CreateFunction(
|
||||
// CefV8ValueImpl
|
||||
|
||||
CefV8ValueImpl::CefV8ValueImpl(v8::Handle<v8::Value> value,
|
||||
CefTrackNode* tracker) {
|
||||
CefTrackNode* tracker)
|
||||
: rethrow_exceptions_(false) {
|
||||
v8_value_ = new CefV8ValueHandle(value, tracker);
|
||||
}
|
||||
|
||||
@@ -708,6 +842,11 @@ bool CefV8ValueImpl::IsInt() {
|
||||
return GetHandle()->IsInt32();
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::IsUInt() {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
return GetHandle()->IsUint32();
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::IsDouble() {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
return GetHandle()->IsNumber();
|
||||
@@ -766,13 +905,20 @@ bool CefV8ValueImpl::GetBoolValue() {
|
||||
}
|
||||
}
|
||||
|
||||
int CefV8ValueImpl::GetIntValue() {
|
||||
int32 CefV8ValueImpl::GetIntValue() {
|
||||
CEF_REQUIRE_UI_THREAD(0);
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Int32> val = GetHandle()->ToInt32();
|
||||
return val->Value();
|
||||
}
|
||||
|
||||
uint32 CefV8ValueImpl::GetUIntValue() {
|
||||
CEF_REQUIRE_UI_THREAD(0);
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Uint32> val = GetHandle()->ToUint32();
|
||||
return val->Value();
|
||||
}
|
||||
|
||||
double CefV8ValueImpl::GetDoubleValue() {
|
||||
CEF_REQUIRE_UI_THREAD(0.);
|
||||
v8::HandleScope handle_scope;
|
||||
@@ -796,12 +942,57 @@ CefString CefV8ValueImpl::GetStringValue() {
|
||||
return rv;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::IsUserCreated() {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
return (tracker != NULL);
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::HasException() {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
return (last_exception_.get() != NULL);
|
||||
}
|
||||
|
||||
CefRefPtr<CefV8Exception> CefV8ValueImpl::GetException() {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(NULL);
|
||||
|
||||
return last_exception_;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::ClearException() {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(NULL);
|
||||
|
||||
last_exception_ = NULL;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::WillRethrowExceptions() {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
return rethrow_exceptions_;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::SetRethrowExceptions(bool rethrow) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
rethrow_exceptions_ = rethrow;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::HasValue(const CefString& key) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (key.empty()) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
@@ -815,10 +1006,8 @@ bool CefV8ValueImpl::HasValue(const CefString& key) {
|
||||
|
||||
bool CefV8ValueImpl::HasValue(int index) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (index < 0) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
@@ -831,10 +1020,7 @@ bool CefV8ValueImpl::HasValue(int index) {
|
||||
|
||||
bool CefV8ValueImpl::DeleteValue(const CefString& key) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (key.empty()) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
@@ -843,15 +1029,17 @@ bool CefV8ValueImpl::DeleteValue(const CefString& key) {
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return obj->Delete(GetV8String(key));
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
bool del = obj->Delete(GetV8String(key));
|
||||
return (!HasCaught(try_catch) && del);
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::DeleteValue(int index) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (index < 0) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
@@ -859,15 +1047,16 @@ bool CefV8ValueImpl::DeleteValue(int index) {
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return obj->Delete(index);
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
bool del = obj->Delete(index);
|
||||
return (!HasCaught(try_catch) && del);
|
||||
}
|
||||
|
||||
CefRefPtr<CefV8Value> CefV8ValueImpl::GetValue(const CefString& key) {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return NULL;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(NULL);
|
||||
|
||||
if (key.empty()) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
@@ -876,15 +1065,19 @@ CefRefPtr<CefV8Value> CefV8ValueImpl::GetValue(const CefString& key) {
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return new CefV8ValueImpl(obj->Get(GetV8String(key)));
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
v8::Local<v8::Value> value = obj->Get(GetV8String(key));
|
||||
if (!HasCaught(try_catch) && !value.IsEmpty())
|
||||
return new CefV8ValueImpl(value);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
CefRefPtr<CefV8Value> CefV8ValueImpl::GetValue(int index) {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return NULL;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(NULL);
|
||||
|
||||
if (index < 0) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return NULL;
|
||||
@@ -892,24 +1085,31 @@ CefRefPtr<CefV8Value> CefV8ValueImpl::GetValue(int index) {
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return new CefV8ValueImpl(obj->Get(v8::Number::New(index)));
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
v8::Local<v8::Value> value = obj->Get(v8::Number::New(index));
|
||||
if (!HasCaught(try_catch) && !value.IsEmpty())
|
||||
return new CefV8ValueImpl(value);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::SetValue(const CefString& key,
|
||||
CefRefPtr<CefV8Value> value,
|
||||
PropertyAttribute attribute) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
CefV8ValueImpl* impl = static_cast<CefV8ValueImpl*>(value.get());
|
||||
if (impl && !key.empty()) {
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return obj->Set(GetV8String(key), impl->GetHandle(),
|
||||
static_cast<v8::PropertyAttribute>(attribute));
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
bool set = obj->Set(GetV8String(key), impl->GetHandle(),
|
||||
static_cast<v8::PropertyAttribute>(attribute));
|
||||
return (!HasCaught(try_catch) && set);
|
||||
} else {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
@@ -918,11 +1118,8 @@ bool CefV8ValueImpl::SetValue(const CefString& key,
|
||||
|
||||
bool CefV8ValueImpl::SetValue(int index, CefRefPtr<CefV8Value> value) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
if (index < 0) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
@@ -932,7 +1129,11 @@ bool CefV8ValueImpl::SetValue(int index, CefRefPtr<CefV8Value> value) {
|
||||
if (impl) {
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
return obj->Set(index, impl->GetHandle());
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
bool set = obj->Set(index, impl->GetHandle());
|
||||
return (!HasCaught(try_catch) && set);
|
||||
} else {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
return false;
|
||||
@@ -942,10 +1143,7 @@ bool CefV8ValueImpl::SetValue(int index, CefRefPtr<CefV8Value> value) {
|
||||
bool CefV8ValueImpl::SetValue(const CefString& key, AccessControl settings,
|
||||
PropertyAttribute attribute) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
if (key.empty()) {
|
||||
NOTREACHED() << "invalid input parameter";
|
||||
@@ -955,26 +1153,31 @@ bool CefV8ValueImpl::SetValue(const CefString& key, AccessControl settings,
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
CefRefPtr<CefV8Accessor> accessorPtr;
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
accessorPtr = tracker->GetAccessor();
|
||||
|
||||
// Verify that an accessor exists for this object.
|
||||
if (!GetAccessor(obj))
|
||||
if (!accessorPtr.get())
|
||||
return false;
|
||||
|
||||
v8::AccessorGetter getter = AccessorGetterCallbackImpl;
|
||||
v8::AccessorSetter setter = (attribute & V8_PROPERTY_ATTRIBUTE_READONLY) ?
|
||||
NULL : AccessorSetterCallbackImpl;
|
||||
|
||||
bool rv = obj->SetAccessor(GetV8String(key), getter, setter, obj,
|
||||
static_cast<v8::AccessControl>(settings),
|
||||
static_cast<v8::PropertyAttribute>(attribute));
|
||||
return rv;
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
bool set = obj->SetAccessor(GetV8String(key), getter, setter, obj,
|
||||
static_cast<v8::AccessControl>(settings),
|
||||
static_cast<v8::PropertyAttribute>(attribute));
|
||||
return (!HasCaught(try_catch) && set);
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::GetKeys(std::vector<CefString>& keys) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return false;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
@@ -989,66 +1192,67 @@ bool CefV8ValueImpl::GetKeys(std::vector<CefString>& keys) {
|
||||
return true;
|
||||
}
|
||||
|
||||
CefRefPtr<CefBase> CefV8ValueImpl::GetUserData() {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return NULL;
|
||||
}
|
||||
bool CefV8ValueImpl::SetUserData(CefRefPtr<CefBase> user_data) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(false);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
v8::Local<v8::Value> value =
|
||||
obj->GetHiddenValue(v8::String::New(kCefUserData));
|
||||
if (!value.IsEmpty())
|
||||
return static_cast<CefBase*>(v8::External::Unwrap(value));
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker) {
|
||||
tracker->SetUserData(user_data);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
CefRefPtr<CefBase> CefV8ValueImpl::GetUserData() {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(NULL);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
return tracker->GetUserData();
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int CefV8ValueImpl::GetExternallyAllocatedMemory() {
|
||||
CEF_REQUIRE_UI_THREAD(0);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return 0;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(0);
|
||||
|
||||
int* counter = GetExternallyAllocatedMemoryCounter();
|
||||
return counter != NULL ? *counter : 0;
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
return tracker->GetExternallyAllocatedMemory();
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CefV8ValueImpl::AdjustExternallyAllocatedMemory(int change_in_bytes) {
|
||||
CEF_REQUIRE_UI_THREAD(0);
|
||||
if (!GetHandle()->IsObject()) {
|
||||
NOTREACHED() << "V8 value is not an object";
|
||||
return 0;
|
||||
}
|
||||
CEF_V8_REQUIRE_OBJECT_RETURN(0);
|
||||
|
||||
int* counter = GetExternallyAllocatedMemoryCounter();
|
||||
if (counter == NULL)
|
||||
return 0;
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
int new_value = *counter + change_in_bytes;
|
||||
if (new_value < 0) {
|
||||
NOTREACHED() << "External memory usage cannot be less than 0 bytes";
|
||||
change_in_bytes = -(*counter);
|
||||
new_value = 0;
|
||||
}
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
return tracker->AdjustExternallyAllocatedMemory(change_in_bytes);
|
||||
|
||||
if (change_in_bytes != 0)
|
||||
v8::V8::AdjustAmountOfExternalAllocatedMemory(change_in_bytes);
|
||||
*counter = new_value;
|
||||
|
||||
return new_value;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CefV8ValueImpl::GetArrayLength() {
|
||||
CEF_REQUIRE_UI_THREAD(0);
|
||||
if (!GetHandle()->IsArray()) {
|
||||
NOTREACHED() << "V8 value is not an array";
|
||||
return 0;
|
||||
}
|
||||
CEF_V8_REQUIRE_ARRAY_RETURN(0);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
@@ -1059,10 +1263,7 @@ int CefV8ValueImpl::GetArrayLength() {
|
||||
CefString CefV8ValueImpl::GetFunctionName() {
|
||||
CefString rv;
|
||||
CEF_REQUIRE_UI_THREAD(rv);
|
||||
if (!GetHandle()->IsFunction()) {
|
||||
NOTREACHED() << "V8 value is not a function";
|
||||
return rv;
|
||||
}
|
||||
CEF_V8_REQUIRE_FUNCTION_RETURN(rv);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
@@ -1073,45 +1274,32 @@ CefString CefV8ValueImpl::GetFunctionName() {
|
||||
|
||||
CefRefPtr<CefV8Handler> CefV8ValueImpl::GetFunctionHandler() {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
if (!GetHandle()->IsFunction()) {
|
||||
NOTREACHED() << "V8 value is not a function";
|
||||
return NULL;
|
||||
}
|
||||
CEF_V8_REQUIRE_FUNCTION_RETURN(NULL);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
|
||||
v8::Local<v8::Value> value =
|
||||
obj->GetHiddenValue(v8::String::New(kCefHandler));
|
||||
if (!value.IsEmpty())
|
||||
return static_cast<CefV8Handler*>(v8::External::Unwrap(value));
|
||||
V8TrackObject* tracker = V8TrackObject::Unwrap(obj);
|
||||
if (tracker)
|
||||
return tracker->GetHandler();
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::ExecuteFunction(CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception,
|
||||
bool rethrow_exception) {
|
||||
CefRefPtr<CefV8Value> CefV8ValueImpl::ExecuteFunction(
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments) {
|
||||
// An empty context value defaults to the current context.
|
||||
CefRefPtr<CefV8Context> context;
|
||||
return ExecuteFunctionWithContext(context, object, arguments, retval,
|
||||
exception, rethrow_exception);
|
||||
return ExecuteFunctionWithContext(context, object, arguments);
|
||||
}
|
||||
|
||||
bool CefV8ValueImpl::ExecuteFunctionWithContext(
|
||||
CefRefPtr<CefV8Context> context,
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception,
|
||||
bool rethrow_exception) {
|
||||
CEF_REQUIRE_UI_THREAD(false);
|
||||
if (!GetHandle()->IsFunction()) {
|
||||
NOTREACHED() << "V8 value is not a function";
|
||||
return false;
|
||||
}
|
||||
CefRefPtr<CefV8Value> CefV8ValueImpl::ExecuteFunctionWithContext(
|
||||
CefRefPtr<CefV8Context> context,
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments) {
|
||||
CEF_REQUIRE_UI_THREAD(NULL);
|
||||
CEF_V8_REQUIRE_FUNCTION_RETURN(NULL);
|
||||
|
||||
v8::HandleScope handle_scope;
|
||||
|
||||
@@ -1146,38 +1334,39 @@ bool CefV8ValueImpl::ExecuteFunctionWithContext(
|
||||
argv[i] = static_cast<CefV8ValueImpl*>(arguments[i].get())->GetHandle();
|
||||
}
|
||||
|
||||
v8::TryCatch try_catch;
|
||||
v8::Local<v8::Value> func_rv = func->Call(recv, argc, argv);
|
||||
if (try_catch.HasCaught()) {
|
||||
exception = new CefV8ExceptionImpl(try_catch.Message());
|
||||
if (rethrow_exception)
|
||||
try_catch.ReThrow();
|
||||
} else {
|
||||
retval = new CefV8ValueImpl(func_rv);
|
||||
CefRefPtr<CefV8Value> retval;
|
||||
|
||||
{
|
||||
v8::TryCatch try_catch;
|
||||
try_catch.SetVerbose(true);
|
||||
v8::Local<v8::Value> func_rv;
|
||||
|
||||
// Execute the function call using the V8Proxy so that inspector
|
||||
// instrumentation works.
|
||||
WebCore::V8Proxy* proxy = WebCore::V8Proxy::retrieve();
|
||||
DCHECK(proxy);
|
||||
if (proxy)
|
||||
func_rv = proxy->callFunction(func, recv, argc, argv);
|
||||
|
||||
if (!HasCaught(try_catch) && !func_rv.IsEmpty())
|
||||
retval = new CefV8ValueImpl(func_rv);
|
||||
}
|
||||
|
||||
if (argv)
|
||||
delete [] argv;
|
||||
|
||||
return true;
|
||||
return retval;
|
||||
}
|
||||
|
||||
// static
|
||||
CefV8Accessor* CefV8ValueImpl::GetAccessor(v8::Handle<v8::Object> object) {
|
||||
v8::Local<v8::Value> value =
|
||||
object->GetHiddenValue(v8::String::New(kCefAccessor));
|
||||
if (!value.IsEmpty())
|
||||
return static_cast<CefV8Accessor*>(v8::External::Unwrap(value));
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int* CefV8ValueImpl::GetExternallyAllocatedMemoryCounter() {
|
||||
v8::HandleScope handle_scope;
|
||||
v8::Local<v8::Object> obj = GetHandle()->ToObject();
|
||||
v8::Local<v8::Value> value =
|
||||
obj->GetHiddenValue(v8::String::New(kCefExternalMemory));
|
||||
|
||||
return value.IsEmpty() ? NULL : static_cast<int*>(
|
||||
v8::External::Unwrap(value));
|
||||
bool CefV8ValueImpl::HasCaught(v8::TryCatch& try_catch) {
|
||||
if (try_catch.HasCaught()) {
|
||||
last_exception_ = new CefV8ExceptionImpl(try_catch.Message());
|
||||
if (rethrow_exceptions_)
|
||||
try_catch.ReThrow();
|
||||
return true;
|
||||
} else {
|
||||
if (last_exception_.get())
|
||||
last_exception_ = NULL;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@@ -7,6 +7,7 @@
|
||||
#pragma once
|
||||
|
||||
#include <vector>
|
||||
|
||||
#include "include/cef_v8.h"
|
||||
#include "v8/include/v8.h"
|
||||
#include "libcef/cef_thread.h"
|
||||
@@ -68,6 +69,9 @@ class CefV8ContextImpl : public CefV8Context {
|
||||
virtual bool Enter() OVERRIDE;
|
||||
virtual bool Exit() OVERRIDE;
|
||||
virtual bool IsSame(CefRefPtr<CefV8Context> that) OVERRIDE;
|
||||
virtual bool Eval(const CefString& code,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception) OVERRIDE;
|
||||
|
||||
v8::Local<v8::Context> GetContext();
|
||||
WebKit::WebFrame* GetWebFrame();
|
||||
@@ -115,6 +119,7 @@ class CefV8ValueImpl : public CefV8Value {
|
||||
virtual bool IsNull() OVERRIDE;
|
||||
virtual bool IsBool() OVERRIDE;
|
||||
virtual bool IsInt() OVERRIDE;
|
||||
virtual bool IsUInt() OVERRIDE;
|
||||
virtual bool IsDouble() OVERRIDE;
|
||||
virtual bool IsDate() OVERRIDE;
|
||||
virtual bool IsString() OVERRIDE;
|
||||
@@ -123,10 +128,17 @@ class CefV8ValueImpl : public CefV8Value {
|
||||
virtual bool IsFunction() OVERRIDE;
|
||||
virtual bool IsSame(CefRefPtr<CefV8Value> value) OVERRIDE;
|
||||
virtual bool GetBoolValue() OVERRIDE;
|
||||
virtual int GetIntValue() OVERRIDE;
|
||||
virtual int32 GetIntValue() OVERRIDE;
|
||||
virtual uint32 GetUIntValue() OVERRIDE;
|
||||
virtual double GetDoubleValue() OVERRIDE;
|
||||
virtual CefTime GetDateValue() OVERRIDE;
|
||||
virtual CefString GetStringValue() OVERRIDE;
|
||||
virtual bool IsUserCreated() OVERRIDE;
|
||||
virtual bool HasException() OVERRIDE;
|
||||
virtual CefRefPtr<CefV8Exception> GetException() OVERRIDE;
|
||||
virtual bool ClearException() OVERRIDE;
|
||||
virtual bool WillRethrowExceptions() OVERRIDE;
|
||||
virtual bool SetRethrowExceptions(bool rethrow) OVERRIDE;
|
||||
virtual bool HasValue(const CefString& key) OVERRIDE;
|
||||
virtual bool HasValue(int index) OVERRIDE;
|
||||
virtual bool DeleteValue(const CefString& key) OVERRIDE;
|
||||
@@ -139,38 +151,33 @@ class CefV8ValueImpl : public CefV8Value {
|
||||
virtual bool SetValue(const CefString& key, AccessControl settings,
|
||||
PropertyAttribute attribute) OVERRIDE;
|
||||
virtual bool GetKeys(std::vector<CefString>& keys) OVERRIDE;
|
||||
virtual bool SetUserData(CefRefPtr<CefBase> user_data) OVERRIDE;
|
||||
virtual CefRefPtr<CefBase> GetUserData() OVERRIDE;
|
||||
virtual int GetExternallyAllocatedMemory() OVERRIDE;
|
||||
virtual int AdjustExternallyAllocatedMemory(int change_in_bytes) OVERRIDE;
|
||||
virtual int GetArrayLength() OVERRIDE;
|
||||
virtual CefString GetFunctionName() OVERRIDE;
|
||||
virtual CefRefPtr<CefV8Handler> GetFunctionHandler() OVERRIDE;
|
||||
virtual bool ExecuteFunction(CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception,
|
||||
bool rethrow_exception) OVERRIDE;
|
||||
virtual bool ExecuteFunctionWithContext(
|
||||
CefRefPtr<CefV8Context> context,
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments,
|
||||
CefRefPtr<CefV8Value>& retval,
|
||||
CefRefPtr<CefV8Exception>& exception,
|
||||
bool rethrow_exception) OVERRIDE;
|
||||
virtual CefRefPtr<CefV8Value> ExecuteFunction(
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments) OVERRIDE;
|
||||
virtual CefRefPtr<CefV8Value> ExecuteFunctionWithContext(
|
||||
CefRefPtr<CefV8Context> context,
|
||||
CefRefPtr<CefV8Value> object,
|
||||
const CefV8ValueList& arguments) OVERRIDE;
|
||||
|
||||
inline v8::Handle<v8::Value> GetHandle() {
|
||||
DCHECK(v8_value_.get());
|
||||
return v8_value_->GetHandle();
|
||||
}
|
||||
|
||||
// Returns the accessor assigned for the specified object, if any.
|
||||
static CefV8Accessor* GetAccessor(v8::Handle<v8::Object> object);
|
||||
|
||||
private:
|
||||
int* GetExternallyAllocatedMemoryCounter();
|
||||
|
||||
protected:
|
||||
// Test for and record any exception.
|
||||
bool HasCaught(v8::TryCatch& try_catch);
|
||||
|
||||
scoped_refptr<CefV8ValueHandle> v8_value_;
|
||||
CefRefPtr<CefV8Exception> last_exception_;
|
||||
bool rethrow_exceptions_;
|
||||
|
||||
IMPLEMENT_REFCOUNTING(CefV8ValueImpl);
|
||||
DISALLOW_COPY_AND_ASSIGN(CefV8ValueImpl);
|
||||
|
@@ -14,9 +14,12 @@
|
||||
#include "webkit/plugins/npapi/gtk_plugin_container_manager.h"
|
||||
#endif
|
||||
|
||||
struct WebPreferences;
|
||||
class BrowserWebViewDelegate;
|
||||
|
||||
namespace webkit_glue {
|
||||
struct WebPreferences;
|
||||
}
|
||||
|
||||
namespace WebKit {
|
||||
class WebDevToolsAgentClient;
|
||||
class WebView;
|
||||
@@ -33,7 +36,7 @@ class WebViewHost : public WebWidgetHost {
|
||||
BrowserWebViewDelegate* delegate,
|
||||
PaintDelegate* paint_delegate,
|
||||
WebKit::WebDevToolsAgentClient* devtools_client,
|
||||
const WebPreferences& prefs);
|
||||
const webkit_glue::WebPreferences& prefs);
|
||||
|
||||
virtual ~WebViewHost();
|
||||
|
||||
|
@@ -28,7 +28,7 @@ WebViewHost* WebViewHost::Create(GtkWidget* parent_view,
|
||||
BrowserWebViewDelegate* delegate,
|
||||
PaintDelegate* paint_delegate,
|
||||
WebDevToolsAgentClient* dev_tools_client,
|
||||
const WebPreferences& prefs) {
|
||||
const webkit_glue::WebPreferences& prefs) {
|
||||
WebViewHost* host = new WebViewHost(delegate);
|
||||
|
||||
host->view_ = WebWidgetHost::CreateWidget(parent_view, host);
|
||||
|
@@ -31,7 +31,7 @@ WebViewHost* WebViewHost::Create(NSView* parent_view,
|
||||
BrowserWebViewDelegate* delegate,
|
||||
PaintDelegate* paint_delegate,
|
||||
WebDevToolsAgentClient* dev_tools_client,
|
||||
const WebPreferences& prefs) {
|
||||
const webkit_glue::WebPreferences& prefs) {
|
||||
WebViewHost* host = new WebViewHost(delegate);
|
||||
|
||||
NSRect content_rect = {{rect.x(), rect.y()}, {rect.width(), rect.height()}};
|
||||
|
@@ -28,7 +28,7 @@ WebViewHost* WebViewHost::Create(HWND parent_view,
|
||||
BrowserWebViewDelegate* delegate,
|
||||
PaintDelegate* paint_delegate,
|
||||
WebDevToolsAgentClient* dev_tools_client,
|
||||
const WebPreferences& prefs) {
|
||||
const webkit_glue::WebPreferences& prefs) {
|
||||
WebViewHost* host = new WebViewHost(delegate);
|
||||
|
||||
if (!paint_delegate) {
|
||||
|
Reference in New Issue
Block a user