| Index: net/quic/quic_connection_test.cc | 
| diff --git a/net/quic/quic_connection_test.cc b/net/quic/quic_connection_test.cc | 
| index 4e58dfdefee0bdd3a08cd2ca5256325d53d503e6..ede61c8a98dc8aaec975c0470b680bef2bad7826 100644 | 
| --- a/net/quic/quic_connection_test.cc | 
| +++ b/net/quic/quic_connection_test.cc | 
| @@ -67,7 +67,7 @@ class TestReceiveAlgorithm : public ReceiveAlgorithmInterface { | 
| } | 
|  | 
| bool GenerateCongestionFeedback( | 
| -      QuicCongestionFeedbackFrame* congestion_feedback) { | 
| +      QuicCongestionFeedbackFrame* congestion_feedback) override { | 
| if (feedback_ == nullptr) { | 
| return false; | 
| } | 
| @@ -95,6 +95,7 @@ class TaggingEncrypter : public QuicEncrypter { | 
|  | 
| // QuicEncrypter interface. | 
| bool SetKey(StringPiece key) override { return true; } | 
| + | 
| bool SetNoncePrefix(StringPiece nonce_prefix) override { return true; } | 
|  | 
| bool Encrypt(StringPiece nonce, | 
| @@ -149,6 +150,7 @@ class TaggingDecrypter : public QuicDecrypter { | 
|  | 
| // QuicDecrypter interface | 
| bool SetKey(StringPiece key) override { return true; } | 
| + | 
| bool SetNoncePrefix(StringPiece nonce_prefix) override { return true; } | 
|  | 
| bool Decrypt(StringPiece nonce, | 
| @@ -258,7 +260,7 @@ class TestConnectionHelper : public QuicConnectionHelperInterface { | 
|  | 
| class TestPacketWriter : public QuicPacketWriter { | 
| public: | 
| -  explicit TestPacketWriter(QuicVersion version) | 
| +  TestPacketWriter(QuicVersion version, MockClock *clock) | 
| : version_(version), | 
| framer_(SupportedVersions(version_)), | 
| last_packet_size_(0), | 
| @@ -268,7 +270,9 @@ class TestPacketWriter : public QuicPacketWriter { | 
| final_bytes_of_last_packet_(0), | 
| final_bytes_of_previous_packet_(0), | 
| use_tagging_decrypter_(false), | 
| -        packets_write_attempts_(0) { | 
| +        packets_write_attempts_(0), | 
| +        clock_(clock), | 
| +        write_pause_time_delta_(QuicTime::Delta::Zero()) { | 
| } | 
|  | 
| // QuicPacketWriter interface | 
| @@ -297,6 +301,10 @@ class TestPacketWriter : public QuicPacketWriter { | 
| return WriteResult(WRITE_STATUS_BLOCKED, -1); | 
| } | 
| last_packet_size_ = packet.length(); | 
| + | 
| +    if (!write_pause_time_delta_.IsZero()) { | 
| +      clock_->AdvanceTime(write_pause_time_delta_); | 
| +    } | 
| return WriteResult(WRITE_STATUS_OK, last_packet_size_); | 
| } | 
|  | 
| @@ -310,6 +318,11 @@ class TestPacketWriter : public QuicPacketWriter { | 
|  | 
| void BlockOnNextWrite() { block_on_next_write_ = true; } | 
|  | 
| +  // Sets the amount of time that the writer should before the actual write. | 
| +  void SetWritePauseTimeDelta(QuicTime::Delta delta) { | 
| +    write_pause_time_delta_ = delta; | 
| +  } | 
| + | 
| const QuicPacketHeader& header() { return framer_.header(); } | 
|  | 
| size_t frame_count() const { return framer_.num_frames(); } | 
| @@ -390,6 +403,10 @@ class TestPacketWriter : public QuicPacketWriter { | 
| uint32 final_bytes_of_previous_packet_; | 
| bool use_tagging_decrypter_; | 
| uint32 packets_write_attempts_; | 
| +  MockClock *clock_; | 
| +  // If non-zero, the clock will pause during WritePacket for this amount of | 
| +  // time. | 
| +  QuicTime::Delta write_pause_time_delta_; | 
|  | 
| DISALLOW_COPY_AND_ASSIGN(TestPacketWriter); | 
| }; | 
| @@ -597,7 +614,7 @@ class MockPacketWriterFactory : public QuicConnection::PacketWriterFactory { | 
| MockPacketWriterFactory(QuicPacketWriter* writer) { | 
| ON_CALL(*this, Create(_)).WillByDefault(Return(writer)); | 
| } | 
| -  virtual ~MockPacketWriterFactory() {} | 
| +  ~MockPacketWriterFactory() override {} | 
|  | 
| MOCK_CONST_METHOD1(Create, QuicPacketWriter*(QuicConnection* connection)); | 
| }; | 
| @@ -611,7 +628,7 @@ class QuicConnectionTest : public ::testing::TestWithParam<QuicVersion> { | 
| send_algorithm_(new StrictMock<MockSendAlgorithm>), | 
| loss_algorithm_(new MockLossAlgorithm()), | 
| helper_(new TestConnectionHelper(&clock_, &random_generator_)), | 
| -        writer_(new TestPacketWriter(version())), | 
| +        writer_(new TestPacketWriter(version(), &clock_)), | 
| factory_(writer_.get()), | 
| connection_(connection_id_, IPEndPoint(), helper_.get(), | 
| factory_, false, version()), | 
| @@ -974,6 +991,10 @@ class QuicConnectionTest : public ::testing::TestWithParam<QuicVersion> { | 
| EXPECT_CALL(visitor_, OnWriteBlocked()).Times(AtLeast(1)); | 
| } | 
|  | 
| +  void SetWritePauseTimeDelta(QuicTime::Delta delta) { | 
| +    writer_->SetWritePauseTimeDelta(delta); | 
| +  } | 
| + | 
| void CongestionBlockWrites() { | 
| EXPECT_CALL(*send_algorithm_, | 
| TimeUntilSend(_, _, _)).WillRepeatedly( | 
| @@ -1548,6 +1569,74 @@ TEST_P(QuicConnectionTest, BasicSending) { | 
| EXPECT_EQ(7u, least_unacked()); | 
| } | 
|  | 
| +// If FLAGS_quic_record_send_time_before_write is disabled, QuicConnection | 
| +// should record the packet sen-tdime after the packet is sent. | 
| +TEST_P(QuicConnectionTest, RecordSentTimeAfterPacketSent) { | 
| +  ValueRestore<bool> old_flag(&FLAGS_quic_record_send_time_before_write, false); | 
| +  // We're using a MockClock for the tests, so we have complete control over the | 
| +  // time. | 
| +  // Our recorded timestamp for the last packet sent time will be passed in to | 
| +  // the send_algorithm.  Make sure that it is set to the correct value. | 
| +  QuicTime actual_recorded_send_time = QuicTime::Zero(); | 
| +  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)) | 
| +      .WillOnce(DoAll(SaveArg<0>(&actual_recorded_send_time), Return(true))); | 
| + | 
| +  // First send without any pause and check the result. | 
| +  QuicTime expected_recorded_send_time = clock_.Now(); | 
| +  connection_.SendStreamDataWithString(1, "foo", 0, !kFin, nullptr); | 
| +  EXPECT_EQ(expected_recorded_send_time, actual_recorded_send_time) | 
| +      << "Expected time = " << expected_recorded_send_time.ToDebuggingValue() | 
| +      << ".  Actual time = " << actual_recorded_send_time.ToDebuggingValue(); | 
| + | 
| +  // Now pause during the write, and check the results. | 
| +  actual_recorded_send_time = QuicTime::Zero(); | 
| +  const QuicTime::Delta kWritePauseTimeDelta = | 
| +      QuicTime::Delta::FromMilliseconds(5000); | 
| +  SetWritePauseTimeDelta(kWritePauseTimeDelta); | 
| +  expected_recorded_send_time = clock_.Now().Add(kWritePauseTimeDelta); | 
| + | 
| +  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)) | 
| +      .WillOnce(DoAll(SaveArg<0>(&actual_recorded_send_time), Return(true))); | 
| +  connection_.SendStreamDataWithString(2, "baz", 0, !kFin, nullptr); | 
| +  EXPECT_EQ(expected_recorded_send_time, actual_recorded_send_time) | 
| +      << "Expected time = " << expected_recorded_send_time.ToDebuggingValue() | 
| +      << ".  Actual time = " << actual_recorded_send_time.ToDebuggingValue(); | 
| +} | 
| + | 
| +// If FLAGS_quic_record_send_time_before_write is enabled, QuicConnection should | 
| +// record the the packet sent-time prior to sending the packet. | 
| +TEST_P(QuicConnectionTest, RecordSentTimeBeforePacketSent) { | 
| +  ValueRestore<bool> old_flag(&FLAGS_quic_record_send_time_before_write, true); | 
| +  // We're using a MockClock for the tests, so we have complete control over the | 
| +  // time. | 
| +  // Our recorded timestamp for the last packet sent time will be passed in to | 
| +  // the send_algorithm.  Make sure that it is set to the correct value. | 
| +  QuicTime actual_recorded_send_time = QuicTime::Zero(); | 
| +  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)) | 
| +      .WillOnce(DoAll(SaveArg<0>(&actual_recorded_send_time), Return(true))); | 
| + | 
| +  // First send without any pause and check the result. | 
| +  QuicTime expected_recorded_send_time = clock_.Now(); | 
| +  connection_.SendStreamDataWithString(1, "foo", 0, !kFin, nullptr); | 
| +  EXPECT_EQ(expected_recorded_send_time, actual_recorded_send_time) | 
| +      << "Expected time = " << expected_recorded_send_time.ToDebuggingValue() | 
| +      << ".  Actual time = " << actual_recorded_send_time.ToDebuggingValue(); | 
| + | 
| +  // Now pause during the write, and check the results. | 
| +  actual_recorded_send_time = QuicTime::Zero(); | 
| +  const QuicTime::Delta kWritePauseTimeDelta = | 
| +      QuicTime::Delta::FromMilliseconds(5000); | 
| +  SetWritePauseTimeDelta(kWritePauseTimeDelta); | 
| +  expected_recorded_send_time = clock_.Now(); | 
| + | 
| +  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)) | 
| +      .WillOnce(DoAll(SaveArg<0>(&actual_recorded_send_time), Return(true))); | 
| +  connection_.SendStreamDataWithString(2, "baz", 0, !kFin, nullptr); | 
| +  EXPECT_EQ(expected_recorded_send_time, actual_recorded_send_time) | 
| +      << "Expected time = " << expected_recorded_send_time.ToDebuggingValue() | 
| +      << ".  Actual time = " << actual_recorded_send_time.ToDebuggingValue(); | 
| +} | 
| + | 
| TEST_P(QuicConnectionTest, FECSending) { | 
| // All packets carry version info till version is negotiated. | 
| QuicPacketCreator* creator = | 
| @@ -1565,7 +1654,8 @@ TEST_P(QuicConnectionTest, FECSending) { | 
| creator->set_max_packet_length(length); | 
|  | 
| // Send 4 protected data packets, which should also trigger 1 FEC packet. | 
| -  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)).Times(5); | 
| +  EXPECT_CALL(*send_algorithm_, | 
| +              OnPacketSent(_, _, _, _, HAS_RETRANSMITTABLE_DATA)).Times(5); | 
| // The first stream frame will have 2 fewer overhead bytes than the other 3. | 
| const string payload(payload_length * 4 + 2, 'a'); | 
| connection_.SendStreamDataWithStringWithFec(1, payload, 0, !kFin, nullptr); | 
| @@ -1601,7 +1691,8 @@ TEST_P(QuicConnectionTest, AbandonFECFromCongestionWindow) { | 
| &connection_)->IsFecEnabled()); | 
|  | 
| // 1 Data and 1 FEC packet. | 
| -  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)).Times(2); | 
| +  EXPECT_CALL(*send_algorithm_, | 
| +              OnPacketSent(_, _, _, _, HAS_RETRANSMITTABLE_DATA)).Times(2); | 
| connection_.SendStreamDataWithStringWithFec(3, "foo", 0, !kFin, nullptr); | 
|  | 
| const QuicTime::Delta retransmission_time = | 
| @@ -1620,8 +1711,9 @@ TEST_P(QuicConnectionTest, DontAbandonAckedFEC) { | 
| EXPECT_TRUE(QuicConnectionPeer::GetPacketCreator( | 
| &connection_)->IsFecEnabled()); | 
|  | 
| -  // 1 Data and 1 FEC packet. | 
| -  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)).Times(6); | 
| +  // 3 Data and 3 FEC packets. | 
| +  EXPECT_CALL(*send_algorithm_, | 
| +              OnPacketSent(_, _, _, _, HAS_RETRANSMITTABLE_DATA)).Times(6); | 
| connection_.SendStreamDataWithStringWithFec(3, "foo", 0, !kFin, nullptr); | 
| // Send some more data afterwards to ensure early retransmit doesn't trigger. | 
| connection_.SendStreamDataWithStringWithFec(3, "foo", 3, !kFin, nullptr); | 
| @@ -1648,8 +1740,9 @@ TEST_P(QuicConnectionTest, AbandonAllFEC) { | 
| EXPECT_TRUE(QuicConnectionPeer::GetPacketCreator( | 
| &connection_)->IsFecEnabled()); | 
|  | 
| -  // 1 Data and 1 FEC packet. | 
| -  EXPECT_CALL(*send_algorithm_, OnPacketSent(_, _, _, _, _)).Times(6); | 
| +  // 3 Data and 3 FEC packet. | 
| +  EXPECT_CALL(*send_algorithm_, | 
| +              OnPacketSent(_, _, _, _, HAS_RETRANSMITTABLE_DATA)).Times(6); | 
| connection_.SendStreamDataWithStringWithFec(3, "foo", 0, !kFin, nullptr); | 
| // Send some more data afterwards to ensure early retransmit doesn't trigger. | 
| connection_.SendStreamDataWithStringWithFec(3, "foo", 3, !kFin, nullptr); | 
| @@ -3070,22 +3163,25 @@ TEST_P(QuicConnectionTest, SendDelayedAck) { | 
| EXPECT_FALSE(connection_.GetAckAlarm()->IsSet()); | 
| } | 
|  | 
| -TEST_P(QuicConnectionTest, SendEarlyDelayedAckForCrypto) { | 
| -  QuicTime ack_time = clock_.ApproximateNow(); | 
| +TEST_P(QuicConnectionTest, SendDelayedAckOnHandshakeConfirmed) { | 
| EXPECT_CALL(visitor_, OnSuccessfulVersionNegotiation(_)); | 
| -  EXPECT_FALSE(connection_.GetAckAlarm()->IsSet()); | 
| -  // Process a packet from the crypto stream, which is frame1_'s default. | 
| ProcessPacket(1); | 
| -  // Check if delayed ack timer is running for the expected interval. | 
| +  // Check that ack is sent and that delayed ack alarm is set. | 
| +  EXPECT_TRUE(connection_.GetAckAlarm()->IsSet()); | 
| +  QuicTime ack_time = clock_.ApproximateNow().Add(DefaultDelayedAckTime()); | 
| +  EXPECT_EQ(ack_time, connection_.GetAckAlarm()->deadline()); | 
| + | 
| +  // Completing the handshake as the server does nothing. | 
| +  QuicConnectionPeer::SetIsServer(&connection_, true); | 
| +  connection_.OnHandshakeComplete(); | 
| EXPECT_TRUE(connection_.GetAckAlarm()->IsSet()); | 
| EXPECT_EQ(ack_time, connection_.GetAckAlarm()->deadline()); | 
| -  // Simulate delayed ack alarm firing. | 
| -  connection_.GetAckAlarm()->Fire(); | 
| -  // Check that ack is sent and that delayed ack alarm is reset. | 
| -  EXPECT_EQ(2u, writer_->frame_count()); | 
| -  EXPECT_FALSE(writer_->stop_waiting_frames().empty()); | 
| -  EXPECT_FALSE(writer_->ack_frames().empty()); | 
| -  EXPECT_FALSE(connection_.GetAckAlarm()->IsSet()); | 
| + | 
| +  // Complete the handshake as the client decreases the delayed ack time to 0ms. | 
| +  QuicConnectionPeer::SetIsServer(&connection_, false); | 
| +  connection_.OnHandshakeComplete(); | 
| +  EXPECT_TRUE(connection_.GetAckAlarm()->IsSet()); | 
| +  EXPECT_EQ(clock_.ApproximateNow(), connection_.GetAckAlarm()->deadline()); | 
| } | 
|  | 
| TEST_P(QuicConnectionTest, SendDelayedAckOnSecondPacket) { | 
|  |