From: csagan5 <32685696+csagan5@users.noreply.github.com> Date: Wed, 30 Oct 2019 11:50:13 +0100 Subject: Block all connection requests with 'qjz9zk' in the domain name or with a 'trk:' scheme. An info bar is displayed unless the --disable-trkbar command-line flag or the chrome://flag option is used. This patch is based on Iridium's 'net: add "trk:" scheme and help identify URLs being retrieved' --- .../chrome_autocomplete_scheme_classifier.cc | 1 + chrome/browser/history/history_utils.cc | 1 + chrome/browser/ui/singleton_tabs.cc | 3 +- .../omnibox/browser/autocomplete_input.cc | 7 +++-- components/url_formatter/url_fixer.cc | 4 +++ .../child_process_security_policy_impl.cc | 1 + net/BUILD.gn | 2 ++ net/url_request/trk_protocol_handler.cc | 25 +++++++++++++++ net/url_request/trk_protocol_handler.h | 31 +++++++++++++++++++ net/url_request/url_request.cc | 8 +++++ .../url_request_context_builder.cc | 3 ++ url/url_constants.cc | 1 + url/url_constants.h | 1 + url/url_util.cc | 2 ++ 14 files changed, 87 insertions(+), 3 deletions(-) create mode 100644 net/url_request/trk_protocol_handler.cc create mode 100644 net/url_request/trk_protocol_handler.h diff --git a/chrome/browser/autocomplete/chrome_autocomplete_scheme_classifier.cc b/chrome/browser/autocomplete/chrome_autocomplete_scheme_classifier.cc --- a/chrome/browser/autocomplete/chrome_autocomplete_scheme_classifier.cc +++ b/chrome/browser/autocomplete/chrome_autocomplete_scheme_classifier.cc @@ -56,6 +56,7 @@ ChromeAutocompleteSchemeClassifier::GetInputTypeForScheme( if (base::IsStringASCII(scheme) && (ProfileIOData::IsHandledProtocol(scheme) || base::LowerCaseEqualsASCII(scheme, content::kViewSourceScheme) || + base::LowerCaseEqualsASCII(scheme, url::kTraceScheme) || base::LowerCaseEqualsASCII(scheme, url::kJavaScriptScheme) || base::LowerCaseEqualsASCII(scheme, url::kDataScheme))) { return metrics::OmniboxInputType::URL; diff --git a/chrome/browser/history/history_utils.cc b/chrome/browser/history/history_utils.cc --- a/chrome/browser/history/history_utils.cc +++ b/chrome/browser/history/history_utils.cc @@ -21,6 +21,7 @@ bool CanAddURLToHistory(const GURL& url) { url.SchemeIs(content::kChromeDevToolsScheme) || url.SchemeIs(content::kChromeUIScheme) || url.SchemeIs(content::kViewSourceScheme) || + url.SchemeIs(url::kTraceScheme) || url.SchemeIs(chrome::kChromeNativeScheme) || url.SchemeIs(chrome::kChromeSearchScheme) || url.SchemeIs(dom_distiller::kDomDistillerScheme)) diff --git a/chrome/browser/ui/singleton_tabs.cc b/chrome/browser/ui/singleton_tabs.cc --- a/chrome/browser/ui/singleton_tabs.cc +++ b/chrome/browser/ui/singleton_tabs.cc @@ -99,7 +99,8 @@ int GetIndexOfExistingTab(Browser* browser, const NavigateParams& params) { // Skip view-source tabs. This is needed because RewriteURLIfNecessary // removes the "view-source:" scheme which leads to incorrect matching. - if (tab_url.SchemeIs(content::kViewSourceScheme)) + if (tab_url.SchemeIs(content::kViewSourceScheme) || + tab_url.SchemeIs(url::kTraceScheme)) continue; GURL rewritten_tab_url = tab_url; diff --git a/components/omnibox/browser/autocomplete_input.cc b/components/omnibox/browser/autocomplete_input.cc --- a/components/omnibox/browser/autocomplete_input.cc +++ b/components/omnibox/browser/autocomplete_input.cc @@ -486,7 +486,8 @@ void AutocompleteInput::ParseForEmphasizeComponents( // For the view-source and blob schemes, we should emphasize the host of the // URL qualified by the view-source or blob prefix. if ((base::LowerCaseEqualsASCII(scheme_str, kViewSourceScheme) || - base::LowerCaseEqualsASCII(scheme_str, url::kBlobScheme)) && + base::LowerCaseEqualsASCII(scheme_str, url::kBlobScheme) || + base::LowerCaseEqualsASCII(scheme_str, url::kTraceScheme)) && (static_cast(text.length()) > after_scheme_and_colon)) { // Obtain the URL prefixed by view-source or blob and parse it. base::string16 real_url(text.substr(after_scheme_and_colon)); @@ -559,7 +560,9 @@ int AutocompleteInput::NumNonHostComponents(const url::Parsed& parts) { bool AutocompleteInput::HasHTTPScheme(const base::string16& input) { std::string utf8_input(base::UTF16ToUTF8(input)); url::Component scheme; - if (url::FindAndCompareScheme(utf8_input, kViewSourceScheme, &scheme)) { + if (url::FindAndCompareScheme(utf8_input, url::kTraceScheme, &scheme)) { + return false; + } else if (url::FindAndCompareScheme(utf8_input, kViewSourceScheme, &scheme)) { utf8_input.erase(0, scheme.end() + 1); } return url::FindAndCompareScheme(utf8_input, url::kHttpScheme, nullptr); diff --git a/components/url_formatter/url_fixer.cc b/components/url_formatter/url_fixer.cc --- a/components/url_formatter/url_fixer.cc +++ b/components/url_formatter/url_fixer.cc @@ -560,6 +560,10 @@ GURL FixupURL(const std::string& text, const std::string& desired_tld) { } } + if (scheme == url::kTraceScheme) { + return GURL(); + } + // We handle the file scheme separately. if (scheme == url::kFileScheme) return GURL(parts.scheme.is_valid() ? text : FixupPath(text)); diff --git a/content/browser/child_process_security_policy_impl.cc b/content/browser/child_process_security_policy_impl.cc --- a/content/browser/child_process_security_policy_impl.cc +++ b/content/browser/child_process_security_policy_impl.cc @@ -767,6 +767,7 @@ ChildProcessSecurityPolicyImpl::ChildProcessSecurityPolicyImpl() { #endif // BUILDFLAG(ENABLE_WEBSOCKETS) RegisterWebSafeScheme(url::kFtpScheme); RegisterWebSafeScheme(url::kDataScheme); + RegisterWebSafeScheme(url::kTraceScheme); RegisterWebSafeScheme("feed"); // TODO(nick): https://crbug.com/651534 blob: and filesystem: schemes embed diff --git a/net/BUILD.gn b/net/BUILD.gn --- a/net/BUILD.gn +++ b/net/BUILD.gn @@ -1083,6 +1083,8 @@ component("net") { "url_request/report_sender.h", "url_request/static_http_user_agent_settings.cc", "url_request/static_http_user_agent_settings.h", + "url_request/trk_protocol_handler.cc", + "url_request/trk_protocol_handler.h", "url_request/url_fetcher.cc", "url_request/url_fetcher.h", "url_request/url_fetcher_core.cc", diff --git a/net/url_request/trk_protocol_handler.cc b/net/url_request/trk_protocol_handler.cc new file mode 100644 --- /dev/null +++ b/net/url_request/trk_protocol_handler.cc @@ -0,0 +1,25 @@ +// Copyright (c) 2018 The ungoogled-chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#include "net/url_request/trk_protocol_handler.h" + +#include "base/logging.h" +#include "net/base/net_errors.h" +#include "net/url_request/url_request_error_job.h" + +namespace net { + +TrkProtocolHandler::TrkProtocolHandler() = default; + +std::unique_ptr TrkProtocolHandler::CreateJob( + URLRequest* request) const { + LOG(ERROR) << "Blocked URL in TrkProtocolHandler: " << request->original_url(); + return std::make_unique(request, ERR_BLOCKED_BY_CLIENT); +} + +bool TrkProtocolHandler::IsSafeRedirectTarget(const GURL& location) const { + return true; +} + +} // namespace net diff --git a/net/url_request/trk_protocol_handler.h b/net/url_request/trk_protocol_handler.h new file mode 100644 --- /dev/null +++ b/net/url_request/trk_protocol_handler.h @@ -0,0 +1,31 @@ +// Copyright (c) 2018 The ungoogled-chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef NET_URL_REQUEST_TRK_PROTOCOL_HANDLER_H_ +#define NET_URL_REQUEST_TRK_PROTOCOL_HANDLER_H_ + +#include "base/compiler_specific.h" +#include "base/macros.h" +#include "net/base/net_export.h" +#include "net/url_request/url_request_job_factory.h" + +namespace net { + +class URLRequestJob; + +// Implements a ProtocolHandler for Trk jobs. +class NET_EXPORT TrkProtocolHandler + : public URLRequestJobFactory::ProtocolHandler { + public: + TrkProtocolHandler(); + std::unique_ptr CreateJob(URLRequest* request) const override; + bool IsSafeRedirectTarget(const GURL& location) const override; + + private: + DISALLOW_COPY_AND_ASSIGN(TrkProtocolHandler); +}; + +} // namespace net + +#endif // NET_URL_REQUEST_TRK_PROTOCOL_HANDLER_H_ diff --git a/net/url_request/url_request.cc b/net/url_request/url_request.cc --- a/net/url_request/url_request.cc +++ b/net/url_request/url_request.cc @@ -13,6 +13,7 @@ #include "base/metrics/histogram_macros.h" #include "base/rand_util.h" #include "base/stl_util.h" +#include "base/strings/string_util.h" #include "base/strings/utf_string_conversions.h" #include "base/synchronization/lock.h" #include "base/threading/thread_task_runner_handle.h" @@ -40,6 +41,7 @@ #include "net/url_request/url_request_redirect_job.h" #include "url/gurl.h" #include "url/origin.h" +#include "url/url_constants.h" using base::Time; using std::string; @@ -566,6 +568,12 @@ URLRequest::URLRequest(const GURL& url, // Sanity check out environment. DCHECK(base::ThreadTaskRunnerHandle::IsSet()); + if (!url.SchemeIs(url::kTraceScheme) && + base::EndsWith(url.host(), "qjz9zk", base::CompareCase::INSENSITIVE_ASCII)) { + LOG(ERROR) << "Block URL in URLRequest: " << url; + url_chain_[0] = GURL(url::kTraceScheme + (":" + url.possibly_invalid_spec())); + } + context->url_requests()->insert(this); net_log_.BeginEvent(NetLogEventType::REQUEST_ALIVE, [&] { return NetLogURLRequestConstructorParams(url, priority_, diff --git a/net/url_request/url_request_context_builder.cc b/net/url_request/url_request_context_builder.cc --- a/net/url_request/url_request_context_builder.cc +++ b/net/url_request/url_request_context_builder.cc @@ -44,6 +44,7 @@ #include "net/quic/quic_stream_factory.h" #include "net/ssl/ssl_config_service_defaults.h" #include "net/url_request/static_http_user_agent_settings.h" +#include "net/url_request/trk_protocol_handler.h" #include "net/url_request/url_request_context.h" #include "net/url_request/url_request_context_storage.h" #include "net/url_request/url_request_job_factory.h" @@ -614,6 +615,8 @@ std::unique_ptr URLRequestContextBuilder::Build() { job_factory->SetProtocolHandler(scheme_handler.first, std::move(scheme_handler.second)); } + job_factory->SetProtocolHandler(url::kTraceScheme, + std::make_unique()); protocol_handlers_.clear(); #if !BUILDFLAG(DISABLE_FTP_SUPPORT) diff --git a/url/url_constants.cc b/url/url_constants.cc --- a/url/url_constants.cc +++ b/url/url_constants.cc @@ -28,6 +28,7 @@ const char kMailToScheme[] = "mailto"; // See also: https://www.iana.org/assignments/uri-schemes/prov/quic-transport const char kQuicTransportScheme[] = "quic-transport"; const char kTelScheme[] = "tel"; +const char kTraceScheme[] = "trk"; const char kWsScheme[] = "ws"; const char kWssScheme[] = "wss"; diff --git a/url/url_constants.h b/url/url_constants.h --- a/url/url_constants.h +++ b/url/url_constants.h @@ -32,6 +32,7 @@ COMPONENT_EXPORT(URL) extern const char kJavaScriptScheme[]; COMPONENT_EXPORT(URL) extern const char kMailToScheme[]; COMPONENT_EXPORT(URL) extern const char kQuicTransportScheme[]; COMPONENT_EXPORT(URL) extern const char kTelScheme[]; +COMPONENT_EXPORT(URL) extern const char kTraceScheme[]; COMPONENT_EXPORT(URL) extern const char kWsScheme[]; COMPONENT_EXPORT(URL) extern const char kWssScheme[]; diff --git a/url/url_util.cc b/url/url_util.cc --- a/url/url_util.cc +++ b/url/url_util.cc @@ -34,6 +34,7 @@ struct SchemeRegistry { std::vector standard_schemes = { {kHttpsScheme, SCHEME_WITH_HOST_PORT_AND_USER_INFORMATION}, {kHttpScheme, SCHEME_WITH_HOST_PORT_AND_USER_INFORMATION}, + {kTraceScheme, SCHEME_WITH_HOST_PORT_AND_USER_INFORMATION}, // Yes, file URLs can have a hostname, so file URLs should be handled as // "standard". File URLs never have a port as specified by the SchemeType // field. Unlike other SCHEME_WITH_HOST schemes, the 'host' in a file @@ -77,6 +78,7 @@ struct SchemeRegistry { kAboutScheme, kJavaScriptScheme, kDataScheme, + kTraceScheme, }; // Schemes that can be sent CORS requests. -- 2.17.1