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

Side by Side Diff: net/quic/chromium/quic_network_transaction_unittest.cc

Issue 2789093003: Mark QUIC broken when the network blackholes after the handshake (Closed)
Patch Set: Address comments Created 3 years, 8 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 <memory> 5 #include <memory>
6 #include <ostream> 6 #include <ostream>
7 #include <string> 7 #include <string>
8 #include <utility> 8 #include <utility>
9 #include <vector> 9 #include <vector>
10 10
(...skipping 23 matching lines...) Expand all
34 #include "net/log/test_net_log.h" 34 #include "net/log/test_net_log.h"
35 #include "net/log/test_net_log_entry.h" 35 #include "net/log/test_net_log_entry.h"
36 #include "net/log/test_net_log_util.h" 36 #include "net/log/test_net_log_util.h"
37 #include "net/proxy/proxy_config_service_fixed.h" 37 #include "net/proxy/proxy_config_service_fixed.h"
38 #include "net/proxy/proxy_resolver.h" 38 #include "net/proxy/proxy_resolver.h"
39 #include "net/proxy/proxy_service.h" 39 #include "net/proxy/proxy_service.h"
40 #include "net/quic/chromium/crypto/proof_verifier_chromium.h" 40 #include "net/quic/chromium/crypto/proof_verifier_chromium.h"
41 #include "net/quic/chromium/mock_crypto_client_stream_factory.h" 41 #include "net/quic/chromium/mock_crypto_client_stream_factory.h"
42 #include "net/quic/chromium/mock_network_change_notifier.h" 42 #include "net/quic/chromium/mock_network_change_notifier.h"
43 #include "net/quic/chromium/mock_quic_data.h" 43 #include "net/quic/chromium/mock_quic_data.h"
44 #include "net/quic/chromium/quic_chromium_alarm_factory.h"
44 #include "net/quic/chromium/quic_http_utils.h" 45 #include "net/quic/chromium/quic_http_utils.h"
46 #include "net/quic/chromium/quic_stream_factory_peer.h"
45 #include "net/quic/chromium/quic_test_packet_maker.h" 47 #include "net/quic/chromium/quic_test_packet_maker.h"
48 #include "net/quic/chromium/test_task_runner.h"
46 #include "net/quic/core/crypto/quic_decrypter.h" 49 #include "net/quic/core/crypto/quic_decrypter.h"
47 #include "net/quic/core/crypto/quic_encrypter.h" 50 #include "net/quic/core/crypto/quic_encrypter.h"
48 #include "net/quic/core/quic_framer.h" 51 #include "net/quic/core/quic_framer.h"
49 #include "net/quic/platform/api/quic_string_piece.h" 52 #include "net/quic/platform/api/quic_string_piece.h"
50 #include "net/quic/test_tools/crypto_test_utils.h" 53 #include "net/quic/test_tools/crypto_test_utils.h"
51 #include "net/quic/test_tools/mock_clock.h" 54 #include "net/quic/test_tools/mock_clock.h"
52 #include "net/quic/test_tools/mock_random.h" 55 #include "net/quic/test_tools/mock_random.h"
53 #include "net/quic/test_tools/quic_test_utils.h" 56 #include "net/quic/test_tools/quic_test_utils.h"
54 #include "net/socket/client_socket_factory.h" 57 #include "net/socket/client_socket_factory.h"
55 #include "net/socket/mock_client_socket_pool_manager.h" 58 #include "net/socket/mock_client_socket_pool_manager.h"
(...skipping 230 matching lines...) Expand 10 before | Expand all | Expand 10 after
286 289
287 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket( 290 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket(
288 QuicPacketNumber packet_number, 291 QuicPacketNumber packet_number,
289 QuicPacketNumber largest_received, 292 QuicPacketNumber largest_received,
290 QuicPacketNumber least_unacked) { 293 QuicPacketNumber least_unacked) {
291 return client_maker_.MakeAckPacket(packet_number, largest_received, 294 return client_maker_.MakeAckPacket(packet_number, largest_received,
292 least_unacked, least_unacked, true); 295 least_unacked, least_unacked, true);
293 } 296 }
294 297
295 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket( 298 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket(
299 QuicPacketNumber packet_number,
300 QuicPacketNumber largest_received,
301 QuicPacketNumber least_unacked,
302 QuicTime::Delta ack_delay_time) {
303 return client_maker_.MakeAckPacket(packet_number, largest_received,
304 least_unacked, least_unacked, true,
305 ack_delay_time);
306 }
307
308 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket(
296 QuicPacketNumber largest_received, 309 QuicPacketNumber largest_received,
297 QuicPacketNumber least_unacked) { 310 QuicPacketNumber least_unacked) {
298 return client_maker_.MakeAckPacket(2, largest_received, least_unacked, 311 return client_maker_.MakeAckPacket(2, largest_received, least_unacked,
299 least_unacked, true); 312 least_unacked, true);
300 } 313 }
301 314
302 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket( 315 std::unique_ptr<QuicEncryptedPacket> ConstructClientAckPacket(
303 QuicPacketNumber packet_number, 316 QuicPacketNumber packet_number,
304 QuicPacketNumber largest_received, 317 QuicPacketNumber largest_received,
305 QuicPacketNumber ack_least_unacked, 318 QuicPacketNumber ack_least_unacked,
(...skipping 1041 matching lines...) Expand 10 before | Expand all | Expand 10 after
1347 EXPECT_THAT(callback.WaitForResult(), IsOk()); 1360 EXPECT_THAT(callback.WaitForResult(), IsOk());
1348 1361
1349 // Check whether this transaction is correctly marked as received a go-away 1362 // Check whether this transaction is correctly marked as received a go-away
1350 // because of migrating port. 1363 // because of migrating port.
1351 NetErrorDetails details; 1364 NetErrorDetails details;
1352 EXPECT_FALSE(details.quic_port_migration_detected); 1365 EXPECT_FALSE(details.quic_port_migration_detected);
1353 trans.PopulateNetErrorDetails(&details); 1366 trans.PopulateNetErrorDetails(&details);
1354 EXPECT_TRUE(details.quic_port_migration_detected); 1367 EXPECT_TRUE(details.quic_port_migration_detected);
1355 } 1368 }
1356 1369
1370 // Verify that if a QUIC connection times out, the QuicHttpStream will
1371 // return QUIC_PROTOCOL_ERROR.
1372 TEST_P(QuicNetworkTransactionTest, TimeoutAfterHandshakeConfirmed) {
1373 params_.quic_idle_connection_timeout_seconds = 5;
1374
1375 // The request will initially go out over QUIC.
1376 MockQuicData quic_data;
1377 QuicStreamOffset header_stream_offset = 0;
1378 SpdyPriority priority =
1379 ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY);
1380
1381 std::string request_data;
1382 quic_data.AddWrite(client_maker_.MakeRequestHeadersPacketAndSaveData(
1383 1, kClientDataStreamId1, true, true, priority,
1384 GetRequestHeaders("GET", "https", "/"), nullptr, &header_stream_offset,
1385 &request_data));
1386
1387 std::string settings_data;
1388 QuicStreamOffset settings_offset = header_stream_offset;
1389 quic_data.AddWrite(client_maker_.MakeSettingsPacketAndSaveData(
1390 2, SETTINGS_MAX_HEADER_LIST_SIZE, kDefaultMaxUncompressedHeaderSize, true,
1391 &header_stream_offset, &settings_data));
1392 // TLP 1
1393 quic_data.AddWrite(client_maker_.MakeDataPacket(3, kHeadersStreamId, true,
1394 false, 0, request_data));
1395 // TLP 2
1396 quic_data.AddWrite(client_maker_.MakeDataPacket(
1397 4, kHeadersStreamId, true, false, settings_offset, settings_data));
1398 // RTO 1
1399 quic_data.AddWrite(client_maker_.MakeDataPacket(5, kHeadersStreamId, true,
1400 false, 0, request_data));
1401 quic_data.AddWrite(client_maker_.MakeDataPacket(
1402 6, kHeadersStreamId, true, false, settings_offset, settings_data));
1403 // RTO 2
1404 quic_data.AddWrite(client_maker_.MakeDataPacket(7, kHeadersStreamId, true,
1405 false, 0, request_data));
1406 quic_data.AddWrite(client_maker_.MakeDataPacket(
1407 8, kHeadersStreamId, true, false, settings_offset, settings_data));
1408 // RTO 3
1409 quic_data.AddWrite(client_maker_.MakeDataPacket(9, kHeadersStreamId, true,
Jana 2017/04/06 02:29:18 Is it easy to set the number of timeouts for conne
Ryan Hamilton 2017/04/06 03:43:39 I didn't see an obvious mechanism :/
1410 false, 0, request_data));
1411 quic_data.AddWrite(client_maker_.MakeDataPacket(
1412 10, kHeadersStreamId, true, false, settings_offset, settings_data));
1413
1414 quic_data.AddRead(ASYNC, ERR_IO_PENDING);
1415 quic_data.AddRead(ASYNC, OK);
1416 quic_data.AddSocketDataToFactory(&socket_factory_);
1417
1418 // In order for a new QUIC session to be established via alternate-protocol
1419 // without racing an HTTP connection, we need the host resolution to happen
1420 // synchronously. Of course, even though QUIC *could* perform a 0-RTT
1421 // connection to the the server, in this test we require confirmation
1422 // before encrypting so the HTTP job will still start.
Jana 2017/04/06 02:29:18 Nice -- thanks for the elaborate comments!
Ryan Hamilton 2017/04/06 03:43:38 Yay! Thanks!
1423 host_resolver_.set_synchronous_mode(true);
1424 host_resolver_.rules()->AddIPLiteralRule("mail.example.org", "192.168.0.1",
1425 "");
1426 HostResolver::RequestInfo info(HostPortPair("mail.example.org", 443));
1427 AddressList address;
1428 std::unique_ptr<HostResolver::Request> request;
1429 host_resolver_.Resolve(info, DEFAULT_PRIORITY, &address, CompletionCallback(),
1430 &request, net_log_.bound());
1431
1432 CreateSession();
1433 // Use a TestTaskRunner to avoid waiting in real time for timeouts.
1434 scoped_refptr<TestTaskRunner> quic_task_runner_(new TestTaskRunner(clock_));
1435 QuicStreamFactoryPeer::SetAlarmFactory(
1436 session_->quic_stream_factory(),
1437 base::MakeUnique<QuicChromiumAlarmFactory>(quic_task_runner_.get(),
1438 clock_));
1439
1440 AddQuicAlternateProtocolMapping(MockCryptoClientStream::ZERO_RTT);
1441
1442 HttpNetworkTransaction trans(DEFAULT_PRIORITY, session_.get());
1443 TestCompletionCallback callback;
1444 int rv = trans.Start(&request_, callback.callback(), net_log_.bound());
1445 EXPECT_THAT(rv, IsError(ERR_IO_PENDING));
1446
1447 // Pump the message loop to get the request started.
1448 base::RunLoop().RunUntilIdle();
1449 // Explicitly confirm the handshake.
1450 crypto_client_stream_factory_.last_stream()->SendOnCryptoHandshakeEvent(
1451 QuicSession::HANDSHAKE_CONFIRMED);
1452
1453 // Run the QUIC session to completion.
1454 quic_task_runner_->RunUntilIdle();
1455
1456 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1457 EXPECT_THAT(callback.WaitForResult(), IsError(ERR_QUIC_PROTOCOL_ERROR));
1458 }
1459
1460 // Verify that if a QUIC connection RTOs, the QuicHttpStream will
1461 // return QUIC_PROTOCOL_ERROR.
1462 TEST_P(QuicNetworkTransactionTest, TooManyRtosAfterHandshakeConfirmed) {
Jana 2017/04/06 02:29:18 Isn't the test above sufficient to test this case?
Ryan Hamilton 2017/04/06 03:43:38 The previous test handles the IDLE_NETWORK_TIMEOUT
1463 params_.quic_connection_options.push_back(k5RTO);
1464
1465 // The request will initially go out over QUIC.
1466 MockQuicData quic_data;
1467 QuicStreamOffset header_stream_offset = 0;
1468 SpdyPriority priority =
1469 ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY);
1470
1471 std::string request_data;
1472 quic_data.AddWrite(client_maker_.MakeRequestHeadersPacketAndSaveData(
1473 1, kClientDataStreamId1, true, true, priority,
1474 GetRequestHeaders("GET", "https", "/"), nullptr, &header_stream_offset,
1475 &request_data));
1476
1477 std::string settings_data;
1478 QuicStreamOffset settings_offset = header_stream_offset;
1479 quic_data.AddWrite(client_maker_.MakeSettingsPacketAndSaveData(
1480 2, SETTINGS_MAX_HEADER_LIST_SIZE, kDefaultMaxUncompressedHeaderSize, true,
1481 &header_stream_offset, &settings_data));
1482 // TLP 1
1483 quic_data.AddWrite(client_maker_.MakeDataPacket(3, kHeadersStreamId, true,
1484 false, 0, request_data));
1485 // TLP 2
1486 quic_data.AddWrite(client_maker_.MakeDataPacket(
1487 4, kHeadersStreamId, true, false, settings_offset, settings_data));
1488 // RTO 1
1489 quic_data.AddWrite(client_maker_.MakeDataPacket(5, kHeadersStreamId, true,
1490 false, 0, request_data));
1491 quic_data.AddWrite(client_maker_.MakeDataPacket(
1492 6, kHeadersStreamId, true, false, settings_offset, settings_data));
1493 // RTO 2
1494 quic_data.AddWrite(client_maker_.MakeDataPacket(7, kHeadersStreamId, true,
1495 false, 0, request_data));
1496 quic_data.AddWrite(client_maker_.MakeDataPacket(
1497 8, kHeadersStreamId, true, false, settings_offset, settings_data));
1498 // RTO 3
1499 quic_data.AddWrite(client_maker_.MakeDataPacket(9, kHeadersStreamId, true,
1500 false, 0, request_data));
1501 quic_data.AddWrite(client_maker_.MakeDataPacket(
1502 10, kHeadersStreamId, true, false, settings_offset, settings_data));
1503 // RTO 4
1504 quic_data.AddWrite(client_maker_.MakeDataPacket(11, kHeadersStreamId, true,
1505 false, 0, request_data));
1506 quic_data.AddWrite(client_maker_.MakeDataPacket(
1507 12, kHeadersStreamId, true, false, settings_offset, settings_data));
1508 // RTO 5
1509 quic_data.AddWrite(client_maker_.MakeAckAndConnectionClosePacket(
1510 13, true, QuicTime::Delta::Infinite(), 0, 1, QUIC_TOO_MANY_RTOS,
1511 "5 consecutive retransmission timeouts"));
1512
1513 quic_data.AddRead(ASYNC, OK);
1514 quic_data.AddSocketDataToFactory(&socket_factory_);
1515
1516 // In order for a new QUIC session to be established via alternate-protocol
1517 // without racing an HTTP connection, we need the host resolution to happen
1518 // synchronously. Of course, even though QUIC *could* perform a 0-RTT
1519 // connection to the the server, in this test we require confirmation
1520 // before encrypting so the HTTP job will still start.
1521 host_resolver_.set_synchronous_mode(true);
1522 host_resolver_.rules()->AddIPLiteralRule("mail.example.org", "192.168.0.1",
1523 "");
1524 HostResolver::RequestInfo info(HostPortPair("mail.example.org", 443));
1525 AddressList address;
1526 std::unique_ptr<HostResolver::Request> request;
1527 host_resolver_.Resolve(info, DEFAULT_PRIORITY, &address, CompletionCallback(),
1528 &request, net_log_.bound());
1529
1530 CreateSession();
1531 // Use a TestTaskRunner to avoid waiting in real time for timeouts.
1532 scoped_refptr<TestTaskRunner> quic_task_runner_(new TestTaskRunner(clock_));
1533 QuicStreamFactoryPeer::SetAlarmFactory(
1534 session_->quic_stream_factory(),
1535 base::MakeUnique<QuicChromiumAlarmFactory>(quic_task_runner_.get(),
1536 clock_));
1537
1538 AddQuicAlternateProtocolMapping(MockCryptoClientStream::ZERO_RTT);
1539
1540 HttpNetworkTransaction trans(DEFAULT_PRIORITY, session_.get());
1541 TestCompletionCallback callback;
1542 int rv = trans.Start(&request_, callback.callback(), net_log_.bound());
1543 EXPECT_THAT(rv, IsError(ERR_IO_PENDING));
1544
1545 // Pump the message loop to get the request started.
1546 base::RunLoop().RunUntilIdle();
1547 // Explicitly confirm the handshake.
1548 crypto_client_stream_factory_.last_stream()->SendOnCryptoHandshakeEvent(
1549 QuicSession::HANDSHAKE_CONFIRMED);
1550
1551 // Run the QUIC session to completion.
1552 quic_task_runner_->RunUntilIdle();
1553
1554 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1555 EXPECT_THAT(callback.WaitForResult(), IsError(ERR_QUIC_PROTOCOL_ERROR));
1556 }
1557
1558 // Verify that with mark_quic_broken_when_network_suspected enabled, if a QUIC
1559 // connection times out, then QUIC will be marked as broken and the request
1560 // retried over TCP.
1561 TEST_P(QuicNetworkTransactionTest, TimeoutAfterHandshakeConfirmedThenBroken) {
1562 params_.mark_quic_broken_when_network_suspected = true;
1563 params_.quic_idle_connection_timeout_seconds = 5;
1564
1565 // The request will initially go out over QUIC.
1566 MockQuicData quic_data;
1567 QuicStreamOffset header_stream_offset = 0;
1568 SpdyPriority priority =
1569 ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY);
1570
1571 std::string request_data;
1572 quic_data.AddWrite(client_maker_.MakeRequestHeadersPacketAndSaveData(
1573 1, kClientDataStreamId1, true, true, priority,
1574 GetRequestHeaders("GET", "https", "/"), nullptr, &header_stream_offset,
1575 &request_data));
1576
1577 std::string settings_data;
1578 QuicStreamOffset settings_offset = header_stream_offset;
1579 quic_data.AddWrite(client_maker_.MakeSettingsPacketAndSaveData(
1580 2, SETTINGS_MAX_HEADER_LIST_SIZE, kDefaultMaxUncompressedHeaderSize, true,
1581 &header_stream_offset, &settings_data));
1582 // TLP 1
1583 quic_data.AddWrite(client_maker_.MakeDataPacket(3, kHeadersStreamId, true,
1584 false, 0, request_data));
1585 // TLP 2
1586 quic_data.AddWrite(client_maker_.MakeDataPacket(
1587 4, kHeadersStreamId, true, false, settings_offset, settings_data));
1588 // RTO 1
1589 quic_data.AddWrite(client_maker_.MakeDataPacket(5, kHeadersStreamId, true,
1590 false, 0, request_data));
1591 quic_data.AddWrite(client_maker_.MakeDataPacket(
1592 6, kHeadersStreamId, true, false, settings_offset, settings_data));
1593 // RTO 2
1594 quic_data.AddWrite(client_maker_.MakeDataPacket(7, kHeadersStreamId, true,
1595 false, 0, request_data));
1596 quic_data.AddWrite(client_maker_.MakeDataPacket(
1597 8, kHeadersStreamId, true, false, settings_offset, settings_data));
1598 // RTO 3
1599 quic_data.AddWrite(client_maker_.MakeDataPacket(9, kHeadersStreamId, true,
1600 false, 0, request_data));
1601 quic_data.AddWrite(client_maker_.MakeDataPacket(
1602 10, kHeadersStreamId, true, false, settings_offset, settings_data));
1603
1604 quic_data.AddRead(ASYNC, ERR_IO_PENDING);
1605 quic_data.AddRead(ASYNC, OK);
1606 quic_data.AddSocketDataToFactory(&socket_factory_);
1607
1608 // After that fails, it will be resent via HTTP.
Jana 2017/04/06 02:29:18 via TCP?
Ryan Hamilton 2017/04/06 03:43:38 Done.
1609 MockWrite http_writes[] = {
1610 MockWrite(SYNCHRONOUS, 0, "GET / HTTP/1.1\r\n"),
1611 MockWrite(SYNCHRONOUS, 1, "Host: mail.example.org\r\n"),
1612 MockWrite(SYNCHRONOUS, 2, "Connection: keep-alive\r\n\r\n")};
1613
1614 MockRead http_reads[] = {
1615 MockRead(SYNCHRONOUS, 3, "HTTP/1.1 200 OK\r\n"),
1616 MockRead(SYNCHRONOUS, 4, kQuicAlternativeServiceHeader),
1617 MockRead(SYNCHRONOUS, 5, "hello world"), MockRead(SYNCHRONOUS, OK, 6)};
1618 SequencedSocketData http_data(http_reads, arraysize(http_reads), http_writes,
1619 arraysize(http_writes));
1620 socket_factory_.AddSocketDataProvider(&http_data);
1621 socket_factory_.AddSSLSocketDataProvider(&ssl_data_);
1622
1623 // In order for a new QUIC session to be established via alternate-protocol
1624 // without racing an HTTP connection, we need the host resolution to happen
1625 // synchronously. Of course, even though QUIC *could* perform a 0-RTT
1626 // connection to the the server, in this test we require confirmation
1627 // before encrypting so the HTTP job will still start.
1628 host_resolver_.set_synchronous_mode(true);
1629 host_resolver_.rules()->AddIPLiteralRule("mail.example.org", "192.168.0.1",
1630 "");
1631 HostResolver::RequestInfo info(HostPortPair("mail.example.org", 443));
1632 AddressList address;
1633 std::unique_ptr<HostResolver::Request> request;
1634 host_resolver_.Resolve(info, DEFAULT_PRIORITY, &address, CompletionCallback(),
1635 &request, net_log_.bound());
1636
1637 CreateSession();
1638 // Use a TestTaskRunner to avoid waiting in real time for timeouts.
1639 scoped_refptr<TestTaskRunner> quic_task_runner_(new TestTaskRunner(clock_));
1640 QuicStreamFactoryPeer::SetAlarmFactory(
1641 session_->quic_stream_factory(),
1642 base::MakeUnique<QuicChromiumAlarmFactory>(quic_task_runner_.get(),
1643 clock_));
1644
1645 AddQuicAlternateProtocolMapping(MockCryptoClientStream::ZERO_RTT);
1646
1647 HttpNetworkTransaction trans(DEFAULT_PRIORITY, session_.get());
1648 TestCompletionCallback callback;
1649 int rv = trans.Start(&request_, callback.callback(), net_log_.bound());
1650 EXPECT_THAT(rv, IsError(ERR_IO_PENDING));
1651
1652 // Pump the message loop to get the request started.
1653 base::RunLoop().RunUntilIdle();
1654 // Explicitly confirm the handshake.
1655 crypto_client_stream_factory_.last_stream()->SendOnCryptoHandshakeEvent(
1656 QuicSession::HANDSHAKE_CONFIRMED);
1657
1658 // Run the QUIC session to completion.
1659 quic_task_runner_->RunUntilIdle();
1660 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1661
1662 // Let the transaction proceed which will result in QUIC being marked
1663 // as broken and the request falling back to TCP.
1664 EXPECT_THAT(callback.WaitForResult(), IsOk());
1665
1666 ExpectBrokenAlternateProtocolMapping();
1667 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1668 ASSERT_FALSE(http_data.AllReadDataConsumed());
1669
1670 // Read the response body over TCP.
1671 CheckResponseData(&trans, "hello world");
1672 ASSERT_TRUE(http_data.AllWriteDataConsumed());
1673 ASSERT_TRUE(http_data.AllReadDataConsumed());
1674 }
1675
1676 // Verify that with mark_quic_broken_when_network_suspected enabled, if a QUIC
1677 // connection times out, then QUIC will be marked as broken but the request
1678 // will not be retried over TCP.
1679 TEST_P(QuicNetworkTransactionTest,
1680 TimeoutAfterHandshakeConfirmedAndHeadersThenBrokenNotRetried) {
1681 params_.mark_quic_broken_when_network_suspected = true;
1682 params_.quic_idle_connection_timeout_seconds = 5;
1683
1684 // The request will initially go out over QUIC.
1685 MockQuicData quic_data;
1686 QuicStreamOffset header_stream_offset = 0;
1687 SpdyPriority priority =
1688 ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY);
1689
1690 std::string request_data;
1691 quic_data.AddWrite(client_maker_.MakeRequestHeadersPacketAndSaveData(
1692 1, kClientDataStreamId1, true, true, priority,
1693 GetRequestHeaders("GET", "https", "/"), nullptr, &header_stream_offset,
1694 &request_data));
1695
1696 std::string settings_data;
1697 QuicStreamOffset settings_offset = header_stream_offset;
1698 quic_data.AddWrite(client_maker_.MakeSettingsPacketAndSaveData(
1699 2, SETTINGS_MAX_HEADER_LIST_SIZE, kDefaultMaxUncompressedHeaderSize, true,
1700 &header_stream_offset, &settings_data));
1701
1702 quic_data.AddRead(ConstructServerResponseHeadersPacket(
1703 1, kClientDataStreamId1, false, false, GetResponseHeaders("200 OK")));
1704 // quic_data.AddWrite(ConstructClientAckPacket(3, 1, 1));
1705 quic_data.AddWrite(
1706 ConstructClientAckPacket(3, 1, 1, QuicTime::Delta::FromMilliseconds(25)));
1707
1708 // TLP 1
1709 quic_data.AddWrite(client_maker_.MakeDataPacket(4, kHeadersStreamId, false,
1710 false, 0, request_data));
1711 // TLP 2
1712 quic_data.AddWrite(client_maker_.MakeDataPacket(
1713 5, kHeadersStreamId, false, false, settings_offset, settings_data));
1714 // RTO 1
1715 quic_data.AddWrite(client_maker_.MakeDataPacket(6, kHeadersStreamId, false,
1716 false, 0, request_data));
1717 quic_data.AddWrite(client_maker_.MakeDataPacket(
1718 7, kHeadersStreamId, false, false, settings_offset, settings_data));
1719 // RTO 2
1720 quic_data.AddWrite(client_maker_.MakeDataPacket(8, kHeadersStreamId, false,
1721 false, 0, request_data));
1722 quic_data.AddWrite(client_maker_.MakeDataPacket(
1723 9, kHeadersStreamId, false, false, settings_offset, settings_data));
1724 // RTO 3
1725 quic_data.AddWrite(client_maker_.MakeDataPacket(10, kHeadersStreamId, false,
1726 false, 0, request_data));
1727 quic_data.AddWrite(client_maker_.MakeDataPacket(
1728 11, kHeadersStreamId, false, false, settings_offset, settings_data));
1729
1730 quic_data.AddRead(ASYNC, ERR_IO_PENDING);
1731 quic_data.AddRead(ASYNC, OK);
1732 quic_data.AddSocketDataToFactory(&socket_factory_);
1733
1734 // In order for a new QUIC session to be established via alternate-protocol
1735 // without racing an HTTP connection, we need the host resolution to happen
1736 // synchronously. Of course, even though QUIC *could* perform a 0-RTT
1737 // connection to the the server, in this test we require confirmation
1738 // before encrypting so the HTTP job will still start.
1739 host_resolver_.set_synchronous_mode(true);
1740 host_resolver_.rules()->AddIPLiteralRule("mail.example.org", "192.168.0.1",
1741 "");
1742 HostResolver::RequestInfo info(HostPortPair("mail.example.org", 443));
1743 AddressList address;
1744 std::unique_ptr<HostResolver::Request> request;
1745 host_resolver_.Resolve(info, DEFAULT_PRIORITY, &address, CompletionCallback(),
1746 &request, net_log_.bound());
1747
1748 CreateSession();
1749 // Use a TestTaskRunner to avoid waiting in real time for timeouts.
1750 scoped_refptr<TestTaskRunner> quic_task_runner_(new TestTaskRunner(clock_));
1751 QuicStreamFactoryPeer::SetAlarmFactory(
1752 session_->quic_stream_factory(),
1753 base::MakeUnique<QuicChromiumAlarmFactory>(quic_task_runner_.get(),
1754 clock_));
1755
1756 AddQuicAlternateProtocolMapping(MockCryptoClientStream::ZERO_RTT);
1757
1758 HttpNetworkTransaction trans(DEFAULT_PRIORITY, session_.get());
1759 TestCompletionCallback callback;
1760 int rv = trans.Start(&request_, callback.callback(), net_log_.bound());
1761 EXPECT_THAT(rv, IsError(ERR_IO_PENDING));
1762
1763 // Pump the message loop to get the request started.
1764 base::RunLoop().RunUntilIdle();
1765 // Explicitly confirm the handshake.
1766 crypto_client_stream_factory_.last_stream()->SendOnCryptoHandshakeEvent(
1767 QuicSession::HANDSHAKE_CONFIRMED);
1768
1769 // Pump the message loop to get the request started.
1770 base::RunLoop().RunUntilIdle();
1771
1772 // Run the QUIC session to completion.
1773 quic_task_runner_->RunUntilIdle();
1774 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1775
1776 // Let the transaction proceed which will result in QUIC being marked
1777 // as broken and the request falling back to TCP.
1778 EXPECT_THAT(callback.WaitForResult(), IsOk());
1779
1780 ExpectBrokenAlternateProtocolMapping();
1781 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1782
1783 std::string response_data;
1784 ASSERT_THAT(ReadTransaction(&trans, &response_data),
1785 IsError(ERR_QUIC_PROTOCOL_ERROR));
1786 }
1787
1788 // Verify that with mark_quic_broken_when_network_suspected enabled, if a QUIC
1789 // connection RTOs, then QUIC will be marked as broken and the request retried
1790 // over TCP.
1791 TEST_P(QuicNetworkTransactionTest,
1792 TooManyRtosAfterHandshakeConfirmedThenBroken) {
1793 params_.mark_quic_broken_when_network_suspected = true;
1794 params_.quic_connection_options.push_back(k5RTO);
1795
1796 // The request will initially go out over QUIC.
1797 MockQuicData quic_data;
1798 QuicStreamOffset header_stream_offset = 0;
1799 SpdyPriority priority =
1800 ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY);
1801
1802 std::string request_data;
1803 quic_data.AddWrite(client_maker_.MakeRequestHeadersPacketAndSaveData(
1804 1, kClientDataStreamId1, true, true, priority,
1805 GetRequestHeaders("GET", "https", "/"), nullptr, &header_stream_offset,
1806 &request_data));
1807
1808 std::string settings_data;
1809 QuicStreamOffset settings_offset = header_stream_offset;
1810 quic_data.AddWrite(client_maker_.MakeSettingsPacketAndSaveData(
1811 2, SETTINGS_MAX_HEADER_LIST_SIZE, kDefaultMaxUncompressedHeaderSize, true,
1812 &header_stream_offset, &settings_data));
1813 // TLP 1
1814 quic_data.AddWrite(client_maker_.MakeDataPacket(3, kHeadersStreamId, true,
1815 false, 0, request_data));
1816 // TLP 2
1817 quic_data.AddWrite(client_maker_.MakeDataPacket(
1818 4, kHeadersStreamId, true, false, settings_offset, settings_data));
1819 // RTO 1
1820 quic_data.AddWrite(client_maker_.MakeDataPacket(5, kHeadersStreamId, true,
1821 false, 0, request_data));
1822 quic_data.AddWrite(client_maker_.MakeDataPacket(
1823 6, kHeadersStreamId, true, false, settings_offset, settings_data));
1824 // RTO 2
1825 quic_data.AddWrite(client_maker_.MakeDataPacket(7, kHeadersStreamId, true,
1826 false, 0, request_data));
1827 quic_data.AddWrite(client_maker_.MakeDataPacket(
1828 8, kHeadersStreamId, true, false, settings_offset, settings_data));
1829 // RTO 3
1830 quic_data.AddWrite(client_maker_.MakeDataPacket(9, kHeadersStreamId, true,
1831 false, 0, request_data));
1832 quic_data.AddWrite(client_maker_.MakeDataPacket(
1833 10, kHeadersStreamId, true, false, settings_offset, settings_data));
1834 // RTO 4
1835 quic_data.AddWrite(client_maker_.MakeDataPacket(11, kHeadersStreamId, true,
1836 false, 0, request_data));
1837 quic_data.AddWrite(client_maker_.MakeDataPacket(
1838 12, kHeadersStreamId, true, false, settings_offset, settings_data));
1839
1840 quic_data.AddWrite(client_maker_.MakeAckAndConnectionClosePacket(
1841 13, true, QuicTime::Delta::Infinite(), 0, 1, QUIC_TOO_MANY_RTOS,
1842 "5 consecutive retransmission timeouts"));
1843
1844 quic_data.AddRead(ASYNC, OK);
1845 quic_data.AddSocketDataToFactory(&socket_factory_);
1846
1847 // After that fails, it will be resent via HTTP.
1848 MockWrite http_writes[] = {
1849 MockWrite(SYNCHRONOUS, 0, "GET / HTTP/1.1\r\n"),
1850 MockWrite(SYNCHRONOUS, 1, "Host: mail.example.org\r\n"),
1851 MockWrite(SYNCHRONOUS, 2, "Connection: keep-alive\r\n\r\n")};
1852
1853 MockRead http_reads[] = {
1854 MockRead(SYNCHRONOUS, 3, "HTTP/1.1 200 OK\r\n"),
1855 MockRead(SYNCHRONOUS, 4, kQuicAlternativeServiceHeader),
1856 MockRead(SYNCHRONOUS, 5, "hello world"), MockRead(SYNCHRONOUS, OK, 6)};
1857 SequencedSocketData http_data(http_reads, arraysize(http_reads), http_writes,
1858 arraysize(http_writes));
1859 socket_factory_.AddSocketDataProvider(&http_data);
1860 socket_factory_.AddSSLSocketDataProvider(&ssl_data_);
1861
1862 // In order for a new QUIC session to be established via alternate-protocol
1863 // without racing an HTTP connection, we need the host resolution to happen
1864 // synchronously. Of course, even though QUIC *could* perform a 0-RTT
1865 // connection to the the server, in this test we require confirmation
1866 // before encrypting so the HTTP job will still start.
1867 host_resolver_.set_synchronous_mode(true);
1868 host_resolver_.rules()->AddIPLiteralRule("mail.example.org", "192.168.0.1",
1869 "");
1870 HostResolver::RequestInfo info(HostPortPair("mail.example.org", 443));
1871 AddressList address;
1872 std::unique_ptr<HostResolver::Request> request;
1873 host_resolver_.Resolve(info, DEFAULT_PRIORITY, &address, CompletionCallback(),
1874 &request, net_log_.bound());
1875
1876 CreateSession();
1877 // Use a TestTaskRunner to avoid waiting in real time for timeouts.
1878 scoped_refptr<TestTaskRunner> quic_task_runner_(new TestTaskRunner(clock_));
1879 QuicStreamFactoryPeer::SetAlarmFactory(
1880 session_->quic_stream_factory(),
1881 base::MakeUnique<QuicChromiumAlarmFactory>(quic_task_runner_.get(),
1882 clock_));
1883
1884 AddQuicAlternateProtocolMapping(MockCryptoClientStream::ZERO_RTT);
1885
1886 HttpNetworkTransaction trans(DEFAULT_PRIORITY, session_.get());
1887 TestCompletionCallback callback;
1888 int rv = trans.Start(&request_, callback.callback(), net_log_.bound());
1889 EXPECT_THAT(rv, IsError(ERR_IO_PENDING));
1890
1891 // Pump the message loop to get the request started.
1892 base::RunLoop().RunUntilIdle();
1893 // Explicitly confirm the handshake.
1894 crypto_client_stream_factory_.last_stream()->SendOnCryptoHandshakeEvent(
1895 QuicSession::HANDSHAKE_CONFIRMED);
1896
1897 // Run the QUIC session to completion.
1898 quic_task_runner_->RunUntilIdle();
1899 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1900
1901 // Let the transaction proceed which will result in QUIC being marked
1902 // as broken and the request falling back to TCP.
1903 EXPECT_THAT(callback.WaitForResult(), IsOk());
1904
1905 ExpectBrokenAlternateProtocolMapping();
1906 ASSERT_TRUE(quic_data.AllWriteDataConsumed());
1907 ASSERT_FALSE(http_data.AllReadDataConsumed());
1908
1909 // Read the response body over TCP.
1910 CheckResponseData(&trans, "hello world");
1911 ASSERT_TRUE(http_data.AllWriteDataConsumed());
1912 ASSERT_TRUE(http_data.AllReadDataConsumed());
1913 }
1914
1357 TEST_P(QuicNetworkTransactionTest, 1915 TEST_P(QuicNetworkTransactionTest,
1358 DoNotUseAlternativeServiceQuicUnsupportedVersion) { 1916 DoNotUseAlternativeServiceQuicUnsupportedVersion) {
1359 std::string altsvc_header = base::StringPrintf( 1917 std::string altsvc_header = base::StringPrintf(
1360 "Alt-Svc: quic=\":443\"; v=\"%u\"\r\n\r\n", version_ - 1); 1918 "Alt-Svc: quic=\":443\"; v=\"%u\"\r\n\r\n", version_ - 1);
1361 MockRead http_reads[] = { 1919 MockRead http_reads[] = {
1362 MockRead("HTTP/1.1 200 OK\r\n"), MockRead(altsvc_header.c_str()), 1920 MockRead("HTTP/1.1 200 OK\r\n"), MockRead(altsvc_header.c_str()),
1363 MockRead("hello world"), 1921 MockRead("hello world"),
1364 MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ), 1922 MockRead(SYNCHRONOUS, ERR_TEST_PEER_CLOSE_AFTER_NEXT_MOCK_READ),
1365 MockRead(ASYNC, OK)}; 1923 MockRead(ASYNC, OK)};
1366 1924
(...skipping 2146 matching lines...) Expand 10 before | Expand all | Expand 10 after
3513 AddHangingSocketData(); 4071 AddHangingSocketData();
3514 4072
3515 SendRequestAndExpectQuicResponse(origin1_); 4073 SendRequestAndExpectQuicResponse(origin1_);
3516 SendRequestAndExpectQuicResponse(origin2_); 4074 SendRequestAndExpectQuicResponse(origin2_);
3517 4075
3518 EXPECT_TRUE(AllDataConsumed()); 4076 EXPECT_TRUE(AllDataConsumed());
3519 } 4077 }
3520 4078
3521 } // namespace test 4079 } // namespace test
3522 } // namespace net 4080 } // namespace net
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698