OLD | NEW |
1 // Copyright (c) 2010 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2010 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_network_transaction.h" | 5 #include "net/http/http_network_transaction.h" |
6 | 6 |
7 #include "base/compiler_specific.h" | 7 #include "base/compiler_specific.h" |
8 #include "base/field_trial.h" | 8 #include "base/field_trial.h" |
9 #include "base/format_macros.h" | 9 #include "base/format_macros.h" |
10 #include "base/histogram.h" | 10 #include "base/histogram.h" |
(...skipping 248 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
259 return rv; | 259 return rv; |
260 } | 260 } |
261 | 261 |
262 int HttpNetworkTransaction::RestartIgnoringLastError( | 262 int HttpNetworkTransaction::RestartIgnoringLastError( |
263 CompletionCallback* callback) { | 263 CompletionCallback* callback) { |
264 if (connection_->socket() && connection_->socket()->IsConnectedAndIdle()) { | 264 if (connection_->socket() && connection_->socket()->IsConnectedAndIdle()) { |
265 // TODO(wtc): Should we update any of the connection histograms that we | 265 // TODO(wtc): Should we update any of the connection histograms that we |
266 // update in DoSSLConnectComplete if |result| is OK? | 266 // update in DoSSLConnectComplete if |result| is OK? |
267 if (using_spdy_) { | 267 if (using_spdy_) { |
268 // TODO(cbentzel): Add auth support to spdy. See http://crbug.com/46620 | 268 // TODO(cbentzel): Add auth support to spdy. See http://crbug.com/46620 |
269 next_state_ = STATE_SPDY_SEND_REQUEST; | 269 next_state_ = STATE_SPDY_GET_STREAM; |
270 } else { | 270 } else { |
271 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN; | 271 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN; |
272 } | 272 } |
273 } else { | 273 } else { |
274 if (connection_->socket()) | 274 if (connection_->socket()) |
275 connection_->socket()->Disconnect(); | 275 connection_->socket()->Disconnect(); |
276 connection_->Reset(); | 276 connection_->Reset(); |
277 next_state_ = STATE_INIT_CONNECTION; | 277 next_state_ = STATE_INIT_CONNECTION; |
278 } | 278 } |
279 int rv = DoLoop(OK); | 279 int rv = DoLoop(OK); |
(...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
430 switch (next_state_) { | 430 switch (next_state_) { |
431 case STATE_RESOLVE_PROXY_COMPLETE: | 431 case STATE_RESOLVE_PROXY_COMPLETE: |
432 return LOAD_STATE_RESOLVING_PROXY_FOR_URL; | 432 return LOAD_STATE_RESOLVING_PROXY_FOR_URL; |
433 case STATE_INIT_CONNECTION_COMPLETE: | 433 case STATE_INIT_CONNECTION_COMPLETE: |
434 return connection_->GetLoadState(); | 434 return connection_->GetLoadState(); |
435 case STATE_SSL_CONNECT_COMPLETE: | 435 case STATE_SSL_CONNECT_COMPLETE: |
436 return LOAD_STATE_SSL_HANDSHAKE; | 436 return LOAD_STATE_SSL_HANDSHAKE; |
437 case STATE_GENERATE_PROXY_AUTH_TOKEN_COMPLETE: | 437 case STATE_GENERATE_PROXY_AUTH_TOKEN_COMPLETE: |
438 case STATE_GENERATE_SERVER_AUTH_TOKEN_COMPLETE: | 438 case STATE_GENERATE_SERVER_AUTH_TOKEN_COMPLETE: |
439 case STATE_SEND_REQUEST_COMPLETE: | 439 case STATE_SEND_REQUEST_COMPLETE: |
| 440 case STATE_SPDY_GET_STREAM: |
440 case STATE_SPDY_SEND_REQUEST_COMPLETE: | 441 case STATE_SPDY_SEND_REQUEST_COMPLETE: |
441 return LOAD_STATE_SENDING_REQUEST; | 442 return LOAD_STATE_SENDING_REQUEST; |
442 case STATE_READ_HEADERS_COMPLETE: | 443 case STATE_READ_HEADERS_COMPLETE: |
443 case STATE_SPDY_READ_HEADERS_COMPLETE: | 444 case STATE_SPDY_READ_HEADERS_COMPLETE: |
444 return LOAD_STATE_WAITING_FOR_RESPONSE; | 445 return LOAD_STATE_WAITING_FOR_RESPONSE; |
445 case STATE_READ_BODY_COMPLETE: | 446 case STATE_READ_BODY_COMPLETE: |
446 case STATE_SPDY_READ_BODY_COMPLETE: | 447 case STATE_SPDY_READ_BODY_COMPLETE: |
447 return LOAD_STATE_READING_RESPONSE; | 448 return LOAD_STATE_READING_RESPONSE; |
448 default: | 449 default: |
449 return LOAD_STATE_IDLE; | 450 return LOAD_STATE_IDLE; |
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
563 DCHECK_EQ(OK, rv); | 564 DCHECK_EQ(OK, rv); |
564 net_log_.BeginEvent( | 565 net_log_.BeginEvent( |
565 NetLog::TYPE_HTTP_TRANSACTION_DRAIN_BODY_FOR_AUTH_RESTART, NULL); | 566 NetLog::TYPE_HTTP_TRANSACTION_DRAIN_BODY_FOR_AUTH_RESTART, NULL); |
566 rv = DoDrainBodyForAuthRestart(); | 567 rv = DoDrainBodyForAuthRestart(); |
567 break; | 568 break; |
568 case STATE_DRAIN_BODY_FOR_AUTH_RESTART_COMPLETE: | 569 case STATE_DRAIN_BODY_FOR_AUTH_RESTART_COMPLETE: |
569 rv = DoDrainBodyForAuthRestartComplete(rv); | 570 rv = DoDrainBodyForAuthRestartComplete(rv); |
570 net_log_.EndEvent( | 571 net_log_.EndEvent( |
571 NetLog::TYPE_HTTP_TRANSACTION_DRAIN_BODY_FOR_AUTH_RESTART, NULL); | 572 NetLog::TYPE_HTTP_TRANSACTION_DRAIN_BODY_FOR_AUTH_RESTART, NULL); |
572 break; | 573 break; |
| 574 case STATE_SPDY_GET_STREAM: |
| 575 DCHECK_EQ(OK, rv); |
| 576 rv = DoSpdyGetStream(); |
| 577 break; |
| 578 case STATE_SPDY_GET_STREAM_COMPLETE: |
| 579 rv = DoSpdyGetStreamComplete(rv); |
| 580 break; |
573 case STATE_SPDY_SEND_REQUEST: | 581 case STATE_SPDY_SEND_REQUEST: |
574 DCHECK_EQ(OK, rv); | 582 DCHECK_EQ(OK, rv); |
575 net_log_.BeginEvent(NetLog::TYPE_SPDY_TRANSACTION_SEND_REQUEST, NULL); | 583 net_log_.BeginEvent(NetLog::TYPE_SPDY_TRANSACTION_SEND_REQUEST, NULL); |
576 rv = DoSpdySendRequest(); | 584 rv = DoSpdySendRequest(); |
577 break; | 585 break; |
578 case STATE_SPDY_SEND_REQUEST_COMPLETE: | 586 case STATE_SPDY_SEND_REQUEST_COMPLETE: |
579 rv = DoSpdySendRequestComplete(rv); | 587 rv = DoSpdySendRequestComplete(rv); |
580 net_log_.EndEvent(NetLog::TYPE_SPDY_TRANSACTION_SEND_REQUEST, NULL); | 588 net_log_.EndEvent(NetLog::TYPE_SPDY_TRANSACTION_SEND_REQUEST, NULL); |
581 break; | 589 break; |
582 case STATE_SPDY_READ_HEADERS: | 590 case STATE_SPDY_READ_HEADERS: |
(...skipping 132 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
715 endpoint_.port = session_->fixed_https_port(); | 723 endpoint_.port = session_->fixed_https_port(); |
716 } else if (session_->fixed_http_port() != 0) { | 724 } else if (session_->fixed_http_port() != 0) { |
717 endpoint_.port = session_->fixed_http_port(); | 725 endpoint_.port = session_->fixed_http_port(); |
718 } | 726 } |
719 | 727 |
720 // Check first if we have a spdy session for this group. If so, then go | 728 // Check first if we have a spdy session for this group. If so, then go |
721 // straight to using that. | 729 // straight to using that. |
722 if (session_->spdy_session_pool()->HasSession(endpoint_)) { | 730 if (session_->spdy_session_pool()->HasSession(endpoint_)) { |
723 using_spdy_ = true; | 731 using_spdy_ = true; |
724 reused_socket_ = true; | 732 reused_socket_ = true; |
725 next_state_ = STATE_SPDY_SEND_REQUEST; | 733 next_state_ = STATE_SPDY_GET_STREAM; |
726 return OK; | 734 return OK; |
727 } | 735 } |
728 | 736 |
729 // Build the string used to uniquely identify connections of this type. | 737 // Build the string used to uniquely identify connections of this type. |
730 // Determine the host and port to connect to. | 738 // Determine the host and port to connect to. |
731 std::string connection_group = endpoint_.ToString(); | 739 std::string connection_group = endpoint_.ToString(); |
732 DCHECK(!connection_group.empty()); | 740 DCHECK(!connection_group.empty()); |
733 | 741 |
734 if (using_ssl_) | 742 if (using_ssl_) |
735 connection_group = StringPrintf("ssl/%s", connection_group.c_str()); | 743 connection_group = StringPrintf("ssl/%s", connection_group.c_str()); |
(...skipping 189 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
925 } | 933 } |
926 | 934 |
927 if (result == ERR_SSL_CLIENT_AUTH_CERT_NEEDED) | 935 if (result == ERR_SSL_CLIENT_AUTH_CERT_NEEDED) |
928 return HandleCertificateRequest(result); | 936 return HandleCertificateRequest(result); |
929 if (result < 0) | 937 if (result < 0) |
930 return HandleSSLHandshakeError(result); | 938 return HandleSSLHandshakeError(result); |
931 | 939 |
932 if (using_spdy_) { | 940 if (using_spdy_) { |
933 UpdateConnectionTypeHistograms(CONNECTION_SPDY); | 941 UpdateConnectionTypeHistograms(CONNECTION_SPDY); |
934 // TODO(cbentzel): Add auth support to spdy. See http://crbug.com/46620 | 942 // TODO(cbentzel): Add auth support to spdy. See http://crbug.com/46620 |
935 next_state_ = STATE_SPDY_SEND_REQUEST; | 943 next_state_ = STATE_SPDY_GET_STREAM; |
936 } else { | 944 } else { |
937 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN; | 945 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN; |
938 } | 946 } |
939 return OK; | 947 return OK; |
940 } | 948 } |
941 | 949 |
942 int HttpNetworkTransaction::DoGenerateProxyAuthToken() { | 950 int HttpNetworkTransaction::DoGenerateProxyAuthToken() { |
943 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN_COMPLETE; | 951 next_state_ = STATE_GENERATE_PROXY_AUTH_TOKEN_COMPLETE; |
944 if (!ShouldApplyProxyAuth()) | 952 if (!ShouldApplyProxyAuth()) |
945 return OK; | 953 return OK; |
(...skipping 261 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1207 if (done) { | 1215 if (done) { |
1208 DidDrainBodyForAuthRestart(keep_alive); | 1216 DidDrainBodyForAuthRestart(keep_alive); |
1209 } else { | 1217 } else { |
1210 // Keep draining. | 1218 // Keep draining. |
1211 next_state_ = STATE_DRAIN_BODY_FOR_AUTH_RESTART; | 1219 next_state_ = STATE_DRAIN_BODY_FOR_AUTH_RESTART; |
1212 } | 1220 } |
1213 | 1221 |
1214 return OK; | 1222 return OK; |
1215 } | 1223 } |
1216 | 1224 |
1217 int HttpNetworkTransaction::DoSpdySendRequest() { | 1225 int HttpNetworkTransaction::DoSpdyGetStream() { |
1218 next_state_ = STATE_SPDY_SEND_REQUEST_COMPLETE; | 1226 next_state_ = STATE_SPDY_GET_STREAM_COMPLETE; |
1219 CHECK(!spdy_http_stream_.get()); | 1227 CHECK(!spdy_http_stream_.get()); |
1220 | 1228 |
1221 // First we get a SPDY session. Theoretically, we've just negotiated one, but | 1229 // First we get a SPDY session. Theoretically, we've just negotiated one, but |
1222 // if one already exists, then screw it, use the existing one! Otherwise, | 1230 // if one already exists, then screw it, use the existing one! Otherwise, |
1223 // use the existing TCP socket. | 1231 // use the existing TCP socket. |
1224 | 1232 |
1225 const scoped_refptr<SpdySessionPool> spdy_pool = | 1233 const scoped_refptr<SpdySessionPool> spdy_pool = |
1226 session_->spdy_session_pool(); | 1234 session_->spdy_session_pool(); |
1227 scoped_refptr<SpdySession> spdy_session; | 1235 scoped_refptr<SpdySession> spdy_session; |
1228 | 1236 |
1229 if (spdy_pool->HasSession(endpoint_)) { | 1237 if (spdy_pool->HasSession(endpoint_)) { |
1230 spdy_session = spdy_pool->Get(endpoint_, session_, net_log_); | 1238 spdy_session = spdy_pool->Get(endpoint_, session_, net_log_); |
1231 } else { | 1239 } else { |
1232 // SPDY is negotiated using the TLS next protocol negotiation (NPN) | 1240 // SPDY is negotiated using the TLS next protocol negotiation (NPN) |
1233 // extension, so |connection_| must contain an SSLClientSocket. | 1241 // extension, so |connection_| must contain an SSLClientSocket. |
1234 DCHECK(using_ssl_); | 1242 DCHECK(using_ssl_); |
1235 CHECK(connection_->socket()); | 1243 CHECK(connection_->socket()); |
1236 int error = spdy_pool->GetSpdySessionFromSSLSocket( | 1244 int error = spdy_pool->GetSpdySessionFromSSLSocket( |
1237 endpoint_, session_, connection_.release(), net_log_, | 1245 endpoint_, session_, connection_.release(), net_log_, |
1238 spdy_certificate_error_, &spdy_session); | 1246 spdy_certificate_error_, &spdy_session); |
1239 if (error != OK) | 1247 if (error != OK) |
1240 return error; | 1248 return error; |
1241 } | 1249 } |
1242 | 1250 |
1243 CHECK(spdy_session.get()); | 1251 CHECK(spdy_session.get()); |
1244 if(spdy_session->IsClosed()) | 1252 if(spdy_session->IsClosed()) |
1245 return ERR_CONNECTION_CLOSED; | 1253 return ERR_CONNECTION_CLOSED; |
1246 | 1254 |
1247 UploadDataStream* upload_data = NULL; | 1255 headers_valid_ = false; |
| 1256 |
| 1257 spdy_http_stream_.reset(new SpdyHttpStream()); |
| 1258 return spdy_http_stream_->InitializeStream(spdy_session, *request_, |
| 1259 net_log_, &io_callback_); |
| 1260 } |
| 1261 |
| 1262 int HttpNetworkTransaction::DoSpdyGetStreamComplete(int result) { |
| 1263 if (result < 0) |
| 1264 return result; |
| 1265 |
| 1266 next_state_ = STATE_SPDY_SEND_REQUEST; |
| 1267 return OK; |
| 1268 } |
| 1269 |
| 1270 int HttpNetworkTransaction::DoSpdySendRequest() { |
| 1271 next_state_ = STATE_SPDY_SEND_REQUEST_COMPLETE; |
| 1272 |
| 1273 UploadDataStream* upload_data_stream = NULL; |
1248 if (request_->upload_data) { | 1274 if (request_->upload_data) { |
1249 int error_code = OK; | 1275 int error_code = OK; |
1250 upload_data = UploadDataStream::Create(request_->upload_data, &error_code); | 1276 upload_data_stream = UploadDataStream::Create(request_->upload_data, |
1251 if (!upload_data) | 1277 &error_code); |
| 1278 if (!upload_data_stream) |
1252 return error_code; | 1279 return error_code; |
1253 } | 1280 } |
1254 headers_valid_ = false; | 1281 spdy_http_stream_->InitializeRequest(base::Time::Now(), upload_data_stream); |
1255 scoped_refptr<SpdyStream> spdy_stream; | 1282 |
1256 if (request_->method == "GET") { | |
1257 int error = | |
1258 spdy_session->GetPushStream(request_->url, &spdy_stream, net_log_); | |
1259 if (error != OK) | |
1260 return error; | |
1261 } | |
1262 if (spdy_stream.get()) { | |
1263 DCHECK(spdy_stream->pushed()); | |
1264 CHECK(spdy_stream->GetDelegate() == NULL); | |
1265 spdy_http_stream_.reset(new SpdyHttpStream(spdy_stream)); | |
1266 spdy_http_stream_->InitializeRequest(*request_, base::Time::Now(), NULL); | |
1267 } else { | |
1268 int error = spdy_session->CreateStream(request_->url, | |
1269 request_->priority, | |
1270 &spdy_stream, | |
1271 net_log_); | |
1272 if (error != OK) | |
1273 return error; | |
1274 DCHECK(!spdy_stream->pushed()); | |
1275 CHECK(spdy_stream->GetDelegate() == NULL); | |
1276 spdy_http_stream_.reset(new SpdyHttpStream(spdy_stream)); | |
1277 spdy_http_stream_->InitializeRequest( | |
1278 *request_, base::Time::Now(), upload_data); | |
1279 } | |
1280 return spdy_http_stream_->SendRequest(&response_, &io_callback_); | 1283 return spdy_http_stream_->SendRequest(&response_, &io_callback_); |
1281 } | 1284 } |
1282 | 1285 |
1283 int HttpNetworkTransaction::DoSpdySendRequestComplete(int result) { | 1286 int HttpNetworkTransaction::DoSpdySendRequestComplete(int result) { |
1284 if (result < 0) | 1287 if (result < 0) |
1285 return result; | 1288 return result; |
1286 | 1289 |
1287 next_state_ = STATE_SPDY_READ_HEADERS; | 1290 next_state_ = STATE_SPDY_READ_HEADERS; |
1288 return OK; | 1291 return OK; |
1289 } | 1292 } |
(...skipping 486 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1776 STATE_CASE(STATE_GENERATE_SERVER_AUTH_TOKEN); | 1779 STATE_CASE(STATE_GENERATE_SERVER_AUTH_TOKEN); |
1777 STATE_CASE(STATE_GENERATE_SERVER_AUTH_TOKEN_COMPLETE); | 1780 STATE_CASE(STATE_GENERATE_SERVER_AUTH_TOKEN_COMPLETE); |
1778 STATE_CASE(STATE_SEND_REQUEST); | 1781 STATE_CASE(STATE_SEND_REQUEST); |
1779 STATE_CASE(STATE_SEND_REQUEST_COMPLETE); | 1782 STATE_CASE(STATE_SEND_REQUEST_COMPLETE); |
1780 STATE_CASE(STATE_READ_HEADERS); | 1783 STATE_CASE(STATE_READ_HEADERS); |
1781 STATE_CASE(STATE_READ_HEADERS_COMPLETE); | 1784 STATE_CASE(STATE_READ_HEADERS_COMPLETE); |
1782 STATE_CASE(STATE_READ_BODY); | 1785 STATE_CASE(STATE_READ_BODY); |
1783 STATE_CASE(STATE_READ_BODY_COMPLETE); | 1786 STATE_CASE(STATE_READ_BODY_COMPLETE); |
1784 STATE_CASE(STATE_DRAIN_BODY_FOR_AUTH_RESTART); | 1787 STATE_CASE(STATE_DRAIN_BODY_FOR_AUTH_RESTART); |
1785 STATE_CASE(STATE_DRAIN_BODY_FOR_AUTH_RESTART_COMPLETE); | 1788 STATE_CASE(STATE_DRAIN_BODY_FOR_AUTH_RESTART_COMPLETE); |
| 1789 STATE_CASE(STATE_SPDY_GET_STREAM); |
| 1790 STATE_CASE(STATE_SPDY_GET_STREAM_COMPLETE); |
1786 STATE_CASE(STATE_SPDY_SEND_REQUEST); | 1791 STATE_CASE(STATE_SPDY_SEND_REQUEST); |
1787 STATE_CASE(STATE_SPDY_SEND_REQUEST_COMPLETE); | 1792 STATE_CASE(STATE_SPDY_SEND_REQUEST_COMPLETE); |
1788 STATE_CASE(STATE_SPDY_READ_HEADERS); | 1793 STATE_CASE(STATE_SPDY_READ_HEADERS); |
1789 STATE_CASE(STATE_SPDY_READ_HEADERS_COMPLETE); | 1794 STATE_CASE(STATE_SPDY_READ_HEADERS_COMPLETE); |
1790 STATE_CASE(STATE_SPDY_READ_BODY); | 1795 STATE_CASE(STATE_SPDY_READ_BODY); |
1791 STATE_CASE(STATE_SPDY_READ_BODY_COMPLETE); | 1796 STATE_CASE(STATE_SPDY_READ_BODY_COMPLETE); |
1792 STATE_CASE(STATE_NONE); | 1797 STATE_CASE(STATE_NONE); |
1793 default: | 1798 default: |
1794 description = StringPrintf("Unknown state 0x%08X (%u)", state, state); | 1799 description = StringPrintf("Unknown state 0x%08X (%u)", state, state); |
1795 break; | 1800 break; |
1796 } | 1801 } |
1797 return description; | 1802 return description; |
1798 } | 1803 } |
1799 | 1804 |
1800 #undef STATE_CASE | 1805 #undef STATE_CASE |
1801 | 1806 |
1802 } // namespace net | 1807 } // namespace net |
OLD | NEW |