Enable support for QUIC 13.

This does NOT cause Chrome to use QUIC 13, that will come later.
Refactors the mechanims that QUIC tests use to to create packets.

Review URL: https://codereview.chromium.org/110853010

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@242130 0039d316-1c4b-4281-b951-d872f2087c98
diff --git a/net/quic/quic_network_transaction_unittest.cc b/net/quic/quic_network_transaction_unittest.cc
index 2e4610c..5830e56 100644
--- a/net/quic/quic_network_transaction_unittest.cc
+++ b/net/quic/quic_network_transaction_unittest.cc
@@ -2,6 +2,8 @@
 // Use of this source code is governed by a BSD-style license that can be
 // found in the LICENSE file.
 
+#include <vector>
+
 #include "base/basictypes.h"
 #include "base/compiler_specific.h"
 #include "base/memory/scoped_ptr.h"
@@ -30,6 +32,7 @@
 #include "net/quic/test_tools/mock_clock.h"
 #include "net/quic/test_tools/mock_crypto_client_stream_factory.h"
 #include "net/quic/test_tools/mock_random.h"
+#include "net/quic/test_tools/quic_test_packet_maker.h"
 #include "net/quic/test_tools/quic_test_utils.h"
 #include "net/socket/client_socket_factory.h"
 #include "net/socket/mock_client_socket_pool_manager.h"
@@ -50,18 +53,62 @@
     "Alternate-Protocol: 80:quic\r\n\r\n";
 static const char kQuicAlternateProtocolHttpsHeader[] =
     "Alternate-Protocol: 443:quic\r\n\r\n";
