| Index: chrome/browser/io_thread.cc
 | 
| diff --git a/chrome/browser/io_thread.cc b/chrome/browser/io_thread.cc
 | 
| index 99a914c8229e65878c55c0d0a8716ddabe5f111d..61e4e00d9e9664c7486eeaab6a16e0b5d7760cac 100644
 | 
| --- a/chrome/browser/io_thread.cc
 | 
| +++ b/chrome/browser/io_thread.cc
 | 
| @@ -50,6 +50,7 @@
 | 
|  #include "components/data_usage/core/data_use_annotator.h"
 | 
|  #include "components/metrics/metrics_service.h"
 | 
|  #include "components/net_log/chrome_net_log.h"
 | 
| +#include "components/network_session_configurator/network_session_configurator.h"
 | 
|  #include "components/policy/core/common/policy_service.h"
 | 
|  #include "components/prefs/pref_registry_simple.h"
 | 
|  #include "components/prefs/pref_service.h"
 | 
| @@ -86,12 +87,8 @@
 | 
|  #include "net/proxy/proxy_config_service.h"
 | 
|  #include "net/proxy/proxy_script_fetcher_impl.h"
 | 
|  #include "net/proxy/proxy_service.h"
 | 
| -#include "net/quic/crypto/crypto_protocol.h"
 | 
| -#include "net/quic/quic_protocol.h"
 | 
| -#include "net/quic/quic_utils.h"
 | 
|  #include "net/socket/ssl_client_socket.h"
 | 
|  #include "net/socket/tcp_client_socket.h"
 | 
| -#include "net/spdy/spdy_session.h"
 | 
|  #include "net/ssl/channel_id_service.h"
 | 
|  #include "net/ssl/default_channel_id_store.h"
 | 
|  #include "net/url_request/data_protocol_handler.h"
 | 
| @@ -136,55 +133,11 @@ class SafeBrowsingURLRequestContext;
 | 
|  
 | 
