diff options
author | willchan@chromium.org <willchan@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-04-19 22:45:53 +0000 |
---|---|---|
committer | willchan@chromium.org <willchan@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-04-19 22:45:53 +0000 |
commit | 61a86c4d5644817d291e7f22ffd0b0b5cef56295 (patch) | |
tree | dfd15e590bbbf44af479f702875d24aa19d1f491 /net/http | |
parent | 74d7e1d0cb8040ba0bfe15619ccb240e5c7d5c19 (diff) | |
download | chromium_src-61a86c4d5644817d291e7f22ffd0b0b5cef56295.zip chromium_src-61a86c4d5644817d291e7f22ffd0b0b5cef56295.tar.gz chromium_src-61a86c4d5644817d291e7f22ffd0b0b5cef56295.tar.bz2 |
Fix crash on IP address change.
Revert r43908: "Flush socket pools and SPDY session pool properly on explicit requests and network changes."
This change was reverted on the 375 branch, but not on trunk.
BUG=41190
Review URL: http://codereview.chromium.org/1604045
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@44973 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'net/http')
-rw-r--r-- | net/http/http_cache.cc | 8 | ||||
-rw-r--r-- | net/http/http_network_layer.cc | 8 | ||||
-rw-r--r-- | net/http/http_network_layer.h | 2 | ||||
-rw-r--r-- | net/http/http_network_session.cc | 65 | ||||
-rw-r--r-- | net/http/http_network_session.h | 21 | ||||
-rw-r--r-- | net/http/http_network_session_unittest.cc | 82 | ||||
-rw-r--r-- | net/http/http_network_transaction_unittest.cc | 11 |
7 files changed, 52 insertions, 145 deletions
diff --git a/net/http/http_cache.cc b/net/http/http_cache.cc index f1ddaf9..3a816f7 100644 --- a/net/http/http_cache.cc +++ b/net/http/http_cache.cc @@ -371,8 +371,12 @@ void HttpCache::CloseCurrentConnections() { net::HttpNetworkLayer* network = static_cast<net::HttpNetworkLayer*>(network_layer_.get()); HttpNetworkSession* session = network->GetSession(); - if (session) - session->Flush(); + if (session) { + session->tcp_socket_pool()->CloseIdleSockets(); + if (session->spdy_session_pool()) + session->spdy_session_pool()->CloseAllSessions(); + session->ReplaceTCPSocketPool(); + } } //----------------------------------------------------------------------------- diff --git a/net/http/http_network_layer.cc b/net/http/http_network_layer.cc index 4915cd1..4e53abe 100644 --- a/net/http/http_network_layer.cc +++ b/net/http/http_network_layer.cc @@ -12,6 +12,7 @@ #include "net/spdy/spdy_framer.h" #include "net/spdy/spdy_network_transaction.h" #include "net/spdy/spdy_session.h" +#include "net/spdy/spdy_session_pool.h" namespace net { @@ -56,6 +57,7 @@ HttpNetworkLayer::HttpNetworkLayer( proxy_service_(proxy_service), ssl_config_service_(ssl_config_service), session_(NULL), + spdy_session_pool_(NULL), http_auth_handler_factory_(http_auth_handler_factory), suspended_(false) { DCHECK(proxy_service_); @@ -67,6 +69,7 @@ HttpNetworkLayer::HttpNetworkLayer(HttpNetworkSession* session) network_change_notifier_(NULL), ssl_config_service_(NULL), session_(session), + spdy_session_pool_(session->spdy_session_pool()), http_auth_handler_factory_(NULL), suspended_(false) { DCHECK(session_.get()); @@ -94,15 +97,16 @@ void HttpNetworkLayer::Suspend(bool suspend) { suspended_ = suspend; if (suspend && session_) - session_->Flush(); + session_->tcp_socket_pool()->CloseIdleSockets(); } HttpNetworkSession* HttpNetworkLayer::GetSession() { if (!session_) { DCHECK(proxy_service_); + SpdySessionPool* spdy_pool = new SpdySessionPool; session_ = new HttpNetworkSession( network_change_notifier_, host_resolver_, proxy_service_, - socket_factory_, ssl_config_service_, + socket_factory_, ssl_config_service_, spdy_pool, http_auth_handler_factory_); // These were just temps for lazy-initializing HttpNetworkSession. network_change_notifier_ = NULL; diff --git a/net/http/http_network_layer.h b/net/http/http_network_layer.h index 63df00b..2d4130d 100644 --- a/net/http/http_network_layer.h +++ b/net/http/http_network_layer.h @@ -20,6 +20,7 @@ class HttpNetworkSession; class NetworkChangeNotifier; class ProxyInfo; class ProxyService; +class SpdySessionPool; class SSLConfigService; class HttpNetworkLayer : public HttpTransactionFactory { @@ -81,6 +82,7 @@ class HttpNetworkLayer : public HttpTransactionFactory { scoped_refptr<SSLConfigService> ssl_config_service_; scoped_refptr<HttpNetworkSession> session_; + scoped_refptr<SpdySessionPool> spdy_session_pool_; HttpAuthHandlerFactory* http_auth_handler_factory_; diff --git a/net/http/http_network_session.cc b/net/http/http_network_session.cc index ea8d1d7..146223b6 100644 --- a/net/http/http_network_session.cc +++ b/net/http/http_network_session.cc @@ -29,68 +29,49 @@ HttpNetworkSession::HttpNetworkSession( ProxyService* proxy_service, ClientSocketFactory* client_socket_factory, SSLConfigService* ssl_config_service, + SpdySessionPool* spdy_session_pool, HttpAuthHandlerFactory* http_auth_handler_factory) : network_change_notifier_(network_change_notifier), + tcp_socket_pool_(new TCPClientSocketPool( + max_sockets_, max_sockets_per_group_, "Transport", + host_resolver, client_socket_factory, network_change_notifier_)), + socks_socket_pool_(new SOCKSClientSocketPool( + max_sockets_, max_sockets_per_group_, "SOCKS", host_resolver, + new TCPClientSocketPool(max_sockets_, max_sockets_per_group_, + "TCPForSOCKS", host_resolver, + client_socket_factory, + network_change_notifier_), + network_change_notifier_)), socket_factory_(client_socket_factory), host_resolver_(host_resolver), - tcp_socket_pool_(CreateNewTCPSocketPool()), - socks_socket_pool_(CreateNewSOCKSSocketPool()), proxy_service_(proxy_service), ssl_config_service_(ssl_config_service), - spdy_session_pool_(new SpdySessionPool()), + spdy_session_pool_(spdy_session_pool), http_auth_handler_factory_(http_auth_handler_factory) { DCHECK(proxy_service); DCHECK(ssl_config_service); - - if (network_change_notifier) - network_change_notifier_->AddObserver(this); } HttpNetworkSession::~HttpNetworkSession() { - if (network_change_notifier_) - network_change_notifier_->RemoveObserver(this); } // static void HttpNetworkSession::set_max_sockets_per_group(int socket_count) { - DCHECK_LT(0, socket_count); + DCHECK(0 < socket_count); // The following is a sanity check... but we should NEVER be near this value. - DCHECK_GT(100, socket_count); + DCHECK(100 > socket_count); max_sockets_per_group_ = socket_count; } -void HttpNetworkSession::Flush() { - host_resolver()->Flush(); - tcp_socket_pool()->CloseIdleSockets(); - tcp_socket_pool_ = CreateNewTCPSocketPool(); - socks_socket_pool()->CloseIdleSockets(); - socks_socket_pool_ = CreateNewSOCKSSocketPool(); - spdy_session_pool_->CloseAllSessions(); - spdy_session_pool_ = new SpdySessionPool; -} - -void HttpNetworkSession::OnIPAddressChanged() { - Flush(); -} - -scoped_refptr<TCPClientSocketPool> -HttpNetworkSession::CreateNewTCPSocketPool() { - // TODO(vandebo) when we've completely converted to pools, the base TCP - // pool name should get changed to TCP instead of Transport. - return new TCPClientSocketPool(max_sockets_, - max_sockets_per_group_, - "Transport", - host_resolver_, - socket_factory_); -} - -scoped_refptr<SOCKSClientSocketPool> -HttpNetworkSession::CreateNewSOCKSSocketPool() { - return new SOCKSClientSocketPool( - max_sockets_, max_sockets_per_group_, "SOCKS", host_resolver_, - new TCPClientSocketPool(max_sockets_, max_sockets_per_group_, - "TCPForSOCKS", host_resolver_, - socket_factory_)); +// TODO(vandebo) when we've completely converted to pools, the base TCP +// pool name should get changed to TCP instead of Transport. +void HttpNetworkSession::ReplaceTCPSocketPool() { + tcp_socket_pool_ = new TCPClientSocketPool(max_sockets_, + max_sockets_per_group_, + "Transport", + host_resolver_, + socket_factory_, + network_change_notifier_); } } // namespace net diff --git a/net/http/http_network_session.h b/net/http/http_network_session.h index 23ba526..8f85ce7 100644 --- a/net/http/http_network_session.h +++ b/net/http/http_network_session.h @@ -8,7 +8,6 @@ #include "base/ref_counted.h" #include "base/scoped_ptr.h" #include "net/base/host_resolver.h" -#include "net/base/network_change_notifier.h" #include "net/base/ssl_client_auth_cache.h" #include "net/base/ssl_config_service.h" #include "net/http/http_alternate_protocols.h" @@ -26,9 +25,7 @@ class SpdySessionPool; class NetworkChangeNotifier; // This class holds session objects used by HttpNetworkTransaction objects. -class HttpNetworkSession - : public base::RefCounted<HttpNetworkSession>, - public NetworkChangeNotifier::Observer { +class HttpNetworkSession : public base::RefCounted<HttpNetworkSession> { public: HttpNetworkSession( NetworkChangeNotifier* network_change_notifier, @@ -36,6 +33,7 @@ class HttpNetworkSession ProxyService* proxy_service, ClientSocketFactory* client_socket_factory, SSLConfigService* ssl_config_service, + SpdySessionPool* spdy_session_pool, HttpAuthHandlerFactory* http_auth_handler_factory); HttpAuthCache* auth_cache() { return &auth_cache_; } @@ -77,11 +75,9 @@ class HttpNetworkSession return http_auth_handler_factory_; } - // Flushes cached data in the HttpNetworkSession.
- void Flush();
-
- // NetworkChangeNotifier::Observer methods:
- virtual void OnIPAddressChanged();
+ // Replace the current socket pool with a new one. This effectively + // abandons the current pool. This is only used for debugging. + void ReplaceTCPSocketPool(); static void set_max_sockets_per_group(int socket_count); @@ -97,9 +93,6 @@ class HttpNetworkSession ~HttpNetworkSession(); - scoped_refptr<TCPClientSocketPool> CreateNewTCPSocketPool(); - scoped_refptr<SOCKSClientSocketPool> CreateNewSOCKSSocketPool(); - // Total limit of sockets. Not a constant to allow experiments. static int max_sockets_; @@ -115,10 +108,10 @@ class HttpNetworkSession SSLClientAuthCache ssl_client_auth_cache_; HttpAlternateProtocols alternate_protocols_; NetworkChangeNotifier* const network_change_notifier_; - ClientSocketFactory* socket_factory_; - scoped_refptr<HostResolver> host_resolver_; scoped_refptr<TCPClientSocketPool> tcp_socket_pool_; scoped_refptr<SOCKSClientSocketPool> socks_socket_pool_; + ClientSocketFactory* socket_factory_; + scoped_refptr<HostResolver> host_resolver_; scoped_refptr<ProxyService> proxy_service_; scoped_refptr<SSLConfigService> ssl_config_service_; scoped_refptr<SpdySessionPool> spdy_session_pool_; diff --git a/net/http/http_network_session_unittest.cc b/net/http/http_network_session_unittest.cc deleted file mode 100644 index 329f394c..0000000 --- a/net/http/http_network_session_unittest.cc +++ /dev/null @@ -1,82 +0,0 @@ -// Copyright (c) 2010 The 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/http/http_network_session.h" - -#include "base/ref_counted.h" -#include "net/base/mock_host_resolver.h" -#include "net/base/mock_network_change_notifier.h" -#include "net/base/ssl_config_service_defaults.h" -#include "net/base/test_completion_callback.h" -#include "net/http/http_auth_handler_factory.h" -#include "net/proxy/proxy_service.h" -#include "net/socket/client_socket_handle.h" -#include "net/socket/socket_test_util.h" -#include "net/socket/tcp_client_socket_pool.h" -#include "net/spdy/spdy_session.h" -#include "net/spdy/spdy_session_pool.h" -#include "testing/gtest/include/gtest/gtest.h" - -namespace net { -namespace { - -TEST(HttpNetworkSessionTest, FlushOnNetworkChange) { - MockNetworkChangeNotifier mock_notifier; - scoped_refptr<MockCachingHostResolver> mock_resolver( - new MockCachingHostResolver); - MockClientSocketFactory mock_factory; - scoped_ptr<HttpAuthHandlerFactory> auth_handler_factory( - HttpAuthHandlerFactory::CreateDefault()); - scoped_refptr<HttpNetworkSession> session( - new HttpNetworkSession(&mock_notifier, - mock_resolver, - ProxyService::CreateNull(), - &mock_factory, - new SSLConfigServiceDefaults, - auth_handler_factory.get())); - - scoped_refptr<TCPClientSocketPool> tcp_socket_pool( - session->tcp_socket_pool()); - - StaticSocketDataProvider data; - mock_factory.AddSocketDataProvider(&data); - - TestCompletionCallback callback; - ClientSocketHandle handle; - TCPSocketParams dest("www.google.com", 80, LOW, GURL(), false); - int rv = handle.Init("a", dest, LOW, &callback, tcp_socket_pool, NULL); - EXPECT_EQ(ERR_IO_PENDING, rv); - EXPECT_FALSE(handle.is_initialized()); - EXPECT_FALSE(handle.socket()); - - EXPECT_EQ(OK, callback.WaitForResult()); - EXPECT_TRUE(handle.is_initialized()); - EXPECT_TRUE(handle.socket()); - - handle.Reset(); - - // Need to run all pending to release the socket back to the pool. - MessageLoop::current()->RunAllPending(); - - // Now we should have 1 idle socket. - EXPECT_EQ(1, tcp_socket_pool->IdleSocketCount()); - - HostPortPair host_port_pair("www.google.com", 80); - - scoped_refptr<SpdySession> spdy_session(session->spdy_session_pool()->Get( - host_port_pair, session)); - - EXPECT_TRUE(session->spdy_session_pool()->HasSession(host_port_pair)); - - EXPECT_EQ(1u, mock_resolver->cache()->size()); - - // After an IP address change, we should have 0 idle sockets. - mock_notifier.NotifyIPAddressChange(); - EXPECT_EQ(0, tcp_socket_pool->IdleSocketCount()); - EXPECT_FALSE(session->spdy_session_pool()->HasSession(host_port_pair)); - EXPECT_EQ(0u, mock_resolver->cache()->size()); -} - -} // namespace -} // namespace net diff --git a/net/http/http_network_transaction_unittest.cc b/net/http/http_network_transaction_unittest.cc index df1604e..41408bd 100644 --- a/net/http/http_network_transaction_unittest.cc +++ b/net/http/http_network_transaction_unittest.cc @@ -43,20 +43,23 @@ class SessionDependencies { : host_resolver(new MockHostResolver), proxy_service(ProxyService::CreateNull()), ssl_config_service(new SSLConfigServiceDefaults), - http_auth_handler_factory(HttpAuthHandlerFactory::CreateDefault()) {} + http_auth_handler_factory(HttpAuthHandlerFactory::CreateDefault()), + spdy_session_pool(new SpdySessionPool) {} // Custom proxy service dependency. explicit SessionDependencies(ProxyService* proxy_service) : host_resolver(new MockHostResolver), proxy_service(proxy_service), ssl_config_service(new SSLConfigServiceDefaults), - http_auth_handler_factory(HttpAuthHandlerFactory::CreateDefault()) {} + http_auth_handler_factory(HttpAuthHandlerFactory::CreateDefault()), + spdy_session_pool(new SpdySessionPool) {} scoped_refptr<MockHostResolverBase> host_resolver; scoped_refptr<ProxyService> proxy_service; scoped_refptr<SSLConfigService> ssl_config_service; MockClientSocketFactory socket_factory; scoped_ptr<HttpAuthHandlerFactory> http_auth_handler_factory; + scoped_refptr<SpdySessionPool> spdy_session_pool; }; ProxyService* CreateFixedProxyService(const std::string& proxy) { @@ -71,6 +74,7 @@ HttpNetworkSession* CreateSession(SessionDependencies* session_deps) { session_deps->proxy_service, &session_deps->socket_factory, session_deps->ssl_config_service, + session_deps->spdy_session_pool, session_deps->http_auth_handler_factory.get()); } @@ -184,7 +188,8 @@ class CaptureGroupNameSocketPool : public EmulatedClientSocketPool { CaptureGroupNameSocketPool(HttpNetworkSession* session, SocketSourceType* socket_source) : EmulatedClientSocketPool(0, 0, "CaptureGroupNameTestPool", - session->host_resolver(), socket_source) {} + session->host_resolver(), socket_source, + NULL) {} const std::string last_group_name_received() const { return last_group_name_; } |