+
 }  // namespace
 
 namespace net {
 namespace test {
 
-class QuicNetworkTransactionTest : public PlatformTest {
+// Helper class to encapsulate MockReads and MockWrites for QUIC.
+// Simplify ownership issues and the interaction with the MockSocketFactory.
+class MockQuicData {
+ public:
+  ~MockQuicData() {
+    STLDeleteElements(&packets_);
+  }
+
+  void AddRead(scoped_ptr<QuicEncryptedPacket> packet) {
+    reads_.push_back(MockRead(SYNCHRONOUS, packet->data(), packet->length(),
+                              sequence_number_++));
+    packets_.push_back(packet.release());
+  }
+
+  void AddRead(IoMode mode, int rv) {
+    reads_.push_back(MockRead(mode, rv));
+  }
+
+  void AddWrite(scoped_ptr<QuicEncryptedPacket> packet) {
+    writes_.push_back(MockWrite(SYNCHRONOUS, packet->data(), packet->length(),
+                                sequence_number_++));
+    packets_.push_back(packet.release());
+  }
+
+  void AddDelayedSocketDataToFactory(MockClientSocketFactory* factory,
+                                     size_t delay) {
+    MockRead* reads = reads_.empty() ? NULL  : &reads_[0];
+    MockWrite* writes = writes_.empty() ? NULL  : &writes_[0];
+    socket_data_.reset(new DelayedSocketData(
+        delay, reads, reads_.size(), writes, writes_.size()));
+    factory->AddSocketDataProvider(socket_data_.get());
+  }
+
+ private:
+  std::vector<QuicEncryptedPacket*> packets_;
+  std::vector<MockWrite> writes_;
+  std::vector<MockRead> reads_;
+  size_t sequence_number_;
+  scoped_ptr<SocketDataProvider> socket_data_;
+};
+
+class QuicNetworkTransactionTest
+    : public PlatformTest,
+      public testing::WithParamInterface<QuicVersion> {
  protected:
   QuicNetworkTransactionTest()
-      : clock_(new MockClock),
+      : maker_(GetParam(), 0),
+        clock_(new MockClock),
         ssl_config_service_(new SSLConfigServiceDefaults),
         proxy_service_(ProxyService::CreateDirect()),
-        compressor_(new QuicSpdyCompressor()),
         auth_handler_factory_(
             HttpAuthHandlerFactory::CreateDefault(&host_resolver_)),
         random_generator_(0),
@@ -90,132 +137,71 @@
   scoped_ptr<QuicEncryptedPacket> ConstructRstPacket(
       QuicPacketSequenceNumber num,
       QuicStreamId stream_id) {
-    QuicPacketHeader header;
-    header.public_header.guid = random_generator_.RandUint64();
-    header.public_header.reset_flag = false;
-    header.public_header.version_flag = false;
-    header.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
-    header.packet_sequence_number = num;
-    header.entropy_flag = false;
-    header.fec_flag = false;
-    header.fec_group = 0;
-
-    QuicRstStreamFrame rst(stream_id, QUIC_STREAM_NO_ERROR);
-    return scoped_ptr<QuicEncryptedPacket>(
-        ConstructPacket(header, QuicFrame(&rst)));
+    return maker_.MakeRstPacket(
+        num, false, stream_id, QUIC_STREAM_NO_ERROR);
   }
 
   scoped_ptr<QuicEncryptedPacket> ConstructConnectionClosePacket(
       QuicPacketSequenceNumber num) {
-    QuicPacketHeader header;
-    header.public_header.guid = random_generator_.RandUint64();
-    header.public_header.reset_flag = false;
-    header.public_header.version_flag = false;
-    header.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
-    header.packet_sequence_number = num;
-    header.entropy_flag = false;
-    header.fec_flag = false;
-    header.fec_group = 0;
-
-    QuicConnectionCloseFrame close;
-    close.error_code = QUIC_CRYPTO_VERSION_NOT_SUPPORTED;
-    close.error_details = "Time to panic!";
-    return scoped_ptr<QuicEncryptedPacket>(
-        ConstructPacket(header, QuicFrame(&close)));
+    return maker_.MakeConnectionClosePacket(num);
   }
 
   scoped_ptr<QuicEncryptedPacket> ConstructAckPacket(
       QuicPacketSequenceNumber largest_received,
       QuicPacketSequenceNumber least_unacked) {
-    QuicPacketHeader header;
-    header.public_header.guid = random_generator_.RandUint64();
-    header.public_header.reset_flag = false;
-    header.public_header.version_flag = false;
-    header.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
-    header.packet_sequence_number = 2;
-    header.entropy_flag = false;
-    header.fec_flag = false;
-    header.fec_group = 0;
+    return maker_.MakeAckPacket(2, largest_received, least_unacked, true);
+  }
 
-    QuicAckFrame ack(largest_received, QuicTime::Zero(), least_unacked);
-
-    QuicCongestionFeedbackFrame feedback;
-    feedback.type = kTCP;
-    feedback.tcp.accumulated_number_of_lost_packets = 0;
-    feedback.tcp.receive_window = 256000;
-
-    QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
-    QuicFrames frames;
-    frames.push_back(QuicFrame(&ack));
-    frames.push_back(QuicFrame(&feedback));
-    scoped_ptr<QuicPacket> packet(
-        framer.BuildUnsizedDataPacket(header, frames).packet);
-    return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
-        ENCRYPTION_NONE, header.packet_sequence_number, *packet));
+  SpdyHeaderBlock GetRequestHeaders(const std::string& method,
+                                    const std::string& scheme,
+                                    const std::string& path) {
+    return maker_.GetRequestHeaders(method, scheme, path);
   }
 
   std::string GetRequestString(const std::string& method,
                                const std::string& scheme,
                                const std::string& path) {
-    SpdyHeaderBlock headers;
-    headers[":method"] = method;
-    headers[":host"] = "www.google.com";
-    headers[":path"] = path;
-    headers[":scheme"] = scheme;
-    headers[":version"] = "HTTP/1.1";
-    return SerializeHeaderBlock(headers);
+    return maker_.GetRequestString(method, scheme, path);
+  }
+
+  SpdyHeaderBlock GetResponseHeaders(const std::string& status) {
+    return maker_.GetResponseHeaders(status);
   }
 
   std::string GetResponseString(const std::string& status,
                                 const std::string& body) {
-    SpdyHeaderBlock headers;
-    headers[":status"] = status;
-    headers[":version"] = "HTTP/1.1";
-    headers["content-type"] = "text/plain";
-    return compressor_->CompressHeaders(headers) + body;
+    return maker_.GetResponseString(status, body);
   }
 
-  std::string SerializeHeaderBlock(const SpdyHeaderBlock& headers) {
-    QuicSpdyCompressor compressor;
-    return compressor.CompressHeadersWithPriority(
-        ConvertRequestPriorityToQuicPriority(DEFAULT_PRIORITY), headers);
-  }
-
-  // Returns a newly created packet to send kData on stream 1.
-  QuicEncryptedPacket* ConstructDataPacket(
+  scoped_ptr<QuicEncryptedPacket> ConstructDataPacket(
       QuicPacketSequenceNumber sequence_number,
       QuicStreamId stream_id,
       bool should_include_version,
       bool fin,
       QuicStreamOffset offset,
       base::StringPiece data) {
-    InitializeHeader(sequence_number, should_include_version);
-    QuicStreamFrame frame(stream_id, fin, offset, MakeIOVector(data));
-    return ConstructPacket(header_, QuicFrame(&frame)).release();
+    return maker_.MakeDataPacket(
+        sequence_number, stream_id, should_include_version, fin, offset, data);
   }
 
-  scoped_ptr<QuicEncryptedPacket> ConstructPacket(
-      const QuicPacketHeader& header,
-      const QuicFrame& frame) {
-    QuicFramer framer(QuicSupportedVersions(), QuicTime::Zero(), false);
-    QuicFrames frames;
-    frames.push_back(frame);
-    scoped_ptr<QuicPacket> packet(
-        framer.BuildUnsizedDataPacket(header, frames).packet);
-    return scoped_ptr<QuicEncryptedPacket>(framer.EncryptPacket(
-        ENCRYPTION_NONE, header.packet_sequence_number, *packet));
+  scoped_ptr<QuicEncryptedPacket> ConstructRequestHeadersPacket(
+      QuicPacketSequenceNumber sequence_number,
+      QuicStreamId stream_id,
+      bool should_include_version,
+      bool fin,
+      const SpdyHeaderBlock& headers) {
+    return maker_.MakeRequestHeadersPacket(
+        sequence_number, stream_id, should_include_version, fin, headers);
   }
 
-  void InitializeHeader(QuicPacketSequenceNumber sequence_number,
-                        bool should_include_version) {
-    header_.public_header.guid = random_generator_.RandUint64();
-    header_.public_header.reset_flag = false;
-    header_.public_header.version_flag = should_include_version;
-    header_.public_header.sequence_number_length = PACKET_1BYTE_SEQUENCE_NUMBER;
-    header_.packet_sequence_number = sequence_number;
-    header_.fec_group = 0;
-    header_.entropy_flag = false;
-    header_.fec_flag = false;
+  scoped_ptr<QuicEncryptedPacket> ConstructResponseHeadersPacket(
+      QuicPacketSequenceNumber sequence_number,
+      QuicStreamId stream_id,
+      bool should_include_version,
+      bool fin,
+      const SpdyHeaderBlock& headers) {
+    return maker_.MakeResponseHeadersPacket(
+        sequence_number, stream_id, should_include_version, fin, headers);
   }
 
   void CreateSession() {
@@ -235,6 +221,7 @@
     params_.ssl_config_service = ssl_config_service_.get();
     params_.http_auth_handler_factory = auth_handler_factory_.get();
     params_.http_server_properties = http_server_properties.GetWeakPtr();
+    params_.quic_supported_versions = SupportedVersions(GetParam());
 
     session_ = new HttpNetworkSession(params_);
     session_->quic_stream_factory()->set_require_confirmation(false);
@@ -314,7 +301,7 @@
     socket_factory_.AddSocketDataProvider(&hanging_data_);
   }
 
-  QuicPacketHeader header_;
+  QuicTestPacketMaker maker_;
   scoped_refptr<HttpNetworkSession> session_;
   MockClientSocketFactory socket_factory_;
   MockCryptoClientStreamFactory crypto_client_stream_factory_;
@@ -324,7 +311,6 @@
   TransportSecurityState transport_security_state_;
   scoped_refptr<SSLConfigServiceDefaults> ssl_config_service_;
   scoped_ptr<ProxyService> proxy_service_;
-  scoped_ptr<QuicSpdyCompressor> compressor_;
   scoped_ptr<HttpAuthHandlerFactory> auth_handler_factory_;
   MockRandom random_generator_;
   HttpServerPropertiesImpl http_server_properties;
@@ -334,35 +320,37 @@
   StaticSocketDataProvider hanging_data_;
 };
 
-TEST_F(QuicNetworkTransactionTest, ForceQuic) {
+INSTANTIATE_TEST_CASE_P(Version, QuicNetworkTransactionTest,
+                        ::testing::ValuesIn(QuicSupportedVersions()));
+
+TEST_P(QuicNetworkTransactionTest, ForceQuic) {
   params_.origin_to_force_quic_on =
       HostPortPair::FromString("www.google.com:80");
 
-  QuicStreamId stream_id = 3;
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, stream_id, true, true, 0,
-                          GetRequestString("GET", "http", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
 
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, stream_id, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // The non-alternate protocol job needs to hang in order to guarantee that
   // the alternate-protocol job will "win".
@@ -405,19 +393,17 @@
 
   int log_stream_id;
   ASSERT_TRUE(entries[pos].GetIntegerValue("stream_id", &log_stream_id));
-  EXPECT_EQ(stream_id, static_cast<QuicStreamId>(log_stream_id));
+  EXPECT_EQ(3, log_stream_id);
 }
 
-TEST_F(QuicNetworkTransactionTest, ForceQuicWithErrorConnecting) {
+TEST_P(QuicNetworkTransactionTest, ForceQuicWithErrorConnecting) {
   params_.origin_to_force_quic_on =
       HostPortPair::FromString("www.google.com:80");
 
-  MockRead quic_reads[] = {
-    MockRead(ASYNC, ERR_SOCKET_NOT_CONNECTED),
-  };
-  StaticSocketDataProvider quic_data(quic_reads, arraysize(quic_reads),
-                                     NULL, 0);
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  MockQuicData mock_quic_data;
+  mock_quic_data.AddRead(ASYNC, ERR_SOCKET_NOT_CONNECTED);
+
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 0);
 
   CreateSession();
 
@@ -429,7 +415,7 @@
   EXPECT_EQ(ERR_CONNECTION_CLOSED, callback.WaitForResult());
 }
 
-TEST_F(QuicNetworkTransactionTest, DoNotForceQuicForHttps) {
+TEST_P(QuicNetworkTransactionTest, DoNotForceQuicForHttps) {
   // Attempt to "force" quic on 443, which will not be honored.
   params_.origin_to_force_quic_on =
       HostPortPair::FromString("www.google.com:443");
@@ -451,7 +437,7 @@
   SendRequestAndExpectHttpResponse("hello world");
 }
 
-TEST_F(QuicNetworkTransactionTest, UseAlternateProtocolForQuic) {
+TEST_P(QuicNetworkTransactionTest, UseAlternateProtocolForQuic) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
   MockRead http_reads[] = {
@@ -466,30 +452,30 @@
                                      NULL, 0);
   socket_factory_.AddSocketDataProvider(&http_data);
 
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, 3, true, true, 0,
-                          GetRequestString("GET", "http", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
 
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, 3, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // The non-alternate protocol job needs to hang in order to guarantee that
   // the alternate-protocol job will "win".
@@ -501,7 +487,7 @@
   SendRequestAndExpectQuicResponse("hello!");
 }
 
-TEST_F(QuicNetworkTransactionTest, UseAlternateProtocolForQuicForHttps) {
+TEST_P(QuicNetworkTransactionTest, UseAlternateProtocolForQuicForHttps) {
   params_.origin_to_force_quic_on =
       HostPortPair::FromString("www.google.com:443");
   params_.enable_quic_https = true;
@@ -519,30 +505,30 @@
                                      NULL, 0);
   socket_factory_.AddSocketDataProvider(&http_data);
 
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, 3, true, true, 0,
-                          GetRequestString("GET", "https", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
 
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, 3, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // The non-alternate protocol job needs to hang in order to guarantee that
   // the alternate-protocol job will "win".
@@ -554,7 +540,7 @@
   SendRequestAndExpectHttpResponse("hello world");
 }
 
-TEST_F(QuicNetworkTransactionTest, HungAlternateProtocol) {
+TEST_P(QuicNetworkTransactionTest, HungAlternateProtocol) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
   crypto_client_stream_factory_.set_handshake_mode(
       MockCryptoClientStream::COLD_START);
@@ -613,33 +599,33 @@
   ASSERT_TRUE(!quic_data.at_write_eof());
 }
 
-TEST_F(QuicNetworkTransactionTest, ZeroRTTWithHttpRace) {
+TEST_P(QuicNetworkTransactionTest, ZeroRTTWithHttpRace) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, 3, true, true, 0,
-                          GetRequestString("GET", "http", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
 
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, 3, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // The non-alternate protocol job needs to hang in order to guarantee that
   // the alternate-protocol job will "win".
@@ -650,33 +636,32 @@
   SendRequestAndExpectQuicResponse("hello!");
 }
 
-TEST_F(QuicNetworkTransactionTest, ZeroRTTWithNoHttpRace) {
+TEST_P(QuicNetworkTransactionTest, ZeroRTTWithNoHttpRace) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, 3, true, true, 0,
-                          GetRequestString("GET", "http", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
-
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, 3, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // In order for a new QUIC session to be established via alternate-protocol
   // without racing an HTTP connection, we need the host resolution to happen
@@ -697,33 +682,32 @@
   SendRequestAndExpectQuicResponse("hello!");
 }
 
-TEST_F(QuicNetworkTransactionTest, ZeroRTTWithConfirmationRequired) {
+TEST_P(QuicNetworkTransactionTest, ZeroRTTWithConfirmationRequired) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
-  scoped_ptr<QuicEncryptedPacket> req(
-      ConstructDataPacket(1, 3, true, true, 0,
-                          GetRequestString("GET", "http", "/")));
-  scoped_ptr<QuicEncryptedPacket> ack(ConstructAckPacket(1, 0));
-
-  MockWrite quic_writes[] = {
-    MockWrite(SYNCHRONOUS, req->data(), req->length()),
-    MockWrite(SYNCHRONOUS, ack->data(), ack->length()),
-  };
-
-  scoped_ptr<QuicEncryptedPacket> resp(
-      ConstructDataPacket(
-          1, 3, false, true, 0, GetResponseString("200 OK", "hello!")));
-  MockRead quic_reads[] = {
-    MockRead(SYNCHRONOUS, resp->data(), resp->length()),
-    MockRead(ASYNC, OK),  // EOF
-  };
-
-  DelayedSocketData quic_data(
-      1,  // wait for one write to finish before reading.
-      quic_reads, arraysize(quic_reads),
-      quic_writes, arraysize(quic_writes));
-
-  socket_factory_.AddSocketDataProvider(&quic_data);
+  QuicStreamId stream_id = GetParam() > QUIC_VERSION_12 ? 5 : 3;
+  MockQuicData mock_quic_data;
+  if (GetParam() > QUIC_VERSION_12) {
+    mock_quic_data.AddWrite(
+        ConstructRequestHeadersPacket(1, stream_id, true, true,
+                                      GetRequestHeaders("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructResponseHeadersPacket(1, stream_id, false, false,
+                                       GetResponseHeaders("200 OK")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(2, stream_id, false, true, 0, "hello!"));
+    mock_quic_data.AddWrite(ConstructAckPacket(2, 1));
+  } else {
+    mock_quic_data.AddWrite(
+        ConstructDataPacket(1, stream_id, true, true, 0,
+                            GetRequestString("GET", "http", "/")));
+    mock_quic_data.AddRead(
+        ConstructDataPacket(1, stream_id, false, true, 0,
+                            GetResponseString("200 OK", "hello!")));
+    mock_quic_data.AddWrite(ConstructAckPacket(1, 0));
+  }
+  mock_quic_data.AddRead(SYNCHRONOUS, 0);  // EOF
+  mock_quic_data.AddDelayedSocketDataToFactory(&socket_factory_, 1);
 
   // The non-alternate protocol job needs to hang in order to guarantee that
   // the alternate-protocol job will "win".
@@ -756,7 +740,7 @@
   EXPECT_EQ(OK, callback.WaitForResult());
 }
 
-TEST_F(QuicNetworkTransactionTest, BrokenAlternateProtocol) {
+TEST_P(QuicNetworkTransactionTest, BrokenAlternateProtocol) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
   // Alternate-protocol job
@@ -787,7 +771,7 @@
   ExpectBrokenAlternateProtocolMapping();
 }
 
-TEST_F(QuicNetworkTransactionTest, BrokenAlternateProtocolReadError) {
+TEST_P(QuicNetworkTransactionTest, BrokenAlternateProtocolReadError) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
   // Alternate-protocol job
@@ -817,7 +801,7 @@
   ExpectBrokenAlternateProtocolMapping();
 }
 
-TEST_F(QuicNetworkTransactionTest, FailedZeroRttBrokenAlternateProtocol) {
+TEST_P(QuicNetworkTransactionTest, FailedZeroRttBrokenAlternateProtocol) {
   HttpStreamFactory::EnableNpnSpdy3();  // Enables QUIC too.
 
   // Alternate-protocol job