|  namespace {
 | 
|  
 | 
| -const char kTCPFastOpenFieldTrialName[] = "TCPFastOpen";
 | 
| -const char kTCPFastOpenHttpsEnabledGroupName[] = "HttpsEnabled";
 | 
| -
 | 
| -const char kQuicFieldTrialName[] = "QUIC";
 | 
| -const char kQuicFieldTrialEnabledGroupName[] = "Enabled";
 | 
| -const char kQuicFieldTrialHttpsEnabledGroupName[] = "HttpsEnabled";
 | 
| -
 | 
| -// The SPDY trial composes two different trial plus control groups:
 | 
| -//  * A "holdback" group with SPDY disabled, and corresponding control
 | 
| -//  (SPDY/3.1). The primary purpose of the holdback group is to encourage site
 | 
| -//  operators to do feature detection rather than UA-sniffing. As such, this
 | 
| -//  trial runs continuously.
 | 
| -//  * A SPDY/4 experiment, for SPDY/4 (aka HTTP/2) vs SPDY/3.1 comparisons and
 | 
| -//  eventual SPDY/4 deployment.
 | 
| -const char kSpdyFieldTrialName[] = "SPDY";
 | 
| -const char kSpdyFieldTrialHoldbackGroupNamePrefix[] = "SpdyDisabled";
 | 
| -const char kSpdyFieldTrialSpdy31GroupNamePrefix[] = "Spdy31Enabled";
 | 
| -const char kSpdyFieldTrialSpdy4GroupNamePrefix[] = "Spdy4Enabled";
 | 
| -const char kSpdyFieldTrialParametrizedPrefix[] = "Parametrized";
 | 
| -
 | 
| -// The AltSvc trial controls whether Alt-Svc headers are parsed.
 | 
| -// Disabled:
 | 
| -//     Alt-Svc headers are not parsed.
 | 
| -//     Alternate-Protocol headers are parsed.
 | 
| -// Enabled:
 | 
| -//     Alt-Svc headers are parsed, but only same-host entries are used by
 | 
| -//     default.  (Use "enable_alternative_service_with_different_host" QUIC
 | 
| -//     parameter to enable entries with different hosts.)
 | 
| -//     Alternate-Protocol headers are ignored for responses that have an Alt-Svc
 | 
| -//     header.
 | 
| -const char kAltSvcFieldTrialName[] = "ParseAltSvc";
 | 
| -const char kAltSvcFieldTrialDisabledPrefix[] = "AltSvcDisabled";
 | 
| -const char kAltSvcFieldTrialEnabledPrefix[] = "AltSvcEnabled";
 | 
| -
 | 
|  // Field trial for network quality estimator. Seeds RTT and downstream
 | 
|  // throughput observations with values that correspond to the connection type
 | 
|  // determined by the operating system.
 | 
|  const char kNetworkQualityEstimatorFieldTrialName[] = "NetworkQualityEstimator";
 | 
|  
 | 
| -// Field trial for NPN.
 | 
| -const char kNpnTrialName[] = "NPN";
 | 
| -const char kNpnTrialEnabledGroupNamePrefix[] = "Enable";
 | 
| -const char kNpnTrialDisabledGroupNamePrefix[] = "Disable";
 | 
| -
 | 
| -// Field trial for priority dependencies.
 | 
| -const char kSpdyDependenciesFieldTrial[] = "SpdyEnableDependencies";
 | 
| -const char kSpdyDependenciesFieldTrialEnable[] = "Enable";
 | 
| -const char kSpdyDepencenciesFieldTrialDisable[] = "Disable";
 | 
| -
 | 
|  #if defined(OS_MACOSX)
 | 
|  void ObserveKeychainEvents() {
 | 
|    DCHECK_CURRENTLY_ON(BrowserThread::UI);
 | 
| @@ -277,28 +230,6 @@ std::unique_ptr<net::HostResolver> CreateGlobalHostResolver(
 | 
|    return std::move(remapped_resolver);
 | 
|  }
 | 
|  
 | 
| -int GetSwitchValueAsInt(const base::CommandLine& command_line,
 | 
| -                        const std::string& switch_name) {
 | 
| -  int value;
 | 
| -  if (!base::StringToInt(command_line.GetSwitchValueASCII(switch_name),
 | 
| -                         &value)) {
 | 
| -    return 0;
 | 
| -  }
 | 
| -  return value;
 | 
| -}
 | 
| -
 | 
| -// Returns the value associated with |key| in |params| or "" if the
 | 
| -// key is not present in the map.
 | 
| -const std::string& GetVariationParam(
 | 
| -    const std::map<std::string, std::string>& params,
 | 
| -    const std::string& key) {
 | 
| -  std::map<std::string, std::string>::const_iterator it = params.find(key);
 | 
| -  if (it == params.end())
 | 
| -    return base::EmptyString();
 | 
| -
 | 
| -  return it->second;
 | 
| -}
 | 
| -
 | 
|  }  // namespace
 | 
|  
 | 
|  class IOThread::LoggingNetworkChangeObserver
 | 
| @@ -814,8 +745,17 @@ void IOThread::Init() {
 | 
|    // TODO(rch): Make the client socket factory a per-network session instance,
 | 
|    // constructed from a NetworkSession::Params, to allow us to move this option
 | 
|    // to IOThread::Globals & HttpNetworkSession::Params.
 | 
| -  network_session_configurator_.ParseFieldTrialsAndCommandLine(
 | 
| -      is_spdy_allowed_by_policy_, is_quic_allowed_by_policy_, ¶ms_);
 | 
| +  std::string quic_user_agent_id = chrome::GetChannelString();
 | 
| +  if (!quic_user_agent_id.empty())
 | 
| +    quic_user_agent_id.push_back(' ');
 | 
| +  quic_user_agent_id.append(
 | 
| +      version_info::GetProductNameAndVersionForUserAgent());
 | 
| +  quic_user_agent_id.push_back(' ');
 | 
| +  quic_user_agent_id.append(content::BuildOSCpuInfo());
 | 
| +  network_session_configurator::ParseFieldTrialsAndCommandLine(
 | 
| +      is_spdy_allowed_by_policy_, is_quic_allowed_by_policy_,
 | 
| +      quic_user_agent_id, ¶ms_);
 | 
| +
 | 
|    bool always_enable_tfo_if_supported =
 | 
|        command_line.HasSwitch(switches::kEnableTcpFastOpen);
 | 
|    // Check for OS support of TCP FastOpen, and turn it on for all connections if
 | 
| @@ -887,198 +827,6 @@ void IOThread::CleanUp() {
 | 
|  }
 | 
|  
 | 
|  // static
 | 
| -void IOThread::NetworkSessionConfigurator::ParseFieldTrials(
 | 
| -    bool is_spdy_allowed_by_policy,
 | 
| -    bool is_quic_allowed_by_policy,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  const base::CommandLine command_line(base::CommandLine::NO_PROGRAM);
 | 
| -  ParseFieldTrialsAndCommandLineInternal(command_line,
 | 
| -                                         is_spdy_allowed_by_policy,
 | 
| -                                         is_quic_allowed_by_policy, params);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ParseFieldTrialsAndCommandLine(
 | 
| -    bool is_spdy_allowed_by_policy,
 | 
| -    bool is_quic_allowed_by_policy,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  const base::CommandLine& command_line =
 | 
| -      *base::CommandLine::ForCurrentProcess();
 | 
| -  ParseFieldTrialsAndCommandLineInternal(command_line,
 | 
| -                                         is_spdy_allowed_by_policy,
 | 
| -                                         is_quic_allowed_by_policy, params);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::
 | 
| -    ParseFieldTrialsAndCommandLineInternal(
 | 
| -        const base::CommandLine& command_line,
 | 
| -        bool is_spdy_allowed_by_policy,
 | 
| -        bool is_quic_allowed_by_policy,
 | 
| -        net::HttpNetworkSession::Params* params) {
 | 
| -  // Parameters only controlled by command line.
 | 
| -  if (command_line.HasSwitch(switches::kIgnoreCertificateErrors))
 | 
| -    params->ignore_certificate_errors = true;
 | 
| -  if (command_line.HasSwitch(switches::kTestingFixedHttpPort)) {
 | 
| -    params->testing_fixed_http_port =
 | 
| -        GetSwitchValueAsInt(command_line, switches::kTestingFixedHttpPort);
 | 
| -  }
 | 
| -  if (command_line.HasSwitch(switches::kTestingFixedHttpsPort)) {
 | 
| -    params->testing_fixed_https_port =
 | 
| -        GetSwitchValueAsInt(command_line, switches::kTestingFixedHttpsPort);
 | 
| -  }
 | 
| -
 | 
| -  // Always fetch the field trial groups to ensure they are reported correctly.
 | 
| -  // The command line flags will be associated with a group that is reported so
 | 
| -  // long as trial is actually queried.
 | 
| -
 | 
| -  std::string altsvc_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kAltSvcFieldTrialName);
 | 
| -  ConfigureAltSvcParams(command_line, altsvc_trial_group, params);
 | 
| -
 | 
| -  std::string quic_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kQuicFieldTrialName);
 | 
| -  VariationParameters quic_trial_params;
 | 
| -  if (!variations::GetVariationParams(kQuicFieldTrialName, &quic_trial_params))
 | 
| -    quic_trial_params.clear();
 | 
| -  ConfigureQuicParams(command_line, quic_trial_group, quic_trial_params,
 | 
| -                      is_quic_allowed_by_policy, params);
 | 
| -
 | 
| -  if (!is_spdy_allowed_by_policy) {
 | 
| -    base::FieldTrial* trial = base::FieldTrialList::Find(kSpdyFieldTrialName);
 | 
| -    if (trial)
 | 
| -      trial->Disable();
 | 
| -  }
 | 
| -  std::string spdy_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kSpdyFieldTrialName);
 | 
| -  VariationParameters spdy_trial_params;
 | 
| -  if (!variations::GetVariationParams(kSpdyFieldTrialName, &spdy_trial_params))
 | 
| -    spdy_trial_params.clear();
 | 
| -  ConfigureSpdyParams(command_line, spdy_trial_group, spdy_trial_params,
 | 
| -                      is_spdy_allowed_by_policy, params);
 | 
| -
 | 
| -  const std::string tfo_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kTCPFastOpenFieldTrialName);
 | 
| -  ConfigureTCPFastOpenParams(tfo_trial_group, params);
 | 
| -
 | 
| -  std::string npn_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kNpnTrialName);
 | 
