From 0000000000000000000000000000000000000000 Mon Sep 17 00:00:00 2001 From: Jeremy Apthorp Date: Tue, 12 Nov 2019 11:50:16 -0800 Subject: add TrustedAuthClient to URLLoaderFactory This allows intercepting authentication requests for the 'net' module. Without this, the 'login' event for electron.net.ClientRequest can't be implemented, because the existing path checks for the presence of a WebContents, and cancels the authentication if there's no WebContents available, which there isn't in the case of the 'net' module. diff --git a/services/network/public/mojom/network_context.mojom b/services/network/public/mojom/network_context.mojom index 41f5c3db2171cbe015dcb8c6a4436b94c377fec8..621dcf406e899ed9561568a812b6eea042e8c427 100644 --- a/services/network/public/mojom/network_context.mojom +++ b/services/network/public/mojom/network_context.mojom @@ -214,6 +214,25 @@ struct CTPolicy { array excluded_legacy_spkis; }; +interface TrustedAuthClient { + OnAuthRequired( + mojo_base.mojom.UnguessableToken? window_id, + uint32 process_id, + uint32 routing_id, + uint32 request_id, + url.mojom.Url url, + bool first_auth_attempt, + AuthChallengeInfo auth_info, + URLResponseHead? head, + pending_remote auth_challenge_responder); +}; +interface TrustedURLLoaderAuthClient { + // When a new URLLoader is created, this will be called to pass a + // corresponding |auth_client|. + OnLoaderCreated(int32 request_id, + pending_receiver auth_client); +}; + interface CertVerifierClient { Verify( int32 default_error, @@ -640,6 +659,8 @@ struct URLLoaderFactoryParams { // impact because of the extra process hops, so use should be minimized. pending_remote? header_client; + pending_remote? auth_client; + // |factory_bound_access_patterns| are used for CORS checks in addition to // the per-context allow patterns that is managed via NetworkContext // interface. This still respects the per-context block lists. diff --git a/services/network/url_loader.cc b/services/network/url_loader.cc index a5c25e290ef79c33117e14c02c05c86ebd558527..b21b39385ba3a15546eb38a26cb14a317bb64227 100644 --- a/services/network/url_loader.cc +++ b/services/network/url_loader.cc @@ -472,6 +472,7 @@ URLLoader::URLLoader( base::WeakPtr keepalive_statistics_recorder, base::WeakPtr network_usage_accumulator, mojom::TrustedURLLoaderHeaderClient* url_loader_header_client, + mojom::TrustedURLLoaderAuthClient* url_loader_auth_client, mojom::OriginPolicyManager* origin_policy_manager, std::unique_ptr trust_token_helper_factory, mojo::PendingRemote cookie_observer) @@ -535,6 +536,11 @@ URLLoader::URLLoader( header_client_.set_disconnect_handler( base::BindOnce(&URLLoader::OnMojoDisconnect, base::Unretained(this))); } + if (url_loader_auth_client) { + url_loader_auth_client->OnLoaderCreated(request_id_, auth_client_.BindNewPipeAndPassReceiver()); + auth_client_.set_disconnect_handler( + base::BindOnce(&URLLoader::OnMojoDisconnect, base::Unretained(this))); + } if (want_raw_headers_) { options_ |= mojom::kURLLoadOptionSendSSLInfoWithResponse | mojom::kURLLoadOptionSendSSLInfoForCertificateError; @@ -1062,7 +1068,7 @@ void URLLoader::OnAuthRequired(net::URLRequest* url_request, // |this| may have been deleted. return; } - if (!network_context_client_) { + if (!network_context_client_ && !auth_client_) { OnAuthCredentials(base::nullopt); return; } @@ -1078,11 +1084,20 @@ void URLLoader::OnAuthRequired(net::URLRequest* url_request, if (url_request->response_headers()) head->headers = url_request->response_headers(); head->auth_challenge_info = auth_info; - network_context_client_->OnAuthRequired( - fetch_window_id_, factory_params_->process_id, render_frame_id_, - request_id_, url_request_->url(), first_auth_attempt_, auth_info, - std::move(head), - auth_challenge_responder_receiver_.BindNewPipeAndPassRemote()); + + if (auth_client_) { + auth_client_->OnAuthRequired( + fetch_window_id_, factory_params_->process_id, render_frame_id_, + request_id_, url_request_->url(), first_auth_attempt_, auth_info, + std::move(head), + auth_challenge_responder_receiver_.BindNewPipeAndPassRemote()); + } else { + network_context_client_->OnAuthRequired( + fetch_window_id_, factory_params_->process_id, render_frame_id_, + request_id_, url_request_->url(), first_auth_attempt_, auth_info, + std::move(head), + auth_challenge_responder_receiver_.BindNewPipeAndPassRemote()); + } auth_challenge_responder_receiver_.set_disconnect_handler( base::BindOnce(&URLLoader::DeleteSelf, base::Unretained(this))); diff --git a/services/network/url_loader.h b/services/network/url_loader.h index 9f4d85ca7913c8de998e18560c6755cec51135d8..04748acc74ce55a335abb1865bb9bef9ae7a33c6 100644 --- a/services/network/url_loader.h +++ b/services/network/url_loader.h @@ -116,6 +116,7 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader base::WeakPtr keepalive_statistics_recorder, base::WeakPtr network_usage_accumulator, mojom::TrustedURLLoaderHeaderClient* url_loader_header_client, + mojom::TrustedURLLoaderAuthClient* url_loader_auth_client, mojom::OriginPolicyManager* origin_policy_manager, std::unique_ptr trust_token_helper_factory, @@ -457,6 +458,7 @@ class COMPONENT_EXPORT(NETWORK_SERVICE) URLLoader base::Optional fetch_window_id_; mojo::Remote header_client_; + mojo::Remote auth_client_; std::unique_ptr file_opener_for_upload_; diff --git a/services/network/url_loader_factory.cc b/services/network/url_loader_factory.cc index 75ae8488efa7e5acfda0b21029657b525fa95f86..5dce71ee5efc97f9f63d0b5f236dccdfb05cfc79 100644 --- a/services/network/url_loader_factory.cc +++ b/services/network/url_loader_factory.cc @@ -75,6 +75,7 @@ URLLoaderFactory::URLLoaderFactory( resource_scheduler_client_(std::move(resource_scheduler_client)), header_client_(std::move(params_->header_client)), coep_reporter_(std::move(params_->coep_reporter)), + auth_client_(std::move(params_->auth_client)), cors_url_loader_factory_(cors_url_loader_factory), cookie_observer_(std::move(params_->cookie_observer)) { DCHECK(context); @@ -254,6 +255,7 @@ void URLLoaderFactory::CreateLoaderAndStart( std::move(keepalive_statistics_recorder), std::move(network_usage_accumulator), header_client_.is_bound() ? header_client_.get() : nullptr, + auth_client_.is_bound() ? auth_client_.get() : nullptr, context_->origin_policy_manager(), std::move(trust_token_factory), std::move(cookie_observer)); diff --git a/services/network/url_loader_factory.h b/services/network/url_loader_factory.h index 8b29b67a5b0663778df3169e09bf818e6bbcec3f..e504fa3d41066907a3fbc41e69daac968415dfa6 100644 --- a/services/network/url_loader_factory.h +++ b/services/network/url_loader_factory.h @@ -75,6 +75,7 @@ class URLLoaderFactory : public mojom::URLLoaderFactory { scoped_refptr resource_scheduler_client_; mojo::Remote header_client_; mojo::Remote coep_reporter_; + mojo::Remote auth_client_; // |cors_url_loader_factory_| owns this. cors::CorsURLLoaderFactory* cors_url_loader_factory_;