Commit 34080e1b authored by Matt Menke's avatar Matt Menke Committed by Commit Bot

ChromeURLRequestContextGetter: Initialize on construction.

Previously, they were initialized on first use, however, now that
initialization sets up NetworkContexts when the network service is
disabled, relying on the first use of the class through the
ChromeURLRequestContextGetter API before setting up the NetworkContext
could cause problems.

Bug: 847555
Change-Id: I2aaac7e717e64fb41ba2fb9141506bb7512b73fa
Reviewed-on: https://chromium-review.googlesource.com/1169319Reviewed-by: default avatarMaks Orlovich <morlovich@chromium.org>
Commit-Queue: Matt Menke <mmenke@chromium.org>
Cr-Commit-Position: refs/heads/master@{#582188}
parent c5bf413b
......@@ -167,37 +167,50 @@ class FactoryForMedia : public ChromeURLRequestContextFactory {
// ChromeURLRequestContextGetter
// ----------------------------------------------------------------------------
ChromeURLRequestContextGetter::ChromeURLRequestContextGetter(
ChromeURLRequestContextFactory* factory)
: factory_(factory),
url_request_context_(nullptr) {
DCHECK(factory);
}
ChromeURLRequestContextGetter::ChromeURLRequestContextGetter()
: url_request_context_(nullptr) {}
ChromeURLRequestContextGetter::~ChromeURLRequestContextGetter() {
// NotifyContextShuttingDown() must have been called.
DCHECK(!factory_.get());
DCHECK(!url_request_context_);
}
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::CreateAndInit(
std::unique_ptr<ChromeURLRequestContextFactory> factory) {
scoped_refptr<ChromeURLRequestContextGetter> url_request_context_getter(
new ChromeURLRequestContextGetter());
// This can't be done in the constructor because it's possible for the task to
// run and complete before the constructor returns, which would reduce the
// reference count from 1 to 0 on completion, and delete the object
// immediately.
content::BrowserThread::PostTask(
content::BrowserThread::IO, FROM_HERE,
base::BindOnce(&ChromeURLRequestContextGetter::Init,
url_request_context_getter,
base::Passed(std::move(factory))));
return url_request_context_getter;
}
void ChromeURLRequestContextGetter::Init(
std::unique_ptr<ChromeURLRequestContextFactory> factory) {
DCHECK(factory);
DCHECK(!url_request_context_);
url_request_context_ = factory->Create();
}
// Lazily create a URLRequestContext using our factory.
net::URLRequestContext*
ChromeURLRequestContextGetter::GetURLRequestContext() {
DCHECK_CURRENTLY_ON(BrowserThread::IO);
if (factory_.get()) {
DCHECK(!url_request_context_);
url_request_context_ = factory_->Create();
factory_.reset();
}
return url_request_context_;
}
void ChromeURLRequestContextGetter::NotifyContextShuttingDown() {
DCHECK_CURRENTLY_ON(BrowserThread::IO);
factory_.reset();
url_request_context_ = nullptr;
URLRequestContextGetter::NotifyContextShuttingDown();
}
......@@ -208,33 +221,37 @@ ChromeURLRequestContextGetter::GetNetworkTaskRunner() const {
}
// static
ChromeURLRequestContextGetter* ChromeURLRequestContextGetter::Create(
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::Create(
Profile* profile,
const ProfileIOData* profile_io_data,
content::ProtocolHandlerMap* protocol_handlers,
content::URLRequestInterceptorScopedVector request_interceptors) {
return new ChromeURLRequestContextGetter(new FactoryForMain(
profile_io_data, protocol_handlers, std::move(request_interceptors)));
return ChromeURLRequestContextGetter::CreateAndInit(
std::make_unique<FactoryForMain>(profile_io_data, protocol_handlers,
std::move(request_interceptors)));
}
// static
ChromeURLRequestContextGetter*
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::CreateForMedia(
Profile* profile, const ProfileIOData* profile_io_data) {
return new ChromeURLRequestContextGetter(
new FactoryForMedia(profile_io_data));
Profile* profile,
const ProfileIOData* profile_io_data) {
return ChromeURLRequestContextGetter::CreateAndInit(
std::make_unique<FactoryForMedia>(profile_io_data));
}
// static
ChromeURLRequestContextGetter*
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::CreateForExtensions(
Profile* profile, const ProfileIOData* profile_io_data) {
return new ChromeURLRequestContextGetter(
new FactoryForExtensions(profile_io_data));
Profile* profile,
const ProfileIOData* profile_io_data) {
return ChromeURLRequestContextGetter::CreateAndInit(
std::make_unique<FactoryForExtensions>(profile_io_data));
}
// static
ChromeURLRequestContextGetter*
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::CreateForIsolatedApp(
Profile* profile,
const ProfileIOData* profile_io_data,
......@@ -245,20 +262,21 @@ ChromeURLRequestContextGetter::CreateForIsolatedApp(
content::URLRequestInterceptorScopedVector request_interceptors) {
ChromeURLRequestContextGetter* main_context =
static_cast<ChromeURLRequestContextGetter*>(profile->GetRequestContext());
return new ChromeURLRequestContextGetter(new FactoryForIsolatedApp(
profile_io_data, partition_descriptor, main_context,
std::move(protocol_handler_interceptor), protocol_handlers,
std::move(request_interceptors)));
return ChromeURLRequestContextGetter::CreateAndInit(
std::make_unique<FactoryForIsolatedApp>(
profile_io_data, partition_descriptor, main_context,
std::move(protocol_handler_interceptor), protocol_handlers,
std::move(request_interceptors)));
}
// static
ChromeURLRequestContextGetter*
scoped_refptr<ChromeURLRequestContextGetter>
ChromeURLRequestContextGetter::CreateForIsolatedMedia(
Profile* profile,
ChromeURLRequestContextGetter* app_context,
const ProfileIOData* profile_io_data,
const StoragePartitionDescriptor& partition_descriptor) {
return new ChromeURLRequestContextGetter(
new FactoryForIsolatedMedia(
return ChromeURLRequestContextGetter::CreateAndInit(
std::make_unique<FactoryForIsolatedMedia>(
profile_io_data, partition_descriptor, app_context));
}
......@@ -28,11 +28,6 @@ struct StoragePartitionDescriptor;
// the destructor and GetURLRequestContext().
class ChromeURLRequestContextGetter : public net::URLRequestContextGetter {
public:
// Constructs a ChromeURLRequestContextGetter that will use |factory| to
// create the URLRequestContext.
explicit ChromeURLRequestContextGetter(
ChromeURLRequestContextFactory* factory);
// Note that GetURLRequestContext() can only be called from the IO
// thread (it will assert otherwise).
// GetIOTaskRunner however can be called from any thread.
......@@ -44,7 +39,7 @@ class ChromeURLRequestContextGetter : public net::URLRequestContextGetter {
// Create an instance for use with an 'original' (non-OTR) profile. This is
// expected to get called on the UI thread.
static ChromeURLRequestContextGetter* Create(
static scoped_refptr<ChromeURLRequestContextGetter> Create(
Profile* profile,
const ProfileIOData* profile_io_data,
content::ProtocolHandlerMap* protocol_handlers,
......@@ -53,17 +48,19 @@ class ChromeURLRequestContextGetter : public net::URLRequestContextGetter {
// Create an instance for an original profile for media. This is expected to
// get called on UI thread. This method takes a profile and reuses the
// 'original' net::URLRequestContext for common files.
static ChromeURLRequestContextGetter* CreateForMedia(
Profile* profile, const ProfileIOData* profile_io_data);
static scoped_refptr<ChromeURLRequestContextGetter> CreateForMedia(
Profile* profile,
const ProfileIOData* profile_io_data);
// Create an instance for an original profile for extensions. This is expected
// to get called on UI thread.
static ChromeURLRequestContextGetter* CreateForExtensions(
Profile* profile, const ProfileIOData* profile_io_data);
static scoped_refptr<ChromeURLRequestContextGetter> CreateForExtensions(
Profile* profile,
const ProfileIOData* profile_io_data);
// Create an instance for an original profile for an app with isolated
// storage. This is expected to get called on UI thread.
static ChromeURLRequestContextGetter* CreateForIsolatedApp(
static scoped_refptr<ChromeURLRequestContextGetter> CreateForIsolatedApp(
Profile* profile,
const ProfileIOData* profile_io_data,
const StoragePartitionDescriptor& partition_descriptor,
......@@ -74,7 +71,7 @@ class ChromeURLRequestContextGetter : public net::URLRequestContextGetter {
// Create an instance for an original profile for media with isolated
// storage. This is expected to get called on UI thread.
static ChromeURLRequestContextGetter* CreateForIsolatedMedia(
static scoped_refptr<ChromeURLRequestContextGetter> CreateForIsolatedMedia(
Profile* profile,
ChromeURLRequestContextGetter* app_context,
const ProfileIOData* profile_io_data,
......@@ -85,15 +82,21 @@ class ChromeURLRequestContextGetter : public net::URLRequestContextGetter {
void NotifyContextShuttingDown();
private:
ChromeURLRequestContextGetter();
~ChromeURLRequestContextGetter() override;
// Deferred logic for creating a URLRequestContext.
// Access only from the IO thread.
std::unique_ptr<ChromeURLRequestContextFactory> factory_;
// Called on IO thread. Calls |factory's| Create method and populates
// |url_request_context_|, which is actually owned by the ProfileIOData.
void Init(std::unique_ptr<ChromeURLRequestContextFactory> factory);
// Should be used instead of constructor. Both creates object and triggers
// initialization on the IO thread.
static scoped_refptr<ChromeURLRequestContextGetter> CreateAndInit(
std::unique_ptr<ChromeURLRequestContextFactory> factory);
// NULL before initialization and after invalidation.
// Otherwise, it is the URLRequestContext instance that
// was lazily created by GetURLRequestContext().
// Otherwise, it is the URLRequestContext instance that was created by the
// |factory| used by Init(). The object is owned by the ProfileIOData.
// Access only from the IO thread.
net::URLRequestContext* url_request_context_;
......
......@@ -145,7 +145,7 @@ OffTheRecordProfileIOData::Handle::CreateIsolatedAppRequestContextGetter(
protocol_handler_interceptor(
ProtocolHandlerRegistryFactory::GetForBrowserContext(profile_)
->CreateJobInterceptorFactory());
ChromeURLRequestContextGetter* context =
scoped_refptr<ChromeURLRequestContextGetter> context =
ChromeURLRequestContextGetter::CreateForIsolatedApp(
profile_, io_data_, descriptor,
std::move(protocol_handler_interceptor), protocol_handlers,
......
......@@ -324,14 +324,14 @@ ProfileImplIOData::Handle::CreateIsolatedAppRequestContextGetter(
protocol_handler_interceptor(
ProtocolHandlerRegistryFactory::GetForBrowserContext(profile_)
->CreateJobInterceptorFactory());
ChromeURLRequestContextGetter* context =
scoped_refptr<ChromeURLRequestContextGetter> context =
ChromeURLRequestContextGetter::CreateForIsolatedApp(
profile_, io_data_, descriptor,
std::move(protocol_handler_interceptor), protocol_handlers,
std::move(request_interceptors));
app_request_context_getter_map_[descriptor] = context;
return context;
return context.get();
}
scoped_refptr<ChromeURLRequestContextGetter>
......@@ -357,7 +357,7 @@ ProfileImplIOData::Handle::GetIsolatedMediaRequestContextGetter(
app_request_context_getter_map_.find(descriptor);
DCHECK(app_iter != app_request_context_getter_map_.end());
ChromeURLRequestContextGetter* app_context = app_iter->second.get();
ChromeURLRequestContextGetter* context =
scoped_refptr<ChromeURLRequestContextGetter> context =
ChromeURLRequestContextGetter::CreateForIsolatedMedia(
profile_, app_context, io_data_, descriptor);
isolated_media_request_context_getter_map_[descriptor] = context;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment