Wait for CefBrowserContext initialization (see issue #2969)

With the Chrome runtime, Profile initialization may be asynchronous. Code that
waited on CefBrowserContext creation now needs to wait on CefBrowserContext
initialization instead.
This commit is contained in:
Marshall Greenblatt 2021-04-14 19:28:22 -04:00
parent fc7f9ff505
commit 34c63a665d
39 changed files with 779 additions and 477 deletions

View File

@ -720,6 +720,8 @@ static_library("libcef_static") {
"libcef/common/net/upload_data.h", "libcef/common/net/upload_data.h",
"libcef/common/net/upload_element.cc", "libcef/common/net/upload_element.cc",
"libcef/common/net/upload_element.h", "libcef/common/net/upload_element.h",
"libcef/common/net/url_util.cc",
"libcef/common/net/url_util.h",
"libcef/common/net_service/net_service_util.cc", "libcef/common/net_service/net_service_util.cc",
"libcef/common/net_service/net_service_util.h", "libcef/common/net_service/net_service_util.h",
"libcef/common/parser_impl.cc", "libcef/common/parser_impl.cc",

View File

@ -33,7 +33,7 @@
// by hand. See the translator.README.txt file in the tools directory for // by hand. See the translator.README.txt file in the tools directory for
// more information. // more information.
// //
// $hash=3767c7759578cd4abc1c2ecef504e7ed60775abb$ // $hash=79e4e38c732c0cfeef495c8a9726e105054012bb$
// //
#ifndef CEF_INCLUDE_CAPI_CEF_MEDIA_ROUTER_CAPI_H_ #ifndef CEF_INCLUDE_CAPI_CEF_MEDIA_ROUTER_CAPI_H_
@ -41,6 +41,7 @@
#pragma once #pragma once
#include "include/capi/cef_base_capi.h" #include "include/capi/cef_base_capi.h"
#include "include/capi/cef_callback_capi.h"
#include "include/capi/cef_registration_capi.h" #include "include/capi/cef_registration_capi.h"
#ifdef __cplusplus #ifdef __cplusplus
@ -110,11 +111,14 @@ typedef struct _cef_media_router_t {
} cef_media_router_t; } cef_media_router_t;
/// ///
// Returns the MediaRouter object associated with the global request context. // Returns the MediaRouter object associated with the global request context. If
// Equivalent to calling cef_request_context_t::cef_request_context_get_global_c // |callback| is non-NULL it will be executed asnychronously on the UI thread
// ontext()->get_media_router(). // after the manager's storage has been initialized. Equivalent to calling cef_r
// equest_context_t::cef_request_context_get_global_context()->get_media_router(
// ).
/// ///
CEF_EXPORT cef_media_router_t* cef_media_router_get_global(); CEF_EXPORT cef_media_router_t* cef_media_router_get_global(
struct _cef_completion_callback_t* callback);
/// ///
// Implemented by the client to observe MediaRouter events and registered via // Implemented by the client to observe MediaRouter events and registered via

View File

@ -33,7 +33,7 @@
// by hand. See the translator.README.txt file in the tools directory for // by hand. See the translator.README.txt file in the tools directory for
// more information. // more information.
// //
// $hash=d5079b6a5146ccd2085c3bbf948925c009d329ed$ // $hash=2e42334fc22050e207e5a0af6fe290a592e4105f$
// //
#ifndef CEF_INCLUDE_CAPI_CEF_REQUEST_CONTEXT_CAPI_H_ #ifndef CEF_INCLUDE_CAPI_CEF_REQUEST_CONTEXT_CAPI_H_
@ -132,7 +132,7 @@ typedef struct _cef_request_context_t {
/// ///
// Returns the cookie manager for this object. If |callback| is non-NULL it // Returns the cookie manager for this object. If |callback| is non-NULL it
// will be executed asnychronously on the IO thread after the manager's // will be executed asnychronously on the UI thread after the manager's
// storage has been initialized. // storage has been initialized.
/// ///
struct _cef_cookie_manager_t*(CEF_CALLBACK* get_cookie_manager)( struct _cef_cookie_manager_t*(CEF_CALLBACK* get_cookie_manager)(
@ -356,10 +356,13 @@ typedef struct _cef_request_context_t {
const cef_string_t* extension_id); const cef_string_t* extension_id);
/// ///
// Returns the MediaRouter object associated with this context. // Returns the MediaRouter object associated with this context. If |callback|
// is non-NULL it will be executed asnychronously on the UI thread after the
// manager's context has been initialized.
/// ///
struct _cef_media_router_t*(CEF_CALLBACK* get_media_router)( struct _cef_media_router_t*(CEF_CALLBACK* get_media_router)(
struct _cef_request_context_t* self); struct _cef_request_context_t* self,
struct _cef_completion_callback_t* callback);
} cef_request_context_t; } cef_request_context_t;
/// ///

View File

@ -42,13 +42,13 @@
// way that may cause binary incompatibility with other builds. The universal // way that may cause binary incompatibility with other builds. The universal
// hash value will change if any platform is affected whereas the platform hash // hash value will change if any platform is affected whereas the platform hash
// values will change only if that particular platform is affected. // values will change only if that particular platform is affected.
#define CEF_API_HASH_UNIVERSAL "0468b890ed1832b3763cb5f16c7b007219964b06" #define CEF_API_HASH_UNIVERSAL "d128245052a84dd90cd38fed0e6be65824d37de5"
#if defined(OS_WIN) #if defined(OS_WIN)
#define CEF_API_HASH_PLATFORM "dbe7a5bb3fa66b97a57175575d870a003ce632fe" #define CEF_API_HASH_PLATFORM "9b1a4706bf1fca26d542aa5f8b05d222f483c872"
#elif defined(OS_MAC) #elif defined(OS_MAC)
#define CEF_API_HASH_PLATFORM "f1f736e3e19916d0f3f11de71deff8448dc3a35f" #define CEF_API_HASH_PLATFORM "0038a822915e3567f2434053ebc49723fe6951d5"
#elif defined(OS_LINUX) #elif defined(OS_LINUX)
#define CEF_API_HASH_PLATFORM "de19204124690a84b9b24102f3bd41991781e044" #define CEF_API_HASH_PLATFORM "66613a535ec6a1aafce6ece8e98cd3876f79633b"
#endif #endif
#ifdef __cplusplus #ifdef __cplusplus

View File

@ -40,6 +40,7 @@
#include <vector> #include <vector>
#include "include/cef_base.h" #include "include/cef_base.h"
#include "include/cef_callback.h"
#include "include/cef_registration.h" #include "include/cef_registration.h"
class CefMediaObserver; class CefMediaObserver;
@ -59,11 +60,13 @@ class CefMediaRouter : public virtual CefBaseRefCounted {
public: public:
/// ///
// Returns the MediaRouter object associated with the global request context. // Returns the MediaRouter object associated with the global request context.
// Equivalent to calling // If |callback| is non-NULL it will be executed asnychronously on the UI
// CefRequestContext::GetGlobalContext()->GetMediaRouter(). // thread after the manager's storage has been initialized. Equivalent to
// calling CefRequestContext::GetGlobalContext()->GetMediaRouter().
/// ///
/*--cef()--*/ /*--cef(optional_param=callback)--*/
static CefRefPtr<CefMediaRouter> GetGlobalMediaRouter(); static CefRefPtr<CefMediaRouter> GetGlobalMediaRouter(
CefRefPtr<CefCompletionCallback> callback);
/// ///
// Add an observer for MediaRouter events. The observer will remain registered // Add an observer for MediaRouter events. The observer will remain registered

View File

@ -146,7 +146,7 @@ class CefRequestContext : public virtual CefBaseRefCounted {
/// ///
// Returns the cookie manager for this object. If |callback| is non-NULL it // Returns the cookie manager for this object. If |callback| is non-NULL it
// will be executed asnychronously on the IO thread after the manager's // will be executed asnychronously on the UI thread after the manager's
// storage has been initialized. // storage has been initialized.
/// ///
/*--cef(optional_param=callback)--*/ /*--cef(optional_param=callback)--*/
@ -364,10 +364,13 @@ class CefRequestContext : public virtual CefBaseRefCounted {
const CefString& extension_id) = 0; const CefString& extension_id) = 0;
/// ///
// Returns the MediaRouter object associated with this context. // Returns the MediaRouter object associated with this context. If |callback|
// is non-NULL it will be executed asnychronously on the UI thread after the
// manager's context has been initialized.
/// ///
/*--cef()--*/ /*--cef(optional_param=callback)--*/
virtual CefRefPtr<CefMediaRouter> GetMediaRouter() = 0; virtual CefRefPtr<CefMediaRouter> GetMediaRouter(
CefRefPtr<CefCompletionCallback> callback) = 0;
}; };
#endif // CEF_INCLUDE_CEF_REQUEST_CONTEXT_H_ #endif // CEF_INCLUDE_CEF_REQUEST_CONTEXT_H_

View File

