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

Side by Side Diff: net/http/http_stream_factory_impl_job_controller.cc

Issue 2332193003: JobController3: Move MarkAlternativeServiceBroken to job controller (Closed)
Patch Set: rebase Created 4 years, 3 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) 2016 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2016 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/http/http_stream_factory_impl_job_controller.h" 5 #include "net/http/http_stream_factory_impl_job_controller.h"
6 6
7 #include "base/metrics/histogram_macros.h" 7 #include "base/metrics/histogram_macros.h"
8 #include "base/strings/string_number_conversions.h" 8 #include "base/strings/string_number_conversions.h"
9 #include "base/strings/string_util.h" 9 #include "base/strings/string_util.h"
10 #include "base/values.h" 10 #include "base/values.h"
(...skipping 20 matching lines...) Expand all
31 HttpStreamFactoryImpl* factory, 31 HttpStreamFactoryImpl* factory,
32 HttpStreamRequest::Delegate* delegate, 32 HttpStreamRequest::Delegate* delegate,
33 HttpNetworkSession* session, 33 HttpNetworkSession* session,
34 JobFactory* job_factory) 34 JobFactory* job_factory)
35 : factory_(factory), 35 : factory_(factory),
36 session_(session), 36 session_(session),
37 job_factory_(job_factory), 37 job_factory_(job_factory),
38 request_(nullptr), 38 request_(nullptr),
39 delegate_(delegate), 39 delegate_(delegate),
40 is_preconnect_(false), 40 is_preconnect_(false),
41 alternative_service_is_broken_(false),
41 job_bound_(false), 42 job_bound_(false),
42 main_job_is_blocked_(false), 43 main_job_is_blocked_(false),
43 bound_job_(nullptr), 44 bound_job_(nullptr),
44 can_start_alternative_proxy_job_(false), 45 can_start_alternative_proxy_job_(false),
45 ptr_factory_(this) { 46 ptr_factory_(this) {
46 DCHECK(factory); 47 DCHECK(factory);
47 } 48 }
48 49
49 HttpStreamFactoryImpl::JobController::~JobController() { 50 HttpStreamFactoryImpl::JobController::~JobController() {
50 main_job_.reset(); 51 main_job_.reset();
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after
212 request_->OnBidirectionalStreamImplReady(used_ssl_config, used_proxy_info, 213 request_->OnBidirectionalStreamImplReady(used_ssl_config, used_proxy_info,
213 stream.release()); 214 stream.release());
214 } 215 }
215 216
216 void HttpStreamFactoryImpl::JobController::OnWebSocketHandshakeStreamReady( 217 void HttpStreamFactoryImpl::JobController::OnWebSocketHandshakeStreamReady(
217 Job* job, 218 Job* job,
218 const SSLConfig& used_ssl_config, 219 const SSLConfig& used_ssl_config,
219 const ProxyInfo& used_proxy_info, 220 const ProxyInfo& used_proxy_info,
220 WebSocketHandshakeStreamBase* stream) { 221 WebSocketHandshakeStreamBase* stream) {
221 DCHECK(job); 222 DCHECK(job);
222
223 MarkRequestComplete(job->was_npn_negotiated(), job->negotiated_protocol(), 223 MarkRequestComplete(job->was_npn_negotiated(), job->negotiated_protocol(),
224 job->using_spdy()); 224 job->using_spdy());
225 225
226 if (!request_) 226 if (!request_)
227 return; 227 return;
228 DCHECK(factory_->for_websockets_); 228 DCHECK(factory_->for_websockets_);
229 DCHECK_EQ(HttpStreamRequest::HTTP_STREAM, request_->stream_type()); 229 DCHECK_EQ(HttpStreamRequest::HTTP_STREAM, request_->stream_type());
230 DCHECK(stream); 230 DCHECK(stream);
231 231
232 OnJobSucceeded(job); 232 OnJobSucceeded(job);
233 request_->OnWebSocketHandshakeStreamReady(used_ssl_config, used_proxy_info, 233 request_->OnWebSocketHandshakeStreamReady(used_ssl_config, used_proxy_info,
234 stream); 234 stream);
235 } 235 }
236 236
237 void HttpStreamFactoryImpl::JobController::OnStreamFailed( 237 void HttpStreamFactoryImpl::JobController::OnStreamFailed(
238 Job* job, 238 Job* job,
239 int status, 239 int status,
240 const SSLConfig& used_ssl_config) { 240 const SSLConfig& used_ssl_config) {
241 if (job->job_type() == ALTERNATIVE)
242 MarkAlternativeServiceBroken(job);
243
241 MaybeResumeMainJob(job, base::TimeDelta()); 244 MaybeResumeMainJob(job, base::TimeDelta());
242 245
243 if (job_bound_ && bound_job_ != job) { 246 if ((job_bound_ && bound_job_ != job) || !request_) {
244 // We have bound a job to the associated Request, |job| has been orphaned. 247 if (job->job_type() == ALTERNATIVE)
245 OnOrphanedJobComplete(job); 248 ReportAlternativeServiceBroken(job);
249 if (request_) {
Ryan Hamilton 2016/09/14 21:45:42 I'm having a hard time following this. I think tha
Zhongyi Shi 2016/09/14 23:07:07 Yup. I have moved the logic up to OnAlternativeJob
250 // We have bound a job to the associated Request, |job| has been orphaned.
251 OnOrphanedJobComplete(job);
252 }
246 return; 253 return;
247 } 254 }
248
249 if (!request_)
250 return;
251 DCHECK_NE(OK, status); 255 DCHECK_NE(OK, status);
252 DCHECK(job); 256 DCHECK(job);
253 257
254 if (!bound_job_) { 258 if (!bound_job_) {
255 if (main_job_ && alternative_job_) { 259 if (main_job_ && alternative_job_) {
256 // Hey, we've got other jobs! Maybe one of them will succeed, let's just 260 // Hey, we've got other jobs! Maybe one of them will succeed, let's just
257 // ignore this failure. 261 // ignore this failure.
258 factory_->request_map_.erase(job); 262 factory_->request_map_.erase(job);
259 // Notify all the other jobs that this one failed.
260 if (job->job_type() == MAIN) { 263 if (job->job_type() == MAIN) {
261 alternative_job_->MarkOtherJobComplete(*job);
262 main_job_.reset(); 264 main_job_.reset();
263 } else { 265 } else {
264 DCHECK(job->job_type() == ALTERNATIVE); 266 DCHECK(job->job_type() == ALTERNATIVE);
265 main_job_->MarkOtherJobComplete(*job);
266 alternative_job_.reset(); 267 alternative_job_.reset();
267 } 268 }
268 return; 269 return;
269 } else { 270 } else {
270 BindJob(job); 271 BindJob(job);
271 } 272 }
272 } 273 }
273 274
274 request_->OnStreamFailed(status, used_ssl_config); 275 request_->OnStreamFailed(status, used_ssl_config);
275 } 276 }
(...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after
413 const bool was_npn_negotiated = job->was_npn_negotiated(); 414 const bool was_npn_negotiated = job->was_npn_negotiated();
414 const NextProto negotiated_protocol = job->negotiated_protocol(); 415 const NextProto negotiated_protocol = job->negotiated_protocol();
415 const bool using_spdy = job->using_spdy(); 416 const bool using_spdy = job->using_spdy();
416 const BoundNetLog net_log = job->net_log(); 417 const BoundNetLog net_log = job->net_log();
417 418
418 // Cache this so we can still use it if the JobController is deleted. 419 // Cache this so we can still use it if the JobController is deleted.
419 HttpStreamFactoryImpl* factory = factory_; 420 HttpStreamFactoryImpl* factory = factory_;
420 421
421 // Notify |request_|. 422 // Notify |request_|.
422 if (!is_preconnect_ && !is_job_orphaned) { 423 if (!is_preconnect_ && !is_job_orphaned) {
424 if (job->job_type() == MAIN && alternative_service_is_broken_) {
425 // Report alternative service marked as broken.
426 ReportAlternativeServiceBroken(job);
427 }
428
423 DCHECK(request_); 429 DCHECK(request_);
424 430
425 // The first case is the usual case. 431 // The first case is the usual case.
426 if (!job_bound_) { 432 if (!job_bound_) {
427 BindJob(job); 433 BindJob(job);
428 } 434 }
429 435
430 MarkRequestComplete(was_npn_negotiated, negotiated_protocol, using_spdy); 436 MarkRequestComplete(was_npn_negotiated, negotiated_protocol, using_spdy);
431 437
432 std::unique_ptr<HttpStream> stream; 438 std::unique_ptr<HttpStream> stream;
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after
497 base::Bind(&NetLogHttpStreamJobDelayCallback, main_job_wait_time_)); 503 base::Bind(&NetLogHttpStreamJobDelayCallback, main_job_wait_time_));
498 504
499 main_job_->Resume(); 505 main_job_->Resume();
500 main_job_wait_time_ = base::TimeDelta(); 506 main_job_wait_time_ = base::TimeDelta();
501 } 507 }
502 508
503 void HttpStreamFactoryImpl::JobController::MaybeResumeMainJob( 509 void HttpStreamFactoryImpl::JobController::MaybeResumeMainJob(
504 Job* job, 510 Job* job,
505 const base::TimeDelta& delay) { 511 const base::TimeDelta& delay) {
506 DCHECK(job == main_job_.get() || job == alternative_job_.get()); 512 DCHECK(job == main_job_.get() || job == alternative_job_.get());
513
507 if (!main_job_is_blocked_ || job != alternative_job_.get() || !main_job_) 514 if (!main_job_is_blocked_ || job != alternative_job_.get() || !main_job_)
508 return; 515 return;
509 516
510 main_job_is_blocked_ = false; 517 main_job_is_blocked_ = false;
511 518
512 if (!main_job_->is_waiting()) 519 if (!main_job_->is_waiting())
513 return; 520 return;
514 521
515 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 522 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
516 FROM_HERE, 523 FROM_HERE,
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after
724 // because we *WANT* to cancel the unnecessary Jobs from other requests if 731 // because we *WANT* to cancel the unnecessary Jobs from other requests if
725 // another Job completes first. 732 // another Job completes first.
726 // TODO(mbelshe): Revisit this when we implement ip connection pooling of 733 // TODO(mbelshe): Revisit this when we implement ip connection pooling of
727 // SpdySessions. Do we want to orphan the jobs for a different hostname so 734 // SpdySessions. Do we want to orphan the jobs for a different hostname so
728 // they complete? Or do we want to prevent connecting a new SpdySession if 735 // they complete? Or do we want to prevent connecting a new SpdySession if
729 // we've already got one available for a different hostname where the ip 736 // we've already got one available for a different hostname where the ip
730 // address matches up? 737 // address matches up?
731 CancelJobs(); 738 CancelJobs();
732 return; 739 return;
733 } 740 }
741
742 if (job->job_type() == MAIN && alternative_service_is_broken_) {
743 ReportAlternativeServiceBroken(job);
744 }
745
734 if (!bound_job_) { 746 if (!bound_job_) {
735 if (main_job_ && alternative_job_) { 747 if (main_job_ && alternative_job_)
736 job->ReportJobSucceededForRequest(); 748 job->ReportJobSucceededForRequest();
737 // Notify all the other jobs that this one succeeded.
738 if (job->job_type() == MAIN) {
739 alternative_job_->MarkOtherJobComplete(*job);
740 } else {
741 DCHECK(job->job_type() == ALTERNATIVE);
742 main_job_->MarkOtherJobComplete(*job);
743 }
744 }
745 BindJob(job); 749 BindJob(job);
746 return; 750 return;
747 } 751 }
748 DCHECK(bound_job_); 752 DCHECK(bound_job_);
749 } 753 }
750 754
751 void HttpStreamFactoryImpl::JobController::MarkRequestComplete( 755 void HttpStreamFactoryImpl::JobController::MarkRequestComplete(
752 bool was_npn_negotiated, 756 bool was_npn_negotiated,
753 NextProto negotiated_protocol, 757 NextProto negotiated_protocol,
754 bool using_spdy) { 758 bool using_spdy) {
755 if (request_) 759 if (request_)
756 request_->Complete(was_npn_negotiated, negotiated_protocol, using_spdy); 760 request_->Complete(was_npn_negotiated, negotiated_protocol, using_spdy);
757 } 761 }
758 762
763 void HttpStreamFactoryImpl::JobController::MarkAlternativeServiceBroken(
764 Job* job) {
765 DCHECK_EQ(job->job_type(), ALTERNATIVE);
766
767 alternative_service_is_broken_ = true;
768
769 if (job->alternative_proxy_server().is_valid()) {
770 broken_alternative_proxy_server_ = job->alternative_proxy_server();
771 } else {
772 DCHECK(!broken_alternative_proxy_server_.is_valid());
773 broken_alternative_service_ = job->alternative_service();
774 }
775 }
776
777 void HttpStreamFactoryImpl::JobController::ReportAlternativeServiceBroken(
778 Job* job) {
Ryan Hamilton 2016/09/14 21:45:42 This |job| argument is unused, right? If so, it's
Zhongyi Shi 2016/09/14 23:07:07 Done.
779 DCHECK(broken_alternative_service_.protocol !=
780 UNINITIALIZED_ALTERNATE_PROTOCOL ||
781 broken_alternative_proxy_server_.is_valid());
782
783 if (broken_alternative_proxy_server_.is_valid()) {
784 ProxyDelegate* proxy_delegate = session_->params().proxy_delegate;
785 if (proxy_delegate)
786 proxy_delegate->OnAlternativeProxyBroken(
787 broken_alternative_proxy_server_);
788 } else {
789 HistogramBrokenAlternateProtocolLocation(
790 BROKEN_ALTERNATE_PROTOCOL_LOCATION_HTTP_STREAM_FACTORY_IMPL_JOB_ALT);
791 session_->http_server_properties()->MarkAlternativeServiceBroken(
792 broken_alternative_service_);
793 }
794 session_->quic_stream_factory()->OnTcpJobCompleted(true);
795 }
796
759 void HttpStreamFactoryImpl::JobController::MaybeNotifyFactoryOfCompletion() { 797 void HttpStreamFactoryImpl::JobController::MaybeNotifyFactoryOfCompletion() {
760 if (!request_ && !main_job_ && !alternative_job_) { 798 if (!request_ && !main_job_ && !alternative_job_) {
761 DCHECK(!bound_job_); 799 DCHECK(!bound_job_);
762 factory_->OnJobControllerComplete(this); 800 factory_->OnJobControllerComplete(this);
763 } 801 }
764 } 802 }
765 803
766 GURL HttpStreamFactoryImpl::JobController::ApplyHostMappingRules( 804 GURL HttpStreamFactoryImpl::JobController::ApplyHostMappingRules(
767 const GURL& url, 805 const GURL& url,
768 HostPortPair* endpoint) { 806 HostPortPair* endpoint) {
(...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after
1000 // Check that QUIC is enabled globally, and it is not disabled. 1038 // Check that QUIC is enabled globally, and it is not disabled.
1001 if (!session_->params().enable_quic || 1039 if (!session_->params().enable_quic ||
1002 session_->quic_stream_factory()->IsQuicDisabled()) { 1040 session_->quic_stream_factory()->IsQuicDisabled()) {
1003 return false; 1041 return false;
1004 } 1042 }
1005 } 1043 }
1006 1044
1007 return true; 1045 return true;
1008 } 1046 }
1009 } 1047 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698