Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(640)

Side by Side Diff: net/spdy/spdy_session_pool.cc

Issue 2749123002: ABANDONED Allow SpdySessionPool to find/create SpdySession with IP pooling disabled. (Closed)
Patch Set: Created 3 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "net/spdy/spdy_session_pool.h" 5 #include "net/spdy/spdy_session_pool.h"
6 6
7 #include <utility> 7 #include <utility>
8 8
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/memory/ptr_util.h" 10 #include "base/memory/ptr_util.h"
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after
100 auto new_session = base::MakeUnique<SpdySession>( 100 auto new_session = base::MakeUnique<SpdySession>(
101 key, http_server_properties_, transport_security_state_, 101 key, http_server_properties_, transport_security_state_,
102 enable_sending_initial_data_, enable_ping_based_connection_checking_, 102 enable_sending_initial_data_, enable_ping_based_connection_checking_,
103 session_max_recv_window_size_, initial_settings_, time_func_, 103 session_max_recv_window_size_, initial_settings_, time_func_,
104 push_delegate_, proxy_delegate_, net_log.net_log()); 104 push_delegate_, proxy_delegate_, net_log.net_log());
105 105
106 new_session->InitializeWithSocket(std::move(connection), this, is_secure); 106 new_session->InitializeWithSocket(std::move(connection), this, is_secure);
107 107
108 base::WeakPtr<SpdySession> available_session = new_session->GetWeakPtr(); 108 base::WeakPtr<SpdySession> available_session = new_session->GetWeakPtr();
109 sessions_.insert(new_session.release()); 109 sessions_.insert(new_session.release());
110 MapKeyToAvailableSession(key, available_session); 110 MapKeyToAvailableSession(key, available_session, /* ip_pooled = */ false);
111 111
112 net_log.AddEvent( 112 net_log.AddEvent(
113 NetLogEventType::HTTP2_SESSION_POOL_IMPORTED_SESSION_FROM_SOCKET, 113 NetLogEventType::HTTP2_SESSION_POOL_IMPORTED_SESSION_FROM_SOCKET,
114 available_session->net_log().source().ToEventParametersCallback()); 114 available_session->net_log().source().ToEventParametersCallback());
115 115
116 // Look up the IP address for this session so that we can match 116 // Look up the IP address for this session so that we can match
117 // future sessions (potentially to different domains) which can 117 // future sessions (potentially to different domains) which can
118 // potentially be pooled with this one. Because GetPeerAddress() 118 // potentially be pooled with this one. Because GetPeerAddress()
119 // reports the proxy's address instead of the origin server, check 119 // reports the proxy's address instead of the origin server, check
120 // to see if this is a direct connection. 120 // to see if this is a direct connection.
121 if (key.proxy_server().is_direct()) { 121 if (key.proxy_server().is_direct()) {
122 IPEndPoint address; 122 IPEndPoint address;
123 if (available_session->GetPeerAddress(&address) == OK) 123 if (available_session->GetPeerAddress(&address) == OK)
124 aliases_[address] = key; 124 aliases_[address] = key;
125 } 125 }
126 126
127 return available_session; 127 return available_session;
128 } 128 }
129 129
130 base::WeakPtr<SpdySession> SpdySessionPool::FindAvailableSession( 130 base::WeakPtr<SpdySession> SpdySessionPool::FindAvailableSession(
131 const SpdySessionKey& key, 131 const SpdySessionKey& key,
132 const GURL& url, 132 const GURL& url,
133 bool enable_ip_based_pooling,
133 const NetLogWithSource& net_log) { 134 const NetLogWithSource& net_log) {
134 UnclaimedPushedStreamMap::iterator url_it = 135 UnclaimedPushedStreamMap::iterator url_it =
135 unclaimed_pushed_streams_.find(url); 136 unclaimed_pushed_streams_.find(url);
136 if (!url.is_empty() && url_it != unclaimed_pushed_streams_.end()) { 137 if (!url.is_empty() && url_it != unclaimed_pushed_streams_.end()) {
137 DCHECK(url.SchemeIsCryptographic()); 138 DCHECK(url.SchemeIsCryptographic());
138 for (WeakSessionList::iterator it = url_it->second.begin(); 139 for (WeakSessionList::iterator it = url_it->second.begin();
139 it != url_it->second.end();) { 140 it != url_it->second.end();) {
140 base::WeakPtr<SpdySession> spdy_session = *it; 141 base::WeakPtr<SpdySession> spdy_session = *it;
141 // Lazy deletion of destroyed SpdySessions. 142 // Lazy deletion of destroyed SpdySessions.
142 if (!spdy_session) { 143 if (!spdy_session) {
(...skipping 19 matching lines...) Expand all
162 163
163 AvailableSessionMap::iterator it = LookupAvailableSessionByKey(key); 164 AvailableSessionMap::iterator it = LookupAvailableSessionByKey(key);
164 if (it != available_sessions_.end()) { 165 if (it != available_sessions_.end()) {
165 if (key.Equals(it->second->spdy_session_key())) { 166 if (key.Equals(it->second->spdy_session_key())) {
166 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet", FOUND_EXISTING, 167 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet", FOUND_EXISTING,
167 SPDY_SESSION_GET_MAX); 168 SPDY_SESSION_GET_MAX);
168 net_log.AddEvent( 169 net_log.AddEvent(
169 NetLogEventType::HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION, 170 NetLogEventType::HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION,
170 it->second->net_log().source().ToEventParametersCallback()); 171 it->second->net_log().source().ToEventParametersCallback());
171 } else { 172 } else {
173 if (!enable_ip_based_pooling)
174 return base::WeakPtr<SpdySession>();
175
172 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet", 176 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet",
173 FOUND_EXISTING_FROM_IP_POOL, 177 FOUND_EXISTING_FROM_IP_POOL,
174 SPDY_SESSION_GET_MAX); 178 SPDY_SESSION_GET_MAX);
175 net_log.AddEvent( 179 net_log.AddEvent(
176 NetLogEventType:: 180 NetLogEventType::
177 HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION_FROM_IP_POOL, 181 HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION_FROM_IP_POOL,
178 it->second->net_log().source().ToEventParametersCallback()); 182 it->second->net_log().source().ToEventParametersCallback());
179 } 183 }
180 return it->second; 184 return it->second;
181 } 185 }
182 186
187 if (!enable_ip_based_pooling)
188 return base::WeakPtr<SpdySession>();
189
183 // Look up IP addresses from resolver cache. 190 // Look up IP addresses from resolver cache.
184 HostResolver::RequestInfo resolve_info(key.host_port_pair()); 191 HostResolver::RequestInfo resolve_info(key.host_port_pair());
185 AddressList addresses; 192 AddressList addresses;
186 int rv = resolver_->ResolveFromCache(resolve_info, &addresses, net_log); 193 int rv = resolver_->ResolveFromCache(resolve_info, &addresses, net_log);
187 DCHECK_NE(rv, ERR_IO_PENDING); 194 DCHECK_NE(rv, ERR_IO_PENDING);
188 if (rv != OK) 195 if (rv != OK)
189 return base::WeakPtr<SpdySession>(); 196 return base::WeakPtr<SpdySession>();
190 197
191 // Check if we have a session through a domain alias. 198 // Check if we have a session through a domain alias.
192 for (AddressList::const_iterator address_it = addresses.begin(); 199 for (AddressList::const_iterator address_it = addresses.begin();
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
224 } 231 }
225 232
226 UMA_HISTOGRAM_ENUMERATION("Net.SpdyIPPoolDomainMatch", 1, 2); 233 UMA_HISTOGRAM_ENUMERATION("Net.SpdyIPPoolDomainMatch", 1, 2);
227 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet", 234 UMA_HISTOGRAM_ENUMERATION("Net.SpdySessionGet",
228 FOUND_EXISTING_FROM_IP_POOL, 235 FOUND_EXISTING_FROM_IP_POOL,
229 SPDY_SESSION_GET_MAX); 236 SPDY_SESSION_GET_MAX);
230 net_log.AddEvent( 237 net_log.AddEvent(
231 NetLogEventType::HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION_FROM_IP_POOL, 238 NetLogEventType::HTTP2_SESSION_POOL_FOUND_EXISTING_SESSION_FROM_IP_POOL,
232 available_session->net_log().source().ToEventParametersCallback()); 239 available_session->net_log().source().ToEventParametersCallback());
233 // Add this session to the map so that we can find it next time. 240 // Add this session to the map so that we can find it next time.
234 MapKeyToAvailableSession(key, available_session); 241 MapKeyToAvailableSession(key, available_session, /* ip_pooled = */ true);
235 available_session->AddPooledAlias(key); 242 available_session->AddPooledAlias(key);
236 return available_session; 243 return available_session;
237 } 244 }
238 245
239 return base::WeakPtr<SpdySession>(); 246 return base::WeakPtr<SpdySession>();
240 } 247 }
241 248
242 void SpdySessionPool::MakeSessionUnavailable( 249 void SpdySessionPool::MakeSessionUnavailable(
243 const base::WeakPtr<SpdySession>& available_session) { 250 const base::WeakPtr<SpdySession>& available_session) {
244 UnmapKey(available_session->spdy_session_key()); 251 UnmapKey(available_session->spdy_session_key(), /* ip_pooled = */ false);
Ryan Hamilton 2017/03/14 22:20:20 Can you add a comment for why we use false here, a
Bence 2017/03/15 10:05:26 Done.
245 RemoveAliases(available_session->spdy_session_key()); 252 RemoveAliases(available_session->spdy_session_key());
246 const std::set<SpdySessionKey>& aliases = available_session->pooled_aliases(); 253 const std::set<SpdySessionKey>& aliases = available_session->pooled_aliases();
247 for (std::set<SpdySessionKey>::const_iterator it = aliases.begin(); 254 for (std::set<SpdySessionKey>::const_iterator it = aliases.begin();
248 it != aliases.end(); ++it) { 255 it != aliases.end(); ++it) {
249 UnmapKey(*it); 256 UnmapKey(*it, /* ip_pooled = */ true);
250 RemoveAliases(*it); 257 RemoveAliases(*it);
251 } 258 }
252 DCHECK(!IsSessionAvailable(available_session)); 259 DCHECK(!IsSessionAvailable(available_session));
253 } 260 }
254 261
255 void SpdySessionPool::RemoveUnavailableSession( 262 void SpdySessionPool::RemoveUnavailableSession(
256 const base::WeakPtr<SpdySession>& unavailable_session) { 263 const base::WeakPtr<SpdySession>& unavailable_session) {
257 DCHECK(!IsSessionAvailable(unavailable_session)); 264 DCHECK(!IsSessionAvailable(unavailable_session));
258 265
259 unavailable_session->net_log().AddEvent( 266 unavailable_session->net_log().AddEvent(
(...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after
420 base::trace_event::MemoryAllocatorDump::kUnitsBytes, 427 base::trace_event::MemoryAllocatorDump::kUnitsBytes,
421 buffer_size); 428 buffer_size);
422 dump->AddScalar("cert_count", 429 dump->AddScalar("cert_count",
423 base::trace_event::MemoryAllocatorDump::kUnitsObjects, 430 base::trace_event::MemoryAllocatorDump::kUnitsObjects,
424 cert_count); 431 cert_count);
425 dump->AddScalar("cert_size", 432 dump->AddScalar("cert_size",
426 base::trace_event::MemoryAllocatorDump::kUnitsBytes, 433 base::trace_event::MemoryAllocatorDump::kUnitsBytes,
427 cert_size); 434 cert_size);
428 } 435 }
429 436
437 template <class T, class U>
438 SpdySessionPool::AvailableSessionMap::Iterator<T, U>::Iterator()
439 : ip_pooled_(false), session_map_(nullptr) {}
440
441 template <class T, class U>
442 SpdySessionPool::AvailableSessionMap::Iterator<T, U>::Iterator(
443 const Iterator& other)
444 : iterator_(other.iterator_),
445 ip_pooled_(other.ip_pooled_),
446 session_map_(other.session_map_) {}
447
448 template <class T, class U>
449 void SpdySessionPool::AvailableSessionMap::Iterator<T, U>::operator=(
450 const Iterator& other) {
451 iterator_ = other.iterator_;
452 ip_pooled_ = other.ip_pooled_;
453 session_map_ = other.session_map_;
454 }
455
456 template <class T, class U>
457 SpdySessionPool::AvailableSessionMap::Iterator<T, U>::~Iterator() {}
458
459 template <class T, class U>
460 bool SpdySessionPool::AvailableSessionMap::Iterator<T, U>::operator==(
461 const SpdySessionPool::AvailableSessionMap::Iterator<T, U>& other) const {
462 // Compare |iterator_| last, because comparing iterators from different
463 // containers results in a runtime error when using debug_map.
464 return session_map_ == other.session_map_ && ip_pooled_ == other.ip_pooled_ &&
465 iterator_ == other.iterator_;
466 }
467
468 template <class T, class U>
469 bool SpdySessionPool::AvailableSessionMap::Iterator<T, U>::operator!=(
470 const SpdySessionPool::AvailableSessionMap::Iterator<T, U>& other) const {
471 return !(*this == other);
472 }
473
474 template <class T, class U>
475 T& SpdySessionPool::AvailableSessionMap::Iterator<T, U>::operator->() {
476 return iterator_;
477 }
478
479 template <class T, class U>
480 SpdySessionPool::AvailableSessionMap::Iterator<T, U>&
481 SpdySessionPool::AvailableSessionMap::Iterator<T, U>::operator++() {
482 // ++(std_map.end()) is undefined, and so is ++(available_session_map.end()).
Ryan Hamilton 2017/03/14 22:20:20 DCHECK_NE(available_session_map.end(), iterator_);
Bence 2017/03/15 10:05:26 Done.
483 ++iterator_;
484
485 if (ip_pooled_)
Ryan Hamilton 2017/03/14 22:20:20 Can you add a comment which explains why this is t
Bence 2017/03/15 10:05:26 Done.
486 return *this;
487
488 if (iterator_ == session_map_->non_ip_pooled_sessions_.end()) {
489 // This might coincide with ip_pooled_sessions_.end()
490 // if ip_pooled_sessions_ is empty,
491 // which yields the internal representation of available_session_map.end().
Ryan Hamilton 2017/03/14 22:20:20 I don't understand this comment. Perhaps you're sa
Bence 2017/03/15 10:05:26 Done.
492 iterator_ = session_map_->ip_pooled_sessions_.begin();
493 ip_pooled_ = true;
494 }
495
496 return *this;
497 }
498
499 template <class T, class U>
500 SpdySessionPool::AvailableSessionMap::Iterator<T, U>::Iterator(T iterator,
501 bool ip_pooled,
502 U* session_map)
503 : iterator_(iterator), ip_pooled_(ip_pooled), session_map_(session_map) {}
504
505 SpdySessionPool::AvailableSessionMap::AvailableSessionMap() {}
506 SpdySessionPool::AvailableSessionMap::~AvailableSessionMap() {}
507
508 SpdySessionPool::AvailableSessionMap::const_iterator
509 SpdySessionPool::AvailableSessionMap::begin() const {
510 // Must return a dereferencable iterator unless both maps are empty.
511 if (non_ip_pooled_sessions_.empty()) {
512 // If |ip_pooled_sessions_| is not empty, this is deferencable.
513 // If |ip_pooled_sessions_| is empty, then |cbegin() == cend()|, therefore
514 // the return value represents AvailableSessionMap::end().
515 return SpdySessionPool::AvailableSessionMap::Iterator<
516 MapType::const_iterator, const SpdySessionPool::AvailableSessionMap>(
517 ip_pooled_sessions_.cbegin(), /* ip_pooled = */ true, this);
518 } else {
Ryan Hamilton 2017/03/14 22:20:20 nit: since 517 returned, you can avoid the else he
Bence 2017/03/15 10:05:26 Done.
519 // |non_ip_pooled_sessions_| is not empty, therefore this is dereferencable.
520 return SpdySessionPool::AvailableSessionMap::Iterator<
521 MapType::const_iterator, const SpdySessionPool::AvailableSessionMap>(
522 non_ip_pooled_sessions_.cbegin(), /* ip_pooled = */ false, this);
Ryan Hamilton 2017/03/14 22:20:20 I think it would make more sense to move all of th
Bence 2017/03/15 10:05:26 Done. Ended up using a static factory method. Te
523 }
524 }
525
526 SpdySessionPool::AvailableSessionMap::const_iterator
527 SpdySessionPool::AvailableSessionMap::end() const {
528 return SpdySessionPool::AvailableSessionMap::Iterator<
529 MapType::const_iterator, const SpdySessionPool::AvailableSessionMap>(
530 ip_pooled_sessions_.cend(), /* ip_pooled = */ true, this);
Ryan Hamilton 2017/03/14 22:20:20 Consider implementing end() directly in Iterator '
Bence 2017/03/15 10:05:26 Done.
531 }
532
533 SpdySessionPool::AvailableSessionMap::iterator
534 SpdySessionPool::AvailableSessionMap::begin() {
535 // Must return a dereferencable iterator unless both maps are empty.
536 if (non_ip_pooled_sessions_.empty()) {
537 // If |ip_pooled_sessions_| is not empty, this is deferencable.
538 // If |ip_pooled_sessions_| is empty, then |cbegin() == cend()|, therefore
539 // the return value represents AvailableSessionMap::end().
540 return SpdySessionPool::AvailableSessionMap::Iterator<
541 MapType::iterator, SpdySessionPool::AvailableSessionMap>(
542 ip_pooled_sessions_.begin(), /* ip_pooled = */ true, this);
543 } else {
544 // |non_ip_pooled_sessions_| is not empty, therefore this is dereferencable.
545 return SpdySessionPool::AvailableSessionMap::Iterator<
546 MapType::iterator, SpdySessionPool::AvailableSessionMap>(
547 non_ip_pooled_sessions_.begin(), /* ip_pooled = */ false, this);
548 }
Ryan Hamilton 2017/03/14 22:20:20 ditto to const begin.
Bence 2017/03/15 10:05:26 Done.
549 }
550
551 SpdySessionPool::AvailableSessionMap::iterator
552 SpdySessionPool::AvailableSessionMap::end() {
553 return SpdySessionPool::AvailableSessionMap::Iterator<
554 MapType::iterator, SpdySessionPool::AvailableSessionMap>(
555 ip_pooled_sessions_.end(), /* ip_pooled = */ true, this);
556 }
557
558 bool SpdySessionPool::AvailableSessionMap::empty() const {
559 return non_ip_pooled_sessions_.empty() && ip_pooled_sessions_.empty();
560 }
561
562 SpdySessionPool::AvailableSessionMap::iterator
563 SpdySessionPool::AvailableSessionMap::find(const key_type& key) {
564 MapType::iterator it = non_ip_pooled_sessions_.find(key);
565 if (it != non_ip_pooled_sessions_.end())
566 return SpdySessionPool::AvailableSessionMap::Iterator<
567 MapType::iterator, SpdySessionPool::AvailableSessionMap>(
568 it,
569 /* ip_pooled = */ false, this);
570
571 it = ip_pooled_sessions_.find(key);
572 // If |it == ip_pooled_sessions_.end()|, then this is the internal
573 // representation of AvailableSessionMap::end().
574 return SpdySessionPool::AvailableSessionMap::Iterator<
575 MapType::iterator, SpdySessionPool::AvailableSessionMap>(
576 it, /* ip_pooled = */ true, this);
577 }
578
579 void SpdySessionPool::AvailableSessionMap::insert(const value_type& value,
580 bool ip_pooled) {
581 // A session is non IP pooled with respect to the key
582 // iff the key matches the session's proper key.
583 CHECK_EQ(!ip_pooled, value.first.Equals(value.second->spdy_session_key()));
584
585 // There must not already be an entry with key |value.first| in the map.
586 std::pair<MapType::iterator, bool> result =
587 ip_pooled ? ip_pooled_sessions_.insert(value)
588 : non_ip_pooled_sessions_.insert(value);
589 CHECK(result.second);
590 }
591
592 void SpdySessionPool::AvailableSessionMap::erase(const key_type& key,
593 bool ip_pooled) {
594 // |key| must exist in the map.
595 if (ip_pooled) {
596 MapType::iterator it = ip_pooled_sessions_.find(key);
597 CHECK(it != ip_pooled_sessions_.end());
598 ip_pooled_sessions_.erase(it);
599 } else {
600 MapType::iterator it = non_ip_pooled_sessions_.find(key);
601 CHECK(it != non_ip_pooled_sessions_.end());
602 non_ip_pooled_sessions_.erase(it);
603 }
604 }
605
430 bool SpdySessionPool::IsSessionAvailable( 606 bool SpdySessionPool::IsSessionAvailable(
431 const base::WeakPtr<SpdySession>& session) const { 607 const base::WeakPtr<SpdySession>& session) const {
432 for (AvailableSessionMap::const_iterator it = available_sessions_.begin(); 608 for (AvailableSessionMap::const_iterator it = available_sessions_.begin();
433 it != available_sessions_.end(); ++it) { 609 it != available_sessions_.end(); ++it) {
434 if (it->second.get() == session.get()) 610 if (it->second.get() == session.get())
435 return true; 611 return true;
436 } 612 }
437 return false; 613 return false;
438 } 614 }
439 615
440 void SpdySessionPool::MapKeyToAvailableSession( 616 void SpdySessionPool::MapKeyToAvailableSession(
441 const SpdySessionKey& key, 617 const SpdySessionKey& key,
442 const base::WeakPtr<SpdySession>& session) { 618 const base::WeakPtr<SpdySession>& session,
619 bool ip_pooled) {
443 DCHECK(base::ContainsKey(sessions_, session.get())); 620 DCHECK(base::ContainsKey(sessions_, session.get()));
444 std::pair<AvailableSessionMap::iterator, bool> result = 621 available_sessions_.insert(std::make_pair(key, session), ip_pooled);
445 available_sessions_.insert(std::make_pair(key, session));
446 CHECK(result.second);
447 } 622 }
448 623
449 SpdySessionPool::AvailableSessionMap::iterator 624 SpdySessionPool::AvailableSessionMap::iterator
450 SpdySessionPool::LookupAvailableSessionByKey( 625 SpdySessionPool::LookupAvailableSessionByKey(
451 const SpdySessionKey& key) { 626 const SpdySessionKey& key) {
452 return available_sessions_.find(key); 627 return available_sessions_.find(key);
453 } 628 }
454 629
455 void SpdySessionPool::UnmapKey(const SpdySessionKey& key) { 630 void SpdySessionPool::UnmapKey(const SpdySessionKey& key, bool ip_pooled) {
456 AvailableSessionMap::iterator it = LookupAvailableSessionByKey(key); 631 available_sessions_.erase(key, ip_pooled);
457 CHECK(it != available_sessions_.end());
458 available_sessions_.erase(it);
459 } 632 }
460 633
461 void SpdySessionPool::RemoveAliases(const SpdySessionKey& key) { 634 void SpdySessionPool::RemoveAliases(const SpdySessionKey& key) {
462 // Walk the aliases map, find references to this pair. 635 // Walk the aliases map, find references to this pair.
463 // TODO(mbelshe): Figure out if this is too expensive. 636 // TODO(mbelshe): Figure out if this is too expensive.
464 for (AliasMap::iterator it = aliases_.begin(); it != aliases_.end(); ) { 637 for (AliasMap::iterator it = aliases_.begin(); it != aliases_.end(); ) {
465 if (it->second.Equals(key)) { 638 if (it->second.Equals(key)) {
466 AliasMap::iterator old_it = it; 639 AliasMap::iterator old_it = it;
467 ++it; 640 ++it;
468 aliases_.erase(old_it); 641 aliases_.erase(old_it);
(...skipping 24 matching lines...) Expand all
493 666
494 if (idle_only && (*it)->is_active()) 667 if (idle_only && (*it)->is_active())
495 continue; 668 continue;
496 669
497 (*it)->CloseSessionOnError(error, description); 670 (*it)->CloseSessionOnError(error, description);
498 DCHECK(!IsSessionAvailable(*it)); 671 DCHECK(!IsSessionAvailable(*it));
499 } 672 }
500 } 673 }
501 674
502 } // namespace net 675 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698