@ -113,6 +113,18 @@ AlloyBrowserContext::~AlloyBrowserContext() {
} }
} }
bool AlloyBrowserContext::IsInitialized() const {
CEF_REQUIRE_UIT();
return !!key_;
}
void AlloyBrowserContext::StoreOrTriggerInitCallback(
base::OnceClosure callback) {
CEF_REQUIRE_UIT();
// Initialization is always synchronous.
std::move(callback).Run();
}
void AlloyBrowserContext::Initialize() { void AlloyBrowserContext::Initialize() {
CefBrowserContext::Initialize(); CefBrowserContext::Initialize();

View File

@ -42,6 +42,8 @@ class AlloyBrowserContext : public ChromeProfileAlloy,
// CefBrowserContext overrides. // CefBrowserContext overrides.
content::BrowserContext* AsBrowserContext() override { return this; } content::BrowserContext* AsBrowserContext() override { return this; }
Profile* AsProfile() override { return this; } Profile* AsProfile() override { return this; }
bool IsInitialized() const override;
void StoreOrTriggerInitCallback(base::OnceClosure callback) override;
void Initialize() override; void Initialize() override;
void Shutdown() override; void Shutdown() override;
void RemoveCefRequestContext(CefRequestContextImpl* context) override; void RemoveCefRequestContext(CefRequestContextImpl* context) override;

View File

@ -24,6 +24,7 @@
#include "libcef/common/cef_messages.h" #include "libcef/common/cef_messages.h"
#include "libcef/common/cef_switches.h" #include "libcef/common/cef_switches.h"
#include "libcef/common/drag_data_impl.h" #include "libcef/common/drag_data_impl.h"
#include "libcef/common/net/url_util.h"
#include "libcef/common/request_impl.h" #include "libcef/common/request_impl.h"
#include "libcef/common/values_impl.h" #include "libcef/common/values_impl.h"
#include "libcef/features/runtime_checks.h" #include "libcef/features/runtime_checks.h"
@ -175,12 +176,13 @@ CefRefPtr<AlloyBrowserHostImpl> AlloyBrowserHostImpl::Create(
if (!browser) if (!browser)
return nullptr; return nullptr;
GURL url = url_util::MakeGURL(create_params.url, /*fixup=*/true);
if (create_params.extension) { if (create_params.extension) {
platform_delegate_ptr->CreateExtensionHost( platform_delegate_ptr->CreateExtensionHost(
create_params.extension, create_params.url, create_params.extension, url, create_params.extension_host_type);
create_params.extension_host_type); } else if (!url.is_empty()) {
} else if (!create_params.url.is_empty()) { content::OpenURLParams params(url, content::Referrer(),
content::OpenURLParams params(create_params.url, content::Referrer(),
WindowOpenDisposition::CURRENT_TAB, WindowOpenDisposition::CURRENT_TAB,
CefFrameHostImpl::kPageTransitionExplicit, CefFrameHostImpl::kPageTransitionExplicit,
/*is_renderer_initiated=*/false); /*is_renderer_initiated=*/false);

View File

@ -12,6 +12,7 @@
#include "libcef/browser/extensions/extension_web_contents_observer.h" #include "libcef/browser/extensions/extension_web_contents_observer.h"
#include "libcef/browser/printing/print_view_manager.h" #include "libcef/browser/printing/print_view_manager.h"
#include "libcef/common/extensions/extensions_util.h" #include "libcef/common/extensions/extensions_util.h"
#include "libcef/common/net/url_util.h"
#include "libcef/features/runtime_checks.h" #include "libcef/features/runtime_checks.h"
#include "base/logging.h" #include "base/logging.h"
@ -58,12 +59,13 @@ content::WebContents* CefBrowserPlatformDelegateAlloy::CreateWebContents(
} }
scoped_refptr<content::SiteInstance> site_instance; scoped_refptr<content::SiteInstance> site_instance;
if (extensions::ExtensionsEnabled() && !create_params.url.is_empty()) { if (extensions::ExtensionsEnabled() && !create_params.url.empty()) {
GURL gurl = url_util::MakeGURL(create_params.url, /*fixup=*/true);
if (!create_params.extension) { if (!create_params.extension) {
// We might be loading an extension app view where the extension URL is // We might be loading an extension app view where the extension URL is
// provided by the client. // provided by the client.
create_params.extension = create_params.extension =
extensions::GetExtensionForUrl(browser_context, create_params.url); extensions::GetExtensionForUrl(browser_context, gurl);
} }
if (create_params.extension) { if (create_params.extension) {
if (create_params.extension_host_type == extensions::VIEW_TYPE_INVALID) { if (create_params.extension_host_type == extensions::VIEW_TYPE_INVALID) {
@ -79,7 +81,7 @@ content::WebContents* CefBrowserPlatformDelegateAlloy::CreateWebContents(
// ExtensionProtocolHandler::MaybeCreateJob will return false resulting in // ExtensionProtocolHandler::MaybeCreateJob will return false resulting in
// ERR_BLOCKED_BY_CLIENT). // ERR_BLOCKED_BY_CLIENT).
site_instance = extensions::ProcessManager::Get(browser_context) site_instance = extensions::ProcessManager::Get(browser_context)
->GetSiteInstanceForURL(create_params.url); ->GetSiteInstanceForURL(gurl);
DCHECK(site_instance); DCHECK(site_instance);
} }
} }

View File

@ -112,6 +112,13 @@ class CefBrowserContext {
virtual content::BrowserContext* AsBrowserContext() = 0; virtual content::BrowserContext* AsBrowserContext() = 0;
virtual Profile* AsProfile() = 0; virtual Profile* AsProfile() = 0;
// Returns true if the context is fully initialized.
virtual bool IsInitialized() const = 0;
// If the context is fully initialized execute |callback|, otherwise
// store it until the context is fully initialized.
virtual void StoreOrTriggerInitCallback(base::OnceClosure callback) = 0;
// Called from CefRequestContextImpl to track associated objects. This // Called from CefRequestContextImpl to track associated objects. This
// object will delete itself when the count reaches zero. // object will delete itself when the count reaches zero.
void AddCefRequestContext(CefRequestContextImpl* context); void AddCefRequestContext(CefRequestContextImpl* context);

View File

@ -9,13 +9,13 @@
#include "libcef/browser/image_impl.h" #include "libcef/browser/image_impl.h"
#include "libcef/browser/navigation_entry_impl.h" #include "libcef/browser/navigation_entry_impl.h"
#include "libcef/browser/thread_util.h" #include "libcef/browser/thread_util.h"
#include "libcef/common/net/url_util.h"
#include "base/logging.h" #include "base/logging.h"
#include "chrome/browser/spellchecker/spellcheck_factory.h" #include "chrome/browser/spellchecker/spellcheck_factory.h"
#include "chrome/browser/spellchecker/spellcheck_service.h" #include "chrome/browser/spellchecker/spellcheck_service.h"
#include "components/favicon/core/favicon_url.h" #include "components/favicon/core/favicon_url.h"
#include "components/spellcheck/common/spellcheck_features.h" #include "components/spellcheck/common/spellcheck_features.h"
#include "components/url_formatter/url_fixer.h"
#include "content/public/browser/browser_context.h" #include "content/public/browser/browser_context.h"
#include "content/public/browser/download_manager.h" #include "content/public/browser/download_manager.h"
#include "content/public/browser/download_request_utils.h" #include "content/public/browser/download_request_utils.h"
@ -761,16 +761,9 @@ bool CefBrowserHostBase::Navigate(const content::OpenURLParams& params) {
CEF_REQUIRE_UIT(); CEF_REQUIRE_UIT();
auto web_contents = GetWebContents(); auto web_contents = GetWebContents();
if (web_contents) { if (web_contents) {
// Fix common problems with user-typed text. Among other things, this: GURL gurl = params.url;
// - Converts absolute file paths to "file://" URLs. if (!url_util::FixupGURL(gurl))
// - Normalizes "about:" and "chrome:" to "chrome://" URLs.
// - Adds the "http://" scheme if none was specified.
GURL gurl = url_formatter::FixupURL(params.url.possibly_invalid_spec(),
std::string());
if (!gurl.is_valid()) {
LOG(ERROR) << "Invalid URL: " << params.url.possibly_invalid_spec();
return false; return false;
}
web_contents->GetController().LoadURL( web_contents->GetController().LoadURL(
gurl, params.referrer, params.transition, params.extra_headers); gurl, params.referrer, params.transition, params.extra_headers);

View File

@ -65,7 +65,7 @@ struct CefBrowserCreateParams {
// Initial URL to load. May be empty. If this is a valid extension URL then // Initial URL to load. May be empty. If this is a valid extension URL then
// the browser will be created as an app view extension host. // the browser will be created as an app view extension host.
GURL url; CefString url;
// Browser settings. // Browser settings.
CefBrowserSettings settings; CefBrowserSettings settings;

View File

@ -10,8 +10,6 @@
#include "libcef/browser/thread_util.h" #include "libcef/browser/thread_util.h"
#include "libcef/features/runtime.h" #include "libcef/features/runtime.h"
#include "components/url_formatter/url_fixer.h"
namespace { namespace {
class CreateBrowserHelper { class CreateBrowserHelper {
@ -29,6 +27,11 @@ class CreateBrowserHelper {
extra_info_(extra_info), extra_info_(extra_info),
request_context_(request_context) {} request_context_(request_context) {}
void Run() {
CefBrowserHost::CreateBrowserSync(window_info_, client_, url_, settings_,
extra_info_, request_context_);
}
CefWindowInfo window_info_; CefWindowInfo window_info_;
CefRefPtr<CefClient> client_; CefRefPtr<CefClient> client_;
CefString url_; CefString url_;
@ -73,19 +76,20 @@ bool CefBrowserHost::CreateBrowser(
"reduced performance or runtime errors."; "reduced performance or runtime errors.";
} }
// Create the browser on the UI thread. if (!request_context) {
CreateBrowserHelper* helper = new CreateBrowserHelper( request_context = CefRequestContext::GetGlobalContext();
}
auto helper = std::make_unique<CreateBrowserHelper>(
windowInfo, client, url, settings, extra_info, request_context); windowInfo, client, url, settings, extra_info, request_context);
CEF_POST_TASK(CEF_UIT, base::BindOnce(
[](CreateBrowserHelper* helper) { auto request_context_impl =
CefBrowserHost::CreateBrowserSync( static_cast<CefRequestContextImpl*>(request_context.get());
helper->window_info_, helper->client_,
helper->url_, helper->settings_, // Wait for the browser context to be initialized before creating the browser.
helper->extra_info_, request_context_impl->ExecuteWhenBrowserContextInitialized(base::BindOnce(
helper->request_context_); [](std::unique_ptr<CreateBrowserHelper> helper) { helper->Run(); },
delete helper; std::move(helper)));
},
helper));
return true; return true;
} }
@ -110,9 +114,10 @@ CefRefPtr<CefBrowser> CefBrowserHost::CreateBrowserSync(
return nullptr; return nullptr;
} }
// Verify that this method is being called on the UI thread. // Verify that the browser context is valid.
if (!CEF_CURRENTLY_ON_UIT()) { auto request_context_impl =
NOTREACHED() << "called on invalid thread"; static_cast<CefRequestContextImpl*>(request_context.get());
if (!request_context_impl->VerifyBrowserContext()) {
return nullptr; return nullptr;
} }
@ -126,15 +131,7 @@ CefRefPtr<CefBrowser> CefBrowserHost::CreateBrowserSync(
CefBrowserCreateParams create_params; CefBrowserCreateParams create_params;
create_params.window_info.reset(new CefWindowInfo(windowInfo)); create_params.window_info.reset(new CefWindowInfo(windowInfo));
create_params.client = client; create_params.client = client;
create_params.url = GURL(url.ToString()); create_params.url = url;
if (!url.empty() && !create_params.url.is_valid() &&
!create_params.url.has_scheme()) {
std::string fixed_scheme(url::kHttpScheme);
fixed_scheme.append(url::kStandardSchemeSeparator);
std::string new_url = url;
new_url.insert(0, fixed_scheme);
create_params.url = GURL(new_url);
}
create_params.settings = settings; create_params.settings = settings;
create_params.extra_info = extra_info; create_params.extra_info = extra_info;
create_params.request_context = request_context; create_params.request_context = request_context;
@ -145,22 +142,6 @@ CefRefPtr<CefBrowser> CefBrowserHost::CreateBrowserSync(
// static // static
CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::Create( CefRefPtr<CefBrowserHostBase> CefBrowserHostBase::Create(
CefBrowserCreateParams& create_params) { CefBrowserCreateParams& create_params) {
if (!create_params.url.is_empty()) {
// Fix common problems with user-typed text. Among other things, this:
// - Converts absolute file paths to "file://" URLs.
// - Normalizes "about:" and "chrome:" to "chrome://" URLs.
// - Adds the "http://" scheme if none was specified.
GURL gurl = url_formatter::FixupURL(
create_params.url.possibly_invalid_spec(), std::string());
if (gurl.is_valid()) {
create_params.url = gurl;
} else {
LOG(ERROR) << "Invalid URL: "
<< create_params.url.possibly_invalid_spec();
create_params.url = GURL();
}
}
if (cef::IsChromeRuntimeEnabled()) { if (cef::IsChromeRuntimeEnabled()) {
auto browser = ChromeBrowserHostImpl::Create(create_params); auto browser = ChromeBrowserHostImpl::Create(create_params);
return browser.get(); return browser.get();

View File

@ -5,6 +5,7 @@
#include "libcef/browser/chrome/chrome_browser_context.h" #include "libcef/browser/chrome/chrome_browser_context.h"
#include "libcef/browser/prefs/browser_prefs.h" #include "libcef/browser/prefs/browser_prefs.h"
#include "libcef/browser/thread_util.h"
#include "chrome/browser/browser_process.h" #include "chrome/browser/browser_process.h"
#include "chrome/browser/profiles/off_the_record_profile_impl.h" #include "chrome/browser/profiles/off_the_record_profile_impl.h"
@ -23,8 +24,23 @@ Profile* ChromeBrowserContext::AsProfile() {
return profile_; return profile_;
} }
bool ChromeBrowserContext::IsInitialized() const {
CEF_REQUIRE_UIT();
return !!profile_;
}
void ChromeBrowserContext::StoreOrTriggerInitCallback(
base::OnceClosure callback) {
CEF_REQUIRE_UIT();
if (IsInitialized()) {
std::move(callback).Run();
} else {
init_callbacks_.emplace_back(std::move(callback));
}
}
void ChromeBrowserContext::InitializeAsync(base::OnceClosure initialized_cb) { void ChromeBrowserContext::InitializeAsync(base::OnceClosure initialized_cb) {
initialized_cb_ = std::move(initialized_cb); init_callbacks_.emplace_back(std::move(initialized_cb));
CefBrowserContext::Initialize(); CefBrowserContext::Initialize();
@ -106,6 +122,11 @@ void ChromeBrowserContext::ProfileCreated(Profile* profile,
parent_profile->NotifyOffTheRecordProfileCreated(otr_profile); parent_profile->NotifyOffTheRecordProfileCreated(otr_profile);
} }
std::move(initialized_cb_).Run(); if (!init_callbacks_.empty()) {
for (auto& callback : init_callbacks_) {
std::move(callback).Run();
}
init_callbacks_.clear();
}
} }
} }

View File

@ -22,6 +22,8 @@ class ChromeBrowserContext : public CefBrowserContext {
// CefBrowserContext overrides. // CefBrowserContext overrides.
content::BrowserContext* AsBrowserContext() override; content::BrowserContext* AsBrowserContext() override;
Profile* AsProfile() override; Profile* AsProfile() override;
bool IsInitialized() const override;
void StoreOrTriggerInitCallback(base::OnceClosure callback) override;
void Shutdown() override; void Shutdown() override;
private: private:
@ -33,6 +35,8 @@ class ChromeBrowserContext : public CefBrowserContext {
Profile* profile_ = nullptr; Profile* profile_ = nullptr;
bool should_destroy_ = false; bool should_destroy_ = false;
std::vector<base::OnceClosure> init_callbacks_;
base::WeakPtrFactory<ChromeBrowserContext> weak_ptr_factory_; base::WeakPtrFactory<ChromeBrowserContext> weak_ptr_factory_;
DISALLOW_COPY_AND_ASSIGN(ChromeBrowserContext); DISALLOW_COPY_AND_ASSIGN(ChromeBrowserContext);

View File

@ -8,6 +8,7 @@
#include "libcef/browser/chrome/browser_platform_delegate_chrome.h" #include "libcef/browser/chrome/browser_platform_delegate_chrome.h"
#include "libcef/browser/thread_util.h" #include "libcef/browser/thread_util.h"
#include "libcef/browser/views/browser_view_impl.h" #include "libcef/browser/views/browser_view_impl.h"
#include "libcef/common/net/url_util.h"
#include "libcef/features/runtime_checks.h" #include "libcef/features/runtime_checks.h"
#include "base/logging.h" #include "base/logging.h"
@ -21,8 +22,6 @@
#include "chrome/browser/ui/browser_window.h" #include "chrome/browser/ui/browser_window.h"
#include "chrome/browser/ui/tabs/tab_strip_model.h" #include "chrome/browser/ui/tabs/tab_strip_model.h"
#include "chrome/common/pref_names.h" #include "chrome/common/pref_names.h"
#include "components/url_formatter/url_fixer.h"
#include "url/url_constants.h"
#if defined(TOOLKIT_VIEWS) #if defined(TOOLKIT_VIEWS)
#include "libcef/browser/chrome/views/chrome_browser_frame.h" #include "libcef/browser/chrome/views/chrome_browser_frame.h"
@ -34,7 +33,7 @@ CefRefPtr<ChromeBrowserHostImpl> ChromeBrowserHostImpl::Create(
const CefBrowserCreateParams& params) { const CefBrowserCreateParams& params) {
auto browser = CreateBrowser(params); auto browser = CreateBrowser(params);
GURL url = params.url; GURL url = url_util::MakeGURL(params.url, /*fixup=*/true);
if (url.is_empty()) { if (url.is_empty()) {
// Chrome will navigate to kChromeUINewTabURL by default. We want to keep // Chrome will navigate to kChromeUINewTabURL by default. We want to keep
// the current CEF behavior of not navigating at all. Use a special URL that // the current CEF behavior of not navigating at all. Use a special URL that
@ -392,16 +391,9 @@ bool ChromeBrowserHostImpl::Navigate(const content::OpenURLParams& params) {
} }
if (browser_) { if (browser_) {
// Fix common problems with user-typed text. Among other things, this: GURL gurl = params.url;
// - Converts absolute file paths to "file://" URLs. if (!url_util::FixupGURL(gurl))
// - Normalizes "about:" and "chrome:" to "chrome://" URLs.
// - Adds the "http://" scheme if none was specified.
GURL gurl = url_formatter::FixupURL(params.url.possibly_invalid_spec(),
std::string());
if (!gurl.is_valid()) {
LOG(ERROR) << "Invalid URL: " << params.url.possibly_invalid_spec();
return false; return false;
}
// This is generally equivalent to calling Browser::OpenURL, except: // This is generally equivalent to calling Browser::OpenURL, except:
// 1. It doesn't trigger a call to CefRequestHandler::OnOpenURLFromTab, and // 1. It doesn't trigger a call to CefRequestHandler::OnOpenURLFromTab, and
@ -448,6 +440,7 @@ Browser* ChromeBrowserHostImpl::CreateBrowser(
auto cef_browser_context = request_context_impl->GetBrowserContext(); auto cef_browser_context = request_context_impl->GetBrowserContext();
CHECK(cef_browser_context); CHECK(cef_browser_context);
auto profile = cef_browser_context->AsProfile(); auto profile = cef_browser_context->AsProfile();
CHECK(profile);
Browser::CreateParams chrome_params = Browser::CreateParams chrome_params =
Browser::CreateParams(profile, /*user_gesture=*/false); Browser::CreateParams(profile, /*user_gesture=*/false);

View File

@ -5,6 +5,7 @@
#include "libcef/browser/context.h" #include "libcef/browser/context.h"
#include "libcef/browser/browser_info_manager.h" #include "libcef/browser/browser_info_manager.h"
#include "libcef/browser/request_context_impl.h"
#include "libcef/browser/thread_util.h" #include "libcef/browser/thread_util.h"
#include "libcef/browser/trace_subscriber.h" #include "libcef/browser/trace_subscriber.h"
#include "libcef/common/cef_switches.h" #include "libcef/common/cef_switches.h"
@ -474,12 +475,19 @@ bool CefContext::HasObserver(Observer* observer) const {
void CefContext::OnContextInitialized() { void CefContext::OnContextInitialized() {
CEF_REQUIRE_UIT(); CEF_REQUIRE_UIT();
// Notify the handler.
if (application_) { if (application_) {
// Notify the handler after the global browser context has initialized.
CefRefPtr<CefRequestContext> request_context =
CefRequestContext::GetGlobalContext();
auto impl = static_cast<CefRequestContextImpl*>(request_context.get());
impl->ExecuteWhenBrowserContextInitialized(base::BindOnce(
[](CefRefPtr<CefApp> app) {
CefRefPtr<CefBrowserProcessHandler> handler = CefRefPtr<CefBrowserProcessHandler> handler =
application_->GetBrowserProcessHandler(); app->GetBrowserProcessHandler();
if (handler) if (handler)
handler->OnContextInitialized(); handler->OnContextInitialized();
},
application_));
} }
} }

View File

@ -366,7 +366,7 @@ base::DictionaryValue* CefExtensionFunctionDetails::OpenTab(
return nullptr; return nullptr;
CefBrowserCreateParams create_params; CefBrowserCreateParams create_params;
create_params.url = url; create_params.url = url.spec();
create_params.request_context = request_context; create_params.request_context = request_context;
create_params.window_info.reset(new CefWindowInfo); create_params.window_info.reset(new CefWindowInfo);
@ -381,9 +381,9 @@ base::DictionaryValue* CefExtensionFunctionDetails::OpenTab(
CefRefPtr<CefExtensionHandler> handler = cef_extension->GetHandler(); CefRefPtr<CefExtensionHandler> handler = cef_extension->GetHandler();
if (handler.get() && if (handler.get() &&
handler->OnBeforeBrowser(cef_extension, sender_browser.get(), handler->OnBeforeBrowser(cef_extension, sender_browser.get(),
active_browser.get(), index, url.spec(), active, active_browser.get(), index, create_params.url,
*create_params.window_info, create_params.client, active, *create_params.window_info,
create_params.settings)) { create_params.client, create_params.settings)) {
// Cancel the browser creation. // Cancel the browser creation.
return nullptr; return nullptr;
} }

View File

@ -251,13 +251,13 @@ bool CefExtensionsBrowserClient::CreateBackgroundExtensionHost(
} }
CefBrowserCreateParams create_params; CefBrowserCreateParams create_params;
create_params.url = url; create_params.url = url.spec();
create_params.request_context = request_context; create_params.request_context = request_context;
CefRefPtr<CefExtensionHandler> handler = cef_extension->GetHandler(); CefRefPtr<CefExtensionHandler> handler = cef_extension->GetHandler();
if (handler.get() && handler->OnBeforeBackgroundBrowser( if (handler.get() && handler->OnBeforeBackgroundBrowser(
cef_extension, url.spec(), create_params.client, cef_extension, create_params.url,
create_params.settings)) { create_params.client, create_params.settings)) {
// Cancel the background host creation. // Cancel the background host creation.
return true; return true;
} }

View File

@ -13,11 +13,11 @@
#include "libcef/browser/net_service/browser_urlrequest_impl.h" #include "libcef/browser/net_service/browser_urlrequest_impl.h"
#include "libcef/common/cef_messages.h" #include "libcef/common/cef_messages.h"
#include "libcef/common/frame_util.h" #include "libcef/common/frame_util.h"
#include "libcef/common/net/url_util.h"
#include "libcef/common/process_message_impl.h" #include "libcef/common/process_message_impl.h"
#include "libcef/common/request_impl.h" #include "libcef/common/request_impl.h"
#include "libcef/common/task_runner_impl.h" #include "libcef/common/task_runner_impl.h"
#include "components/url_formatter/url_fixer.h"
#include "content/browser/renderer_host/frame_tree_node.h" #include "content/browser/renderer_host/frame_tree_node.h"
#include "content/public/browser/render_process_host.h" #include "content/public/browser/render_process_host.h"
#include "content/public/browser/render_view_host.h" #include "content/public/browser/render_view_host.h"
@ -310,16 +310,9 @@ void CefFrameHostImpl::NotifyMoveOrResizeStarted() {
void CefFrameHostImpl::Navigate(const CefNavigateParams& params) { void CefFrameHostImpl::Navigate(const CefNavigateParams& params) {
CefMsg_LoadRequest_Params request; CefMsg_LoadRequest_Params request;
// Fix common problems with user-typed text. Among other things, this: request.url = params.url;
// - Converts absolute file paths to "file://" URLs. if (!url_util::FixupGURL(request.url))
// - Normalizes "about:" and "chrome:" to "chrome://" URLs.
// - Adds the "http://" scheme if none was specified.
request.url = url_formatter::FixupURL(params.url.possibly_invalid_spec(),
std::string());
if (!request.url.is_valid()) {
LOG(ERROR) << "Invalid URL: " << params.url.possibly_invalid_spec();
return; return;
}
request.method = params.method; request.method = params.method;
request.referrer = params.referrer.url; request.referrer = params.referrer.url;
@ -347,16 +340,8 @@ void CefFrameHostImpl::LoadURLWithExtras(const std::string& url,
if (frame_id < CefFrameHostImpl::kMainFrameId) if (frame_id < CefFrameHostImpl::kMainFrameId)
return; return;
// Any necessary fixup of the URL will occur in // Any necessary fixup will occur in Navigate.
// [CefBrowserHostBase|CefFrameHostImpl]::Navigate(). GURL gurl = url_util::MakeGURL(url, /*fixup=*/false);
GURL gurl(url);
if (!url.empty() && !gurl.is_valid() && !gurl.has_scheme()) {
std::string fixed_scheme(url::kHttpScheme);
fixed_scheme.append(url::kStandardSchemeSeparator);
std::string new_url = url;
new_url.insert(0, fixed_scheme);
gurl = GURL(new_url);
}
if (frame_id == CefFrameHostImpl::kMainFrameId) { if (frame_id == CefFrameHostImpl::kMainFrameId) {
// Load via the browser using NavigationController. // Load via the browser using NavigationController.

View File

@ -144,11 +144,27 @@ CefMediaRouterImpl::CefMediaRouterImpl() {
} }
void CefMediaRouterImpl::Initialize( void CefMediaRouterImpl::Initialize(
const CefBrowserContext::Getter& browser_context_getter) { const CefBrowserContext::Getter& browser_context_getter,
CefRefPtr<CefCompletionCallback> callback) {
CEF_REQUIRE_UIT(); CEF_REQUIRE_UIT();
DCHECK(!initialized_);
DCHECK(!browser_context_getter.is_null()); DCHECK(!browser_context_getter.is_null());
DCHECK(browser_context_getter_.is_null()); DCHECK(browser_context_getter_.is_null());
browser_context_getter_ = browser_context_getter; browser_context_getter_ = browser_context_getter;
initialized_ = true;
if (!init_callbacks_.empty()) {
for (auto& callback : init_callbacks_) {
std::move(callback).Run();
}
init_callbacks_.clear();
}
if (callback) {
// Execute client callback asynchronously for consistency.
CEF_POST_TASK(CEF_UIT, base::Bind(&CefCompletionCallback::OnComplete,
callback.get()));
}
} }
CefRefPtr<CefRegistration> CefMediaRouterImpl::AddObserver( CefRefPtr<CefRegistration> CefMediaRouterImpl::AddObserver(
@ -157,7 +173,8 @@ CefRefPtr<CefRegistration> CefMediaRouterImpl::AddObserver(
return nullptr; return nullptr;
CefRefPtr<CefRegistrationImpl> registration = CefRefPtr<CefRegistrationImpl> registration =
new CefRegistrationImpl(observer); new CefRegistrationImpl(observer);
InitializeRegistrationOnUIThread(registration); StoreOrTriggerInitCallback(base::BindOnce(
&CefMediaRouterImpl::InitializeRegistrationInternal, this, registration));
return registration.get(); return registration.get();
} }
@ -181,11 +198,32 @@ CefRefPtr<CefMediaSource> CefMediaRouterImpl::GetSource(const CefString& urn) {
} }
void CefMediaRouterImpl::NotifyCurrentSinks() { void CefMediaRouterImpl::NotifyCurrentSinks() {
if (!CEF_CURRENTLY_ON_UIT()) { StoreOrTriggerInitCallback(
CEF_POST_TASK( base::BindOnce(&CefMediaRouterImpl::NotifyCurrentSinksInternal, this));
CEF_UIT, base::BindOnce(&CefMediaRouterImpl::NotifyCurrentSinks, this)); }
return;
} void CefMediaRouterImpl::CreateRoute(
CefRefPtr<CefMediaSource> source,
CefRefPtr<CefMediaSink> sink,
CefRefPtr<CefMediaRouteCreateCallback> callback) {
StoreOrTriggerInitCallback(base::BindOnce(
&CefMediaRouterImpl::CreateRouteInternal, this, source, sink, callback));
}
void CefMediaRouterImpl::NotifyCurrentRoutes() {
StoreOrTriggerInitCallback(
base::BindOnce(&CefMediaRouterImpl::NotifyCurrentRoutesInternal, this));
}
void CefMediaRouterImpl::InitializeRegistrationInternal(
CefRefPtr<CefRegistrationImpl> registration) {
DCHECK(ValidContext());
registration->Initialize(browser_context_getter_);
}
void CefMediaRouterImpl::NotifyCurrentSinksInternal() {
DCHECK(ValidContext());
auto browser_context = GetBrowserContext(browser_context_getter_); auto browser_context = GetBrowserContext(browser_context_getter_);
if (!browser_context) if (!browser_context)
@ -194,21 +232,17 @@ void CefMediaRouterImpl::NotifyCurrentSinks() {
browser_context->GetMediaRouterManager()->NotifyCurrentSinks(); browser_context->GetMediaRouterManager()->NotifyCurrentSinks();
} }
void CefMediaRouterImpl::CreateRoute( void CefMediaRouterImpl::CreateRouteInternal(
CefRefPtr<CefMediaSource> source, CefRefPtr<CefMediaSource> source,
CefRefPtr<CefMediaSink> sink, CefRefPtr<CefMediaSink> sink,
CefRefPtr<CefMediaRouteCreateCallback> callback) { CefRefPtr<CefMediaRouteCreateCallback> callback) {
if (!CEF_CURRENTLY_ON_UIT()) { DCHECK(ValidContext());
CEF_POST_TASK(CEF_UIT, base::BindOnce(&CefMediaRouterImpl::CreateRoute,
this, source, sink, callback));
return;
}
std::string error; std::string error;
auto browser_context = GetBrowserContext(browser_context_getter_); auto browser_context = GetBrowserContext(browser_context_getter_);
if (!browser_context) { if (!browser_context) {
error = "Context has already been destroyed"; error = "Context is not valid";
} else if (!source) { } else if (!source) {
error = "Source is empty or invalid"; error = "Source is empty or invalid";
} else if (!sink) { } else if (!sink) {
@ -234,12 +268,8 @@ void CefMediaRouterImpl::CreateRoute(
base::BindOnce(&CefMediaRouterImpl::CreateRouteCallback, this, callback)); base::BindOnce(&CefMediaRouterImpl::CreateRouteCallback, this, callback));
} }
void CefMediaRouterImpl::NotifyCurrentRoutes() { void CefMediaRouterImpl::NotifyCurrentRoutesInternal() {
if (!CEF_CURRENTLY_ON_UIT()) { DCHECK(ValidContext());
CEF_POST_TASK(CEF_UIT, base::BindOnce(
&CefMediaRouterImpl::NotifyCurrentRoutes, this));
return;
}
auto browser_context = GetBrowserContext(browser_context_getter_); auto browser_context = GetBrowserContext(browser_context_getter_);
if (!browser_context) if (!browser_context)
@ -248,22 +278,10 @@ void CefMediaRouterImpl::NotifyCurrentRoutes() {
browser_context->GetMediaRouterManager()->NotifyCurrentRoutes(); browser_context->GetMediaRouterManager()->NotifyCurrentRoutes();
} }
void CefMediaRouterImpl::InitializeRegistrationOnUIThread(
CefRefPtr<CefRegistrationImpl> registration) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(&CefMediaRouterImpl::InitializeRegistrationOnUIThread,
this, registration));
return;
}
registration->Initialize(browser_context_getter_);
}
void CefMediaRouterImpl::CreateRouteCallback( void CefMediaRouterImpl::CreateRouteCallback(
CefRefPtr<CefMediaRouteCreateCallback> callback, CefRefPtr<CefMediaRouteCreateCallback> callback,
const media_router::RouteRequestResult& result) { const media_router::RouteRequestResult& result) {
CEF_REQUIRE_UIT(); DCHECK(ValidContext());
if (result.result_code() != media_router::RouteRequestResult::OK) { if (result.result_code() != media_router::RouteRequestResult::OK) {
LOG(WARNING) << "Media route creation failed: " << result.error() << " (" LOG(WARNING) << "Media route creation failed: " << result.error() << " ("
@ -284,7 +302,30 @@ void CefMediaRouterImpl::CreateRouteCallback(
result.error(), route); result.error(), route);
} }
// static void CefMediaRouterImpl::StoreOrTriggerInitCallback(
CefRefPtr<CefMediaRouter> CefMediaRouter::GetGlobalMediaRouter() { base::OnceClosure callback) {
return CefRequestContext::GetGlobalContext()->GetMediaRouter(); if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT, base::BindOnce(&CefMediaRouterImpl::StoreOrTriggerInitCallback,
this, std::move(callback)));
return;
}
if (initialized_) {
std::move(callback).Run();
} else {
init_callbacks_.emplace_back(std::move(callback));
}
}
bool CefMediaRouterImpl::ValidContext() const {
return CEF_CURRENTLY_ON_UIT() && initialized_;
}
// CefMediaRouter methods ------------------------------------------------------
// static
CefRefPtr<CefMediaRouter> CefMediaRouter::GetGlobalMediaRouter(
CefRefPtr<CefCompletionCallback> callback) {
return CefRequestContext::GetGlobalContext()->GetMediaRouter(callback);
} }

View File

@ -20,7 +20,8 @@ class CefMediaRouterImpl : public CefMediaRouter {
// Called on the UI thread after object creation and before any other object // Called on the UI thread after object creation and before any other object
// methods are executed on the UI thread. // methods are executed on the UI thread.
void Initialize(const CefBrowserContext::Getter& browser_context_getter); void Initialize(const CefBrowserContext::Getter& browser_context_getter,
CefRefPtr<CefCompletionCallback> callback);
// CefMediaRouter methods. // CefMediaRouter methods.
CefRefPtr<CefRegistration> AddObserver( CefRefPtr<CefRegistration> AddObserver(
@ -33,15 +34,29 @@ class CefMediaRouterImpl : public CefMediaRouter {
void NotifyCurrentRoutes() override; void NotifyCurrentRoutes() override;
private: private:
void InitializeRegistrationOnUIThread( void InitializeRegistrationInternal(
CefRefPtr<CefRegistrationImpl> registration); CefRefPtr<CefRegistrationImpl> registration);
void NotifyCurrentSinksInternal();
void CreateRouteInternal(CefRefPtr<CefMediaSource> source,
CefRefPtr<CefMediaSink> sink,
CefRefPtr<CefMediaRouteCreateCallback> callback);
void NotifyCurrentRoutesInternal();
void CreateRouteCallback(CefRefPtr<CefMediaRouteCreateCallback> callback, void CreateRouteCallback(CefRefPtr<CefMediaRouteCreateCallback> callback,
const media_router::RouteRequestResult& result); const media_router::RouteRequestResult& result);
// If the context is fully initialized execute |callback|, otherwise
// store it until the context is fully initialized.
void StoreOrTriggerInitCallback(base::OnceClosure callback);
bool ValidContext() const;
// Only accessed on the UI thread. Will be non-null after Initialize(). // Only accessed on the UI thread. Will be non-null after Initialize().
CefBrowserContext::Getter browser_context_getter_; CefBrowserContext::Getter browser_context_getter_;
bool initialized_ = false;
std::vector<base::OnceClosure> init_callbacks_;
IMPLEMENT_REFCOUNTING(CefMediaRouterImpl); IMPLEMENT_REFCOUNTING(CefMediaRouterImpl);
DISALLOW_COPY_AND_ASSIGN(CefMediaRouterImpl); DISALLOW_COPY_AND_ASSIGN(CefMediaRouterImpl);
}; };

View File

@ -144,9 +144,15 @@ class CefBrowserURLRequest::Context
if (!url.is_valid()) if (!url.is_valid())
return false; return false;
CEF_POST_TASK( if (!request_context_) {
CEF_UIT, request_context_ = CefRequestContext::GetGlobalContext();
base::BindOnce( }
auto request_context_impl =
static_cast<CefRequestContextImpl*>(request_context_.get());
// Wait for the browser context to be initialized before continuing.
request_context_impl->ExecuteWhenBrowserContextInitialized(base::BindOnce(
&CefBrowserURLRequest::Context::GetURLLoaderFactoryGetterOnUIThread, &CefBrowserURLRequest::Context::GetURLLoaderFactoryGetterOnUIThread,
frame_, request_context_, weak_ptr_factory_.GetWeakPtr(), frame_, request_context_, weak_ptr_factory_.GetWeakPtr(),
task_runner_)); task_runner_));
@ -193,11 +199,12 @@ class CefBrowserURLRequest::Context
// Get or create the request context and browser context. // Get or create the request context and browser context.
CefRefPtr<CefRequestContextImpl> request_context_impl = CefRefPtr<CefRequestContextImpl> request_context_impl =
CefRequestContextImpl::GetOrCreateForRequestContext(request_context); CefRequestContextImpl::GetOrCreateForRequestContext(request_context);
DCHECK(request_context_impl); CHECK(request_context_impl);
CefBrowserContext* cef_browser_context = CefBrowserContext* cef_browser_context =
request_context_impl->GetBrowserContext(); request_context_impl->GetBrowserContext();
DCHECK(cef_browser_context); CHECK(cef_browser_context);
auto browser_context = cef_browser_context->AsBrowserContext(); auto browser_context = cef_browser_context->AsBrowserContext();
CHECK(browser_context);
int render_frame_id = MSG_ROUTING_NONE; int render_frame_id = MSG_ROUTING_NONE;
scoped_refptr<net_service::URLLoaderFactoryGetter> loader_factory_getter; scoped_refptr<net_service::URLLoaderFactoryGetter> loader_factory_getter;

View File

@ -123,9 +123,19 @@ void CefCookieManagerImpl::Initialize(
CefBrowserContext::Getter browser_context_getter, CefBrowserContext::Getter browser_context_getter,
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
CEF_REQUIRE_UIT(); CEF_REQUIRE_UIT();
DCHECK(!initialized_);
DCHECK(!browser_context_getter.is_null()); DCHECK(!browser_context_getter.is_null());
DCHECK(browser_context_getter_.is_null()); DCHECK(browser_context_getter_.is_null());
browser_context_getter_ = browser_context_getter; browser_context_getter_ = browser_context_getter;
initialized_ = true;
if (!init_callbacks_.empty()) {
for (auto& callback : init_callbacks_) {
std::move(callback).Run();
}
init_callbacks_.clear();
}
RunAsyncCompletionOnUIThread(callback); RunAsyncCompletionOnUIThread(callback);
} }
@ -134,22 +144,14 @@ bool CefCookieManagerImpl::VisitAllCookies(
if (!visitor.get()) if (!visitor.get())
return false; return false;
if (!CEF_CURRENTLY_ON_UIT()) { if (!ValidContext()) {
CEF_POST_TASK( StoreOrTriggerInitCallback(base::BindOnce(
CEF_UIT, base::IgnoreResult(&CefCookieManagerImpl::VisitAllCookiesInternal),
base::Bind(base::IgnoreResult(&CefCookieManagerImpl::VisitAllCookies),
this, visitor)); this, visitor));
return true; return true;
} }
auto browser_context = GetBrowserContext(browser_context_getter_); return VisitAllCookiesInternal(visitor);
if (!browser_context)
return false;
GetCookieManager(browser_context)
->GetAllCookies(base::Bind(&GetAllCookiesCallbackImpl, visitor,
browser_context_getter_));
return true;
} }
bool CefCookieManagerImpl::VisitUrlCookies( bool CefCookieManagerImpl::VisitUrlCookies(
@ -163,14 +165,87 @@ bool CefCookieManagerImpl::VisitUrlCookies(
if (!gurl.is_valid()) if (!gurl.is_valid())
return false; return false;
if (!CEF_CURRENTLY_ON_UIT()) { if (!ValidContext()) {
CEF_POST_TASK( StoreOrTriggerInitCallback(base::BindOnce(
CEF_UIT, base::IgnoreResult(&CefCookieManagerImpl::VisitUrlCookiesInternal),
base::Bind(base::IgnoreResult(&CefCookieManagerImpl::VisitUrlCookies), this, gurl, includeHttpOnly, visitor));
this, url, includeHttpOnly, visitor));
return true; return true;
} }
return VisitUrlCookiesInternal(gurl, includeHttpOnly, visitor);
}
bool CefCookieManagerImpl::SetCookie(const CefString& url,
const CefCookie& cookie,
CefRefPtr<CefSetCookieCallback> callback) {
GURL gurl = GURL(url.ToString());
if (!gurl.is_valid())
return false;
if (!ValidContext()) {
StoreOrTriggerInitCallback(base::BindOnce(
base::IgnoreResult(&CefCookieManagerImpl::SetCookieInternal), this,
gurl, cookie, callback));
return true;
}
return SetCookieInternal(gurl, cookie, callback);
}
bool CefCookieManagerImpl::DeleteCookies(
const CefString& url,
const CefString& cookie_name,
CefRefPtr<CefDeleteCookiesCallback> callback) {
// Empty URLs are allowed but not invalid URLs.
GURL gurl = GURL(url.ToString());
if (!gurl.is_empty() && !gurl.is_valid())
return false;
if (!ValidContext()) {
StoreOrTriggerInitCallback(base::BindOnce(
base::IgnoreResult(&CefCookieManagerImpl::DeleteCookiesInternal), this,
gurl, cookie_name, callback));
return true;
}
return DeleteCookiesInternal(gurl, cookie_name, callback);
}
bool CefCookieManagerImpl::FlushStore(
CefRefPtr<CefCompletionCallback> callback) {
if (!ValidContext()) {
StoreOrTriggerInitCallback(base::BindOnce(
base::IgnoreResult(&CefCookieManagerImpl::FlushStoreInternal), this,
callback));
return true;
}
return FlushStoreInternal(callback);
}
bool CefCookieManagerImpl::VisitAllCookiesInternal(
CefRefPtr<CefCookieVisitor> visitor) {
DCHECK(ValidContext());
DCHECK(visitor);
auto browser_context = GetBrowserContext(browser_context_getter_);
if (!browser_context)
return false;
GetCookieManager(browser_context)
->GetAllCookies(base::Bind(&GetAllCookiesCallbackImpl, visitor,
browser_context_getter_));
return true;
}
bool CefCookieManagerImpl::VisitUrlCookiesInternal(
const GURL& url,
bool includeHttpOnly,
CefRefPtr<CefCookieVisitor> visitor) {
DCHECK(ValidContext());
DCHECK(visitor);
DCHECK(url.is_valid());
net::CookieOptions options; net::CookieOptions options;
if (includeHttpOnly) if (includeHttpOnly)
options.set_include_httponly(); options.set_include_httponly();
@ -182,26 +257,18 @@ bool CefCookieManagerImpl::VisitUrlCookies(
return false; return false;
GetCookieManager(browser_context) GetCookieManager(browser_context)
->GetCookieList(gurl, options, ->GetCookieList(url, options,
base::Bind(&GetCookiesCallbackImpl, visitor, base::Bind(&GetCookiesCallbackImpl, visitor,
browser_context_getter_)); browser_context_getter_));
return true; return true;
} }
bool CefCookieManagerImpl::SetCookie(const CefString& url, bool CefCookieManagerImpl::SetCookieInternal(
const GURL& url,
const CefCookie& cookie, const CefCookie& cookie,
CefRefPtr<CefSetCookieCallback> callback) { CefRefPtr<CefSetCookieCallback> callback) {
GURL gurl = GURL(url.ToString()); DCHECK(ValidContext());
if (!gurl.is_valid()) DCHECK(url.is_valid());
return false;
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::Bind(base::IgnoreResult(&CefCookieManagerImpl::SetCookie), this,
url, cookie, callback));
return true;
}
std::string name = CefString(&cookie.name).ToString(); std::string name = CefString(&cookie.name).ToString();
std::string value = CefString(&cookie.value).ToString(); std::string value = CefString(&cookie.value).ToString();
@ -218,7 +285,7 @@ bool CefCookieManagerImpl::SetCookie(const CefString& url,
net_service::MakeCookiePriority(cookie.priority); net_service::MakeCookiePriority(cookie.priority);
auto canonical_cookie = net::CanonicalCookie::CreateSanitizedCookie( auto canonical_cookie = net::CanonicalCookie::CreateSanitizedCookie(
gurl, name, value, domain, path, url, name, value, domain, path,
base::Time(), // Creation time. base::Time(), // Creation time.
expiration_time, expiration_time,
base::Time(), // Last access time. base::Time(), // Last access time.
@ -243,39 +310,29 @@ bool CefCookieManagerImpl::SetCookie(const CefString& url,
return false; return false;
GetCookieManager(browser_context) GetCookieManager(browser_context)
->SetCanonicalCookie(*canonical_cookie, gurl, options, ->SetCanonicalCookie(*canonical_cookie, url, options,
base::Bind(SetCookieCallbackImpl, callback)); base::Bind(SetCookieCallbackImpl, callback));
return true; return true;
} }
bool CefCookieManagerImpl::DeleteCookies( bool CefCookieManagerImpl::DeleteCookiesInternal(
const CefString& url, const GURL& url,
const CefString& cookie_name, const CefString& cookie_name,
CefRefPtr<CefDeleteCookiesCallback> callback) { CefRefPtr<CefDeleteCookiesCallback> callback) {
// Empty URLs are allowed but not invalid URLs. DCHECK(ValidContext());
GURL gurl = GURL(url.ToString()); DCHECK(url.is_empty() || url.is_valid());
if (!gurl.is_empty() && !gurl.is_valid())
return false;
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::Bind(base::IgnoreResult(&CefCookieManagerImpl::DeleteCookies),
this, url, cookie_name, callback));
return true;
}
network::mojom::CookieDeletionFilterPtr deletion_filter = network::mojom::CookieDeletionFilterPtr deletion_filter =
network::mojom::CookieDeletionFilter::New(); network::mojom::CookieDeletionFilter::New();
if (gurl.is_empty()) { if (url.is_empty()) {
// Delete all cookies. // Delete all cookies.
} else if (cookie_name.empty()) { } else if (cookie_name.empty()) {
// Delete all matching host cookies. // Delete all matching host cookies.
deletion_filter->host_name = gurl.host(); deletion_filter->host_name = url.host();
} else { } else {
// Delete all matching host and domain cookies. // Delete all matching host and domain cookies.
deletion_filter->url = gurl; deletion_filter->url = url;
deletion_filter->cookie_name = cookie_name; deletion_filter->cookie_name = cookie_name;
} }
@ -289,15 +346,9 @@ bool CefCookieManagerImpl::DeleteCookies(
return true; return true;
} }
bool CefCookieManagerImpl::FlushStore( bool CefCookieManagerImpl::FlushStoreInternal(
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
if (!CEF_CURRENTLY_ON_UIT()) { DCHECK(ValidContext());
CEF_POST_TASK(
CEF_UIT,
base::Bind(base::IgnoreResult(&CefCookieManagerImpl::FlushStore), this,
callback));
return true;
}
auto browser_context = GetBrowserContext(browser_context_getter_); auto browser_context = GetBrowserContext(browser_context_getter_);
if (!browser_context) if (!browser_context)
@ -308,6 +359,27 @@ bool CefCookieManagerImpl::FlushStore(
return true; return true;
} }
void CefCookieManagerImpl::StoreOrTriggerInitCallback(
base::OnceClosure callback) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(&CefCookieManagerImpl::StoreOrTriggerInitCallback, this,
std::move(callback)));
return;
}
if (initialized_) {
std::move(callback).Run();
} else {
init_callbacks_.emplace_back(std::move(callback));
}
}
bool CefCookieManagerImpl::ValidContext() const {
return CEF_CURRENTLY_ON_UIT() && initialized_;
}
// CefCookieManager methods ---------------------------------------------------- // CefCookieManager methods ----------------------------------------------------
// static // static

View File

@ -36,9 +36,30 @@ class CefCookieManagerImpl : public CefCookieManager {
bool FlushStore(CefRefPtr<CefCompletionCallback> callback) override; bool FlushStore(CefRefPtr<CefCompletionCallback> callback) override;
private: private:
bool VisitAllCookiesInternal(CefRefPtr<CefCookieVisitor> visitor);
bool VisitUrlCookiesInternal(const GURL& url,
bool includeHttpOnly,
CefRefPtr<CefCookieVisitor> visitor);
bool SetCookieInternal(const GURL& url,
const CefCookie& cookie,
CefRefPtr<CefSetCookieCallback> callback);
bool DeleteCookiesInternal(const GURL& url,
const CefString& cookie_name,
CefRefPtr<CefDeleteCookiesCallback> callback);
bool FlushStoreInternal(CefRefPtr<CefCompletionCallback> callback);
// If the context is fully initialized execute |callback|, otherwise
// store it until the context is fully initialized.
void StoreOrTriggerInitCallback(base::OnceClosure callback);
bool ValidContext() const;
// Only accessed on the UI thread. Will be non-null after Initialize(). // Only accessed on the UI thread. Will be non-null after Initialize().
CefBrowserContext::Getter browser_context_getter_; CefBrowserContext::Getter browser_context_getter_;
bool initialized_ = false;
std::vector<base::OnceClosure> init_callbacks_;
IMPLEMENT_REFCOUNTING(CefCookieManagerImpl); IMPLEMENT_REFCOUNTING(CefCookieManagerImpl);
DISALLOW_COPY_AND_ASSIGN(CefCookieManagerImpl); DISALLOW_COPY_AND_ASSIGN(CefCookieManagerImpl);
}; };

View File

@ -228,17 +228,67 @@ CefRequestContextImpl::GetOrCreateForRequestContext(
return CefRequestContextImpl::GetOrCreateRequestContext(config); return CefRequestContextImpl::GetOrCreateRequestContext(config);
} }
bool CefRequestContextImpl::VerifyBrowserContext() const {
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return false;
}
if (!browser_context() || !browser_context()->IsInitialized()) {
NOTREACHED() << "Uninitialized context";
return false;
}
return true;
}
CefBrowserContext* CefRequestContextImpl::GetBrowserContext() { CefBrowserContext* CefRequestContextImpl::GetBrowserContext() {
EnsureBrowserContext(); CHECK(VerifyBrowserContext());
return browser_context(); return browser_context();
} }
void CefRequestContextImpl::ExecuteWhenBrowserContextInitialized(
base::OnceClosure callback) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT,
base::BindOnce(
&CefRequestContextImpl::ExecuteWhenBrowserContextInitialized, this,
std::move(callback)));
return;
}
EnsureBrowserContext();
browser_context()->StoreOrTriggerInitCallback(std::move(callback));
}
void CefRequestContextImpl::GetBrowserContext( void CefRequestContextImpl::GetBrowserContext(
scoped_refptr<base::SingleThreadTaskRunner> task_runner, scoped_refptr<base::SingleThreadTaskRunner> task_runner,
const BrowserContextCallback& callback) { BrowserContextCallback callback) {
if (!task_runner.get()) if (!task_runner.get())
task_runner = CefTaskRunnerImpl::GetCurrentTaskRunner(); task_runner = CefTaskRunnerImpl::GetCurrentTaskRunner();
GetBrowserContextOnUIThread(task_runner, callback);
ExecuteWhenBrowserContextInitialized(base::BindOnce(
[](CefRefPtr<CefRequestContextImpl> context,
scoped_refptr<base::SingleThreadTaskRunner> task_runner,
BrowserContextCallback callback) {
CEF_REQUIRE_UIT();
auto browser_context = context->browser_context();
DCHECK(browser_context->IsInitialized());
if (task_runner->BelongsToCurrentThread()) {
// Execute the callback immediately.
std::move(callback).Run(browser_context->getter());
} else {
// Execute the callback on the target thread.
task_runner->PostTask(
FROM_HERE,
base::BindOnce(std::move(callback), browser_context->getter()));
}
},
CefRefPtr<CefRequestContextImpl>(this), task_runner,
std::move(callback)));
} }
bool CefRequestContextImpl::IsSame(CefRefPtr<CefRequestContext> other) { bool CefRequestContextImpl::IsSame(CefRefPtr<CefRequestContext> other) {
@ -312,7 +362,7 @@ CefString CefRequestContextImpl::GetCachePath() {
CefRefPtr<CefCookieManager> CefRequestContextImpl::GetCookieManager( CefRefPtr<CefCookieManager> CefRequestContextImpl::GetCookieManager(
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
CefRefPtr<CefCookieManagerImpl> cookie_manager = new CefCookieManagerImpl(); CefRefPtr<CefCookieManagerImpl> cookie_manager = new CefCookieManagerImpl();
InitializeCookieManagerOnUIThread(cookie_manager, callback); InitializeCookieManagerInternal(cookie_manager, callback);
return cookie_manager.get(); return cookie_manager.get();
} }
@ -320,56 +370,45 @@ bool CefRequestContextImpl::RegisterSchemeHandlerFactory(
const CefString& scheme_name, const CefString& scheme_name,
const CefString& domain_name, const CefString& domain_name,
CefRefPtr<CefSchemeHandlerFactory> factory) { CefRefPtr<CefSchemeHandlerFactory> factory) {
if (!CEF_CURRENTLY_ON_UIT()) { GetBrowserContext(
CEF_POST_TASK(CEF_UIT, content::GetUIThreadTaskRunner({}),
base::BindOnce( base::BindOnce(
base::IgnoreResult( [](const CefString& scheme_name, const CefString& domain_name,
&CefRequestContextImpl::RegisterSchemeHandlerFactory), CefRefPtr<CefSchemeHandlerFactory> factory,
this, scheme_name, domain_name, factory)); CefBrowserContext::Getter browser_context_getter) {
return true; auto browser_context = browser_context_getter.Run();
if (browser_context) {
browser_context->RegisterSchemeHandlerFactory(
scheme_name, domain_name, factory);
} }
},
scheme_name, domain_name, factory));
// Make sure the browser context exists.
EnsureBrowserContext();
browser_context()->RegisterSchemeHandlerFactory(scheme_name, domain_name,
factory);
return true; return true;
} }
bool CefRequestContextImpl::ClearSchemeHandlerFactories() { bool CefRequestContextImpl::ClearSchemeHandlerFactories() {
if (!CEF_CURRENTLY_ON_UIT()) { GetBrowserContext(
CEF_POST_TASK( content::GetUIThreadTaskRunner({}),
CEF_UIT, base::BindOnce([](CefBrowserContext::Getter browser_context_getter) {
base::BindOnce(base::IgnoreResult( auto browser_context = browser_context_getter.Run();
&CefRequestContextImpl::ClearSchemeHandlerFactories), if (browser_context)
this)); browser_context->ClearSchemeHandlerFactories();
return true; }));
}
// Make sure the browser context exists.
EnsureBrowserContext();
browser_context()->ClearSchemeHandlerFactories();
return true; return true;
} }
void CefRequestContextImpl::PurgePluginListCache(bool reload_pages) { void CefRequestContextImpl::PurgePluginListCache(bool reload_pages) {
GetBrowserContext( GetBrowserContext(
content::GetUIThreadTaskRunner({}), content::GetUIThreadTaskRunner({}),
base::Bind(&CefRequestContextImpl::PurgePluginListCacheInternal, this, base::BindOnce(&CefRequestContextImpl::PurgePluginListCacheInternal, this,
reload_pages)); reload_pages));
} }
bool CefRequestContextImpl::HasPreference(const CefString& name) { bool CefRequestContextImpl::HasPreference(const CefString& name) {
// Verify that this method is being called on the UI thread. if (!VerifyBrowserContext())
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return false; return false;
}
// Make sure the browser context exists.
EnsureBrowserContext();
PrefService* pref_service = browser_context()->AsProfile()->GetPrefs(); PrefService* pref_service = browser_context()->AsProfile()->GetPrefs();
return (pref_service->FindPreference(name) != nullptr); return (pref_service->FindPreference(name) != nullptr);
@ -377,14 +416,8 @@ bool CefRequestContextImpl::HasPreference(const CefString& name) {
CefRefPtr<CefValue> CefRequestContextImpl::GetPreference( CefRefPtr<CefValue> CefRequestContextImpl::GetPreference(
const CefString& name) { const CefString& name) {
// Verify that this method is being called on the UI thread. if (!VerifyBrowserContext())
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return nullptr; return nullptr;
}
// Make sure the browser context exists.
EnsureBrowserContext();
PrefService* pref_service = browser_context()->AsProfile()->GetPrefs(); PrefService* pref_service = browser_context()->AsProfile()->GetPrefs();
const PrefService::Preference* pref = pref_service->FindPreference(name); const PrefService::Preference* pref = pref_service->FindPreference(name);
@ -395,14 +428,8 @@ CefRefPtr<CefValue> CefRequestContextImpl::GetPreference(
CefRefPtr<CefDictionaryValue> CefRequestContextImpl::GetAllPreferences( CefRefPtr<CefDictionaryValue> CefRequestContextImpl::GetAllPreferences(
bool include_defaults) { bool include_defaults) {
// Verify that this method is being called on the UI thread. if (!VerifyBrowserContext())
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return nullptr; return nullptr;
}
// Make sure the browser context exists.
EnsureBrowserContext();
PrefService* pref_service = browser_context()->AsProfile()->GetPrefs(); PrefService* pref_service = browser_context()->AsProfile()->GetPrefs();
@ -419,14 +446,8 @@ CefRefPtr<CefDictionaryValue> CefRequestContextImpl::GetAllPreferences(
} }
bool CefRequestContextImpl::CanSetPreference(const CefString& name) { bool CefRequestContextImpl::CanSetPreference(const CefString& name) {
// Verify that this method is being called on the UI thread. if (!VerifyBrowserContext())
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return false; return false;
}
// Make sure the browser context exists.
EnsureBrowserContext();
PrefService* pref_service = browser_context()->AsProfile()->GetPrefs(); PrefService* pref_service = browser_context()->AsProfile()->GetPrefs();
const PrefService::Preference* pref = pref_service->FindPreference(name); const PrefService::Preference* pref = pref_service->FindPreference(name);
@ -436,14 +457,8 @@ bool CefRequestContextImpl::CanSetPreference(const CefString& name) {
bool CefRequestContextImpl::SetPreference(const CefString& name, bool CefRequestContextImpl::SetPreference(const CefString& name,
CefRefPtr<CefValue> value, CefRefPtr<CefValue> value,
CefString& error) { CefString& error) {
// Verify that this method is being called on the UI thread. if (!VerifyBrowserContext())
if (!CEF_CURRENTLY_ON_UIT()) {
NOTREACHED() << "called on invalid thread";
return false; return false;
}
// Make sure the browser context exists.
EnsureBrowserContext();
PrefService* pref_service = browser_context()->AsProfile()->GetPrefs(); PrefService* pref_service = browser_context()->AsProfile()->GetPrefs();
@ -492,7 +507,7 @@ void CefRequestContextImpl::ClearCertificateExceptions(
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
GetBrowserContext( GetBrowserContext(
content::GetUIThreadTaskRunner({}), content::GetUIThreadTaskRunner({}),
base::Bind(&CefRequestContextImpl::ClearCertificateExceptionsInternal, base::BindOnce(&CefRequestContextImpl::ClearCertificateExceptionsInternal,
this, callback)); this, callback));
} }
@ -500,15 +515,15 @@ void CefRequestContextImpl::ClearHttpAuthCredentials(
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
GetBrowserContext( GetBrowserContext(
content::GetUIThreadTaskRunner({}), content::GetUIThreadTaskRunner({}),
base::Bind(&CefRequestContextImpl::ClearHttpAuthCredentialsInternal, this, base::BindOnce(&CefRequestContextImpl::ClearHttpAuthCredentialsInternal,
callback)); this, callback));
} }
void CefRequestContextImpl::CloseAllConnections( void CefRequestContextImpl::CloseAllConnections(
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
GetBrowserContext( GetBrowserContext(
content::GetUIThreadTaskRunner({}), content::GetUIThreadTaskRunner({}),
base::Bind(&CefRequestContextImpl::CloseAllConnectionsInternal, this, base::BindOnce(&CefRequestContextImpl::CloseAllConnectionsInternal, this,
callback)); callback));
} }
@ -516,7 +531,7 @@ void CefRequestContextImpl::ResolveHost(
const CefString& origin, const CefString& origin,
CefRefPtr<CefResolveCallback> callback) { CefRefPtr<CefResolveCallback> callback) {
GetBrowserContext(content::GetUIThreadTaskRunner({}), GetBrowserContext(content::GetUIThreadTaskRunner({}),
base::Bind(&CefRequestContextImpl::ResolveHostInternal, base::BindOnce(&CefRequestContextImpl::ResolveHostInternal,
this, origin, callback)); this, origin, callback));
} }
@ -524,17 +539,21 @@ void CefRequestContextImpl::LoadExtension(
const CefString& root_directory, const CefString& root_directory,
CefRefPtr<CefDictionaryValue> manifest, CefRefPtr<CefDictionaryValue> manifest,
CefRefPtr<CefExtensionHandler> handler) { CefRefPtr<CefExtensionHandler> handler) {
if (!CEF_CURRENTLY_ON_UIT()) { GetBrowserContext(content::GetUIThreadTaskRunner({}),
CEF_POST_TASK(CEF_UIT, base::BindOnce(
base::BindOnce(&CefRequestContextImpl::LoadExtension, this, [](const CefString& root_directory,
root_directory, manifest, handler)); CefRefPtr<CefDictionaryValue> manifest,
return; CefRefPtr<CefExtensionHandler> handler,
CefRefPtr<CefRequestContextImpl> self,
CefBrowserContext::Getter browser_context_getter) {
auto browser_context = browser_context_getter.Run();
if (browser_context) {
browser_context->LoadExtension(
root_directory, manifest, handler, self);
} }
},
// Make sure the browser context exists. root_directory, manifest, handler,
EnsureBrowserContext(); CefRefPtr<CefRequestContextImpl>(this)));
browser_context()->LoadExtension(root_directory, manifest, handler, this);
} }
bool CefRequestContextImpl::DidLoadExtension(const CefString& extension_id) { bool CefRequestContextImpl::DidLoadExtension(const CefString& extension_id) {
@ -551,33 +570,24 @@ bool CefRequestContextImpl::GetExtensions(
std::vector<CefString>& extension_ids) { std::vector<CefString>& extension_ids) {
extension_ids.clear(); extension_ids.clear();
if (!CEF_CURRENTLY_ON_UIT()) { if (!VerifyBrowserContext())
NOTREACHED() << "called on invalid thread";
return false; return false;
}
// Make sure the browser context exists.
EnsureBrowserContext();
return browser_context()->GetExtensions(extension_ids); return browser_context()->GetExtensions(extension_ids);
} }
CefRefPtr<CefExtension> CefRequestContextImpl::GetExtension( CefRefPtr<CefExtension> CefRequestContextImpl::GetExtension(
const CefString& extension_id) { const CefString& extension_id) {
if (!CEF_CURRENTLY_ON_UIT()) { if (!VerifyBrowserContext())
NOTREACHED() << "called on invalid thread";
return nullptr; return nullptr;
}
// Make sure the browser context exists.
EnsureBrowserContext();
return browser_context()->GetExtension(extension_id); return browser_context()->GetExtension(extension_id);
} }
CefRefPtr<CefMediaRouter> CefRequestContextImpl::GetMediaRouter() { CefRefPtr<CefMediaRouter> CefRequestContextImpl::GetMediaRouter(
CefRefPtr<CefCompletionCallback> callback) {
CefRefPtr<CefMediaRouterImpl> media_router = new CefMediaRouterImpl(); CefRefPtr<CefMediaRouterImpl> media_router = new CefMediaRouterImpl();
InitializeMediaRouterOnUIThread(media_router); InitializeMediaRouterInternal(media_router, callback);
return media_router.get(); return media_router.get();
} }
@ -614,14 +624,12 @@ CefRequestContextImpl::GetOrCreateRequestContext(const Config& config) {
// The new context will be initialized later by EnsureBrowserContext(). // The new context will be initialized later by EnsureBrowserContext().
CefRefPtr<CefRequestContextImpl> context = new CefRequestContextImpl(config); CefRefPtr<CefRequestContextImpl> context = new CefRequestContextImpl(config);
if (config.handler) { // Initialize ASAP so that any tasks blocked on initialization will execute.
// Keep the context alive until OnRequestContextInitialized is called.
if (CEF_CURRENTLY_ON_UIT()) { if (CEF_CURRENTLY_ON_UIT()) {
context->Initialize(); context->Initialize();
} else { } else {
CEF_POST_TASK( CEF_POST_TASK(CEF_UIT,
CEF_UIT, base::BindOnce(&CefRequestContextImpl::Initialize, context)); base::BindOnce(&CefRequestContextImpl::Initialize, context));
}
} }
return context; return context;
@ -638,8 +646,8 @@ void CefRequestContextImpl::Initialize() {
if (config_.other) { if (config_.other) {
// Share storage with |config_.other|. // Share storage with |config_.other|.
browser_context_ = config_.other->GetBrowserContext(); browser_context_ = config_.other->browser_context();
DCHECK(browser_context_); CHECK(browser_context_);
} }
if (!browser_context_) { if (!browser_context_) {
@ -670,7 +678,7 @@ void CefRequestContextImpl::Initialize() {
} else { } else {
// Share the same settings as the existing context. // Share the same settings as the existing context.
config_.settings = browser_context_->settings(); config_.settings = browser_context_->settings();
std::move(initialized_cb).Run(); browser_context_->StoreOrTriggerInitCallback(std::move(initialized_cb));
} }
// We'll disassociate from |browser_context_| on destruction. // We'll disassociate from |browser_context_| on destruction.
@ -701,32 +709,13 @@ void CefRequestContextImpl::EnsureBrowserContext() {
DCHECK(browser_context()); DCHECK(browser_context());
} }
void CefRequestContextImpl::GetBrowserContextOnUIThread(
scoped_refptr<base::SingleThreadTaskRunner> task_runner,
const BrowserContextCallback& callback) {
if (!CEF_CURRENTLY_ON_UIT()) {
CEF_POST_TASK(
CEF_UIT, base::Bind(&CefRequestContextImpl::GetBrowserContextOnUIThread,
this, task_runner, callback));
return;
}
// Make sure the browser context exists.
EnsureBrowserContext();
if (task_runner->BelongsToCurrentThread()) {
// Execute the callback immediately.
callback.Run(browser_context());
} else {
// Execute the callback on the target thread.
task_runner->PostTask(FROM_HERE, base::Bind(callback, browser_context()));
}
}
void CefRequestContextImpl::PurgePluginListCacheInternal( void CefRequestContextImpl::PurgePluginListCacheInternal(
bool reload_pages, bool reload_pages,
CefBrowserContext* browser_context) { CefBrowserContext::Getter browser_context_getter) {
CEF_REQUIRE_UIT(); auto browser_context = browser_context_getter.Run();
if (!browser_context)
return;
browser_context->ClearPluginLoadDecision(-1); browser_context->ClearPluginLoadDecision(-1);
content::PluginService::GetInstance()->PurgePluginListCache( content::PluginService::GetInstance()->PurgePluginListCache(
browser_context->AsBrowserContext(), false); browser_context->AsBrowserContext(), false);
@ -734,8 +723,10 @@ void CefRequestContextImpl::PurgePluginListCacheInternal(
void CefRequestContextImpl::ClearCertificateExceptionsInternal( void CefRequestContextImpl::ClearCertificateExceptionsInternal(
CefRefPtr<CefCompletionCallback> callback, CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext* browser_context) { CefBrowserContext::Getter browser_context_getter) {
CEF_REQUIRE_UIT(); auto browser_context = browser_context_getter.Run();
if (!browser_context)
return;
content::SSLHostStateDelegate* ssl_delegate = content::SSLHostStateDelegate* ssl_delegate =
browser_context->AsBrowserContext()->GetSSLHostStateDelegate(); browser_context->AsBrowserContext()->GetSSLHostStateDelegate();
@ -750,8 +741,10 @@ void CefRequestContextImpl::ClearCertificateExceptionsInternal(
void CefRequestContextImpl::ClearHttpAuthCredentialsInternal( void CefRequestContextImpl::ClearHttpAuthCredentialsInternal(
CefRefPtr<CefCompletionCallback> callback, CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext* browser_context) { CefBrowserContext::Getter browser_context_getter) {
CEF_REQUIRE_UIT(); auto browser_context = browser_context_getter.Run();
if (!browser_context)
return;
browser_context->GetNetworkContext()->ClearHttpAuthCache( browser_context->GetNetworkContext()->ClearHttpAuthCache(
/*start_time=*/base::Time(), /*end_time=*/base::Time::Max(), /*start_time=*/base::Time(), /*end_time=*/base::Time::Max(),
@ -760,8 +753,10 @@ void CefRequestContextImpl::ClearHttpAuthCredentialsInternal(
void CefRequestContextImpl::CloseAllConnectionsInternal( void CefRequestContextImpl::CloseAllConnectionsInternal(
CefRefPtr<CefCompletionCallback> callback, CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext* browser_context) { CefBrowserContext::Getter browser_context_getter) {
CEF_REQUIRE_UIT(); auto browser_context = browser_context_getter.Run();
if (!browser_context)
return;
browser_context->GetNetworkContext()->CloseAllConnections( browser_context->GetNetworkContext()->CloseAllConnections(
base::Bind(&CefCompletionCallback::OnComplete, callback)); base::Bind(&CefCompletionCallback::OnComplete, callback));
@ -770,41 +765,42 @@ void CefRequestContextImpl::CloseAllConnectionsInternal(
void CefRequestContextImpl::ResolveHostInternal( void CefRequestContextImpl::ResolveHostInternal(
const CefString& origin, const CefString& origin,
CefRefPtr<CefResolveCallback> callback, CefRefPtr<CefResolveCallback> callback,
CefBrowserContext* browser_context) { CefBrowserContext::Getter browser_context_getter) {
CEF_REQUIRE_UIT(); auto browser_context = browser_context_getter.Run();
if (!browser_context)
return;
// |helper| will be deleted in ResolveHostHelper::OnComplete(). // |helper| will be deleted in ResolveHostHelper::OnComplete().
ResolveHostHelper* helper = new ResolveHostHelper(callback); ResolveHostHelper* helper = new ResolveHostHelper(callback);
helper->Start(browser_context, origin); helper->Start(browser_context, origin);
} }
void CefRequestContextImpl::InitializeCookieManagerOnUIThread( void CefRequestContextImpl::InitializeCookieManagerInternal(
CefRefPtr<CefCookieManagerImpl> cookie_manager, CefRefPtr<CefCookieManagerImpl> cookie_manager,
CefRefPtr<CefCompletionCallback> callback) { CefRefPtr<CefCompletionCallback> callback) {
if (!CEF_CURRENTLY_ON_UIT()) { GetBrowserContext(content::GetUIThreadTaskRunner({}),
CEF_POST_TASK( base::BindOnce(
CEF_UIT, [](CefRefPtr<CefCookieManagerImpl> cookie_manager,
base::Bind(&CefRequestContextImpl::InitializeCookieManagerOnUIThread, CefRefPtr<CefCompletionCallback> callback,
this, cookie_manager, callback)); CefBrowserContext::Getter browser_context_getter) {
return; cookie_manager->Initialize(browser_context_getter,
} callback);
},
auto browser_context = GetBrowserContext(); cookie_manager, callback));
cookie_manager->Initialize(browser_context->getter(), callback);
} }
void CefRequestContextImpl::InitializeMediaRouterOnUIThread( void CefRequestContextImpl::InitializeMediaRouterInternal(
CefRefPtr<CefMediaRouterImpl> media_router) { CefRefPtr<CefMediaRouterImpl> media_router,
if (!CEF_CURRENTLY_ON_UIT()) { CefRefPtr<CefCompletionCallback> callback) {
CEF_POST_TASK( GetBrowserContext(content::GetUIThreadTaskRunner({}),
CEF_UIT, base::BindOnce(
base::Bind(&CefRequestContextImpl::InitializeMediaRouterOnUIThread, [](CefRefPtr<CefMediaRouterImpl> media_router,
this, media_router)); CefRefPtr<CefCompletionCallback> callback,
return; CefBrowserContext::Getter browser_context_getter) {
} media_router->Initialize(browser_context_getter,
callback);
auto browser_context = GetBrowserContext(); },
media_router->Initialize(browser_context->getter()); media_router, callback));
} }
CefBrowserContext* CefRequestContextImpl::browser_context() const { CefBrowserContext* CefRequestContextImpl::browser_context() const {

View File

@ -30,17 +30,27 @@ class CefRequestContextImpl : public CefRequestContext {
static CefRefPtr<CefRequestContextImpl> GetOrCreateForRequestContext( static CefRefPtr<CefRequestContextImpl> GetOrCreateForRequestContext(
CefRefPtr<CefRequestContext> request_context); CefRefPtr<CefRequestContext> request_context);
// Returns the browser context object. Can only be called on the UI thread. // Verify that the browser context can be directly accessed (e.g. on the UI
// thread and initialized).
bool VerifyBrowserContext() const;
// Returns the browser context object. Can only be called on the UI thread
// after the browser context has been initialized.
CefBrowserContext* GetBrowserContext(); CefBrowserContext* GetBrowserContext();
// Executes |callback| either synchronously or asynchronously with the browser // If the context is fully initialized execute |callback|, otherwise
// context object when it's available. If |task_runner| is NULL the callback // store it until the context is fully initialized.
// will be executed on the originating thread. The resulting context object void ExecuteWhenBrowserContextInitialized(base::OnceClosure callback);
// can only be accessed on the UI thread.
typedef base::Callback<void(CefBrowserContext*)> BrowserContextCallback; // Executes |callback| either synchronously or asynchronously after the
// browser context object has been initialized. If |task_runner| is NULL the
// callback will be executed on the originating thread. The resulting getter
// can only be executed on the UI thread.
using BrowserContextCallback =
base::OnceCallback<void(CefBrowserContext::Getter)>;
void GetBrowserContext( void GetBrowserContext(
scoped_refptr<base::SingleThreadTaskRunner> task_runner, scoped_refptr<base::SingleThreadTaskRunner> task_runner,
const BrowserContextCallback& callback); BrowserContextCallback callback);
bool IsSame(CefRefPtr<CefRequestContext> other) override; bool IsSame(CefRefPtr<CefRequestContext> other) override;
bool IsSharingWith(CefRefPtr<CefRequestContext> other) override; bool IsSharingWith(CefRefPtr<CefRequestContext> other) override;
@ -77,7 +87,8 @@ class CefRequestContextImpl : public CefRequestContext {
bool HasExtension(const CefString& extension_id) override; bool HasExtension(const CefString& extension_id) override;
bool GetExtensions(std::vector<CefString>& extension_ids) override; bool GetExtensions(std::vector<CefString>& extension_ids) override;
CefRefPtr<CefExtension> GetExtension(const CefString& extension_id) override; CefRefPtr<CefExtension> GetExtension(const CefString& extension_id) override;
CefRefPtr<CefMediaRouter> GetMediaRouter() override; CefRefPtr<CefMediaRouter> GetMediaRouter(
CefRefPtr<CefCompletionCallback> callback) override;
const CefRequestContextSettings& settings() const { return config_.settings; } const CefRequestContextSettings& settings() const { return config_.settings; }
@ -133,29 +144,27 @@ class CefRequestContextImpl : public CefRequestContext {
// Make sure the browser context exists. Only called on the UI thread. // Make sure the browser context exists. Only called on the UI thread.
void EnsureBrowserContext(); void EnsureBrowserContext();
void GetBrowserContextOnUIThread( void PurgePluginListCacheInternal(
scoped_refptr<base::SingleThreadTaskRunner> task_runner, bool reload_pages,
const BrowserContextCallback& callback); CefBrowserContext::Getter browser_context_getter);
void PurgePluginListCacheInternal(bool reload_pages,
CefBrowserContext* browser_context);
void ClearCertificateExceptionsInternal( void ClearCertificateExceptionsInternal(
CefRefPtr<CefCompletionCallback> callback, CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext* browser_context); CefBrowserContext::Getter browser_context_getter);
void ClearHttpAuthCredentialsInternal( void ClearHttpAuthCredentialsInternal(
CefRefPtr<CefCompletionCallback> callback, CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext* browser_context); CefBrowserContext::Getter browser_context_getter);
void CloseAllConnectionsInternal(CefRefPtr<CefCompletionCallback> callback, void CloseAllConnectionsInternal(
CefBrowserContext* browser_context); CefRefPtr<CefCompletionCallback> callback,
CefBrowserContext::Getter browser_context_getter);
void ResolveHostInternal(const CefString& origin, void ResolveHostInternal(const CefString& origin,
CefRefPtr<CefResolveCallback> callback, CefRefPtr<CefResolveCallback> callback,
CefBrowserContext* browser_context); CefBrowserContext::Getter browser_context_getter);
void InitializeCookieManagerOnUIThread( void InitializeCookieManagerInternal(
CefRefPtr<CefCookieManagerImpl> cookie_manager, CefRefPtr<CefCookieManagerImpl> cookie_manager,
CefRefPtr<CefCompletionCallback> callback); CefRefPtr<CefCompletionCallback> callback);
void InitializeMediaRouterOnUIThread( void InitializeMediaRouterInternal(CefRefPtr<CefMediaRouterImpl> media_router,
CefRefPtr<CefMediaRouterImpl> media_router); CefRefPtr<CefCompletionCallback> callback);
CefBrowserContext* browser_context() const; CefBrowserContext* browser_context() const;

View File

@ -8,6 +8,7 @@
#include "libcef/browser/browser_util.h" #include "libcef/browser/browser_util.h"
#include "libcef/browser/chrome/views/chrome_browser_view.h" #include "libcef/browser/chrome/views/chrome_browser_view.h"
#include "libcef/browser/context.h" #include "libcef/browser/context.h"
#include "libcef/browser/request_context_impl.h"
#include "libcef/browser/thread_util.h" #include "libcef/browser/thread_util.h"
#include "libcef/browser/views/window_impl.h" #include "libcef/browser/views/window_impl.h"
@ -48,6 +49,18 @@ CefRefPtr<CefBrowserViewImpl> CefBrowserViewImpl::Create(
CefRefPtr<CefBrowserViewDelegate> delegate) { CefRefPtr<CefBrowserViewDelegate> delegate) {
CEF_REQUIRE_UIT_RETURN(nullptr); CEF_REQUIRE_UIT_RETURN(nullptr);
if (!request_context) {
request_context = CefRequestContext::GetGlobalContext();
}
// Verify that the browser context is valid. Do this here instead of risking
// potential browser creation failure when this view is added to the window.
auto request_context_impl =
static_cast<CefRequestContextImpl*>(request_context.get());
if (!request_context_impl->VerifyBrowserContext()) {
return nullptr;
}
CefRefPtr<CefBrowserViewImpl> browser_view = new CefBrowserViewImpl(delegate); CefRefPtr<CefBrowserViewImpl> browser_view = new CefBrowserViewImpl(delegate);
browser_view->SetPendingBrowserCreateParams(client, url, settings, extra_info, browser_view->SetPendingBrowserCreateParams(client, url, settings, extra_info,
request_context); request_context);
@ -207,7 +220,7 @@ void CefBrowserViewImpl::SetPendingBrowserCreateParams(
DCHECK(!pending_browser_create_params_); DCHECK(!pending_browser_create_params_);
pending_browser_create_params_.reset(new CefBrowserCreateParams()); pending_browser_create_params_.reset(new CefBrowserCreateParams());
pending_browser_create_params_->client = client; pending_browser_create_params_->client = client;
pending_browser_create_params_->url = GURL(url.ToString()); pending_browser_create_params_->url = url;
pending_browser_create_params_->settings = settings; pending_browser_create_params_->settings = settings;
pending_browser_create_params_->extra_info = extra_info; pending_browser_create_params_->extra_info = extra_info;
pending_browser_create_params_->request_context = request_context; pending_browser_create_params_->request_context = request_context;

View File

@ -0,0 +1,41 @@
// Copyright (c) 2021 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/common/net/url_util.h"
#include "base/logging.h"
#include "components/url_formatter/url_fixer.h"
namespace url_util {
GURL MakeGURL(const CefString& url, bool fixup) {
GURL gurl = GURL(url.ToString());
if (!url.empty() && !gurl.is_valid() && !gurl.has_scheme()) {
std::string fixed_scheme(url::kHttpScheme);
fixed_scheme.append(url::kStandardSchemeSeparator);
std::string new_url = url;
new_url.insert(0, fixed_scheme);
gurl = GURL(new_url);
}
if (fixup)
FixupGURL(gurl);
return gurl;
}
bool FixupGURL(GURL& gurl) {
if (!gurl.is_empty()) {
GURL fixup_url =
url_formatter::FixupURL(gurl.possibly_invalid_spec(), std::string());
if (fixup_url.is_valid()) {
gurl = fixup_url;
} else {
LOG(ERROR) << "Invalid URL: " << gurl.possibly_invalid_spec();
gurl = GURL();
return false;
}
}
return true;
}
} // namespace url_util

View File

@ -0,0 +1,27 @@
// Copyright (c) 2021 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_COMMON_NET_URL_UTIL_H_
#define CEF_LIBCEF_COMMON_NET_URL_UTIL_H_
#pragma once
#include "include/cef_base.h"
class GURL;
namespace url_util {
// Convert |url| to a GURL, adding a scheme prefix if necessary.
// If |fixup| is true then FixupGURL() will also be called.
GURL MakeGURL(const CefString& url, bool fixup);
// Fix common problems with user-typed text. Among other things, this:
// - Converts absolute file paths to "file://" URLs.
// - Normalizes "about:" and "chrome:" to "chrome://" URLs
// Modifies |gurl| if necessary. Returns true if |gurl| is empty or valid.
bool FixupGURL(GURL& gurl);
} // namespace url_util
#endif // CEF_LIBCEF_COMMON_NET_URL_UTIL_H_

View File

@ -9,26 +9,31 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=3deccadb24380ee63afe228ca2a91b90e96affca$ // $hash=f60f51701b15100a8ad9463adfe0deb37c2d6b4f$
// //
#include "libcef_dll/cpptoc/media_router_cpptoc.h" #include "libcef_dll/cpptoc/media_router_cpptoc.h"
#include "libcef_dll/cpptoc/media_sink_cpptoc.h" #include "libcef_dll/cpptoc/media_sink_cpptoc.h"
#include "libcef_dll/cpptoc/media_source_cpptoc.h" #include "libcef_dll/cpptoc/media_source_cpptoc.h"
#include "libcef_dll/cpptoc/registration_cpptoc.h" #include "libcef_dll/cpptoc/registration_cpptoc.h"
#include "libcef_dll/ctocpp/completion_callback_ctocpp.h"
#include "libcef_dll/ctocpp/media_observer_ctocpp.h" #include "libcef_dll/ctocpp/media_observer_ctocpp.h"
#include "libcef_dll/ctocpp/media_route_create_callback_ctocpp.h" #include "libcef_dll/ctocpp/media_route_create_callback_ctocpp.h"
#include "libcef_dll/shutdown_checker.h" #include "libcef_dll/shutdown_checker.h"
// GLOBAL FUNCTIONS - Body may be edited by hand. // GLOBAL FUNCTIONS - Body may be edited by hand.
CEF_EXPORT cef_media_router_t* cef_media_router_get_global() { CEF_EXPORT cef_media_router_t* cef_media_router_get_global(
cef_completion_callback_t* callback) {
shutdown_checker::AssertNotShutdown(); shutdown_checker::AssertNotShutdown();
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING // AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
// Unverified params: callback
// Execute // Execute
CefRefPtr<CefMediaRouter> _retval = CefMediaRouter::GetGlobalMediaRouter(); CefRefPtr<CefMediaRouter> _retval = CefMediaRouter::GetGlobalMediaRouter(
CefCompletionCallbackCToCpp::Wrap(callback));
// Return type: refptr_same // Return type: refptr_same
return CefMediaRouterCppToC::Wrap(_retval); return CefMediaRouterCppToC::Wrap(_retval);

View File

@ -9,7 +9,7 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=3e91639f70988c2a48470e380c7317db5f27153e$ // $hash=38ae668703b71d27d2bcd7cd9230817edd5b8f41$
// //
#include "libcef_dll/cpptoc/request_context_cpptoc.h" #include "libcef_dll/cpptoc/request_context_cpptoc.h"
@ -542,16 +542,19 @@ request_context_get_extension(struct _cef_request_context_t* self,
} }
cef_media_router_t* CEF_CALLBACK cef_media_router_t* CEF_CALLBACK
request_context_get_media_router(struct _cef_request_context_t* self) { request_context_get_media_router(struct _cef_request_context_t* self,
cef_completion_callback_t* callback) {
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING // AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
DCHECK(self); DCHECK(self);
if (!self) if (!self)
return NULL; return NULL;
// Unverified params: callback
// Execute // Execute
CefRefPtr<CefMediaRouter> _retval = CefRefPtr<CefMediaRouter> _retval =
CefRequestContextCppToC::Get(self)->GetMediaRouter(); CefRequestContextCppToC::Get(self)->GetMediaRouter(
CefCompletionCallbackCToCpp::Wrap(callback));
// Return type: refptr_same // Return type: refptr_same
return CefMediaRouterCppToC::Wrap(_retval); return CefMediaRouterCppToC::Wrap(_retval);

View File

@ -9,10 +9,11 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=ae6ec27ec52df5eb0db397c27b0df4969474dc0c$ // $hash=8e7b2e3e8124ede620b8a04116656550949f89f1$
// //
#include "libcef_dll/ctocpp/media_router_ctocpp.h" #include "libcef_dll/ctocpp/media_router_ctocpp.h"
#include "libcef_dll/cpptoc/completion_callback_cpptoc.h"
#include "libcef_dll/cpptoc/media_observer_cpptoc.h" #include "libcef_dll/cpptoc/media_observer_cpptoc.h"
#include "libcef_dll/cpptoc/media_route_create_callback_cpptoc.h" #include "libcef_dll/cpptoc/media_route_create_callback_cpptoc.h"
#include "libcef_dll/ctocpp/media_sink_ctocpp.h" #include "libcef_dll/ctocpp/media_sink_ctocpp.h"
@ -23,13 +24,17 @@
// STATIC METHODS - Body may be edited by hand. // STATIC METHODS - Body may be edited by hand.
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
CefRefPtr<CefMediaRouter> CefMediaRouter::GetGlobalMediaRouter() { CefRefPtr<CefMediaRouter> CefMediaRouter::GetGlobalMediaRouter(
CefRefPtr<CefCompletionCallback> callback) {
shutdown_checker::AssertNotShutdown(); shutdown_checker::AssertNotShutdown();
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING // AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
// Unverified params: callback
// Execute // Execute
cef_media_router_t* _retval = cef_media_router_get_global(); cef_media_router_t* _retval =
cef_media_router_get_global(CefCompletionCallbackCppToC::Wrap(callback));
// Return type: refptr_same // Return type: refptr_same
return CefMediaRouterCToCpp::Wrap(_retval); return CefMediaRouterCToCpp::Wrap(_retval);

View File

@ -9,7 +9,7 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=fde747bf60e627912a0f242a2475af69be80f298$ // $hash=67bc021917c8f7d1e386859bbfae6e007b292f45$
// //
#include "libcef_dll/ctocpp/request_context_ctocpp.h" #include "libcef_dll/ctocpp/request_context_ctocpp.h"
@ -527,15 +527,19 @@ CefRefPtr<CefExtension> CefRequestContextCToCpp::GetExtension(
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
CefRefPtr<CefMediaRouter> CefRequestContextCToCpp::GetMediaRouter() { CefRefPtr<CefMediaRouter> CefRequestContextCToCpp::GetMediaRouter(
CefRefPtr<CefCompletionCallback> callback) {
cef_request_context_t* _struct = GetStruct(); cef_request_context_t* _struct = GetStruct();
if (CEF_MEMBER_MISSING(_struct, get_media_router)) if (CEF_MEMBER_MISSING(_struct, get_media_router))
return nullptr; return nullptr;
// AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING // AUTO-GENERATED CONTENT - DELETE THIS COMMENT BEFORE MODIFYING
// Unverified params: callback
// Execute // Execute
cef_media_router_t* _retval = _struct->get_media_router(_struct); cef_media_router_t* _retval = _struct->get_media_router(
_struct, CefCompletionCallbackCppToC::Wrap(callback));
// Return type: refptr_same // Return type: refptr_same
return CefMediaRouterCToCpp::Wrap(_retval); return CefMediaRouterCToCpp::Wrap(_retval);

View File

@ -9,7 +9,7 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=f54014218a54c7925d85df2f162fd51962dac2ce$ // $hash=0aff81f2ccc5881001e9fd61cc6e349253fb2ac5$
// //
#ifndef CEF_LIBCEF_DLL_CTOCPP_REQUEST_CONTEXT_CTOCPP_H_ #ifndef CEF_LIBCEF_DLL_CTOCPP_REQUEST_CONTEXT_CTOCPP_H_
@ -75,7 +75,8 @@ class CefRequestContextCToCpp
bool HasExtension(const CefString& extension_id) OVERRIDE; bool HasExtension(const CefString& extension_id) OVERRIDE;
bool GetExtensions(std::vector<CefString>& extension_ids) OVERRIDE; bool GetExtensions(std::vector<CefString>& extension_ids) OVERRIDE;
CefRefPtr<CefExtension> GetExtension(const CefString& extension_id) OVERRIDE; CefRefPtr<CefExtension> GetExtension(const CefString& extension_id) OVERRIDE;
CefRefPtr<CefMediaRouter> GetMediaRouter() OVERRIDE; CefRefPtr<CefMediaRouter> GetMediaRouter(
CefRefPtr<CefCompletionCallback> callback) OVERRIDE;
}; };
#endif // CEF_LIBCEF_DLL_CTOCPP_REQUEST_CONTEXT_CTOCPP_H_ #endif // CEF_LIBCEF_DLL_CTOCPP_REQUEST_CONTEXT_CTOCPP_H_

View File

@ -9,7 +9,7 @@
// implementations. See the translator.README.txt file in the tools directory // implementations. See the translator.README.txt file in the tools directory
// for more information. // for more information.
// //
// $hash=51090c9b8afc79ae98d70fe84c98bc7c8a433c3a$ // $hash=9fbe1de9cf7f32c551c535e190d4c82b4947765d$
// //
#include <dlfcn.h> #include <dlfcn.h>
@ -203,7 +203,8 @@ typedef struct _cef_cookie_manager_t* (
struct _cef_completion_callback_t*); struct _cef_completion_callback_t*);
typedef struct _cef_drag_data_t* (*cef_drag_data_create_ptr)(); typedef struct _cef_drag_data_t* (*cef_drag_data_create_ptr)();
typedef struct _cef_image_t* (*cef_image_create_ptr)(); typedef struct _cef_image_t* (*cef_image_create_ptr)();
typedef struct _cef_media_router_t* (*cef_media_router_get_global_ptr)(); typedef struct _cef_media_router_t* (*cef_media_router_get_global_ptr)(
struct _cef_completion_callback_t*);
typedef struct _cef_menu_model_t* (*cef_menu_model_create_ptr)( typedef struct _cef_menu_model_t* (*cef_menu_model_create_ptr)(
struct _cef_menu_model_delegate_t*); struct _cef_menu_model_delegate_t*);
typedef struct _cef_print_settings_t* (*cef_print_settings_create_ptr)(); typedef struct _cef_print_settings_t* (*cef_print_settings_create_ptr)();
@ -1093,8 +1094,8 @@ int cef_create_url(const struct _cef_urlparts_t* parts, cef_string_t* url) {
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
cef_string_userfree_t cef_string_userfree_t cef_format_url_for_security_display(
cef_format_url_for_security_display(const cef_string_t* origin_url) { const cef_string_t* origin_url) {
return g_libcef_pointers.cef_format_url_for_security_display(origin_url); return g_libcef_pointers.cef_format_url_for_security_display(origin_url);
} }
@ -1315,8 +1316,9 @@ NO_SANITIZE("cfi-icall") struct _cef_image_t* cef_image_create() {
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct _cef_media_router_t* cef_media_router_get_global() { struct _cef_media_router_t* cef_media_router_get_global(
return g_libcef_pointers.cef_media_router_get_global(); struct _cef_completion_callback_t* callback) {
return g_libcef_pointers.cef_media_router_get_global(callback);
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
@ -1579,25 +1581,21 @@ struct _cef_translator_test_t* cef_translator_test_create() {
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_ref_ptr_library_t*
_cef_translator_test_ref_ptr_library_t* cef_translator_test_ref_ptr_library_create( cef_translator_test_ref_ptr_library_create(int value) {
int value) {
return g_libcef_pointers.cef_translator_test_ref_ptr_library_create(value); return g_libcef_pointers.cef_translator_test_ref_ptr_library_create(value);
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_ref_ptr_library_child_t*
_cef_translator_test_ref_ptr_library_child_t* cef_translator_test_ref_ptr_library_child_create( cef_translator_test_ref_ptr_library_child_create(int value, int other_value) {
int value,
int other_value) {
return g_libcef_pointers.cef_translator_test_ref_ptr_library_child_create( return g_libcef_pointers.cef_translator_test_ref_ptr_library_child_create(
value, other_value); value, other_value);
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_ref_ptr_library_child_child_t*
_cef_translator_test_ref_ptr_library_child_child_t* cef_translator_test_ref_ptr_library_child_child_create( cef_translator_test_ref_ptr_library_child_child_create(int value,
int value,
int other_value, int other_value,
int other_other_value) { int other_other_value) {
return g_libcef_pointers return g_libcef_pointers
@ -1606,25 +1604,21 @@ struct
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_scoped_library_t*
_cef_translator_test_scoped_library_t* cef_translator_test_scoped_library_create( cef_translator_test_scoped_library_create(int value) {
int value) {
return g_libcef_pointers.cef_translator_test_scoped_library_create(value); return g_libcef_pointers.cef_translator_test_scoped_library_create(value);
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_scoped_library_child_t*
_cef_translator_test_scoped_library_child_t* cef_translator_test_scoped_library_child_create( cef_translator_test_scoped_library_child_create(int value, int other_value) {
int value,
int other_value) {
return g_libcef_pointers.cef_translator_test_scoped_library_child_create( return g_libcef_pointers.cef_translator_test_scoped_library_child_create(
value, other_value); value, other_value);
} }
NO_SANITIZE("cfi-icall") NO_SANITIZE("cfi-icall")
struct struct _cef_translator_test_scoped_library_child_child_t*
_cef_translator_test_scoped_library_child_child_t* cef_translator_test_scoped_library_child_child_create( cef_translator_test_scoped_library_child_child_create(int value,
int value,
int other_value, int other_value,
int other_other_value) { int other_other_value) {
return g_libcef_pointers return g_libcef_pointers

View File

@ -543,7 +543,7 @@ class Handler : public CefMessageRouterBrowserSide::Handler {
} }
CefRefPtr<CefMediaRouter> media_router = CefRefPtr<CefMediaRouter> media_router =
browser->GetHost()->GetRequestContext()->GetMediaRouter(); browser->GetHost()->GetRequestContext()->GetMediaRouter(nullptr);
SubscriptionState* state = new SubscriptionState(); SubscriptionState* state = new SubscriptionState();
state->query_id = query_id; state->query_id = query_id;

View File

@ -398,6 +398,19 @@ void ValidateGet(CefRefPtr<CefRequestContext> context,
class TestRequestContextHandler : public CefRequestContextHandler { class TestRequestContextHandler : public CefRequestContextHandler {
public: public:
TestRequestContextHandler() {} TestRequestContextHandler() {}
explicit TestRequestContextHandler(CefRefPtr<CefWaitableEvent> event)
: event_(event) {}
void OnRequestContextInitialized(
CefRefPtr<CefRequestContext> context) override {
if (event_) {
event_->Signal();
event_ = nullptr;
}
}
private:
CefRefPtr<CefWaitableEvent> event_;
IMPLEMENT_REFCOUNTING(TestRequestContextHandler); IMPLEMENT_REFCOUNTING(TestRequestContextHandler);
}; };
@ -452,9 +465,11 @@ TEST(PreferenceTest, GlobalSetGetShared) {
// Unassociated context. // Unassociated context.
CefRequestContextSettings settings; CefRequestContextSettings settings;
CefRefPtr<CefRequestContext> context4 = CefRefPtr<CefRequestContext> context4 = CefRequestContext::CreateContext(
CefRequestContext::CreateContext(settings, nullptr); settings, new TestRequestContextHandler(event));
EXPECT_TRUE(context4.get()); EXPECT_TRUE(context4.get());
// Wait for the context to be fully initialized.
event->Wait();
// Set/get the values on the first context. // Set/get the values on the first context.
*PendingAction() = "Set/get the values on the first context"; *PendingAction() = "Set/get the values on the first context";
@ -495,9 +510,11 @@ TEST(PreferenceTest, CustomDefaults) {
CefWaitableEvent::CreateWaitableEvent(true, false); CefWaitableEvent::CreateWaitableEvent(true, false);
CefRequestContextSettings settings; CefRequestContextSettings settings;
CefRefPtr<CefRequestContext> context = CefRefPtr<CefRequestContext> context = CefRequestContext::CreateContext(
CefRequestContext::CreateContext(settings, nullptr); settings, new TestRequestContextHandler(event));
EXPECT_TRUE(context.get()); EXPECT_TRUE(context.get());
// Wait for the context to be fully initialized.
event->Wait();
ValidateDefaults(context, false, event); ValidateDefaults(context, false, event);
event->Wait(); event->Wait();
@ -509,9 +526,11 @@ TEST(PreferenceTest, CustomSetGet) {
CefWaitableEvent::CreateWaitableEvent(true, false); CefWaitableEvent::CreateWaitableEvent(true, false);
CefRequestContextSettings settings; CefRequestContextSettings settings;
CefRefPtr<CefRequestContext> context = CefRefPtr<CefRequestContext> context = CefRequestContext::CreateContext(
CefRequestContext::CreateContext(settings, nullptr); settings, new TestRequestContextHandler(event));
EXPECT_TRUE(context.get()); EXPECT_TRUE(context.get());
// Wait for the context to be fully initialized.
event->Wait();
ValidateSetGet(context, event); ValidateSetGet(context, event);
event->Wait(); event->Wait();
@ -527,9 +546,11 @@ TEST(PreferenceTest, CustomSetGetShared) {
CefWaitableEvent::CreateWaitableEvent(true, false); CefWaitableEvent::CreateWaitableEvent(true, false);
CefRequestContextSettings settings; CefRequestContextSettings settings;
CefRefPtr<CefRequestContext> context = CefRefPtr<CefRequestContext> context = CefRequestContext::CreateContext(
CefRequestContext::CreateContext(settings, nullptr); settings, new TestRequestContextHandler(event));
EXPECT_TRUE(context.get()); EXPECT_TRUE(context.get());
// Wait for the context to be fully initialized.
event->Wait();
// Sharing storage. // Sharing storage.
CefRefPtr<CefRequestContext> context2 = CefRefPtr<CefRequestContext> context2 =
@ -542,9 +563,11 @@ TEST(PreferenceTest, CustomSetGetShared) {
EXPECT_TRUE(context3.get()); EXPECT_TRUE(context3.get());
// Unassociated context. // Unassociated context.
CefRefPtr<CefRequestContext> context4 = CefRefPtr<CefRequestContext> context4 = CefRequestContext::CreateContext(
CefRequestContext::CreateContext(settings, nullptr); settings, new TestRequestContextHandler(event));
EXPECT_TRUE(context4.get()); EXPECT_TRUE(context4.get());
// Wait for the context to be fully initialized.
event->Wait();
// Set/get the values on the first context. // Set/get the values on the first context.
*PendingAction() = "Set/get the values on the first context"; *PendingAction() = "Set/get the values on the first context";