| -  ConfigureNPNParams(command_line, npn_trial_group, params);
 | 
| -
 | 
| -  std::string priority_dependencies_trial_group =
 | 
| -      base::FieldTrialList::FindFullName(kSpdyDependenciesFieldTrial);
 | 
| -  ConfigurePriorityDependencies(priority_dependencies_trial_group, params);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigureTCPFastOpenParams(
 | 
| -    base::StringPiece tfo_trial_group,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  if (tfo_trial_group == kTCPFastOpenHttpsEnabledGroupName)
 | 
| -    params->enable_tcp_fast_open_for_ssl = true;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigureSpdyParams(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece spdy_trial_group,
 | 
| -    const VariationParameters& spdy_trial_params,
 | 
| -    bool is_spdy_allowed_by_policy,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  // Only handle SPDY field trial parameters and command line flags if
 | 
| -  // "spdy.disabled" preference is not forced via policy.
 | 
| -  if (!is_spdy_allowed_by_policy) {
 | 
| -    params->enable_spdy31 = false;
 | 
| -    params->enable_http2 = false;
 | 
| -    return;
 | 
| -  }
 | 
| -
 | 
| -  if (command_line.HasSwitch(switches::kIgnoreUrlFetcherCertRequests))
 | 
| -    net::URLFetcher::SetIgnoreCertificateRequests(true);
 | 
| -
 | 
| -  if (command_line.HasSwitch(switches::kDisableHttp2)) {
 | 
| -    params->enable_spdy31 = false;
 | 
| -    params->enable_http2 = false;
 | 
| -    return;
 | 
| -  }
 | 
| -
 | 
| -  if (spdy_trial_group.starts_with(kSpdyFieldTrialHoldbackGroupNamePrefix)) {
 | 
| -    net::HttpStreamFactory::set_spdy_enabled(false);
 | 
| -    return;
 | 
| -  }
 | 
| -  if (spdy_trial_group.starts_with(kSpdyFieldTrialSpdy31GroupNamePrefix)) {
 | 
| -    params->enable_spdy31 = true;
 | 
| -    params->enable_http2 = false;
 | 
| -    return;
 | 
| -  }
 | 
| -  if (spdy_trial_group.starts_with(kSpdyFieldTrialSpdy4GroupNamePrefix)) {
 | 
| -    params->enable_spdy31 = true;
 | 
| -    params->enable_http2 = true;
 | 
| -    return;
 | 
| -  }
 | 
| -  if (spdy_trial_group.starts_with(kSpdyFieldTrialParametrizedPrefix)) {
 | 
| -    bool spdy_enabled = false;
 | 
| -    params->enable_spdy31 = false;
 | 
| -    params->enable_http2 = false;
 | 
| -    if (base::LowerCaseEqualsASCII(
 | 
| -            GetVariationParam(spdy_trial_params, "enable_http2"), "true")) {
 | 
| -      spdy_enabled = true;
 | 
| -      params->enable_http2 = true;
 | 
| -    }
 | 
| -    if (base::LowerCaseEqualsASCII(
 | 
| -            GetVariationParam(spdy_trial_params, "enable_spdy31"), "true")) {
 | 
| -      spdy_enabled = true;
 | 
| -      params->enable_spdy31 = true;
 | 
| -    }
 | 
| -    // TODO(bnc): https://crbug.com/521597
 | 
| -    // HttpStreamFactory::spdy_enabled_ is redundant with params->enable_http2
 | 
| -    // and enable_spdy31, can it be eliminated?
 | 
| -    net::HttpStreamFactory::set_spdy_enabled(spdy_enabled);
 | 
| -    return;
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigureAltSvcParams(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece altsvc_trial_group,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  if (command_line.HasSwitch(switches::kEnableAlternativeServices) ||
 | 
| -      altsvc_trial_group.starts_with(kAltSvcFieldTrialEnabledPrefix)) {
 | 
| -    params->parse_alternative_services = true;
 | 
| -    return;
 | 
| -  }
 | 
| -  if (altsvc_trial_group.starts_with(kAltSvcFieldTrialDisabledPrefix)) {
 | 
| -    params->parse_alternative_services = false;
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigureNPNParams(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece npn_trial_group,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  if (npn_trial_group.starts_with(kNpnTrialEnabledGroupNamePrefix)) {
 | 
| -    params->enable_npn = true;
 | 
| -  } else if (npn_trial_group.starts_with(kNpnTrialDisabledGroupNamePrefix)) {
 | 
| -    params->enable_npn = false;
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigurePriorityDependencies(
 | 
| -    base::StringPiece priority_dependencies_trial_group,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  if (priority_dependencies_trial_group.starts_with(
 | 
| -          kSpdyDependenciesFieldTrialEnable)) {
 | 
| -    params->enable_priority_dependencies = true;
 | 
| -  } else if (priority_dependencies_trial_group.starts_with(
 | 
| -                 kSpdyDepencenciesFieldTrialDisable)) {
 | 
| -    params->enable_priority_dependencies = false;
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -// static
 | 
|  void IOThread::RegisterPrefs(PrefRegistrySimple* registry) {
 | 
|    registry->RegisterStringPref(prefs::kAuthSchemes,
 | 
|                                 "basic,digest,ntlm,negotiate");
 | 
| @@ -1165,7 +913,7 @@ base::TimeTicks IOThread::creation_time() const {
 | 
|  bool IOThread::ShouldEnableQuicForDataReductionProxy() {
 | 
|    const base::CommandLine& command_line =
 | 
|        *base::CommandLine::ForCurrentProcess();
 | 
| -  return NetworkSessionConfigurator::ShouldEnableQuicForDataReductionProxy(
 | 
| +  return network_session_configurator::ShouldEnableQuicForDataReductionProxy(
 | 
|        command_line);
 | 
|  }
 | 
|  
 | 
| @@ -1222,427 +970,6 @@ void IOThread::UpdateDnsClientEnabled() {
 | 
|  }
 | 
|  
 | 
|  // static
 | 
| -void IOThread::NetworkSessionConfigurator::ConfigureQuicParams(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece quic_trial_group,
 | 
| -    const VariationParameters& quic_trial_params,
 | 
| -    bool is_quic_allowed_by_policy,
 | 
| -    net::HttpNetworkSession::Params* params) {
 | 
| -  params->enable_quic = ShouldEnableQuic(command_line, quic_trial_group,
 | 
| -                                         is_quic_allowed_by_policy);
 | 
| -  params->disable_quic_on_timeout_with_open_streams =
 | 
| -      ShouldDisableQuicWhenConnectionTimesOutWithOpenStreams(quic_trial_params);
 | 
| -  params->enable_quic_for_proxies = ShouldEnableQuicForProxies(
 | 
| -      command_line, quic_trial_group, is_quic_allowed_by_policy);
 | 
| -
 | 
| -  if (ShouldQuicEnableAlternativeServicesForDifferentHost(command_line,
 | 
| -                                                          quic_trial_params)) {
 | 
| -    params->enable_alternative_service_with_different_host = true;
 | 
| -    params->parse_alternative_services = true;
 | 
| -  } else {
 | 
| -    params->enable_alternative_service_with_different_host = false;
 | 
| -  }
 | 
| -
 | 
| -  if (params->enable_quic) {
 | 
| -    params->quic_always_require_handshake_confirmation =
 | 
| -        ShouldQuicAlwaysRequireHandshakeConfirmation(quic_trial_params);
 | 
| -    params->quic_disable_connection_pooling =
 | 
| -        ShouldQuicDisableConnectionPooling(quic_trial_params);
 | 
| -    int receive_buffer_size = GetQuicSocketReceiveBufferSize(quic_trial_params);
 | 
| -    if (receive_buffer_size != 0) {
 | 
| -      params->quic_socket_receive_buffer_size = receive_buffer_size;
 | 
| -    }
 | 
| -    params->quic_delay_tcp_race = ShouldQuicDelayTcpRace(quic_trial_params);
 | 
| -    float load_server_info_timeout_srtt_multiplier =
 | 
| -        GetQuicLoadServerInfoTimeoutSrttMultiplier(quic_trial_params);
 | 
| -    if (load_server_info_timeout_srtt_multiplier != 0) {
 | 
| -      params->quic_load_server_info_timeout_srtt_multiplier =
 | 
| -          load_server_info_timeout_srtt_multiplier;
 | 
| -    }
 | 
| -    params->quic_enable_connection_racing =
 | 
| -        ShouldQuicEnableConnectionRacing(quic_trial_params);
 | 
| -    params->quic_enable_non_blocking_io =
 | 
| -        ShouldQuicEnableNonBlockingIO(quic_trial_params);
 | 
| -    params->quic_disable_disk_cache =
 | 
| -        ShouldQuicDisableDiskCache(quic_trial_params);
 | 
| -    params->quic_prefer_aes = ShouldQuicPreferAes(quic_trial_params);
 | 
| -    int max_number_of_lossy_connections = GetQuicMaxNumberOfLossyConnections(
 | 
| -        quic_trial_params);
 | 
| -    if (max_number_of_lossy_connections != 0) {
 | 
| -      params->quic_max_number_of_lossy_connections =
 | 
| -          max_number_of_lossy_connections;
 | 
| -    }
 | 
| -    float packet_loss_threshold = GetQuicPacketLossThreshold(quic_trial_params);
 | 
| -    if (packet_loss_threshold != 0)
 | 
| -      params->quic_packet_loss_threshold = packet_loss_threshold;
 | 
| -    params->enable_quic_port_selection =
 | 
| -        ShouldEnableQuicPortSelection(command_line);
 | 
| -    params->quic_connection_options =
 | 
| -        GetQuicConnectionOptions(command_line, quic_trial_params);
 | 
| -    params->quic_close_sessions_on_ip_change =
 | 
| -        ShouldQuicCloseSessionsOnIpChange(quic_trial_params);
 | 
| -    int idle_connection_timeout_seconds = GetQuicIdleConnectionTimeoutSeconds(
 | 
| -        quic_trial_params);
 | 
| -    if (idle_connection_timeout_seconds != 0) {
 | 
| -      params->quic_idle_connection_timeout_seconds =
 | 
| -          idle_connection_timeout_seconds;
 | 
| -    }
 | 
| -    params->quic_disable_preconnect_if_0rtt =
 | 
| -        ShouldQuicDisablePreConnectIfZeroRtt(quic_trial_params);
 | 
| -    params->quic_host_whitelist =
 | 
| -        GetQuicHostWhitelist(command_line, quic_trial_params);
 | 
| -    params->quic_migrate_sessions_on_network_change =
 | 
| -        ShouldQuicMigrateSessionsOnNetworkChange(quic_trial_params);
 | 
| -    params->quic_migrate_sessions_early =
 | 
| -        ShouldQuicMigrateSessionsEarly(quic_trial_params);
 | 
| -  }
 | 
| -
 | 
| -  size_t max_packet_length = GetQuicMaxPacketLength(command_line,
 | 
| -                                                    quic_trial_params);
 | 
| -  if (max_packet_length != 0) {
 | 
| -    params->quic_max_packet_length = max_packet_length;
 | 
| -  }
 | 
| -
 | 
| -  params->quic_user_agent_id = chrome::GetChannelString();
 | 
| -  if (!params->quic_user_agent_id.empty())
 | 
| -    params->quic_user_agent_id.push_back(' ');
 | 
| -  params->quic_user_agent_id.append(
 | 
| -      version_info::GetProductNameAndVersionForUserAgent());
 | 
| -  params->quic_user_agent_id.push_back(' ');
 | 
| -  params->quic_user_agent_id.append(content::BuildOSCpuInfo());
 | 
| -
 | 
| -  net::QuicVersion version = GetQuicVersion(command_line, quic_trial_params);
 | 
| -  if (version != net::QUIC_VERSION_UNSUPPORTED) {
 | 
| -    net::QuicVersionVector supported_versions;
 | 
| -    supported_versions.push_back(version);
 | 
| -    params->quic_supported_versions = supported_versions;
 | 
| -  }
 | 
| -
 | 
| -  if (command_line.HasSwitch(switches::kOriginToForceQuicOn)) {
 | 
| -    std::string origins =
 | 
| -        command_line.GetSwitchValueASCII(switches::kOriginToForceQuicOn);
 | 
| -    for (const std::string& host_port : base::SplitString(
 | 
| -             origins, ",", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL)) {
 | 
| -      net::HostPortPair quic_origin = net::HostPortPair::FromString(host_port);
 | 
| -      if (!quic_origin.IsEmpty())
 | 
| -        params->origins_to_force_quic_on.insert(quic_origin);
 | 
| -    }
 | 
| -  }
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::
 | 
| -    ShouldDisableQuicWhenConnectionTimesOutWithOpenStreams(
 | 
| -        const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -    GetVariationParam(quic_trial_params,
 | 
| -      "disable_quic_on_timeout_with_open_streams"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldEnableQuic(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece quic_trial_group,
 | 
| -    bool is_quic_allowed_by_policy) {
 | 
| -  if (command_line.HasSwitch(switches::kDisableQuic) ||
 | 
| -      !is_quic_allowed_by_policy)
 | 
| -    return false;
 | 
| -
 | 
| -  if (command_line.HasSwitch(switches::kEnableQuic))
 | 
| -    return true;
 | 
| -
 | 
| -  return quic_trial_group.starts_with(kQuicFieldTrialEnabledGroupName) ||
 | 
| -         quic_trial_group.starts_with(kQuicFieldTrialHttpsEnabledGroupName);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldEnableQuicForProxies(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    base::StringPiece quic_trial_group,
 | 
| -    bool is_quic_allowed_by_policy) {
 | 
| -  return ShouldEnableQuic(command_line, quic_trial_group,
 | 
| -                          is_quic_allowed_by_policy) ||
 | 
| -         ShouldEnableQuicForDataReductionProxy(command_line);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::
 | 
| -    ShouldEnableQuicForDataReductionProxy(
 | 
| -        const base::CommandLine& command_line) {
 | 
| -  if (command_line.HasSwitch(switches::kDisableQuic))
 | 
| -    return false;
 | 
| -
 | 
| -  return data_reduction_proxy::params::IsIncludedInQuicFieldTrial();
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldEnableQuicPortSelection(
 | 
| -    const base::CommandLine& command_line) {
 | 
| -  if (command_line.HasSwitch(switches::kDisableQuicPortSelection))
 | 
| -    return false;
 | 
| -
 | 
| -  if (command_line.HasSwitch(switches::kEnableQuicPortSelection))
 | 
| -    return true;
 | 
| -
 | 
| -  return false;  // Default to disabling port selection on all channels.
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -net::QuicTagVector
 | 
| -IOThread::NetworkSessionConfigurator::GetQuicConnectionOptions(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  if (command_line.HasSwitch(switches::kQuicConnectionOptions)) {
 | 
| -    return net::QuicUtils::ParseQuicConnectionOptions(
 | 
| -        command_line.GetSwitchValueASCII(switches::kQuicConnectionOptions));
 | 
| -  }
 | 
| -
 | 
| -  VariationParameters::const_iterator it =
 | 
| -      quic_trial_params.find("connection_options");
 | 
| -  if (it == quic_trial_params.end()) {
 | 
| -    return net::QuicTagVector();
 | 
| -  }
 | 
| -
 | 
| -  return net::QuicUtils::ParseQuicConnectionOptions(it->second);
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::
 | 
| -    ShouldQuicAlwaysRequireHandshakeConfirmation(
 | 
| -        const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params,
 | 
| -                        "always_require_handshake_confirmation"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicDisableConnectionPooling(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "disable_connection_pooling"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -float IOThread::NetworkSessionConfigurator::
 | 
| -    GetQuicLoadServerInfoTimeoutSrttMultiplier(
 | 
| -        const VariationParameters& quic_trial_params) {
 | 
| -  double value;
 | 
| -  if (base::StringToDouble(GetVariationParam(quic_trial_params,
 | 
| -                                             "load_server_info_time_to_srtt"),
 | 
| -                           &value)) {
 | 
| -    return static_cast<float>(value);
 | 
| -  }
 | 
| -  return 0.0f;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicEnableConnectionRacing(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "enable_connection_racing"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicEnableNonBlockingIO(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "enable_non_blocking_io"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicDisableDiskCache(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "disable_disk_cache"), "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicPreferAes(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "prefer_aes"), "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::
 | 
| -    ShouldQuicEnableAlternativeServicesForDifferentHost(
 | 
| -        const base::CommandLine& command_line,
 | 
| -        const VariationParameters& quic_trial_params) {
 | 
| -  // TODO(bnc): Remove inaccurately named "use_alternative_services" parameter.
 | 
| -  return command_line.HasSwitch(switches::kEnableAlternativeServices) ||
 | 
| -         base::LowerCaseEqualsASCII(
 | 
| -             GetVariationParam(quic_trial_params, "use_alternative_services"),
 | 
| -             "true") ||
 | 
| -         base::LowerCaseEqualsASCII(
 | 
| -             GetVariationParam(
 | 
| -                 quic_trial_params,
 | 
| -                 "enable_alternative_service_with_different_host"),
 | 
| -             "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -int IOThread::NetworkSessionConfigurator::GetQuicMaxNumberOfLossyConnections(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  int value;
 | 
| -  if (base::StringToInt(GetVariationParam(quic_trial_params,
 | 
| -                                          "max_number_of_lossy_connections"),
 | 
| -                        &value)) {
 | 
| -    return value;
 | 
| -  }
 | 
| -  return 0;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -float IOThread::NetworkSessionConfigurator::GetQuicPacketLossThreshold(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  double value;
 | 
| -  if (base::StringToDouble(GetVariationParam(quic_trial_params,
 | 
| -                                             "packet_loss_threshold"),
 | 
| -                           &value)) {
 | 
| -    return static_cast<float>(value);
 | 
| -  }
 | 
| -  return 0.0f;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -int IOThread::NetworkSessionConfigurator::GetQuicSocketReceiveBufferSize(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  int value;
 | 
| -  if (base::StringToInt(GetVariationParam(quic_trial_params,
 | 
| -                                          "receive_buffer_size"),
 | 
| -                        &value)) {
 | 
| -    return value;
 | 
| -  }
 | 
| -  return 0;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicDelayTcpRace(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "delay_tcp_race"), "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicCloseSessionsOnIpChange(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "close_sessions_on_ip_change"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -int IOThread::NetworkSessionConfigurator::GetQuicIdleConnectionTimeoutSeconds(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  int value;
 | 
| -  if (base::StringToInt(GetVariationParam(quic_trial_params,
 | 
| -                                          "idle_connection_timeout_seconds"),
 | 
| -                        &value)) {
 | 
| -    return value;
 | 
| -  }
 | 
| -  return 0;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicDisablePreConnectIfZeroRtt(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "disable_preconnect_if_0rtt"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -std::unordered_set<std::string>
 | 
| -IOThread::NetworkSessionConfigurator::GetQuicHostWhitelist(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  std::string whitelist;
 | 
| -  if (command_line.HasSwitch(switches::kQuicHostWhitelist)) {
 | 
| -    whitelist = command_line.GetSwitchValueASCII(switches::kQuicHostWhitelist);
 | 
| -  } else {
 | 
| -    whitelist = GetVariationParam(quic_trial_params, "quic_host_whitelist");
 | 
| -  }
 | 
| -  std::unordered_set<std::string> hosts;
 | 
| -  for (const std::string& host :base::SplitString(whitelist, ",",
 | 
| -                                                  base::TRIM_WHITESPACE,
 | 
| -                                                  base::SPLIT_WANT_ALL)) {
 | 
| -    hosts.insert(host);
 | 
| -  }
 | 
| -  return hosts;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::
 | 
| -    ShouldQuicMigrateSessionsOnNetworkChange(
 | 
| -        const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params,
 | 
| -                        "migrate_sessions_on_network_change"),
 | 
| -      "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -bool IOThread::NetworkSessionConfigurator::ShouldQuicMigrateSessionsEarly(
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  return base::LowerCaseEqualsASCII(
 | 
| -      GetVariationParam(quic_trial_params, "migrate_sessions_early"), "true");
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -size_t IOThread::NetworkSessionConfigurator::GetQuicMaxPacketLength(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  if (command_line.HasSwitch(switches::kQuicMaxPacketLength)) {
 | 
| -    unsigned value;
 | 
| -    if (!base::StringToUint(
 | 
| -            command_line.GetSwitchValueASCII(switches::kQuicMaxPacketLength),
 | 
| -            &value)) {
 | 
| -      return 0;
 | 
| -    }
 | 
| -    return value;
 | 
| -  }
 | 
| -
 | 
| -  unsigned value;
 | 
| -  if (base::StringToUint(GetVariationParam(quic_trial_params,
 | 
| -                                           "max_packet_length"),
 | 
| -                         &value)) {
 | 
| -    return value;
 | 
| -  }
 | 
| -  return 0;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -net::QuicVersion IOThread::NetworkSessionConfigurator::GetQuicVersion(
 | 
| -    const base::CommandLine& command_line,
 | 
| -    const VariationParameters& quic_trial_params) {
 | 
| -  if (command_line.HasSwitch(switches::kQuicVersion)) {
 | 
| -    return ParseQuicVersion(
 | 
| -        command_line.GetSwitchValueASCII(switches::kQuicVersion));
 | 
| -  }
 | 
| -
 | 
| -  return ParseQuicVersion(GetVariationParam(quic_trial_params, "quic_version"));
 | 
| -}
 | 
| -
 | 
| -// static
 | 
| -net::QuicVersion IOThread::NetworkSessionConfigurator::ParseQuicVersion(
 | 
| -    const std::string& quic_version) {
 | 
| -  net::QuicVersionVector supported_versions = net::QuicSupportedVersions();
 | 
| -  for (size_t i = 0; i < supported_versions.size(); ++i) {
 | 
| -    net::QuicVersion version = supported_versions[i];
 | 
| -    if (net::QuicVersionToString(version) == quic_version) {
 | 
| -      return version;
 | 
| -    }
 | 
| -  }
 | 
| -
 | 
| -  return net::QUIC_VERSION_UNSUPPORTED;
 | 
| -}
 | 
| -
 | 
| -// static
 | 
|  net::URLRequestContext* IOThread::ConstructSystemRequestContext(
 | 
|      IOThread::Globals* globals,
 | 
|      const net::HttpNetworkSession::Params& params,
 | 
| 
 |