From f514f849243f39cd926ae37ee835355034593d2b Mon Sep 17 00:00:00 2001 From: cobalt-github-releaser-bot <95661244+cobalt-github-releaser-bot@users.noreply.github.com> Date: Tue, 13 Aug 2024 16:07:58 -0700 Subject: [PATCH] Cherry pick PR #3979: Add disable_h2 and matching h5vcc.settings (#3980) Refer to the original PR: https://github.com/youtube/cobalt/pull/3979 This adds a command-line switch `disable_h2` that disables the HTTP/2 protocol (spdy), and a matching `h5vcc.settings` parameter 'HTTP2' (with backing by `PersistentSettings`) for run-time disabling of HTTP/2 and spdy. Similar to 'QUIC' and 'HTTP3', the setting takes effect immediately for new connections only. This also ensures that when the command-line parameter `disable_quic` or the new `disable_h2` is used, that that can not be overuled later with `5vcc.settings` or from the corresponding `PersistentSetting`. b/205134049 Co-authored-by: Jelle Foks --- cobalt/h5vcc/h5vcc_settings.cc | 26 +++++++++++++++++++++----- cobalt/network/network_module.cc | 14 ++++++++++++++ cobalt/network/network_module.h | 2 ++ cobalt/network/switches.cc | 3 +++ cobalt/network/switches.h | 1 + cobalt/network/url_request_context.cc | 18 ++++++++++++++++-- cobalt/network/url_request_context.h | 1 + net/http/http_network_session.cc | 15 +++++++++++++++ net/http/http_network_session.h | 1 + net/http/http_stream_factory_job.cc | 1 + 10 files changed, 75 insertions(+), 7 deletions(-) diff --git a/cobalt/h5vcc/h5vcc_settings.cc b/cobalt/h5vcc/h5vcc_settings.cc index 59d76c863024..fa446af4a4a2 100644 --- a/cobalt/h5vcc/h5vcc_settings.cc +++ b/cobalt/h5vcc/h5vcc_settings.cc @@ -51,6 +51,7 @@ bool H5vccSettings::Set(const std::string& name, SetValueType value) const { const char kMediaCodecBlockList[] = "MediaCodecBlockList"; const char kNavigatorUAData[] = "NavigatorUAData"; const char kQUIC[] = "QUIC"; + const char kHTTP2[] = "HTTP2"; #if SB_IS(EVERGREEN) const char kUpdaterMinFreeSpaceBytes[] = "Updater.MinFreeSpaceBytes"; @@ -62,11 +63,6 @@ bool H5vccSettings::Set(const std::string& name, SetValueType value) const { return true; } - if (set_web_setting_func_ && value.IsType() && - set_web_setting_func_.Run(name, value.AsType())) { - return true; - } - if (name.rfind(kMediaPrefix, 0) == 0 && value.IsType()) { return media_module_ ? media_module_->SetConfiguration( @@ -95,12 +91,32 @@ bool H5vccSettings::Set(const std::string& name, SetValueType value) const { } } + if (name.compare(kHTTP2) == 0 && value.IsType()) { + if (!persistent_settings_) { + return false; + } else { + persistent_settings_->SetPersistentSetting( + network::kHttp2EnabledPersistentSettingsKey, + std::make_unique(value.AsType() != 0)); + // Tell NetworkModule (if exists) to re-query persistent settings. + if (network_module_) { + network_module_->SetEnableHttp2FromPersistentSettings(); + } + return true; + } + } + #if SB_IS(EVERGREEN) if (name.compare(kUpdaterMinFreeSpaceBytes) == 0 && value.IsType()) { updater_module_->SetMinFreeSpaceBytes(value.AsType()); return true; } #endif + if (set_web_setting_func_ && value.IsType() && + set_web_setting_func_.Run(name, value.AsType())) { + return true; + } + return false; } diff --git a/cobalt/network/network_module.cc b/cobalt/network/network_module.cc index 888bbe9dc119..aaefae13044d 100644 --- a/cobalt/network/network_module.cc +++ b/cobalt/network/network_module.cc @@ -114,6 +114,19 @@ void NetworkModule::SetEnableQuicFromPersistentSettings() { } } +void NetworkModule::SetEnableHttp2FromPersistentSettings() { + // Called on initialization and when the persistent setting is changed. + if (options_.persistent_settings != nullptr) { + bool enable_http2 = + options_.persistent_settings->GetPersistentSettingAsBool( + kHttp2EnabledPersistentSettingsKey, false); + task_runner()->PostTask( + FROM_HERE, + base::Bind(&URLRequestContext::SetEnableHttp2, + base::Unretained(url_request_context_.get()), enable_http2)); + } +} + void NetworkModule::EnsureStorageManagerStarted() { DCHECK(storage_manager_); storage_manager_->EnsureStarted(); @@ -200,6 +213,7 @@ void NetworkModule::Initialize(const std::string& user_agent_string, url_request_context_.get(), thread_.get()); SetEnableQuicFromPersistentSettings(); + SetEnableHttp2FromPersistentSettings(); } void NetworkModule::OnCreate(base::WaitableEvent* creation_event) { diff --git a/cobalt/network/network_module.h b/cobalt/network/network_module.h index e00a5f1b9b54..dc0209a9c3e4 100644 --- a/cobalt/network/network_module.h +++ b/cobalt/network/network_module.h @@ -63,6 +63,7 @@ enum ClientHintHeadersCallType : int32_t { constexpr int32_t kEnabledClientHintHeaders = (kCallTypeLoader | kCallTypeXHR); const char kQuicEnabledPersistentSettingsKey[] = "QUICEnabled"; +const char kHttp2EnabledPersistentSettingsKey[] = "HTTP2Enabled"; class NetworkSystem; // NetworkModule wraps various networking-related components such as @@ -130,6 +131,7 @@ class NetworkModule : public base::MessageLoop::DestructionObserver { void SetProxy(const std::string& custom_proxy_rules); void SetEnableQuicFromPersistentSettings(); + void SetEnableHttp2FromPersistentSettings(); // Adds the Client Hint Headers to the provided URLFetcher if enabled. void AddClientHintHeaders(net::URLFetcher& url_fetcher, diff --git a/cobalt/network/switches.cc b/cobalt/network/switches.cc index e0c16503b756..494fd5df2b90 100644 --- a/cobalt/network/switches.cc +++ b/cobalt/network/switches.cc @@ -42,6 +42,9 @@ const char kMaxNetworkDelayHelp[] = // Switch to disable use of the Quic network protocol. const char kDisableQuic[] = "disable_quic"; +// Switch to disable use of the HTTP/2 (SPDY) network protocol. +const char kDisableHttp2[] = "disable_h2"; + } // namespace switches } // namespace network } // namespace cobalt diff --git a/cobalt/network/switches.h b/cobalt/network/switches.h index b9fa3a659b2d..293bc128bc2a 100644 --- a/cobalt/network/switches.h +++ b/cobalt/network/switches.h @@ -27,6 +27,7 @@ extern const char kMaxNetworkDelay[]; extern const char kMaxNetworkDelayHelp[]; #endif // ENABLE_DEBUG_COMMAND_LINE_SWITCHES extern const char kDisableQuic[]; +extern const char kDisableHttp2[]; } // namespace switches } // namespace network diff --git a/cobalt/network/url_request_context.cc b/cobalt/network/url_request_context.cc index 2efd31e9c864..22f533b6f86d 100644 --- a/cobalt/network/url_request_context.cc +++ b/cobalt/network/url_request_context.cc @@ -180,8 +180,9 @@ URLRequestContext::URLRequestContext( net::HttpNetworkSession::Params params; + base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); + params.enable_http2 = !command_line->HasSwitch(switches::kDisableHttp2); if (configuration::Configuration::GetInstance()->CobaltEnableQuic()) { - base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); params.enable_quic = !command_line->HasSwitch(switches::kDisableQuic); params.use_quic_for_unknown_origins = params.enable_quic; } @@ -283,7 +284,20 @@ void URLRequestContext::SetProxy(const std::string& proxy_rules) { void URLRequestContext::SetEnableQuic(bool enable_quic) { DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); - storage_.http_network_session()->SetEnableQuic(enable_quic); + base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); + bool quic_commandline_enabled = + !command_line->HasSwitch(switches::kDisableQuic); + storage_.http_network_session()->SetEnableQuic(enable_quic && + quic_commandline_enabled); +} + +void URLRequestContext::SetEnableHttp2(bool enable_http2) { + DCHECK_CALLED_ON_VALID_SEQUENCE(sequence_checker_); + base::CommandLine* command_line = base::CommandLine::ForCurrentProcess(); + bool http2_commandline_enabled = + !command_line->HasSwitch(switches::kDisableHttp2); + storage_.http_network_session()->SetEnableHttp2(enable_http2 && + http2_commandline_enabled); } bool URLRequestContext::using_http_cache() { return using_http_cache_; } diff --git a/cobalt/network/url_request_context.h b/cobalt/network/url_request_context.h index a8e635cd9b4a..747b720a6917 100644 --- a/cobalt/network/url_request_context.h +++ b/cobalt/network/url_request_context.h @@ -52,6 +52,7 @@ class URLRequestContext : public net::URLRequestContext { void SetProxy(const std::string& custom_proxy_rules); void SetEnableQuic(bool enable_quic); + void SetEnableHttp2(bool enable_http2); bool using_http_cache(); diff --git a/net/http/http_network_session.cc b/net/http/http_network_session.cc index ff78b7356b05..3f5aac8ede1d 100644 --- a/net/http/http_network_session.cc +++ b/net/http/http_network_session.cc @@ -550,6 +550,21 @@ void HttpNetworkSession::SetEnableQuic(bool enable_quic) { params_.enable_quic = enable_quic; } +void HttpNetworkSession::SetEnableHttp2(bool enable_http2) { + if (params_.enable_http2 == enable_http2) { + return; + } + params_.enable_http2 = enable_http2; + + if (params_.enable_http2) { + next_protos_.push_back(kProtoHTTP2); + } else { + if (next_protos_.back() == kProtoHTTP2) { + next_protos_.pop_back(); + } + } +} + bool HttpNetworkSession::UseQuicForUnknownOrigin() const { return params_.use_quic_for_unknown_origins; } diff --git a/net/http/http_network_session.h b/net/http/http_network_session.h index 234bb6c4fa01..35ffc0573d6b 100644 --- a/net/http/http_network_session.h +++ b/net/http/http_network_session.h @@ -407,6 +407,7 @@ class NET_EXPORT HttpNetworkSession { void ToggleQuic(); void SetEnableQuic(bool enable_quic); + void SetEnableHttp2(bool enable_http2); // Whether to try QUIC connection for origins without alt-svc on record. bool UseQuicForUnknownOrigin() const; diff --git a/net/http/http_stream_factory_job.cc b/net/http/http_stream_factory_job.cc index ee7e3dfb8a8e..2cd008693608 100644 --- a/net/http/http_stream_factory_job.cc +++ b/net/http/http_stream_factory_job.cc @@ -971,6 +971,7 @@ int HttpStreamFactory::Job::DoInitConnectionImpl() { // actually need to preconnect any sockets, so we're done. if (job_type_ == PRECONNECT) return OK; + negotiated_protocol_ = kProtoHTTP2; using_spdy_ = true; next_state_ = STATE_CREATE_STREAM; return OK;